Commit Graph
184 Commits
Author SHA1 Message Date
Isaac ConnorandClaude Opus 5 a5cd44df35 fix: map deprecated YUVJ pixel formats on the swscale output side fixes #5037
A monitor whose source signals full range (Dahua h264) decodes to
AV_PIX_FMT_YUVJ420P, and Monitor passes that format through to shared memory
unchanged. When zms scales such a frame for montage or console thumbnails,
SWScale::Convert mapped only the input format through fix_deprecated_pix_fmt()
and handed the still-deprecated YUVJ format to swscale as the destination, so
libswscale logged

  deprecated pixel format used, make sure you did set range correctly

for every context it built. Watch view at 100% scale never hit it because
Image::Scale returns early when the dimensions already match.

Map deprecated formats on both sides in SWScale::Convert (both the buffer and
the AVFrame overload), in Image::Assign(AVFrame*), in
Monitor::setupConvertContext and in the LocalCamera conversion context.

Mapping the destination YUVJ format to its non-J equivalent makes swscale
default that side to limited range, which would compress full-range output.
Replace zm_sws_set_input_range() with zm_sws_set_ranges(), which takes the
original pre-fix formats for both sides and sets srcRange/dstRange accordingly.

Image::Assign(AVFrame*) now compares the mapped source and destination formats,
so a YUVJ420P frame into a YUVJ420P image takes the av_image_copy fast path
instead of running through swscale.

Image::Scale built a fresh SWScale, and therefore a fresh sws context, on every
call. That is a full sws_init_context per scaled frame per stream, and it is
what turned the warning into a per-frame flood rather than a one-off. Reuse a
thread_local SWScale; sws_getCachedContext re-inits itself when the geometry
changes.

Tests: zm_swscale_range.cpp installs an av_log callback and asserts that
SWScale::Convert with a YUVJ destination and Image::Scale on a YUVJ420P image
emit no deprecated-format message, plus a luma check that the range handling
still survives the mapping.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01NDhTBPj9xEaT52pRmAufaP
2026-08-05 17:44:37 -04:00
Isaac ConnorandClaude Opus 4.8 74bf0637f0 fix: restore generic decoder fallback for ffmpeg cameras
Extract the "use whatever decoder ffmpeg provides" logic from
FFmpeg_Input into a shared open_fallback_decoder() and call it from
FfmpegCamera, which had lost the fallback: its generic path only ran
inside the preferred-codec loop, so an empty get_decoder_data() result
failed outright instead of trying the codec's default decoder.

The dec_codecs table stays a preference list; a codec present in the
ffmpeg build but absent from the table (e.g. libopenh264 for H264) now
decodes via the fallback instead of requiring a hard-coded entry.

Add tests/zm_ffmpeg_fallback.cpp covering the fallback with a codec not
in dec_codecs (mpeg2video), the optional codec_out argument, and the
no-decoder case.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-19 11:26:03 -04:00
Isaac ConnorandClaude Opus 4.8 346a4baa82 feat: preserve full-range colour when converting YUVJ frames via swscale
swscale assumes limited (MPEG, 16-235) input range by default. Mapping a
full-range JPEG format (YUVJ*) to its non-J equivalent for the conversion
therefore washes the colours out, because full-range luma/chroma gets
treated as limited.

Add pix_fmt_is_jpeg_range() and zm_sws_set_input_range(), which sets
srcRange=1 on the context when the original source format was full range.
Apply it at every conversion site that takes decoded frames: Image::Assign
and both SWScale::Convert overloads. Monitor::setupConvertContext already
did this inline with a hand-rolled switch and colorspace block; replace
that with the shared helpers to remove the duplication.

Add tests/zm_swscale_range.cpp: converting a Y=16 YUVJ420P image to RGB24
keeps luma ~16 (full range) rather than being crushed to ~0 (limited).

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-07-08 19:21:25 -04:00
Isaac Connor 7b21371083 Reapply "fix: replace ZM_COLOUR system with AVPixelFormat for format dispatch"
This reverts commit 60b6b37c60.
2026-05-03 12:24:43 -04:00
Isaac Connor 60b6b37c60 Revert "fix: replace ZM_COLOUR system with AVPixelFormat for format dispatch" 2026-05-02 18:26:48 -04:00
Isaac ConnorandClaude Opus 4.6 b416aa5293 fix: replace ZM_COLOUR_*/ZM_SUBPIX_ORDER_* with AVPixelFormat for format dispatch
ZM_COLOUR_GRAY8, ZM_COLOUR_YUV420P, and ZM_COLOUR_YUVJ420P were all
defined to 1, making format identification via colours ambiguous.
LocalCamera misidentified YUV420P as GRAY8, causing V4L2 MJPEG cameras
to decode to grayscale via expensive sws_scale conversion.

Replace the legacy ZM_COLOUR_*/ZM_SUBPIX_ORDER_* integer pair with
AVPixelFormat as the single source of truth for pixel format dispatch:

- Add src/zm_pixformat.h with central format helpers:
  zm_pixformat_from_colours, zm_colours_from_pixformat,
  zm_bytes_per_pixel, zm_db_colours_to_pixformat, zm_is_rgb32,
  zm_is_rgb24, zm_is_yuv420
- Add AVPixelFormat pixelFormat member + PixelFormat() accessor to Camera
- Add PixFormat() accessor to Image, delegate AVPixFormat methods
  to shared helpers
- Migrate all ~100 format dispatch comparisons in zm_image.cpp,
  zm_local_camera.cpp, zm_ffmpeg_camera.cpp, zm_remote_camera_rtsp.cpp,
  zm_libvlc_camera.cpp, zm_libvnc_camera.cpp, zm_monitor.cpp,
  zm_mpeg.cpp from colours/subpixelorder checks to imagePixFormat/
  AVPixelFormat checks
- Deprecate GetFFMPEGPixelFormat, delegate to zm_pixformat_from_colours
- Fix DeColourise bug: imagePixFormat was not updated to GRAY8
- Deprecate ZM_COLOUR_* and ZM_SUBPIX_ORDER_* constants in zm_rgb.h
- Add deprecation notice on Monitor.Colours web UI dropdown
- Add 13 Catch2 test cases (105 assertions) for format mapping helpers

refs #4735

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-18 11:42:06 -04:00
Isaac Connor 24e16796b7 Add mpeg4 as some older cameras that use are still funcitoning 2026-02-05 09:08:02 -05:00
Isaac ConnorandClaude Opus 4.5 0217cfbab0 fix: correct misleading debug messages in zm_ffmpeg.cpp
Debug messages incorrectly used "!=" when describing matching conditions.
Changed to "==" to accurately reflect that the codec name/id matched.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
2026-02-03 10:21:04 -05:00
Isaac Connor 2eebda8c64 Cleanup hw_pix_fmt and get_hw_format 2026-01-26 14:40:10 -05:00
Isaac Connor edb09314b5 The correct codec name is hevc not h265 2026-01-26 11:56:12 -05:00
Isaac Connor 0a0e29c99b Add get_fps_string to return a string of the fps content to be used later for Debug output. Convert dump_stream to build a string first before Debug 2026-01-26 11:47:21 -05:00
Isaac Connor d604dd69b6 Implement libjpeg_to_ffmpeg_qv 2026-01-26 11:46:47 -05:00
Isaac Connor fd7e2e7935 Fixup sw_pix_fmt options for hevc_vaapi and hevc_cuvid. Add h264_cuvid as an option. 2026-01-25 18:00:28 -05:00
Isaac Connor 30d0544613 Add better debugging of codec_tag in zm_dump_codec and zm_dump_codecpar 2025-10-27 15:04:19 -04:00
Isaac Connor a775d671d0 Move hwaccel decoders to bottom so that we don't get a bunch of failures logged trying to open hwaccel devices 2025-09-23 09:37:21 -04:00
Isaac Connor fbea774eda Fix h265->hevc codec 2025-09-18 14:24:48 -04:00
Isaac Connor 523ee9daf5 Finish change of codec_id to codec_name 2025-09-18 13:40:54 -04:00
Isaac Connor f9204e2d7a Add default options for codecs 2025-09-18 10:25:33 -04:00
Isaac Connor e05a9252ab Finish up zm_dump_stream(AVSstream) 2025-09-18 09:58:10 -04:00
Isaac Connor 24246106a9 Add software h265 codecs 2025-09-18 09:57:40 -04:00
Isaac Connor 40f2f5a27a Deal with ffmpeg 7.1 deprecations 2025-09-18 09:56:35 -04:00
Isaac Connor 5ff08270ec Fix name of h264_v4l2m2m codec. Was h264_v4lm2m. Reorder codecs based on hwaccel 2025-09-18 09:55:58 -04:00
Isaac Connor fa66d2baf4 Break up long line 2025-09-18 09:52:17 -04:00
Isaac Connor e1898c483b Adjust debug level add AVPixelFormat Image::AVPixFormat(AVPixelFormat new_pixelformat) 2025-09-18 09:42:03 -04:00
Isaac Connor c698b611ed Use HAVE_QUADRA instead of QUADRA. Add software h264 decoding 2025-09-18 09:39:54 -04:00
Isaac Connor 1063efbbfa Add handling of c++20 2025-09-18 09:36:54 -04:00
Isaac Connor 7709d9bb7b Move more stuff into zm_ffmpeg from zm_videostore 2025-09-18 09:36:18 -04:00
Isaac Connor e6c3d81f21 Disable avframes stuff 2025-09-18 09:34:09 -04:00
Isaac Connor 1edeaacd9d Add mjpeg decoders, remove Error logging from send_packet_receive_frame 2025-09-18 09:32:20 -04:00
Isaac Connor 4362770672 Remove deprecated avcodec_close 2025-09-18 09:31:13 -04:00
Isaac Connor 25a1c88686 Move codec_data from videostore to ffmpeg. Add dec_codecs and add a function to return relevant codec_data and setup hw_ctx. 2025-09-18 09:27:31 -04:00
Isaac Connor 55982ca423 Log qcompress as well 2025-09-18 09:22:52 -04:00
Steve Gilvarry 88227105b8 Removing avcodec_close, avcodec_free_context is replacement and been around since 2014, so should be no reason to version test. 2024-09-14 11:06:55 +10:00
Aaron Kling c4683d90a9 Format code using astyle google format
Commands used:
astyle --style=google --indent=spaces=2 --keep-one-line-blocks src/*.cpp
astyle --style=google --indent=spaces=2 --keep-one-line-blocks src/*.h
2024-03-26 13:43:58 -05:00
Aaron Kling e710127924 ffmpeg: Rework decode and encode flows
send_packet will fail with -EAGAIN if receive_frame hasn't consumed the
last packet. Similarly send_frame will fail if receive_packet has
pending frames.

This fixes problems with the raspberry pi hardware decoder. The change
likely affects many other codecs as well.
2024-02-19 17:17:24 -06:00
Isaac Connor 0295ef1252 Fix cppcheck complaint 2024-01-29 13:42:40 -05:00
Isaac Connor 3b71944ad1 Fix ffmpeg 5 channels depcrecation 2023-09-21 12:26:12 -04:00
Alejandro Criado-Pérez 543683aa4c Corrections on cpp and h files 2023-08-13 01:27:19 +02:00
Isaac Connor 228b00051b Only do the vsnprintf if the log is actually going to happen 2022-06-07 17:18:43 -04:00
Exuvo d1395dab9a Fix ffmpeg 5 const errors 2022-03-11 21:40:25 +01:00
Isaac Connor 34d7f192b4 Remove field that ffmpeg 5.0 doesn't have. 2022-02-01 07:23:12 -05:00
Isaac Connor 95a7c6c32f fix crash on 32bit pi due to use of %ld instead of %PRId64 2021-09-28 10:29:41 -04:00
Peter Keresztes Schmidt 2d71743372 FFmpeg: Remove code paths required only by 2.8 and older
With Xenial support dropped we require FFmpeg 3.2 and newer.
2021-06-05 20:40:12 +02:00
Peter Keresztes Schmidt 0625f6ca1c Misc: Cleanup some includes 2021-06-05 15:08:38 +02:00
Peter Keresztes Schmidt 3d34e6f177 Build: Promote libswresample to a required dependency
FFmpeg is an integral component of ZM. Promote the appropriate libraries to required dependencies.
This reduces the possible build configurations greatly and thus maintenance burden.
2021-06-05 14:27:42 +02:00
Peter Keresztes Schmidt 1a6904a297 Build: Promote libavutil to a required dependency
FFmpeg is an integral component of ZM. Promote the appropriate libraries to required dependencies.
This reduces the possible build configurations greatly and thus maintenance burden.
2021-06-05 14:21:41 +02:00
Peter Keresztes Schmidt 7d501a6585 Remove libavresample support
libavresample hasn't been maintained for a long time by FFmpeg since libswresample superseded it.
In 2018 it was officially deprecated [1].

Let's remove the support for it since there is no need to maintain this option further.

[1] https://patchwork.ffmpeg.org/project/ffmpeg/patch/20171225175335.18183-1-atomnuker@gmail.com/
2021-06-04 23:46:58 +02:00
Isaac Connor 9f685d6c2b Fixup style and warnings in zm_dump_codecpar 2021-06-04 17:32:45 -04:00
Isaac Connor d713770dea Include more fields in zm_dump_codecpar and zm_dump_codec 2021-06-04 15:01:48 -04:00
Isaac Connor d2941d6b87 Always print SAR and tel about unknown codec type 2021-05-31 16:00:17 -04:00