mirror of
https://github.com/asterinas/asterinas.git
synced 2025-06-27 19:33:23 +00:00
Reduce the held time of scheduling policy lock
This commit is contained in:
committed by
Tate, Hongliang Tian
parent
ea953209ff
commit
364d6af7c8
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MPL-2.0
|
||||
|
||||
use alloc::{collections::binary_heap::BinaryHeap, sync::Arc};
|
||||
use alloc::collections::binary_heap::BinaryHeap;
|
||||
use core::{
|
||||
cmp::{self, Reverse},
|
||||
sync::atomic::{AtomicU64, Ordering::*},
|
||||
@ -13,12 +13,9 @@ use ostd::{
|
||||
|
||||
use super::{
|
||||
time::{base_slice_clocks, min_period_clocks},
|
||||
CurrentRuntime, SchedAttr, SchedClassRq,
|
||||
};
|
||||
use crate::{
|
||||
sched::priority::{Nice, NiceRange},
|
||||
thread::Thread,
|
||||
CurrentRuntime, SchedAttr, SchedClassRq, SchedEntity,
|
||||
};
|
||||
use crate::sched::priority::{Nice, NiceRange};
|
||||
|
||||
const WEIGHT_0: u64 = 1024;
|
||||
pub const fn nice_to_weight(nice: Nice) -> u64 {
|
||||
@ -120,7 +117,7 @@ impl FairAttr {
|
||||
///
|
||||
/// This structure is used to provide the capability for keying in the
|
||||
/// run queue implemented by `BTreeSet` in the `FairClassRq`.
|
||||
struct FairQueueItem(Arc<Thread>);
|
||||
struct FairQueueItem(SchedEntity);
|
||||
|
||||
impl core::fmt::Debug for FairQueueItem {
|
||||
fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
|
||||
@ -130,7 +127,7 @@ impl core::fmt::Debug for FairQueueItem {
|
||||
|
||||
impl FairQueueItem {
|
||||
fn key(&self) -> u64 {
|
||||
self.0.sched_attr().fair.vruntime.load(Relaxed)
|
||||
self.0 .1.sched_attr().fair.vruntime.load(Relaxed)
|
||||
}
|
||||
}
|
||||
|
||||
@ -165,7 +162,7 @@ pub(super) struct FairClassRq {
|
||||
#[allow(unused)]
|
||||
cpu: CpuId,
|
||||
/// The ready-to-run threads.
|
||||
threads: BinaryHeap<Reverse<FairQueueItem>>,
|
||||
entities: BinaryHeap<Reverse<FairQueueItem>>,
|
||||
/// The minimum of vruntime in the run queue. Serves as the initial
|
||||
/// value of newly-enqueued threads.
|
||||
min_vruntime: u64,
|
||||
@ -176,7 +173,7 @@ impl FairClassRq {
|
||||
pub fn new(cpu: CpuId) -> Self {
|
||||
Self {
|
||||
cpu,
|
||||
threads: BinaryHeap::new(),
|
||||
entities: BinaryHeap::new(),
|
||||
min_vruntime: 0,
|
||||
total_weight: 0,
|
||||
}
|
||||
@ -201,13 +198,13 @@ impl FairClassRq {
|
||||
|
||||
// `+ 1` means including the current running thread.
|
||||
let period_single_cpu =
|
||||
(base_slice_clks * (self.threads.len() + 1) as u64).max(min_period_clks);
|
||||
(base_slice_clks * (self.entities.len() + 1) as u64).max(min_period_clks);
|
||||
period_single_cpu * u64::from((1 + num_cpus()).ilog2())
|
||||
}
|
||||
|
||||
/// The virtual time slice for each thread in the run queue, measured in vruntime clocks.
|
||||
fn vtime_slice(&self) -> u64 {
|
||||
self.period() / (self.threads.len() + 1) as u64
|
||||
self.period() / (self.entities.len() + 1) as u64
|
||||
}
|
||||
|
||||
/// The time slice for each thread in the run queue, measured in sched clocks.
|
||||
@ -217,8 +214,8 @@ impl FairClassRq {
|
||||
}
|
||||
|
||||
impl SchedClassRq for FairClassRq {
|
||||
fn enqueue(&mut self, thread: Arc<Thread>, flags: Option<EnqueueFlags>) {
|
||||
let fair_attr = &thread.sched_attr().fair;
|
||||
fn enqueue(&mut self, entity: SchedEntity, flags: Option<EnqueueFlags>) {
|
||||
let fair_attr = &entity.1.sched_attr().fair;
|
||||
let vruntime = match flags {
|
||||
Some(EnqueueFlags::Spawn) => self.min_vruntime + self.vtime_slice(),
|
||||
_ => self.min_vruntime,
|
||||
@ -226,23 +223,23 @@ impl SchedClassRq for FairClassRq {
|
||||
fair_attr.vruntime.fetch_max(vruntime, Relaxed);
|
||||
|
||||
self.total_weight += fair_attr.weight.load(Relaxed);
|
||||
self.threads.push(Reverse(FairQueueItem(thread)));
|
||||
self.entities.push(Reverse(FairQueueItem(entity)));
|
||||
}
|
||||
|
||||
fn len(&mut self) -> usize {
|
||||
self.threads.len()
|
||||
self.entities.len()
|
||||
}
|
||||
|
||||
fn is_empty(&mut self) -> bool {
|
||||
self.threads.is_empty()
|
||||
self.entities.is_empty()
|
||||
}
|
||||
|
||||
fn pick_next(&mut self) -> Option<Arc<Thread>> {
|
||||
let Reverse(FairQueueItem(thread)) = self.threads.pop()?;
|
||||
fn pick_next(&mut self) -> Option<SchedEntity> {
|
||||
let Reverse(FairQueueItem(entity)) = self.entities.pop()?;
|
||||
|
||||
self.total_weight -= thread.sched_attr().fair.weight.load(Relaxed);
|
||||
self.total_weight -= entity.1.sched_attr().fair.weight.load(Relaxed);
|
||||
|
||||
Some(thread)
|
||||
Some(entity)
|
||||
}
|
||||
|
||||
fn update_current(
|
||||
@ -255,7 +252,7 @@ impl SchedClassRq for FairClassRq {
|
||||
UpdateFlags::Yield => true,
|
||||
UpdateFlags::Tick | UpdateFlags::Wait => {
|
||||
let (vruntime, weight) = attr.fair.update_vruntime(rt.delta);
|
||||
self.min_vruntime = match self.threads.peek() {
|
||||
self.min_vruntime = match self.entities.peek() {
|
||||
Some(Reverse(leftmost)) => vruntime.min(leftmost.key()),
|
||||
None => vruntime,
|
||||
};
|
||||
|
Reference in New Issue
Block a user