Skip to content

Commit 2300ce1

Browse files
authored
Allow different GC triggers (#712)
This PR adds `GCTrigger` and forwards calls related with GC triggering to `GCTrigger`. `GCTrigger` would allow different implementations, such as fixed heap size, dynamic resizing, and runtime delegation. This PR only implements `FixedHeapSizeTrigger` and a simplified version of `MemBalancerTrigger`. This PR closes #561, and makes it easier to implement #641. Changes: * Adds `util::heap::gc_trigger::GCTrigger`. `Plan::poll()` is moved to `GCTrigger`. Any call to `Plan::poll()` is replaced with `GCTrigger::poll()`. * Adds `util::options::GCTriggerSelector` and `gc_trigger` in `Options`. `gc_trigger` defaults to a fixed heap size of half of the physical memory. * Refactoring on arguments for creating plans and spaces. * I needed to pass `GCTrigger` to plans and spaces so I think it would be better that I just take this chance to do the refactoring. * We now have structs to organize the arguments and any plan and space will receive the same set of the arguments for their constructors. This greatly simplifies our code.
1 parent fc144cf commit 2300ce1

File tree

30 files changed

+849
-794
lines changed

30 files changed

+849
-794
lines changed

Cargo.toml

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,8 @@ strum = "0.24"
4343
strum_macros = "0.24"
4444
cfg-if = "1.0"
4545
itertools = "0.10.5"
46+
sys-info = "0.9"
47+
regex = "1.7.0"
4648

4749
[dev-dependencies]
4850
rand = "0.7.3"

docs/tutorial/code/mygc_semispace/global.rs

Lines changed: 10 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22
use crate::plan::global::BasePlan; //Modify
33
use crate::plan::global::CommonPlan; // Add
44
use crate::plan::global::GcStatus; // Add
5+
use crate::plan::global::{CreateGeneralPlanArgs, CreateSpecificPlanArgs};
56
use crate::plan::mygc::mutator::ALLOCATOR_MAPPING;
67
use crate::plan::mygc::gc_work::MyGCWorkContext;
78
use crate::plan::AllocationSemantics;
@@ -171,40 +172,21 @@ impl<VM: VMBinding> Plan for MyGC<VM> {
171172
// Add
172173
impl<VM: VMBinding> MyGC<VM> {
173174
// ANCHOR: plan_new
174-
fn new(
175-
vm_map: &'static VMMap,
176-
mmapper: &'static Mmapper,
177-
options: Arc<Options>,
178-
) -> Self {
175+
fn new(args: CreateGeneralPlanArgs<VM>) -> Self {
179176
// Modify
180-
let mut heap = HeapMeta::new(&options);
181-
let global_metadata_specs = SideMetadataContext::new_global_specs(&[]);
177+
let mut plan_args = CreateSpecificPlanArgs {
178+
global_args: args,
179+
constraints: &MYGC_CONSTRAINTS,
180+
global_side_metadata_specs: SideMetadataContext::new_global_specs(&[]),
181+
};
182182

183183
let res = MyGC {
184184
hi: AtomicBool::new(false),
185185
// ANCHOR: copyspace_new
186-
copyspace0: CopySpace::new(
187-
"copyspace0",
188-
false,
189-
true,
190-
VMRequest::discontiguous(),
191-
global_metadata_specs.clone(),
192-
vm_map,
193-
mmapper,
194-
&mut heap,
195-
),
186+
copyspace0: CopySpace::new(plan_args.get_space_args("copyspace0", true, VMRequest::discontiguous()), false),
196187
// ANCHOR_END: copyspace_new
197-
copyspace1: CopySpace::new(
198-
"copyspace1",
199-
true,
200-
true,
201-
VMRequest::discontiguous(),
202-
global_metadata_specs.clone(),
203-
vm_map,
204-
mmapper,
205-
&mut heap,
206-
),
207-
common: CommonPlan::new(vm_map, mmapper, options, heap, &MYGC_CONSTRAINTS, global_metadata_specs.clone()),
188+
copyspace1: CopySpace::new(plan_args.get_space_args("copyspace1", true, VMRequest::discontiguous()), true),
189+
common: CommonPlan::new(plan_args),
208190
};
209191

210192
// Use SideMetadataSanity to check if each spec is valid. This is also needed for check

docs/tutorial/src/mygc/create.md

Lines changed: 3 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -71,17 +71,13 @@ files.
7171
options: Arc<UnsafeOptionsWrapper>,
7272
) -> Box<dyn Plan<VM = VM>> {
7373
match plan {
74-
PlanSelector::NoGC => Box::new(crate::plan::nogc::NoGC::new(vm_map, mmapper, options)),
75-
PlanSelector::SemiSpace => Box::new(crate::plan::semispace::SemiSpace::new(
76-
vm_map, mmapper, options,
77-
)),
74+
PlanSelector::NoGC => Box::new(crate::plan::nogc::NoGC::new(args)),
75+
PlanSelector::SemiSpace => Box::new(crate::plan::semispace::SemiSpace::new(args)),
7876

7977
// ...
8078

8179
// Create MyGC plan based on selector
82-
PlanSelector::MyGC => Box::new(crate::plan::mygc::MyGC::new(
83-
vm_map, mmapper, options,
84-
))
80+
PlanSelector::MyGC => Box::new(crate::plan::mygc::MyGC::new(args))
8581
}
8682
}
8783
```

src/memory_manager.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -416,7 +416,7 @@ pub fn gc_poll<VM: VMBinding>(mmtk: &MMTK<VM>, tls: VMMutatorThread) {
416416
);
417417

418418
let plan = mmtk.get_plan();
419-
if plan.should_trigger_gc_when_heap_is_full() && plan.poll(false, None) {
419+
if plan.should_trigger_gc_when_heap_is_full() && plan.base().gc_trigger.poll(false, None) {
420420
debug!("Collection required");
421421
assert!(plan.is_initialized(), "GC is not allowed here: collection is not initialized (did you call initialize_collection()?).");
422422
VM::VMCollection::block_for_gc(tls);

src/plan/generational/copying/global.rs

Lines changed: 12 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,8 @@ use super::mutator::ALLOCATOR_MAPPING;
44
use crate::plan::generational::global::Gen;
55
use crate::plan::global::BasePlan;
66
use crate::plan::global::CommonPlan;
7+
use crate::plan::global::CreateGeneralPlanArgs;
8+
use crate::plan::global::CreateSpecificPlanArgs;
79
use crate::plan::global::GcStatus;
810
use crate::plan::AllocationSemantics;
911
use crate::plan::Plan;
@@ -13,17 +15,12 @@ use crate::policy::space::Space;
1315
use crate::scheduler::*;
1416
use crate::util::alloc::allocators::AllocatorSelector;
1517
use crate::util::copy::*;
16-
use crate::util::heap::layout::heap_layout::Mmapper;
17-
use crate::util::heap::layout::heap_layout::VMMap;
18-
use crate::util::heap::HeapMeta;
1918
use crate::util::heap::VMRequest;
2019
use crate::util::metadata::side_metadata::SideMetadataSanity;
21-
use crate::util::options::Options;
2220
use crate::util::VMWorkerThread;
2321
use crate::vm::*;
2422
use enum_map::EnumMap;
2523
use std::sync::atomic::{AtomicBool, Ordering};
26-
use std::sync::Arc;
2724

2825
use mmtk_macros::PlanTraceObject;
2926

@@ -175,42 +172,25 @@ impl<VM: VMBinding> Plan for GenCopy<VM> {
175172
}
176173

177174
impl<VM: VMBinding> GenCopy<VM> {
178-
pub fn new(vm_map: &'static VMMap, mmapper: &'static Mmapper, options: Arc<Options>) -> Self {
179-
let mut heap = HeapMeta::new(&options);
180-
// We have no specific side metadata for copying. So just use the ones from generational.
181-
let global_metadata_specs =
182-
crate::plan::generational::new_generational_global_metadata_specs::<VM>();
175+
pub fn new(args: CreateGeneralPlanArgs<VM>) -> Self {
176+
let mut plan_args = CreateSpecificPlanArgs {
177+
global_args: args,
178+
constraints: &GENCOPY_CONSTRAINTS,
179+
global_side_metadata_specs:
180+
crate::plan::generational::new_generational_global_metadata_specs::<VM>(),
181+
};
183182

184183
let copyspace0 = CopySpace::new(
185-
"copyspace0",
184+
plan_args.get_space_args("copyspace0", true, VMRequest::discontiguous()),
186185
false,
187-
true,
188-
VMRequest::discontiguous(),
189-
global_metadata_specs.clone(),
190-
vm_map,
191-
mmapper,
192-
&mut heap,
193186
);
194187
let copyspace1 = CopySpace::new(
195-
"copyspace1",
196-
true,
188+
plan_args.get_space_args("copyspace1", true, VMRequest::discontiguous()),
197189
true,
198-
VMRequest::discontiguous(),
199-
global_metadata_specs.clone(),
200-
vm_map,
201-
mmapper,
202-
&mut heap,
203190
);
204191

205192
let res = GenCopy {
206-
gen: Gen::new(
207-
heap,
208-
global_metadata_specs,
209-
&GENCOPY_CONSTRAINTS,
210-
vm_map,
211-
mmapper,
212-
options,
213-
),
193+
gen: Gen::new(plan_args),
214194
hi: AtomicBool::new(false),
215195
copyspace0,
216196
copyspace1,

src/plan/generational/global.rs

Lines changed: 8 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -1,19 +1,14 @@
11
use crate::plan::global::CommonPlan;
2+
use crate::plan::global::CreateSpecificPlanArgs;
23
use crate::plan::ObjectQueue;
34
use crate::plan::Plan;
4-
use crate::plan::PlanConstraints;
55
use crate::policy::copyspace::CopySpace;
66
use crate::policy::space::Space;
77
use crate::scheduler::*;
88
use crate::util::conversions;
99
use crate::util::copy::CopySemantics;
10-
use crate::util::heap::layout::heap_layout::Mmapper;
11-
use crate::util::heap::layout::heap_layout::VMMap;
12-
use crate::util::heap::HeapMeta;
1310
use crate::util::heap::VMRequest;
1411
use crate::util::metadata::side_metadata::SideMetadataSanity;
15-
use crate::util::metadata::side_metadata::SideMetadataSpec;
16-
use crate::util::options::Options;
1712
use crate::util::statistics::counter::EventCounter;
1813
use crate::util::ObjectReference;
1914
use crate::util::VMWorkerThread;
@@ -42,32 +37,16 @@ pub struct Gen<VM: VMBinding> {
4237
}
4338

4439
impl<VM: VMBinding> Gen<VM> {
45-
pub fn new(
46-
mut heap: HeapMeta,
47-
global_metadata_specs: Vec<SideMetadataSpec>,
48-
constraints: &'static PlanConstraints,
49-
vm_map: &'static VMMap,
50-
mmapper: &'static Mmapper,
51-
options: Arc<Options>,
52-
) -> Self {
40+
pub fn new(mut args: CreateSpecificPlanArgs<VM>) -> Self {
5341
let nursery = CopySpace::new(
54-
"nursery",
55-
false,
42+
args.get_space_args(
43+
"nursery",
44+
true,
45+
VMRequest::fixed_extent(args.global_args.options.get_max_nursery(), false),
46+
),
5647
true,
57-
VMRequest::fixed_extent(options.get_max_nursery(), false),
58-
global_metadata_specs.clone(),
59-
vm_map,
60-
mmapper,
61-
&mut heap,
62-
);
63-
let common = CommonPlan::new(
64-
vm_map,
65-
mmapper,
66-
options,
67-
heap,
68-
constraints,
69-
global_metadata_specs,
7048
);
49+
let common = CommonPlan::new(args);
7150

7251
let full_heap_gc_count = common.base.stats.new_event_counter("majorGC", true, true);
7352

src/plan/generational/immix/global.rs

Lines changed: 15 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,8 @@ use super::gc_work::GenImmixNurseryGCWorkContext;
33
use crate::plan::generational::global::Gen;
44
use crate::plan::global::BasePlan;
55
use crate::plan::global::CommonPlan;
6+
use crate::plan::global::CreateGeneralPlanArgs;
7+
use crate::plan::global::CreateSpecificPlanArgs;
68
use crate::plan::global::GcStatus;
79
use crate::plan::AllocationSemantics;
810
use crate::plan::Plan;
@@ -13,17 +15,13 @@ use crate::policy::space::Space;
1315
use crate::scheduler::GCWorkScheduler;
1416
use crate::util::alloc::allocators::AllocatorSelector;
1517
use crate::util::copy::*;
16-
use crate::util::heap::layout::heap_layout::Mmapper;
17-
use crate::util::heap::layout::heap_layout::VMMap;
18-
use crate::util::heap::HeapMeta;
19-
use crate::util::options::Options;
18+
use crate::util::heap::VMRequest;
2019
use crate::util::VMWorkerThread;
2120
use crate::vm::*;
2221

2322
use enum_map::EnumMap;
2423
use std::sync::atomic::AtomicBool;
2524
use std::sync::atomic::Ordering;
26-
use std::sync::Arc;
2725

2826
use mmtk_macros::PlanTraceObject;
2927

@@ -216,34 +214,21 @@ impl<VM: VMBinding> Plan for GenImmix<VM> {
216214
}
217215

218216
impl<VM: VMBinding> GenImmix<VM> {
219-
pub fn new(
220-
vm_map: &'static VMMap,
221-
mmapper: &'static Mmapper,
222-
options: Arc<Options>,
223-
scheduler: Arc<GCWorkScheduler<VM>>,
224-
) -> Self {
225-
let mut heap = HeapMeta::new(&options);
226-
// We have no specific side metadata for copying. So just use the ones from generational.
227-
let global_metadata_specs =
228-
crate::plan::generational::new_generational_global_metadata_specs::<VM>();
229-
let immix_space = ImmixSpace::new(
217+
pub fn new(args: CreateGeneralPlanArgs<VM>) -> Self {
218+
let mut plan_args = CreateSpecificPlanArgs {
219+
global_args: args,
220+
constraints: &GENIMMIX_CONSTRAINTS,
221+
global_side_metadata_specs:
222+
crate::plan::generational::new_generational_global_metadata_specs::<VM>(),
223+
};
224+
let immix_space = ImmixSpace::new(plan_args.get_space_args(
230225
"immix_mature",
231-
vm_map,
232-
mmapper,
233-
&mut heap,
234-
scheduler,
235-
global_metadata_specs.clone(),
236-
);
226+
true,
227+
VMRequest::discontiguous(),
228+
));
237229

238230
let genimmix = GenImmix {
239-
gen: Gen::new(
240-
heap,
241-
global_metadata_specs,
242-
&GENIMMIX_CONSTRAINTS,
243-
vm_map,
244-
mmapper,
245-
options,
246-
),
231+
gen: Gen::new(plan_args),
247232
immix: immix_space,
248233
last_gc_was_defrag: AtomicBool::new(false),
249234
last_gc_was_full_heap: AtomicBool::new(false),

0 commit comments

Comments
 (0)