summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorDennis Kobert <dennis@kobert.dev>2025-03-05 14:06:34 +0100
committerDennis Kobert <dennis@kobert.dev>2025-03-05 14:06:34 +0100
commit289c7725de8225c4072b2b6ba73608c787657716 (patch)
treec6d178556b989e1c4ceff2c7b5aa30a48e934bef /src
parentad56ba4f498252bd5caafc93dcebd7b9c42a8527 (diff)
Cargo fmt
Diffstat (limited to 'src')
-rw-r--r--src/main.rs69
-rw-r--r--src/mock.rs2
-rw-r--r--src/mock/perf.rs7
3 files changed, 49 insertions, 29 deletions
diff --git a/src/main.rs b/src/main.rs
index faac9a7..e26218e 100644
--- a/src/main.rs
+++ b/src/main.rs
@@ -2,9 +2,9 @@ mod bpf_skel;
pub use bpf_skel::*;
pub mod bpf_intf;
+mod e_core_selector;
mod mock;
mod task_state;
-mod e_core_selector;
#[rustfmt::skip]
mod bpf;
@@ -12,19 +12,20 @@ use bpf::*;
use clap::{Arg, ArgAction, Command};
use e_core_selector::{ECoreSelector, RoundRobinSelector};
+use mock::perf::PerfEstimator;
use scx_utils::UserExitInfo;
use libbpf_rs::OpenObject;
+use mock::{KernelDriver, KernelModule, MockModule};
use task_state::TaskState;
-use mock::{MockModule, KernelModule, KernelDriver};
-use sysinfo::System;
use std::collections::{HashMap, VecDeque};
use std::fs::File;
use std::io::{BufRead, BufReader};
use std::mem::MaybeUninit;
-use std::process;
use std::ops::Range;
+use std::process;
+use sysinfo::System;
use anyhow::Result;
@@ -46,7 +47,11 @@ struct Scheduler<'a> {
}
impl<'a> Scheduler<'a> {
- fn init(open_object: &'a mut MaybeUninit<OpenObject>, use_mocking: bool, power_cap: u64) -> Result<Self> {
+ fn init(
+ open_object: &'a mut MaybeUninit<OpenObject>,
+ use_mocking: bool,
+ power_cap: u64,
+ ) -> Result<Self> {
let bpf = BpfScheduler::init(
open_object,
0, // exit_dump_len (buffer size of exit info, 0 = default)
@@ -55,8 +60,8 @@ impl<'a> Scheduler<'a> {
)?;
dbg!("registering rust user space scheduler");
let module: Box<dyn KernelModule> = if use_mocking {
- Box::new(MockModule)
- } else {
+ Box::new(PerfEstimator::default())
+ } else {
Box::new(KernelDriver::default())
};
@@ -66,7 +71,9 @@ impl<'a> Scheduler<'a> {
let cores: Vec<&str> = line.split('-').collect();
cores[0].parse::<i32>().unwrap()..cores[1].parse::<i32>().unwrap()
} else {
- panic!("Was not able to differentiate between core types. Does the system have e cores?")
+ panic!(
+ "Was not able to differentiate between core types. Does the system have e cores?"
+ )
};
let p_cores_file = File::open("/sys/devices/cpu_core/cpus")?;
@@ -75,7 +82,9 @@ impl<'a> Scheduler<'a> {
let cores: Vec<&str> = line.split('-').collect();
cores[0].parse::<i32>().unwrap()..cores[1].parse::<i32>().unwrap()
} else {
- panic!("Was not able to differentiate between core types. Does the system have e cores?")
+ panic!(
+ "Was not able to differentiate between core types. Does the system have e cores?"
+ )
};
let selector = Box::new(RoundRobinSelector::new(&e_cores));
@@ -95,7 +104,7 @@ impl<'a> Scheduler<'a> {
p_cores,
e_cores,
e_core_selector: selector,
- system
+ system,
})
}
@@ -136,11 +145,14 @@ impl<'a> Scheduler<'a> {
}
} else {
self.module.start_trace(task.pid as u64);
- self.managed_tasks.insert(task.pid as u32, TaskState {
- previous_energy_usage: 0,
- budget: self.maximum_budget,
- children: vec![],
- });
+ self.managed_tasks.insert(
+ task.pid as u32,
+ TaskState {
+ previous_energy_usage: 0,
+ budget: self.maximum_budget,
+ children: vec![],
+ },
+ );
self.task_queue.push_back(task);
}
}
@@ -182,7 +194,9 @@ impl<'a> Scheduler<'a> {
// Notify the BPF component of the number of pending tasks and immediately give a
// chance to run to the dispatched task.
//TODO: should the pending tasks include the ones that don't have any budget left?
- self.bpf.notify_complete(self.task_queue.len() as u64 + self.no_budget_task_queue.len() as u64);
+ self.bpf.notify_complete(
+ self.task_queue.len() as u64 + self.no_budget_task_queue.len() as u64,
+ );
} else if let Some(task) = self.no_budget_task_queue.pop_front() {
//TODO: do something with tasks that have no budget left
let mut dispatched_task = DispatchedTask::new(&task);
@@ -196,7 +210,9 @@ impl<'a> Scheduler<'a> {
dispatched_task.slice_ns = SLICE_US;
self.bpf.dispatch_task(&dispatched_task).unwrap();
- self.bpf.notify_complete(self.task_queue.len() as u64 + self.no_budget_task_queue.len() as u64);
+ self.bpf.notify_complete(
+ self.task_queue.len() as u64 + self.no_budget_task_queue.len() as u64,
+ );
}
}
@@ -206,7 +222,7 @@ impl<'a> Scheduler<'a> {
self.reset_budgets_and_garbage_collect();
//TODO: we should probably not do this every time, but instead wait a predefined amount of time between invocations
self.refresh_children();
-
+
// Consume all tasks before dispatching any.
self.consume_all_tasks();
@@ -253,7 +269,8 @@ impl<'a> Scheduler<'a> {
//TODO: this is probably not very efficient
fn refresh_children(&mut self) {
- self.system.refresh_processes(sysinfo::ProcessesToUpdate::All, true);
+ self.system
+ .refresh_processes(sysinfo::ProcessesToUpdate::All, true);
for entry in self.managed_tasks.values_mut() {
entry.children.clear();
}
@@ -266,22 +283,25 @@ impl<'a> Scheduler<'a> {
}
}
}
-
}
fn main() -> Result<()> {
let matches = Command::new("Energy User Space Scheduler")
- .arg(Arg::new("mock")
+ .arg(
+ Arg::new("mock")
.short('m')
.long("mock")
.help("Use this flag if to activate kernel module mocking")
.action(ArgAction::SetTrue)
- .required(false))
- .arg(Arg::new("power_cap")
+ .required(false),
+ )
+ .arg(
+ Arg::new("power_cap")
.long("energy_cap")
.help("Set a power cap for the processor")
.required(false)
- .value_name("power in watts"))
+ .value_name("power in watts"),
+ )
.get_matches();
let power_cap = *matches.get_one::<u64>("power_cap").unwrap_or(&u64::MAX);
@@ -296,6 +316,5 @@ fn main() -> Result<()> {
}
}
-
Ok(())
}
diff --git a/src/mock.rs b/src/mock.rs
index c5f8b34..5062c8a 100644
--- a/src/mock.rs
+++ b/src/mock.rs
@@ -1,6 +1,6 @@
use iocuddle::*;
use rand::Rng;
-mod perf;
+pub mod perf;
pub trait KernelModule {
fn start_trace(&mut self, _pid: u64) {}
diff --git a/src/mock/perf.rs b/src/mock/perf.rs
index 4bf87c9..d35510d 100644
--- a/src/mock/perf.rs
+++ b/src/mock/perf.rs
@@ -4,7 +4,8 @@ use events::Event;
use perf_event::events::Hardware;
use perf_event::*;
-struct PerfEstimator {
+#[derive(Default)]
+pub struct PerfEstimator {
registry: HashMap<u64, Counters>,
}
@@ -47,10 +48,10 @@ impl super::KernelModule for PerfEstimator {
};
let mut sum = 0;
let counts = counters.group.read().unwrap();
- for ((factor, ty), count) in EVENT_TYPES.iter().zip(counts.iter()) {
+ for ((factor, _ty), count) in EVENT_TYPES.iter().zip(counts.iter()) {
sum += *factor as u64 * count.1;
}
-
+ dbg!(sum);
sum
}
}