fix(video): stop RTSP tiles hanging on "Connecting…" forever (#77) - #78
Conversation
- live sessions passed "stimeout", which FFmpeg 7 ignores, so a camera that accepted TCP but never answered blocked avformat_open_input indefinitely - set the real "timeout" key and wire an interrupt callback with per-call budgets (15s open/probe, 10s read, 1s close) plus abort on Dispose - reconnect watchdog now also abandons attempts stuck in Connecting (45s) and uses a monotonic clock
PR Summary by QodoPrevent RTSP live-view tiles from hanging while connecting
AI Description
Diagram
High-Level Assessment
Files changed (2)
|
Code Review by Qodo
1. Wedged connections leave decoder threads alive
|
| if (_connecting && idle > ConnectTimeoutMs) | ||
| { | ||
| failed.TrySetResult("Connect timed out (no stream after 45s)"); | ||
| return; |
There was a problem hiding this comment.
1. Wedged connections leave decoder threads alive 🐞 Bug ☼ Reliability
The new Connecting watchdog sends a timed-out attempt through inner.DisposeAsync(), which returns after a two-second join even if the decoder thread is still blocked in native setup. When that setup cannot be interrupted, the wrapper starts another attempt while the old thread still holds native resources and is no longer tracked for disposal.
Agent Prompt
## Issue description
The Connecting watchdog retries after disposing an inner session, but disposal can return while its native decoder thread remains blocked. Repeated retries can leave untracked threads and native resources alive.
## Fix Focus Areas
- src/OpenIPC.Viewer.Video/Pipeline/AutoReconnectingVideoSession.cs[259-262]
- src/OpenIPC.Viewer.Video/Pipeline/AutoReconnectingVideoSession.cs[198-204]
- src/OpenIPC.Viewer.Video/Pipeline/FfmpegVideoSession.cs[167-184]
## Recommended Fix
Do not treat a timed-out inner session as fully disposed when its decoder thread has not exited. Retain and track unfinished sessions for eventual cleanup, and bound or defer retries so an uninterruptible setup cannot accumulate decoder threads.
ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools
| ArmIoDeadline(ReadBudgetMs); | ||
| ret = ffmpeg.av_read_frame(fmtCtx, packet); | ||
| if (ret < 0) |
There was a problem hiding this comment.
2. Read timeouts lose their failure reason 🐞 Bug ◔ Observability
Run arms a deadline before av_read_frame, but its negative-result branch logs the returned error and exits without checking whether that deadline expired or setting LastError. If the read is interrupted by the new deadline before the frame watchdog signals failure, the wrapper retries with a null error, so the tile and reconnect log omit the timeout cause.
Agent Prompt
## Issue description
An interrupted `av_read_frame` exits as an ordinary idle transition without recording that the new read deadline expired.
## Fix Focus Areas
- src/OpenIPC.Viewer.Video/Pipeline/FfmpegVideoSession.cs[308-320]
- src/OpenIPC.Viewer.Video/Pipeline/FfmpegVideoSession.cs[416-432]
## Recommended Fix
On a negative read result, distinguish cancellation and EOF from an expired read deadline. Report an expired deadline as a timeout through the session's failure path so `LastError` reaches the reconnect wrapper and UI.
ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools
RTSP cameras get stuck on "Connecting..." after 20–24 hours and require application restart #77
Summary
Related
Type
Checklist
TreatWarningsAsErrors=true).dotnet test); new Core logic has unit tests.AppreferencesCoreonly (Infrastructure / Video / Devices wired via DI in a head).Platforms tested
Screenshots / notes