mirror of
https://chromium.googlesource.com/crosvm/crosvm
synced 2025-02-05 18:20:34 +00:00
crosvm: Allow all vCPU threads to share same cookie for core scheduling
This CL adds --per-vm-core-scheduling command line option to crosvm to allow ARCVM to use per-VM core scheduling for better performance. Note that per-VM core scheduling makes all vCPU threads to share the same core scheduling cookie. The feature is disabled by default, and does not change Linux VMs behavior unless the new command line flag is explicitly passed in. Also, this CL never affect Parallels since it uses the plugin infrastructure (src/plugin/). For ARCVM, the feature will be enabled by default via Chromium's base::Feature (see crrev.com/c/3207747) as an interim solution until the optimized two-level core scheduling is ready. This is based on the latest recommendation from the security team (newfel@, resch@, and others) at go/arcvm-core-scheduling-recommendations. Credit: This CL is based on an idea from joelhockey@ and bgeffon@ at go/exawj BUG=b:194022819 TEST=boot ARCVM with the new flag and verify all vCPU threads have same cookie. Change-Id: Ib97ab9942b2516df9fbffe35517919f29b309a83 Reviewed-on: https://chromium-review.googlesource.com/c/chromiumos/platform/crosvm/+/3101607 Commit-Queue: Yusuke Sato <yusukes@chromium.org> Owners-Override: Yusuke Sato <yusukes@chromium.org> Tested-by: kokoro <noreply+kokoro@google.com> Reviewed-by: Daniel Verkamp <dverkamp@chromium.org> Reviewed-by: Joel Hockey <joelhockey@chromium.org> Reviewed-by: Jorge Lucangeli Obes <jorgelo@chromium.org>
This commit is contained in:
parent
cce4054aa8
commit
31e136aeda
3 changed files with 28 additions and 2 deletions
|
@ -302,6 +302,7 @@ pub struct Config {
|
|||
pub vcpu_affinity: Option<VcpuAffinity>,
|
||||
pub cpu_clusters: Vec<Vec<usize>>,
|
||||
pub cpu_capacity: BTreeMap<usize, u32>, // CPU index -> capacity
|
||||
pub per_vm_core_scheduling: bool,
|
||||
#[cfg(feature = "audio_cras")]
|
||||
pub cras_snd: Option<CrasSndParameters>,
|
||||
pub delay_rt: bool,
|
||||
|
@ -390,6 +391,7 @@ impl Default for Config {
|
|||
vcpu_affinity: None,
|
||||
cpu_clusters: Vec::new(),
|
||||
cpu_capacity: BTreeMap::new(),
|
||||
per_vm_core_scheduling: false,
|
||||
#[cfg(feature = "audio_cras")]
|
||||
cras_snd: None,
|
||||
delay_rt: false,
|
||||
|
|
22
src/linux.rs
22
src/linux.rs
|
@ -1826,6 +1826,7 @@ fn runnable_vcpu<V>(
|
|||
no_smt: bool,
|
||||
has_bios: bool,
|
||||
use_hypervisor_signals: bool,
|
||||
enable_per_vm_core_scheduling: bool,
|
||||
) -> Result<(V, VcpuRunHandle)>
|
||||
where
|
||||
V: VcpuArch,
|
||||
|
@ -1868,8 +1869,11 @@ where
|
|||
)
|
||||
.map_err(Error::ConfigureVcpu)?;
|
||||
|
||||
if let Err(e) = enable_core_scheduling() {
|
||||
error!("Failed to enable core scheduling: {}", e);
|
||||
if !enable_per_vm_core_scheduling {
|
||||
// Do per-vCPU core scheduling by setting a unique cookie to each vCPU.
|
||||
if let Err(e) = enable_core_scheduling() {
|
||||
error!("Failed to enable core scheduling: {}", e);
|
||||
}
|
||||
}
|
||||
|
||||
if run_rt {
|
||||
|
@ -1991,6 +1995,7 @@ fn run_vcpu<V>(
|
|||
#[cfg(all(target_arch = "x86_64", feature = "gdb"))] to_gdb_tube: Option<
|
||||
mpsc::Sender<VcpuDebugStatusMessage>,
|
||||
>,
|
||||
enable_per_vm_core_scheduling: bool,
|
||||
) -> Result<JoinHandle<()>>
|
||||
where
|
||||
V: VcpuArch + 'static,
|
||||
|
@ -2015,6 +2020,7 @@ where
|
|||
no_smt,
|
||||
has_bios,
|
||||
use_hypervisor_signals,
|
||||
enable_per_vm_core_scheduling,
|
||||
);
|
||||
|
||||
start_barrier.wait();
|
||||
|
@ -2654,6 +2660,7 @@ where
|
|||
cfg.sandbox,
|
||||
Arc::clone(&map_request),
|
||||
gralloc,
|
||||
cfg.per_vm_core_scheduling,
|
||||
)
|
||||
}
|
||||
|
||||
|
@ -2746,6 +2753,7 @@ fn run_control<V: VmArch + 'static, Vcpu: VcpuArch + 'static>(
|
|||
sandbox: bool,
|
||||
map_request: Arc<Mutex<Option<ExternalMapping>>>,
|
||||
mut gralloc: RutabagaGralloc,
|
||||
enable_per_vm_core_scheduling: bool,
|
||||
) -> Result<()> {
|
||||
#[derive(PollToken)]
|
||||
enum Token {
|
||||
|
@ -2816,6 +2824,15 @@ fn run_control<V: VmArch + 'static, Vcpu: VcpuArch + 'static>(
|
|||
Some(vec) => vec.into_iter().map(Some).collect(),
|
||||
None => iter::repeat_with(|| None).take(linux.vcpu_count).collect(),
|
||||
};
|
||||
// Enable core scheduling before creating vCPUs so that the cookie will be
|
||||
// shared by all vCPU threads.
|
||||
// TODO(b/199312402): Avoid enabling core scheduling for the crosvm process
|
||||
// itself for even better performance. Only vCPUs need the feature.
|
||||
if enable_per_vm_core_scheduling {
|
||||
if let Err(e) = enable_core_scheduling() {
|
||||
error!("Failed to enable core scheduling: {}", e);
|
||||
}
|
||||
}
|
||||
for (cpu_id, vcpu) in vcpus.into_iter().enumerate() {
|
||||
let (to_vcpu_channel, from_main_channel) = mpsc::channel();
|
||||
let vcpu_affinity = match linux.vcpu_affinity.clone() {
|
||||
|
@ -2843,6 +2860,7 @@ fn run_control<V: VmArch + 'static, Vcpu: VcpuArch + 'static>(
|
|||
use_hypervisor_signals,
|
||||
#[cfg(all(target_arch = "x86_64", feature = "gdb"))]
|
||||
to_gdb_channel.clone(),
|
||||
enable_per_vm_core_scheduling,
|
||||
)?;
|
||||
vcpu_handles.push((handle, to_vcpu_channel));
|
||||
}
|
||||
|
|
|
@ -978,6 +978,9 @@ fn set_argument(cfg: &mut Config, name: &str, value: Option<&str>) -> argument::
|
|||
"cpu-capacity" => {
|
||||
parse_cpu_capacity(value.unwrap(), &mut cfg.cpu_capacity)?;
|
||||
}
|
||||
"per-vm-core-scheduling" => {
|
||||
cfg.per_vm_core_scheduling = true;
|
||||
}
|
||||
#[cfg(feature = "audio_cras")]
|
||||
"cras-snd" => {
|
||||
cfg.cras_snd = Some(
|
||||
|
@ -2041,6 +2044,9 @@ fn run_vm(args: std::env::Args) -> std::result::Result<(), ()> {
|
|||
or colon-separated list of assignments of guest to host CPU assignments (e.g. 0=0:1=1:2=2) (default: no mask)"),
|
||||
Argument::value("cpu-cluster", "CPUSET", "Group the given CPUs into a cluster (default: no clusters)"),
|
||||
Argument::value("cpu-capacity", "CPU=CAP[,CPU=CAP[,...]]", "Set the relative capacity of the given CPU (default: no capacity)"),
|
||||
Argument::flag("per-vm-core-scheduling", "Enable per-VM core scheduling intead of the default one (per-vCPU core scheduing) by
|
||||
making all vCPU threads share same cookie for core scheduling.
|
||||
This option is no-op on devices that have neither MDS nor L1TF vulnerability."),
|
||||
#[cfg(feature = "audio_cras")]
|
||||
Argument::value("cras-snd",
|
||||
"[capture=true,client=crosvm,socket=unified]",
|
||||
|
|
Loading…
Reference in a new issue