From ea0f552c11ac5f234107ffab7c6084419729d8d0 Mon Sep 17 00:00:00 2001 From: Connor Tsui Date: Tue, 11 Aug 2026 08:05:55 -0400 Subject: [PATCH] Harden indexed lane sources Signed-off-by: Connor Tsui --- vortex-compute/src/lane_kernels/source.rs | 23 ++++++++++++++++------- 1 file changed, 16 insertions(+), 7 deletions(-) diff --git a/vortex-compute/src/lane_kernels/source.rs b/vortex-compute/src/lane_kernels/source.rs index 9a486b4789b..f578d7a2952 100644 --- a/vortex-compute/src/lane_kernels/source.rs +++ b/vortex-compute/src/lane_kernels/source.rs @@ -10,9 +10,8 @@ /// reads carry no inter-iteration data dependency — the autovectorizer treats each /// lane independently. pub trait IndexedSource { - /// The per-lane item type. Must be `Copy` so the kernels can pass it through - /// the closure by value without extra moves. - type Item: Copy; + /// The per-lane item type passed through the kernel by value. + type Item; /// Logical lane count. fn len(&self) -> usize; /// Returns true when there are no lanes. @@ -55,10 +54,10 @@ impl IndexedSource for &mut [T] { /// Pair of two [`IndexedSource`]s of equal length. Yields `(A::Item, B::Item)` per lane. /// -/// Use this to drive a binary kernel from two columns. Length equality is enforced -/// at construction. +/// Use this to drive a binary kernel from two columns. Length equality is enforced at +/// construction, and the private fields prevent callers from bypassing that check. #[derive(Clone, Copy)] -pub struct LaneZip(pub A, pub B); +pub struct LaneZip(A, B); impl LaneZip { /// Build a `LaneZip` from two equal-length sources. @@ -80,7 +79,6 @@ impl IndexedSource for LaneZip { type Item = (A::Item, B::Item); #[inline] fn len(&self) -> usize { - debug_assert_eq!(self.0.len(), self.1.len()); self.0.len() } #[inline] @@ -89,3 +87,14 @@ impl IndexedSource for LaneZip { unsafe { (self.0.get_unchecked(i), self.1.get_unchecked(i)) } } } + +#[cfg(test)] +mod tests { + use super::LaneZip; + + #[test] + #[should_panic(expected = "LaneZip operands must have the same length")] + fn rejects_mismatched_lengths() { + _ = LaneZip::new(&[1_u8][..], &[2_u8, 3][..]); + } +}