Skip to content

Commit 68db342

Browse files
committed
refactor(queue): safer write_used_ring method
Now `write_used_ring` makes sure the index is in correct bounds. This way there is no way for a caller to provide index outside of bounds. Signed-off-by: Egor Lazarchuk <[email protected]>
1 parent aef15a6 commit 68db342

File tree

1 file changed

+7
-5
lines changed

1 file changed

+7
-5
lines changed

src/vmm/src/devices/virtio/queue.rs

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -443,12 +443,11 @@ impl Queue {
443443
) -> Result<(), QueueError> {
444444
debug_assert!(self.is_layout_valid(mem));
445445

446-
let next_used = self.next_used.0 % self.actual_size();
447446
let used_element = UsedElement {
448447
id: u32::from(desc_index),
449448
len,
450449
};
451-
self.write_used_ring(mem, next_used, used_element)?;
450+
self.write_used_ring(mem, self.next_used.0, used_element)?;
452451
self.advance_used_ring(mem, 1);
453452
Ok(())
454453
}
@@ -488,11 +487,14 @@ impl Queue {
488487
// We calculate offset into `ring` field.
489488
let used_ring_offset = std::mem::size_of::<u16>()
490489
+ std::mem::size_of::<u16>()
491-
+ std::mem::size_of::<UsedElement>() * usize::from(index);
490+
+ std::mem::size_of::<UsedElement>() * usize::from(index % self.actual_size());
492491
let used_element_address = self.used_ring.unchecked_add(usize_to_u64(used_ring_offset));
493492

494-
mem.write_obj(used_element, used_element_address)
495-
.map_err(QueueError::UsedRing)
493+
// SAFETY:
494+
// `used_element_address` param is bounded by size of the queue as `index` is
495+
// modded by `actual_size()`.
496+
mem.write_obj(used_element, used_element_address).unwrap();
497+
Ok(())
496498
}
497499

498500
/// Fetch the available ring index (`virtq_avail->idx`) from guest memory.

0 commit comments

Comments
 (0)