iter9 Phase 8 close: α-7 inert as predicted; wire-byte search exhausted
α-7 (monotonic timestamp counter) changed wire bytes but H.264 output unchanged (71ac099b...). Confirms Phase 5 CRIT-1 prediction: VP9/MPEG-2 PASS via libva with the same v4l2_timeval_to_ns(&ref->timestamp) pattern; therefore timestamp magnitude was never load-bearing. 5-codec regression sweep: all 4 non-H.264 anchors hold. Zero regression. Cumulative state after iter8+iter9: - 6 hypotheses eliminated (libva-readback, slot-binding, stale-residue, constraint_set_flags, POC sentinel, reference_ts magnitude) - libva-vs-kdirect H.264 wire-byte diff is now empirically zero - α-2 + α-7 shipped as wire-payload hygiene cleanups (zero behavior change but cleaner semantics) iter10 candidate ranking: 1. α-8 OUTPUT bitstream byte dump (compare in-memory slice bytes) 2. α-9 untraced control diff (device-wide controls beyond DECODE_MODE + START_CODE) 3. Kernel-side investigation (rkvdec source dive for 16x32 partial- decode signature) 4. Pivot to Bug 5 (HEVC) or Bug 6 (VP8) Two more iterations of diminishing returns suggest either deeper empirical work (OUTPUT-byte dump or kernel investigation) or pivot to a different bug. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -0,0 +1,112 @@
|
||||
# Iteration 9 — Phase 8 (close)
|
||||
|
||||
Closes 2026-05-13. iter9 = Bug 4 — α-7 timestamp scheme test → confirmed inert. PARTIAL close. Wire-byte search space now exhausted.
|
||||
|
||||
## Summary
|
||||
|
||||
| Metric | Value |
|
||||
|---|---|
|
||||
| Iteration target | Bug 4 — α-7 monotonic timestamp counter |
|
||||
| Fork tip start (iter8 close) | `0226684` |
|
||||
| Fork tip end (iter9 close) | `e0be4e6` (1 fork commit: timestamp counter scheme) |
|
||||
| LOC delta | +23 / -1 across src/context.h, src/context.c, src/picture.c |
|
||||
| Phase 1 criteria | 5/6 PASS (C1 PARTIAL — H.264 hash unchanged) |
|
||||
| Reviews | 1 (Phase 5 CRIT-1 correctly predicted α-7 inert) |
|
||||
| Cumulative hypothesis eliminations | 6 (iter8's 5 + α-7 timestamp) |
|
||||
|
||||
## Results
|
||||
|
||||
| Codec | Anchor | iter9 α-7 | Verdict |
|
||||
|---|---|---|---|
|
||||
| H.264 | `1e7a0bc9…` (kdirect target) | `71ac099b…` (unchanged broken) | **FAIL** (Bug 4 unfixed) |
|
||||
| VP9 | `4f1565e8…` | `4f1565e8…` | PASS unchanged |
|
||||
| MPEG-2 | `19eefbf4…` | `19eefbf4…` | PASS unchanged |
|
||||
| HEVC | `06b2c5a0…` | `06b2c5a0…` | unchanged (Bug 5 deferred) |
|
||||
| VP8 | `bcc57ed5…` | `bcc57ed5…` | unchanged (Bug 6 deferred) |
|
||||
|
||||
α-7 changed the wire-level timestamp values (libva now sends small µs counter values matching kdirect's pattern) but H.264 output remains identical to pre-α-7 broken state. **Timestamp magnitude is not load-bearing.**
|
||||
|
||||
Phase 5 reviewer's CRIT-1 was correct: VP9 (vp9.c:624) and MPEG-2 (mpeg2.c:150,156) use the same `v4l2_timeval_to_ns(&ref->timestamp)` pattern as H.264 and both decode correctly with gettimeofday-derived giant ns. If timestamp magnitude were load-bearing, those would also fail.
|
||||
|
||||
## Wire-byte search space — now exhausted
|
||||
|
||||
After iter8 + iter9, all observable libva-vs-kdirect wire diffs in H.264 control submission have been tested:
|
||||
|
||||
| Field | libva | kdirect | Tested | Verdict |
|
||||
|---|---|---|---|---|
|
||||
| SPS constraint_set_flags | 0x00 | 0x02 | α-1 review | inert (rkvdec source) |
|
||||
| SPS all other bytes | identical | identical | Phase 3 + Phase 0 iter9 | match |
|
||||
| PPS all bytes | identical | identical | Phase 0 iter9 | match |
|
||||
| SCALING_MATRIX | flat 16/16 | flat 16/16 | Phase 3 | match |
|
||||
| DPB[].POC (after α-2) | sentinel-encoded | sentinel-encoded | α-2 implemented | match wire, no behavior change |
|
||||
| DPB[].flags | 0x03 VALID|ACTIVE | 0x03 | Phase 0 iter9 | match |
|
||||
| DPB[].pic_num/frame_num/fields | match | match | Phase 0 iter9 | match |
|
||||
| DPB[].reference_ts magnitude | small µs | small µs (post-α-7) | α-7 implemented | match wire, no behavior change |
|
||||
| DECODE_PARAMS post-DPB (bytes 512-559) | identical | identical | Phase 0 iter9 deep-strace | match |
|
||||
| OUTPUT QBUF bytesused | slices_size | slices_size | Same v4l2_queue_buffer logic | match (untested empirically) |
|
||||
| Slice data bytes in OUTPUT buffer | start_code + raw NAL | start_code + raw NAL | Same backend logic | match (untested empirically) |
|
||||
|
||||
The only NOT-yet-empirically-verified surface is:
|
||||
- **Actual byte content of the OUTPUT buffer**. Both backends construct slice data the same way (start_code prefix + NAL data), but no byte-for-byte dump of the in-memory OUTPUT buffer has been done.
|
||||
- **OUTPUT QBUF m.planes[0].bytesused**. The strace abbreviated this; both backends *should* be setting it from their slice-count tracking variable. Worth confirming via VIDIOC_QBUF dump.
|
||||
|
||||
## Iter9 hypothesis ranking, final state
|
||||
|
||||
| Hypothesis | Status after iter8+iter9 |
|
||||
|---|---|
|
||||
| libva-readback bug | ❌ Eliminated (γ dump) |
|
||||
| Slot-binding wrong | ❌ Eliminated (γ dump) |
|
||||
| Stale residue | ❌ Eliminated (IMP-1 memset) |
|
||||
| SPS constraint_set_flags | ❌ Eliminated (Phase 5b CRIT-1, rkvdec source) |
|
||||
| POC sentinel | ❌ Eliminated (α-2 wire change, no behavior) |
|
||||
| reference_ts magnitude | ❌ Eliminated (α-7 wire change, no behavior; VP9/MPEG-2 use same pattern and PASS) |
|
||||
|
||||
**Bug 4 search space exhaustion on the libva wire-byte side.**
|
||||
|
||||
## Lessons from iter9
|
||||
|
||||
### Lesson 1: Reviewer's empirical CRIT-1 caught α-7 before build
|
||||
|
||||
Phase 5 CRIT-1 correctly identified that VP9/MPEG-2 use the same timestamp path and PASS — making α-7 a low-probability fix. The empirical test (α-7 build + verify) confirmed the prediction. Saved no time vs the prediction itself, but added an empirical confirmation to the elimination.
|
||||
|
||||
### Lesson 2: Two consecutive α-attempts (α-2 POC, α-7 timestamp) changed wire bytes without changing behavior
|
||||
|
||||
Reinforcement of `feedback_wire_vs_behavior.md`: wire-equivalence is necessary but not sufficient. The pattern of "change wire to match kdirect, observe no decoder output change" is now repeated twice in this iteration. Suggests Bug 4 is in something NOT carried by the libva→kernel ioctl payload — likely either the OUTPUT bitstream bytes themselves, or some kernel-internal state that depends on neither.
|
||||
|
||||
### Lesson 3: Wire-byte hypothesis space has finite size
|
||||
|
||||
After 6 eliminations across iter8+iter9, the libva-vs-kdirect H.264 ioctl-payload-byte diff is empirically zero (modulo `constraint_set_flags` which is inert). Any iter10+ Bug 4 fix must either:
|
||||
- (a) Find a diff in OUTPUT bitstream bytes (in-memory dump comparison).
|
||||
- (b) Find a diff in some untraced control (device-init controls, REQBUFS counts, S_FMT details).
|
||||
- (c) Pivot to kernel-side investigation (rkvdec source dive for the 16×32 partial-decode signature).
|
||||
|
||||
## iter9 → iter10 handoff
|
||||
|
||||
Substrate at close:
|
||||
- Fork tip `e0be4e6` on noether + fresnel + gitea.
|
||||
- Backend SHA `a17e3c39671d4f430a7c6f2be04ec128545aa44737a5f4df2b4558b158019a43` on fresnel.
|
||||
- Kernel `linux-fresnel-fourier 7.0-1` unchanged.
|
||||
- All diagnostic instrumentation (γ + IMP-1 memset gate) preserved.
|
||||
- α-2 POC strip removal + α-7 timestamp counter both shipped as hygiene improvements (zero behavior change but cleaner wire-payload semantics).
|
||||
|
||||
iter10 candidate ranking:
|
||||
1. **α-8 OUTPUT bitstream byte dump** — add γ-style dump of `source_data` immediately before OUTPUT QBUF. Compare against kdirect's bytes (kdirect can also be instrumented via LD_PRELOAD or ffmpeg patch). ~30 LOC + analysis time.
|
||||
2. **α-9 untraced control diff** — VIDIOC_S_EXT_CTRLS with device-wide ctrl_class (not request-attached) controls. Currently only DECODE_MODE + START_CODE + HEVC versions are set at init. Check what kdirect's S_EXT_CTRLS does that we don't.
|
||||
3. **kernel-side** — read rkvdec assemble_hw_pps + run_hw fully. Look for a code path that produces a 16×32-byte partial write with luma-neutral default values.
|
||||
4. **Pivot to a different bug** — Bug 5 (HEVC) or Bug 6 (VP8 partial). Bug 4's diminishing-returns curve suggests it may be better to defer until kernel knowledge ramps up.
|
||||
|
||||
Campaign scoreboard (unchanged):
|
||||
|
||||
```
|
||||
H.264 | rkvdec | PARTIAL | Bug 4 narrowed via 6 eliminations
|
||||
HEVC | rkvdec | DEGRADED | Bug 5 deferred
|
||||
VP9 | rkvdec | PASS direct | iter5b-β
|
||||
MPEG-2 | hantro | PASS (env) | iter1
|
||||
VP8 | hantro | PARTIAL (env) | Bug 6 deferred
|
||||
```
|
||||
|
||||
iter8 + iter9 net contribution: significant Bug 4 narrowing (6 hypotheses eliminated, wire-byte search exhausted), plus diagnostic instrumentation infrastructure (γ + memset gate) for any future libva-side investigation. Zero codec fixes shipped.
|
||||
|
||||
## Phase 8 commit
|
||||
|
||||
iter9 PARTIAL close. Fork at `e0be4e6`. Backend SHA `a17e3c39…`. 5/6 criteria PASS. iter10 needs a fundamentally different approach to make progress on Bug 4 — OUTPUT bitstream byte comparison OR kernel-side investigation OR pivot to a different bug.
|
||||
Reference in New Issue
Block a user