[FFmpeg-devel] [PATCH] cbs_h265: Detect more reference combinations which would overflow the DPB
Mark Thompson
sw at jkqxz.net
Sat Feb 20 22:45:58 EET 2021
On 03/02/2021 21:34, Mark Thompson wrote:
> In total, the number of short term references (from the selected short
> term ref pic set), the number of long term references (combining both the
> used candidates from the SPS and those defined in the slice header) and
> the number of instances of the current picture (usually one, but can be
> two if current picture reference is enabled) must never exceed the size
> of the DPB. This is a generalisation of the condition associated with
> num_long_term_pics in 7.4.7.1.
>
> We use this to apply tighter bounds to the number of long term pictures
> referred to in the slice header, and also to detect the invalid case where
> the second reference to the current picture would not fit in the DPB (this
> case can't be detected earlier because an STRPS with 15 pictures can still
> be valid in the same stream when used with a different PPS which does not
> require two DPB slots for the current picture).
> ---
> Michael: does this fix your fuzz case for num_long_term_sps?
>
> Thanks,
>
> - Mark
>
>
> libavcodec/cbs_h265_syntax_template.c | 23 +++++++++++++++++++++--
> 1 file changed, 21 insertions(+), 2 deletions(-)
>
> diff --git a/libavcodec/cbs_h265_syntax_template.c b/libavcodec/cbs_h265_syntax_template.c
> index d09934cfeb..5d216aad36 100644
> --- a/libavcodec/cbs_h265_syntax_template.c
> +++ b/libavcodec/cbs_h265_syntax_template.c
> @@ -1369,6 +1369,7 @@ static int FUNC(slice_segment_header)(CodedBitstreamContext *ctx, RWContext *rw,
> if (current->nal_unit_header.nal_unit_type != HEVC_NAL_IDR_W_RADL &&
> current->nal_unit_header.nal_unit_type != HEVC_NAL_IDR_N_LP) {
> const H265RawSTRefPicSet *rps;
> + int dpb_slots_remaining;
>
> ub(sps->log2_max_pic_order_cnt_lsb_minus4 + 4, slice_pic_order_cnt_lsb);
>
> @@ -1387,6 +1388,22 @@ static int FUNC(slice_segment_header)(CodedBitstreamContext *ctx, RWContext *rw,
> rps = &sps->st_ref_pic_set[0];
> }
>
> + dpb_slots_remaining = HEVC_MAX_DPB_SIZE - 1 -
> + rps->num_negative_pics - rps->num_positive_pics;
> + if (pps->pps_curr_pic_ref_enabled_flag &&
> + (sps->sample_adaptive_offset_enabled_flag ||
> + !pps->pps_deblocking_filter_disabled_flag ||
> + pps->deblocking_filter_override_enabled_flag)) {
> + // This picture will occupy two DPB slots.
> + if (dpb_slots_remaining == 0) {
> + av_log(ctx->log_ctx, AV_LOG_ERROR, "Invalid stream: "
> + "short-term ref pic set contains too many pictures "
> + "to use with current picture reference enabled.\n");
> + return AVERROR_INVALIDDATA;
> + }
> + --dpb_slots_remaining;
> + }
> +
> num_pic_total_curr = 0;
> for (i = 0; i < rps->num_negative_pics; i++)
> if (rps->used_by_curr_pic_s0_flag[i])
> @@ -1399,13 +1416,15 @@ static int FUNC(slice_segment_header)(CodedBitstreamContext *ctx, RWContext *rw,
> unsigned int idx_size;
>
> if (sps->num_long_term_ref_pics_sps > 0) {
> - ue(num_long_term_sps, 0, sps->num_long_term_ref_pics_sps);
> + ue(num_long_term_sps, 0, FFMIN(sps->num_long_term_ref_pics_sps,
> + dpb_slots_remaining));
> idx_size = av_log2(sps->num_long_term_ref_pics_sps - 1) + 1;
> + dpb_slots_remaining -= current->num_long_term_sps;
> } else {
> infer(num_long_term_sps, 0);
> idx_size = 0;
> }
> - ue(num_long_term_pics, 0, HEVC_MAX_REFS - current->num_long_term_sps);
> + ue(num_long_term_pics, 0, dpb_slots_remaining);
>
> for (i = 0; i < current->num_long_term_sps +
> current->num_long_term_pics; i++) {
Ping.
- Mark
More information about the ffmpeg-devel
mailing list