diff --git a/virtio-devices/src/vhost_user/blk.rs b/virtio-devices/src/vhost_user/blk.rs index 5be785fcd..cc4f8bd50 100644 --- a/virtio-devices/src/vhost_user/blk.rs +++ b/virtio-devices/src/vhost_user/blk.rs @@ -191,18 +191,23 @@ impl VirtioDevice for Blk { } fn write_config(&mut self, offset: u64, data: &[u8]) { - let config_slice = self.config.as_mut_slice(); - let data_len = data.len() as u64; - let config_len = config_slice.len() as u64; - if offset + data_len > config_len { - error!("Failed to write config space"); + // The "writeback" field is the only mutable field + let writeback_offset = + (&self.config.writeback as *const _ as u64) - (&self.config as *const _ as u64); + if offset != writeback_offset || data.len() != std::mem::size_of_val(&self.config.writeback) + { + error!( + "Attempt to write to read-only field: offset {:x} length {}", + offset, + data.len() + ); return; } + + self.config.writeback = data[0]; self.vhost_user_blk .set_config(offset as u32, VhostUserConfigFlags::WRITABLE, data) .expect("Failed to set config"); - let (_, right) = config_slice.split_at_mut(offset as usize); - right.copy_from_slice(&data[..]); } fn activate(