Refactor VM config to support different CPU topologies
This is preliminary work to support crosvm's --host-cpu-topology (WIP),
which will make it possible to mirror host's CPU topology in the guest.
As a first step, we refactor AVF's system API to stop accepting number
of vCPUs as an argument, but instead only expose two topology configs:
1 vCPU (default) and matching the host's CPU topology.
For the time being, the latter results in crosvm started with `--cpu
<nproc>`.
Bug: 266664564
Test: atest -p packages/modules/Virtualization:avf-presubmit
Change-Id: I03a37be0b68b93dc0fa6e84fd51ca3bdefbe6dde
diff --git a/compos/common/compos_client.rs b/compos/common/compos_client.rs
index f6811cb..59fdd9f 100644
--- a/compos/common/compos_client.rs
+++ b/compos/common/compos_client.rs
@@ -22,6 +22,7 @@
COMPOS_APEX_ROOT, COMPOS_DATA_ROOT, COMPOS_VSOCK_PORT,
};
use android_system_virtualizationservice::aidl::android::system::virtualizationservice::{
+ CpuTopology::CpuTopology,
IVirtualizationService::IVirtualizationService,
VirtualMachineAppConfig::{DebugLevel::DebugLevel, Payload::Payload, VirtualMachineAppConfig},
VirtualMachineConfig::VirtualMachineConfig,
@@ -32,20 +33,29 @@
use log::{info, warn};
use rustutils::system_properties;
use std::fs::{self, File};
-use std::num::NonZeroU32;
use std::path::{Path, PathBuf};
use vmclient::{DeathReason, ErrorCode, VmInstance, VmWaitError};
/// This owns an instance of the CompOS VM.
pub struct ComposClient(VmInstance);
+/// CPU topology configuration for a virtual machine.
+#[derive(Default, Debug, Clone)]
+pub enum VmCpuTopology {
+ /// Run VM with 1 vCPU only.
+ #[default]
+ OneCpu,
+ /// Run VM vCPU topology matching that of the host.
+ MatchHost,
+}
+
/// Parameters to be used when creating a virtual machine instance.
#[derive(Default, Debug, Clone)]
pub struct VmParameters {
/// Whether the VM should be debuggable.
pub debug_mode: bool,
- /// Number of vCPUs to have in the VM. If None, defaults to 1.
- pub cpus: Option<NonZeroU32>,
+ /// CPU topology of the VM. Defaults to 1 vCPU.
+ pub cpu_topology: VmCpuTopology,
/// List of task profiles to apply to the VM
pub task_profiles: Vec<String>,
/// If present, overrides the amount of RAM to give the VM
@@ -111,6 +121,11 @@
(Some(console_fd), Some(log_fd))
};
+ let cpu_topology = match parameters.cpu_topology {
+ VmCpuTopology::OneCpu => CpuTopology::ONE_CPU,
+ VmCpuTopology::MatchHost => CpuTopology::MATCH_HOST,
+ };
+
let config = VirtualMachineConfig::AppConfig(VirtualMachineAppConfig {
name: String::from("Compos"),
apk: Some(apk_fd),
@@ -122,7 +137,7 @@
extraIdsigs: extra_idsigs,
protectedVm: protected_vm,
memoryMib: parameters.memory_mib.unwrap_or(0), // 0 means use the default
- numCpus: parameters.cpus.map_or(1, NonZeroU32::get) as i32,
+ cpuTopology: cpu_topology,
taskProfiles: parameters.task_profiles.clone(),
});
diff --git a/compos/composd/Android.bp b/compos/composd/Android.bp
index 07a9be3..cee4b01 100644
--- a/compos/composd/Android.bp
+++ b/compos/composd/Android.bp
@@ -17,7 +17,6 @@
"libcompos_common",
"libcomposd_native_rust",
"libminijail_rust",
- "libnum_cpus",
"libnix",
"liblibc",
"liblog_rust",
diff --git a/compos/composd/src/instance_manager.rs b/compos/composd/src/instance_manager.rs
index 0a6c3d6..2db13c7 100644
--- a/compos/composd/src/instance_manager.rs
+++ b/compos/composd/src/instance_manager.rs
@@ -21,9 +21,8 @@
use android_system_virtualizationservice::aidl::android::system::virtualizationservice;
use anyhow::{bail, Result};
use binder::Strong;
-use compos_common::compos_client::VmParameters;
+use compos_common::compos_client::{VmCpuTopology, VmParameters};
use compos_common::{CURRENT_INSTANCE_DIR, TEST_INSTANCE_DIR};
-use std::num::NonZeroU32;
use std::sync::{Arc, Mutex, Weak};
use virtualizationservice::IVirtualizationService::IVirtualizationService;
@@ -80,9 +79,14 @@
// By default, dex2oat starts as many threads as there are CPUs. This can be overridden with
// a system property. Start the VM with all CPUs and assume the guest will start a suitable
// number of dex2oat threads.
- let cpus = NonZeroU32::new(num_cpus::get() as u32);
+ let cpu_topology = VmCpuTopology::MatchHost;
let task_profiles = vec!["SCHED_SP_COMPUTE".to_string()];
- Ok(VmParameters { cpus, task_profiles, memory_mib: Some(VM_MEMORY_MIB), ..Default::default() })
+ Ok(VmParameters {
+ cpu_topology,
+ task_profiles,
+ memory_mib: Some(VM_MEMORY_MIB),
+ ..Default::default()
+ })
}
// Ensures we only run one instance at a time.
diff --git a/compos/verify/verify.rs b/compos/verify/verify.rs
index 528719f..13e9292 100644
--- a/compos/verify/verify.rs
+++ b/compos/verify/verify.rs
@@ -21,7 +21,7 @@
use anyhow::{bail, Context, Result};
use binder::ProcessState;
use clap::{Parser, ValueEnum};
-use compos_common::compos_client::{ComposClient, VmParameters};
+use compos_common::compos_client::{ComposClient, VmCpuTopology, VmParameters};
use compos_common::odrefresh::{
CURRENT_ARTIFACTS_SUBDIR, ODREFRESH_OUTPUT_ROOT_DIR, PENDING_ARTIFACTS_SUBDIR,
TEST_ARTIFACTS_SUBDIR,
@@ -33,7 +33,6 @@
use log::error;
use std::fs::File;
use std::io::Read;
-use std::num::NonZeroU32;
use std::panic;
use std::path::Path;
@@ -116,7 +115,7 @@
&idsig_manifest_apk,
&idsig_manifest_ext_apk,
&VmParameters {
- cpus: Some(NonZeroU32::new(1).unwrap()), // This VM runs very little work at boot
+ cpu_topology: VmCpuTopology::OneCpu, // This VM runs very little work at boot
debug_mode: args.debug,
..Default::default()
},