I found these while reviewing #247 and #250 against libopus v1.6.1. All three are already present on main, and I could not find corpus coverage for any of them.
- PLC does not update
previousMode/previousRedundancy (decodePLCToFloat32). libopus sets prev_mode = mode and prev_redundancy = 0 at the end of every opus_decode_frame, including PLC (src/opus_decoder.c:702-703). After a packet ending in SILK -> CELT redundancy, a loss, and then a SILK or Hybrid packet, libopus takes the transition path and we do not.
- SILK -> CELT redundancy is decoded before the Hybrid -> SILK fade-out (
decodeSilkFrames). libopus decodes the silence frame first (:622-625), then resets CELT and decodes redundancy (from :636). Our fade-out therefore uses a freshly reset CELT state.
- CELT -> SILK redundancy is applied without the
prev_mode != MODE_SILK_ONLY || prev_redundancy guard (:650) in both applySilkTransitions and the Hybrid path.
I think each fix needs a libopus-generated sequence to lock down the behavior.
I found these while reviewing #247 and #250 against libopus v1.6.1. All three are already present on
main, and I could not find corpus coverage for any of them.previousMode/previousRedundancy(decodePLCToFloat32). libopus setsprev_mode = modeandprev_redundancy = 0at the end of everyopus_decode_frame, including PLC (src/opus_decoder.c:702-703). After a packet ending in SILK -> CELT redundancy, a loss, and then a SILK or Hybrid packet, libopus takes the transition path and we do not.decodeSilkFrames). libopus decodes the silence frame first (:622-625), then resets CELT and decodes redundancy (from:636). Our fade-out therefore uses a freshly reset CELT state.prev_mode != MODE_SILK_ONLY || prev_redundancyguard (:650) in bothapplySilkTransitionsand the Hybrid path.I think each fix needs a libopus-generated sequence to lock down the behavior.