From 6cab1dcb098aa15e4d6d646584b32a8fd5bad473 Mon Sep 17 00:00:00 2001 From: Andreas Rheinhardt Date: Mon, 5 May 2025 18:40:28 +0200 Subject: [PATCH 05/11] avcodec/cbs,cbs_jpeg: Split ff_cbs_append_unit_data() It currently has two modes: One where the caller supplies an AVBufferRef* from which a new reference is created and one where it only provides a naked buffer ownership of which passed to the unit (by wrapping it into an AVBuffer). Split these two modes into two separate functions. (One of which is only used by cbs_jpeg which has been adapted to use it.) Signed-off-by: Andreas Rheinhardt --- libavcodec/cbs.c | 34 +++++++++++++++++++--------------- libavcodec/cbs.h | 21 +++++++++++++++------ libavcodec/cbs_jpeg.c | 17 ++++++++--------- 3 files changed, 42 insertions(+), 30 deletions(-) diff --git a/libavcodec/cbs.c b/libavcodec/cbs.c index 6b2ebe597d..39411d4cf5 100644 --- a/libavcodec/cbs.c +++ b/libavcodec/cbs.c @@ -828,25 +828,14 @@ int CBS_FUNC(insert_unit_content)(CodedBitstreamFragment *frag, static int cbs_insert_unit_data(CodedBitstreamFragment *frag, CodedBitstreamUnitType type, uint8_t *data, size_t data_size, - AVBufferRef *data_buf, + AVBufferRef *data_ref, int position) { CodedBitstreamUnit *unit; - AVBufferRef *data_ref; int err; av_assert0(position >= 0 && position <= frag->nb_units); - if (data_buf) - data_ref = av_buffer_ref(data_buf); - else - data_ref = av_buffer_create(data, data_size, NULL, NULL, 0); - if (!data_ref) { - if (!data_buf) - av_free(data); - return AVERROR(ENOMEM); - } - err = cbs_insert_unit(frag, position); if (err < 0) { av_buffer_unref(&data_ref); @@ -863,10 +852,25 @@ static int cbs_insert_unit_data(CodedBitstreamFragment *frag, } int CBS_FUNC(append_unit_data)(CodedBitstreamFragment *frag, - CodedBitstreamUnitType type, - uint8_t *data, size_t data_size, - AVBufferRef *data_buf) + CodedBitstreamUnitType type, + uint8_t *data, size_t data_size, + const AVBufferRef *data_buf) +{ + AVBufferRef *data_ref = av_buffer_ref(data_buf); + if (!data_ref) + return AVERROR(ENOMEM); + + return cbs_insert_unit_data(frag, type, + data, data_size, data_ref, + frag->nb_units); +} + +int CBS_FUNC(append_unit_data_move_ref)(CodedBitstreamFragment *frag, + CodedBitstreamUnitType type, + uint8_t *data, size_t data_size, + AVBufferRef *data_buf) { + av_assert1(data_buf); return cbs_insert_unit_data(frag, type, data, data_size, data_buf, frag->nb_units); diff --git a/libavcodec/cbs.h b/libavcodec/cbs.h index 67f2ec9e50..958b00cc05 100644 --- a/libavcodec/cbs.h +++ b/libavcodec/cbs.h @@ -460,14 +460,23 @@ int CBS_FUNC(insert_unit_content)(CodedBitstreamFragment *frag, /** * Add a new unit to a fragment with the given data bitstream. * - * If data_buf is not supplied then data must have been allocated with - * av_malloc() and will on success become owned by the unit after this - * call or freed on error. + * data must be owned by data_buf (which must be provided); + * ownership of the reference stays with the caller. */ int CBS_FUNC(append_unit_data)(CodedBitstreamFragment *frag, - CodedBitstreamUnitType type, - uint8_t *data, size_t data_size, - AVBufferRef *data_buf); + CodedBitstreamUnitType type, + uint8_t *data, size_t data_size, + const AVBufferRef *data_buf); +/** + * Add a new unit to a fragment with the given data bitstream. + * + * data_buf must be supplied and ownership of it will be transferred + * to the new unit; in case of error, it is unreferenced. + */ +int CBS_FUNC(append_unit_data_move_ref)(CodedBitstreamFragment *frag, + CodedBitstreamUnitType type, + uint8_t *data, size_t data_size, + AVBufferRef *data_buf); /** * Delete a unit from a fragment and free all memory it uses. diff --git a/libavcodec/cbs_jpeg.c b/libavcodec/cbs_jpeg.c index 406147c082..281606e7af 100644 --- a/libavcodec/cbs_jpeg.c +++ b/libavcodec/cbs_jpeg.c @@ -87,7 +87,6 @@ static int cbs_jpeg_split_fragment(CodedBitstreamContext *ctx, CodedBitstreamFragment *frag, int header) { - AVBufferRef *data_ref; uint8_t *data; size_t data_size; int start, end, marker, next_start, next_marker; @@ -180,11 +179,11 @@ static int cbs_jpeg_split_fragment(CodedBitstreamContext *ctx, if (length > end - start) return AVERROR_INVALIDDATA; - data_ref = NULL; - data = av_malloc(end - start + - AV_INPUT_BUFFER_PADDING_SIZE); - if (!data) + AVBufferRef *data_ref = av_buffer_alloc(end - start + + AV_INPUT_BUFFER_PADDING_SIZE); + if (!data_ref) return AVERROR(ENOMEM); + data = data_ref->data; memcpy(data, frag->data + start, length); for (i = start + length, j = length; i < end; i++, j++) { @@ -200,14 +199,14 @@ static int cbs_jpeg_split_fragment(CodedBitstreamContext *ctx, memset(data + data_size, 0, AV_INPUT_BUFFER_PADDING_SIZE); + err = ff_cbs_append_unit_data_move_ref(frag, marker, data, + data_size, data_ref); } else { data = frag->data + start; data_size = end - start; - data_ref = frag->data_ref; + err = ff_cbs_append_unit_data(frag, marker, + data, data_size, frag->data_ref); } - - err = ff_cbs_append_unit_data(frag, marker, - data, data_size, data_ref); if (err < 0) return err; -- 2.45.2