Browse Source

Document measured call FPS loss and bounded audio synchronization queue

master
evgeny 4 days ago
parent
commit
78246e249e
  1. 20
      doc/call_video.txt
  2. 6
      doc/tasks.md
  3. 4
      src/call/call_video_transport.h

20
doc/call_video.txt

@ -187,7 +187,11 @@ KEY содержит config_length:4BE + AnnexB config + access unit. Ядро
границы envelope; содержимое NAL обязан проверять платформенный decoder.
frame_id и capture PTS возрастают на всём протяжении звонка, включая смену generation.
Новый формат требует нового generation и KEY. После пропуска кадра нужен KEY.
На TX один незавершённый кадр, на RX одна ограниченная сборка; deadline 2с.
На TX ограниченная FIFO: до 32 кадров, 500мс по PTS и 4MiB суммарно; на RX одна ограниченная сборка.
Deadline головы TX и сборки RX — 2с. Каждый TX кадр ждёт соответствующего audio_end_pts;
следующие P-кадры сохраняются в FIFO, а не теряются на обычной задержке аудиообработки.
При потере головы отбрасывается вся зависимая цепочка и запрашивается KEY. В сетевой долг
входят только готовые к отправке кадры FIFO; ожидание аудио само по себе не перегружает канал.
receive_ready резервирует возможность принять целый кадр до ACK первого фрагмента.
Callback копирует данные до возврата; платформенная очередь также должна быть ограничена.
Старые кадры другого generation сохраняются до соответствующей позиции аудиоряда.
@ -551,8 +555,10 @@ Android: принимаемое видео сначала занимает ве
навигации и временно скрытые системные кнопки. Видео по-прежнему использует весь экран.
TextureView и Surface сохраняются при показе кнопок; decoder освобождает старый Surface
до его release. Запоздалый detach предыдущего Surface не отключает новый.
Preview берётся из того же Camera2 YUV кадра (до 5 fps, ширина до поворота 192 px), без второй камеры.
Развёрнутое своё видео пока использует это же превью; приём сохраняет исходное качество и частоту кадров.
Preview получает прямой output той же Camera2 через общий StreamPreview/CameraPreviewView,
без Bitmap-конвертации и ограничения 5 fps. Surface удерживается до закрытия CameraCaptureSession/CameraDevice;
разворачивание/миниатюра меняют только геометрию TextureView. На SM подтверждено 29–30 fps.
Отказ preview output логируется и оставляет YUV-output передачи; encoder при attach/detach не перезапускается.
Desktop: первый RX кадр открывает отдельное изменяемое окно видео, без автоматического fullscreen.
Окно звонка с управлением и всеми настройками сохраняет свою геометрию и состояние настроек.
Видео сохраняет пропорции, своя миниатюра — в углу окна видео. F11/двойной щелчок переключают
@ -566,6 +572,14 @@ F11/Esc, закрытие/повторное открытие без hangup, loc
(/tmp/call-video-separate-preview.log). ChatGUI собран; Android assembleDebug и 81 unit-тест — PASS.
Автоматическое ожидание FAR и поворот экрана требуют проверки в следующем реальном звонке.
15.10.2026, диагностика низкого FPS desktop -> Samsung:
До исправления capture=30/s, encoded=20/s, paced=10/s; TX accepted=5/s, audio_busy=15/s,
audio_ahead=140–180ms. RX pulled/decoded/rendered=5/s, late=0: кадры терялись до отправки.
Вместо порога 33333мкс от прошлого кадра desktop использует сетку 30 fps с допуском 1/4 периода;
30 fps с дрожанием сохраняются, 60 fps ограничиваются до 30. FIFO TX сохраняет кадры во время ожидания аудио.
test_call проверяет семь последовательных KEY/P кадров за audio barrier, порядок после release и предел PTS.
Диагностика: /tmp/call-fps-desktop-live.log, /tmp/call-fps-sm-live.log; unit/core/Qt проверки прошли.
Подтверждённая причина фризов раз в 1–2с: коррекция capture timestamp меняла audio source_epoch,
а обе платформы сбрасывали video decoder и ждали KEY. Теперь source_epoch обновляет
аудиопривязку без потери video references, готовых кадров и последнего показанного PTS.

6
doc/tasks.md

@ -62,7 +62,11 @@
Android: Назад из видео открывает управление звонком; две миниатюры разворачиваются нажатием,
второе видео остаётся в углу. RX TextureView/Surface сохраняются при смене режима.
Кнопки учитывают системные панели (включая боковую навигацию) и вырез экрана.
Своё развёрнутое видео пока использует прежнее превью 192 px / 5 fps; RX без снижения качества.
Своё видео теперь идёт напрямую Camera2 -> TextureView через общий StreamPreview: SM 29–30 fps,
без прежней Bitmap-конвертации 192 px / 5 fps; Surface удерживается camera session до закрытия.
Низкий FPS desktop -> SM: capture=30, encoded=20, accepted=5, audio_busy=15, RX late=0.
Исправлены порог 33333мкс (сетка кадров с допуском) и ожидание аудио (FIFO до 32 кадров/500мс/4MiB).
Тесты: KEY/P за audio barrier, порядок и переполнение; Qt cadence/codec/clock; 81 Android unit — PASS.
Видео удерживает экран включённым без proximity-overlay; EARPIECE -> SPEAKER только после FAR,
UNKNOWN/NEAR ждут, ручной выбор/выключение видео/конец звонка отменяют ожидание. HEADSET сохраняется.
Фризы: обе платформы сохраняют decoder при коррекции audio epoch; production RX 90/90 кадров,

4
src/call/call_video_transport.h

@ -24,7 +24,9 @@ int call_video_configure(struct UTUN_INSTANCE *inst, uint64_t call_id, const str
const struct call_video_ops *ops, void *arg);
/* Копирует один полный кадр. 1 принят, 0 backpressure/ожидание KEY, -1 неверный формат/сессия.
* После 0 producer обязан запросить KEY: пропуск P-кадра разрывает цепочку references.
* Неполная отправка ограничена 2с; следующие кадры не увеличивают очередь. */
* FIFO ожидания аудио/сети: до 32 кадров, 500мс PTS и CALL_VIDEO_MAX_FRAME байт суммарно.
* Каждый кадр выходит только после соответствующего аудио; deadline головы 2с.
* При истечении deadline сбрасывается вся зависимая цепочка и запрашивается KEY. */
int call_video_send_frame(struct UTUN_INSTANCE *inst, const struct call_video_frame *frame);
void call_video_resume_receive(struct UTUN_INSTANCE *inst, uint64_t call_id);
/* Decoder потерял references. Запрос идемпотентный, отправляется не чаще раза в 500мс. */

Loading…
Cancel
Save