[read] Fix miscalculation in ComputedArray The 'get' method would always return a result if an array had zero-length items (which is a degenerate case, but possible in irl data.)
diff --git a/read-fonts/src/array.rs b/read-fonts/src/array.rs index 1cf4f5f..973edc9 100644 --- a/read-fonts/src/array.rs +++ b/read-fonts/src/array.rs
@@ -85,6 +85,11 @@ } pub fn get(&self, idx: usize) -> Result<T, ReadError> { + // if our items are zero-length (itself a degenerate case) we want + // to always return oob here since otherwise we will succeed for all indices + if self.item_len == 0 { + return Err(ReadError::OutOfBounds); + } let item_start = idx .checked_mul(self.item_len) .ok_or(ReadError::OutOfBounds)?; @@ -161,3 +166,20 @@ data.read_array(0..len) } } + +#[cfg(test)] +mod tests { + use crate::tables::variations::VariationRegion; + + use super::*; + + #[test] + fn zero_len_get() { + let non_empty_data = FontData::new(&[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]); + let array = ComputedArray::<VariationRegion>::new(non_empty_data, 0).unwrap(); + + assert!(matches!(array.get(usize::MAX), Err(ReadError::OutOfBounds))); + assert!(matches!(array.get(1), Err(ReadError::OutOfBounds))); + assert!(matches!(array.get(0), Err(ReadError::OutOfBounds))); + } +}