From 29f8890fa9150f4077c8a15bd60365f0c5c98a3b Mon Sep 17 00:00:00 2001 From: "Steinar H. Gunderson" Date: Wed, 4 Mar 2020 19:53:49 +0100 Subject: [PATCH] Fix MJPEG white balance information when VA-API is in use. The JPEG headers were cached (per resolution) and never invalidated, causing wrong/outdated information to be sent. I can't really remember why I wanted to cache these, but I suppose I had a reason, so I'm a bit reluctant to just kill the cache. Hopefully, the white balance won't change often enough, and these objects are so small, that we won't need invalidation; we can just let it grow until program exit. --- nageru/mjpeg_encoder.cpp | 12 ++++++------ nageru/mjpeg_encoder.h | 20 ++++++++++++++++++-- 2 files changed, 24 insertions(+), 8 deletions(-) diff --git a/nageru/mjpeg_encoder.cpp b/nageru/mjpeg_encoder.cpp index 19ffd58..4cc929b 100644 --- a/nageru/mjpeg_encoder.cpp +++ b/nageru/mjpeg_encoder.cpp @@ -660,11 +660,11 @@ vector MJPEGEncoder::get_jpeg_header(unsigned width, unsigned height, c return dest.dest; } -MJPEGEncoder::VAData MJPEGEncoder::get_va_data_for_resolution(unsigned width, unsigned height, const RGBTriplet &white_balance) +MJPEGEncoder::VAData MJPEGEncoder::get_va_data_for_parameters(unsigned width, unsigned height, const RGBTriplet &white_balance) { - pair key(width, height); - if (va_data_for_resolution.count(key)) { - return va_data_for_resolution[key]; + VAKey key{width, height, white_balance}; + if (va_data_for_parameters.count(key)) { + return va_data_for_parameters[key]; } // Use libjpeg to generate a header and set sane defaults for e.g. @@ -765,7 +765,7 @@ MJPEGEncoder::VAData MJPEGEncoder::get_va_data_for_resolution(unsigned width, un ret.q = q; ret.huff = huff; ret.parms = parms; - va_data_for_resolution[key] = ret; + va_data_for_parameters[key] = ret; return ret; } @@ -786,7 +786,7 @@ void MJPEGEncoder::encode_jpeg_va(QueuedFrame &&qf) release = ReleaseVAResources(this, resources); } - VAData va_data = get_va_data_for_resolution(width, height, qf.white_balance); + VAData va_data = get_va_data_for_parameters(width, height, qf.white_balance); va_data.pic_param.coded_buf = resources.data_buffer; VABufferID pic_param_buffer; diff --git a/nageru/mjpeg_encoder.h b/nageru/mjpeg_encoder.h index eff361e..87bf3b5 100644 --- a/nageru/mjpeg_encoder.h +++ b/nageru/mjpeg_encoder.h @@ -154,6 +154,22 @@ private: std::unique_ptr va_dpy; VAConfigID config_id; + struct VAKey { + unsigned width, height; + movit::RGBTriplet white_balance; + + bool operator< (const VAKey &other) const { + if (width != other.width) + return width < other.width; + if (height != other.height) + return height < other.height; + if (white_balance.r != other.white_balance.r) + return white_balance.r < other.white_balance.r; + if (white_balance.g != other.white_balance.g) + return white_balance.g < other.white_balance.g; + return white_balance.b < other.white_balance.b; + } + }; struct VAData { std::vector jpeg_header; VAEncPictureParameterBufferJPEG pic_param; @@ -161,8 +177,8 @@ private: VAHuffmanTableBufferJPEGBaseline huff; VAEncSliceParameterBufferJPEG parms; }; - std::map, VAData> va_data_for_resolution; - VAData get_va_data_for_resolution(unsigned width, unsigned height, const movit::RGBTriplet &white_balance); + std::map va_data_for_parameters; + VAData get_va_data_for_parameters(unsigned width, unsigned height, const movit::RGBTriplet &white_balance); std::list va_resources_freelist; std::mutex va_resources_mutex; -- 2.39.2