vhost-user: encode shmem region IDs as array indices

VhostUserShMemConfig::new() previously accepted a dense slice of sizes,
with region IDs implicitly assigned 0..N. Change it to accept (id, size)
pairs and store each size at memory_sizes[id], leaving absent regions as
zero.

This makes the encoding match crosvm's vmm_vhost, where region IDs are
arbitrary u8 values (e.g. VIRTIO_GPU_SHM_ID_HOST_VISIBLE = 1) rather
than always starting at zero.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
Davíð Steinn Geirsson 2026-03-18 16:36:45 +00:00
parent c9b80a1c93
commit dd468710dc
3 changed files with 19 additions and 13 deletions

View file

@ -1079,10 +1079,10 @@ mod tests {
#[test]
fn test_get_shmem_config_multiple_regions() {
let memory_sizes = [
0x1000, 0x2000, 0x3000, 0x4000, 0x5000, 0x6000, 0x7000, 0x8000,
];
let config = VhostUserShMemConfig::new(8, &memory_sizes);
let config = VhostUserShMemConfig::new(&[
(0, 0x1000), (1, 0x2000), (2, 0x3000), (3, 0x4000),
(4, 0x5000), (5, 0x6000), (6, 0x7000), (7, 0x8000),
]);
let (p1, p2) = UnixStream::pair().unwrap();
let mut dummy_backend = DummyBackendReqHandler::new();
@ -1109,9 +1109,8 @@ mod tests {
#[test]
fn test_get_shmem_config_non_continuous_regions() {
// Create a configuration with non-continuous regions
let memory_sizes = [0x10000, 0, 0x20000, 0, 0, 0, 0, 0];
let config = VhostUserShMemConfig::new(2, &memory_sizes);
// Create a configuration with non-contiguous region IDs (0 and 2, skipping 1)
let config = VhostUserShMemConfig::new(&[(0, 0x10000), (2, 0x20000)]);
let (p1, p2) = UnixStream::pair().unwrap();
let mut dummy_backend = DummyBackendReqHandler::new();

View file

@ -1220,7 +1220,7 @@ mod tests {
fn test_frontend_get_shmem_config() {
let (mut frontend, mut peer) = create_pair2();
let expected_config = VhostUserShMemConfig::new(2, &[0x1000, 0x2000]);
let expected_config = VhostUserShMemConfig::new(&[(0, 0x1000), (1, 0x2000)]);
let hdr = VhostUserMsgHeader::new(
FrontendReq::GET_SHMEM_CONFIG,
0x4,

View file

@ -700,7 +700,8 @@ pub struct VhostUserShMemConfig {
pub nregions: u32,
/// Padding for correct alignment
padding: u32,
/// Size of each memory region
/// Size of each memory region, indexed by region ID.
/// A zero entry means the region with that ID is absent.
pub memory_sizes: [u64; 256],
}
@ -715,11 +716,17 @@ impl Default for VhostUserShMemConfig {
}
impl VhostUserShMemConfig {
/// Create a new instance
pub fn new(nregions: u32, memory: &[u64]) -> Self {
let memory_sizes: [u64; 256] = std::array::from_fn(|i| *memory.get(i).unwrap_or(&0));
/// Create a new instance from a list of `(id, size)` pairs.
///
/// Region IDs do not need to be contiguous. Each ID is used directly as an
/// index into the internal array, leaving absent regions as zero.
pub fn new(regions: &[(u8, u64)]) -> Self {
let mut memory_sizes = [0u64; 256];
for &(id, size) in regions {
memory_sizes[usize::from(id)] = size;
}
Self {
nregions,
nregions: regions.len() as u32,
padding: 0,
memory_sizes,
}