Skip to content

Commit c994bc4

Browse files
authored
Refactor HandleTable::insert slightly (#13079)
This commit refactors the handle table accessible to components to remove a theoretical bug where when the table is full of elements it can get in a slightly weird where slots get allocated but traps are returned. This commit updates the modification of the table to happen only after the bounds-check is performed to ensure that once a table is full it's never extended any further.
1 parent a1af4e7 commit c994bc4

1 file changed

Lines changed: 17 additions & 14 deletions

File tree

crates/wasmtime/src/runtime/vm/component/handle_table.rs

Lines changed: 17 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -135,27 +135,30 @@ impl HandleTable {
135135
}
136136

137137
fn insert(&mut self, slot: Slot) -> Result<u32> {
138-
let next = self.next as usize;
139-
if next == self.slots.len() {
140-
self.slots.push(Slot::Free {
141-
next: self.next.checked_add(1).unwrap(),
142-
})?;
143-
}
144-
let ret = self.next;
145-
self.next = match mem::replace(&mut self.slots[next], slot) {
146-
Slot::Free { next } => next,
147-
_ => unreachable!(),
148-
};
138+
let next = self.next;
139+
149140
// The component model reserves index 0 as never allocatable so add one
150141
// to the table index to start the numbering at 1 instead. Also note
151142
// that the component model places an upper-limit per-table on the
152143
// maximum allowed index.
153-
let ret = ret + 1;
154-
if ret >= MAX_HANDLE {
144+
//
145+
// First check to make sure the returned handle is in-bounds, then do
146+
// the actual allocation below.
147+
if next + 1 >= MAX_HANDLE {
155148
bail!("cannot allocate another handle: index overflow");
156149
}
157150

158-
Ok(ret)
151+
if next as usize == self.slots.len() {
152+
self.slots.push(Slot::Free {
153+
next: next.checked_add(1).unwrap(),
154+
})?;
155+
}
156+
self.next = match mem::replace(&mut self.slots[next as usize], slot) {
157+
Slot::Free { next } => next,
158+
_ => unreachable!(),
159+
};
160+
161+
Ok(next + 1)
159162
}
160163

161164
fn remove(&mut self, idx: u32) -> Result<()> {

0 commit comments

Comments
 (0)