diff --git a/crates/runtime/src/instance.rs b/crates/runtime/src/instance.rs index 9ad701432c04..61902beecb97 100644 --- a/crates/runtime/src/instance.rs +++ b/crates/runtime/src/instance.rs @@ -805,7 +805,12 @@ impl Instance { // disconnected from the lifetime of `self`. let module = self.module().clone(); - let empty = TableSegmentElements::Functions(Box::new([])); + // NB: fall back to an expressions-based list of elements which doesn't + // have static type information (as opposed to `Functions`) since we + // don't know just yet what type the table has. The type will be be + // inferred in the next step within `table_init_segment`. + let empty = TableSegmentElements::Expressions(Box::new([])); + let elements = match module.passive_elements_map.get(&elem_index) { Some(index) if !self.dropped_elements.contains(elem_index) => { &module.passive_elements[*index] diff --git a/tests/misc_testsuite/externref-table-dropped-segment-issue-8281.wast b/tests/misc_testsuite/externref-table-dropped-segment-issue-8281.wast new file mode 100644 index 000000000000..723c03c801e3 --- /dev/null +++ b/tests/misc_testsuite/externref-table-dropped-segment-issue-8281.wast @@ -0,0 +1,39 @@ +(module + (table $t 0 0 externref) + + (func (export "f1") + (i32.const 0) + (i32.const 0) + (i32.const 0) + (table.init $t $declared) + ) + + (func (export "f2") + (i32.const 0) + (i32.const 0) + (i32.const 0) + (table.init $t $passive) + + (elem.drop $passive) + + (i32.const 0) + (i32.const 0) + (i32.const 0) + (table.init $t $passive) + ) + + (func (export "f3") + (i32.const 0) + (i32.const 0) + (i32.const 0) + (table.init $t $active) + ) + + (elem $declared declare externref) + (elem $passive externref) + (elem $active (i32.const 0) externref) +) + +(assert_return (invoke "f1")) +(assert_return (invoke "f2")) +(assert_return (invoke "f3"))