mirror of
https://github.com/storytold/filmcraft.git
synced 2026-10-14 19:26:59 -04:00
Merge pull request #14 from storytold/pr/never-crash-av1
av1: never crash (no expect, deny the panicking lints)
This commit is contained in:
4 files changed
+33
-12
No files matched your search
@@ -237,12 +237,16 @@ fn filter_rows<const W: usize>(buf: &[i32; PAD_STRIDE * PAD_STRIDE], taps: &[(is
|
||||
}
|
||||
for i in 0..h {
|
||||
let ci = ((i + 2) * PAD_STRIDE + 2) as isize;
|
||||
let x: [i16; W] = b16[ci as usize..ci as usize + W].try_into().expect("centre row");
|
||||
let Some(&x) = b16.get(ci as usize..).and_then(|r| r.first_chunk::<W>()) else {
|
||||
return;
|
||||
};
|
||||
let (mut sum, mut max, mut min) = ([0i16; W], x, x);
|
||||
for &(off, weight, thr, adj) in taps {
|
||||
let (weight, thr) = (weight as i16, thr as i16);
|
||||
let start = (ci + off) as usize;
|
||||
let p: &[i16; W] = b16[start..start + W].try_into().expect("tap row");
|
||||
let Some(p) = b16.get(start..).and_then(|r| r.first_chunk::<W>()) else {
|
||||
return;
|
||||
};
|
||||
for j in 0..W {
|
||||
// constrain(): .max / .min instead of clamp (whose bound check panics), and
|
||||
// the sign applied branch-free, so the loop vectorises.
|
||||
|
||||
@@ -72,10 +72,12 @@ impl<T: Clone> Slot<T> {
|
||||
|
||||
fn wait(&self) -> Result<T> {
|
||||
let mut g = self.value.lock().unwrap_or_else(|e| e.into_inner());
|
||||
while g.is_none() {
|
||||
loop {
|
||||
if let Some(v) = g.as_ref() {
|
||||
return v.clone();
|
||||
}
|
||||
g = self.cv.wait(g).unwrap_or_else(|e| e.into_inner());
|
||||
}
|
||||
g.as_ref().expect("slot value").clone()
|
||||
}
|
||||
}
|
||||
|
||||
@@ -308,7 +310,7 @@ impl Decoder {
|
||||
if !o.is_ready() && self.out.len() <= max_queue {
|
||||
break;
|
||||
}
|
||||
let o = self.out.pop_front().expect("front");
|
||||
let Some(o) = self.out.pop_front() else { break };
|
||||
pics.push(o.take()?);
|
||||
}
|
||||
parsed?;
|
||||
@@ -358,7 +360,9 @@ impl Decoder {
|
||||
match last {
|
||||
Some((lt, lsid)) if lt == t => {
|
||||
if sid >= lsid {
|
||||
*sel.last_mut().expect("picture") = o;
|
||||
if let Some(l) = sel.last_mut() {
|
||||
*l = o;
|
||||
}
|
||||
last = Some((t, sid));
|
||||
}
|
||||
}
|
||||
@@ -612,7 +616,7 @@ impl Decoder {
|
||||
self.in_flight.push_back(slot);
|
||||
// Bound the frames in flight (memory): wait for the oldest.
|
||||
while self.in_flight.len() > self.max_in_flight {
|
||||
let s = self.in_flight.pop_front().expect("in flight");
|
||||
let Some(s) = self.in_flight.pop_front() else { break };
|
||||
let _ = s.wait();
|
||||
}
|
||||
self.in_flight.retain(|s| !s.is_set());
|
||||
|
||||
+17
-5
@@ -180,7 +180,11 @@ impl TileDecoder<'_, '_> {
|
||||
}
|
||||
|
||||
fn ref_plane(&self, ref_idx: i32, plane: usize) -> &Plane {
|
||||
if ref_idx < 0 { &self.t.cur.planes[plane] } else { &self.fs.refs[ref_idx as usize].as_ref().expect("reference frame").buf.planes[plane] }
|
||||
// A missing reference (rejected earlier for valid streams) predicts from the current frame.
|
||||
match usize::try_from(ref_idx).ok().and_then(|i| self.fs.refs.get(i)).and_then(|r| r.as_ref()) {
|
||||
Some(r) => &r.buf.planes[plane],
|
||||
None => &self.t.cur.planes[plane],
|
||||
}
|
||||
}
|
||||
|
||||
/// Block inter prediction process (7.11.3.4) into `pred` (stride PRED_STRIDE); `tmp` holds
|
||||
@@ -672,12 +676,16 @@ fn hpass<const W: usize>(src: &[u16], hf: &[i16; 8], out: &mut [i32], half: i32,
|
||||
let mut acc = [half; W];
|
||||
for t in 0..8 {
|
||||
let f = hf[t] as i32;
|
||||
let p: &[u16; W] = src[t..t + W].try_into().expect("row");
|
||||
let Some(p) = src.get(t..).and_then(|s| s.first_chunk::<W>()) else {
|
||||
return;
|
||||
};
|
||||
for j in 0..W {
|
||||
acc[j] += f * p[j] as i32;
|
||||
}
|
||||
}
|
||||
let o: &mut [i32; W] = (&mut out[..W]).try_into().expect("row");
|
||||
let Some(o) = out.first_chunk_mut::<W>() else {
|
||||
return;
|
||||
};
|
||||
for j in 0..W {
|
||||
o[j] = acc[j] >> sh;
|
||||
}
|
||||
@@ -689,12 +697,16 @@ fn vpass<const W: usize>(rows: &[i32], vf: &[i16; 8], out: &mut [i32], half: i32
|
||||
let mut acc = [half; W];
|
||||
for t in 0..8 {
|
||||
let f = vf[t] as i32;
|
||||
let p: &[i32; W] = rows[t * W..t * W + W].try_into().expect("row");
|
||||
let Some(p) = rows.get(t * W..).and_then(|s| s.first_chunk::<W>()) else {
|
||||
return;
|
||||
};
|
||||
for j in 0..W {
|
||||
acc[j] += f * p[j];
|
||||
}
|
||||
}
|
||||
let o: &mut [i32; W] = (&mut out[..W]).try_into().expect("row");
|
||||
let Some(o) = out.first_chunk_mut::<W>() else {
|
||||
return;
|
||||
};
|
||||
for j in 0..W {
|
||||
o[j] = acc[j] >> sh;
|
||||
}
|
||||
|
||||
@@ -5,6 +5,7 @@
|
||||
|
||||
// Items used only by stages still being written (inter prediction, post filters).
|
||||
#![allow(dead_code)]
|
||||
#![cfg_attr(not(test), deny(clippy::unwrap_used, clippy::expect_used, clippy::panic, clippy::unimplemented, clippy::todo, clippy::unreachable))]
|
||||
|
||||
mod bits;
|
||||
mod cdef;
|
||||
|
||||
Reference in new issue
Block a user