summary refs log tree commit diff
path: root/devices/src/virtio/input/mod.rs
diff options
context:
space:
mode:
authorDaniel Verkamp <dverkamp@chromium.org>2019-08-09 14:25:03 -0700
committerCommit Bot <commit-bot@chromium.org>2019-08-16 07:20:21 +0000
commit58010b27310cc27df542294f81a19ea95feded5f (patch)
treeb9dc4cc8203edc1b4c5b26bed7c9fc585acc076d /devices/src/virtio/input/mod.rs
parent35a9d838dbb92b89e8baef380a550b8d8a4b15ad (diff)
downloadcrosvm-58010b27310cc27df542294f81a19ea95feded5f.tar
crosvm-58010b27310cc27df542294f81a19ea95feded5f.tar.gz
crosvm-58010b27310cc27df542294f81a19ea95feded5f.tar.bz2
crosvm-58010b27310cc27df542294f81a19ea95feded5f.tar.lz
crosvm-58010b27310cc27df542294f81a19ea95feded5f.tar.xz
crosvm-58010b27310cc27df542294f81a19ea95feded5f.tar.zst
crosvm-58010b27310cc27df542294f81a19ea95feded5f.zip
devices: virtio: add copy_config() helper function
Add a new virtio configuration copying function to replace all of the
slightly varying read_config() and write_config() implementations in our
virtio devices.  This replaces a lot of tricky bounds-checking code with
a single central implementation, simplifying the devices to a single
call to copy_config() in most cases.

The balloon device is also changed to represent its config space as a
DataInit struct to match most other devices and remove several unwrap()
calls.

BUG=None
TEST=./build_test
TEST=Boot vm_kernel+vm_rootfs in crosvm
TEST=Start Crostini on nami

Change-Id: Ia49bd6dbe609d17455b9562086bc0b24f327be3f
Signed-off-by: Daniel Verkamp <dverkamp@chromium.org>
Reviewed-on: https://chromium-review.googlesource.com/c/chromiumos/platform/crosvm/+/1749562
Reviewed-by: Dylan Reid <dgreid@chromium.org>
Tested-by: kokoro <noreply+kokoro@google.com>
Diffstat (limited to 'devices/src/virtio/input/mod.rs')
-rw-r--r--devices/src/virtio/input/mod.rs53
1 files changed, 11 insertions, 42 deletions
diff --git a/devices/src/virtio/input/mod.rs b/devices/src/virtio/input/mod.rs
index 3bed5ef..29152a2 100644
--- a/devices/src/virtio/input/mod.rs
+++ b/devices/src/virtio/input/mod.rs
@@ -16,7 +16,7 @@ use data_model::{DataInit, Le16, Le32};
 use sys_util::{error, warn, EventFd, GuestAddress, GuestMemory, PollContext, PollToken};
 
 use self::event_source::{input_event, EvdevEventSource, EventSource, SocketEventSource};
-use super::{Queue, VirtioDevice, INTERRUPT_STATUS_USED_RING, TYPE_INPUT};
+use super::{copy_config, Queue, VirtioDevice, INTERRUPT_STATUS_USED_RING, TYPE_INPUT};
 use std::collections::BTreeMap;
 use std::fmt::{self, Display};
 use std::io::Read;
@@ -233,8 +233,6 @@ pub struct VirtioInputConfig {
 }
 
 impl VirtioInputConfig {
-    const CONFIG_MEM_SIZE: usize = size_of::<virtio_input_config>();
-
     fn new(
         device_ids: virtio_input_device_ids,
         name: Vec<u8>,
@@ -266,19 +264,6 @@ impl VirtioInputConfig {
         ))
     }
 
-    fn validate_read_offsets(&self, offset: usize, len: usize) -> bool {
-        if offset + len > VirtioInputConfig::CONFIG_MEM_SIZE {
-            error!(
-                "Attempt to read from invalid config range: [{}..{}], valid ranges in [0..{}]",
-                offset,
-                offset + len,
-                VirtioInputConfig::CONFIG_MEM_SIZE
-            );
-            return false;
-        }
-        true
-    }
-
     fn build_config_memory(&self) -> virtio_input_config {
         let mut cfg = virtio_input_config::new();
         cfg.select = self.select;
@@ -322,35 +307,19 @@ impl VirtioInputConfig {
     }
 
     fn read(&self, offset: usize, data: &mut [u8]) {
-        let data_len = data.len();
-        if self.validate_read_offsets(offset, data_len) {
-            let config = self.build_config_memory();
-            data.clone_from_slice(&config.as_slice()[offset..offset + data_len]);
-        }
-    }
-
-    fn validate_write_offsets(&self, offset: usize, len: usize) -> bool {
-        const MAX_WRITABLE_BYTES: usize = 2;
-        if offset + len > MAX_WRITABLE_BYTES {
-            error!(
-                "Attempt to write to invalid config range: [{}..{}], valid ranges in [0..{}]",
-                offset,
-                offset + len,
-                MAX_WRITABLE_BYTES
-            );
-            return false;
-        }
-        true
+        copy_config(
+            data,
+            0,
+            self.build_config_memory().as_slice(),
+            offset as u64,
+        );
     }
 
     fn write(&mut self, offset: usize, data: &[u8]) {
-        let len = data.len();
-        if self.validate_write_offsets(offset, len) {
-            let mut selectors: [u8; 2] = [self.select, self.subsel];
-            selectors[offset..offset + len].clone_from_slice(&data);
-            self.select = selectors[0];
-            self.subsel = selectors[1];
-        }
+        let mut config = self.build_config_memory();
+        copy_config(config.as_mut_slice(), offset as u64, data, 0);
+        self.select = config.select;
+        self.subsel = config.subsel;
     }
 }