]> git.sesse.net Git - ffmpeg/blobdiff - libavcodec/cbs.c
avformat: Constify all muxer/demuxers
[ffmpeg] / libavcodec / cbs.c
index 7c1aa005c212f5c9d9ef69cb81cdf1f7bf5a5e26..bbfafb653092aeefbc881de8ba3e1c791fb3b923 100644 (file)
 #include "libavutil/avassert.h"
 #include "libavutil/buffer.h"
 #include "libavutil/common.h"
+#include "libavutil/opt.h"
 
 #include "cbs.h"
 #include "cbs_internal.h"
 
 
-static const CodedBitstreamType *cbs_type_table[] = {
+static const CodedBitstreamType *const cbs_type_table[] = {
 #if CONFIG_CBS_AV1
     &ff_cbs_type_av1,
 #endif
@@ -93,7 +94,7 @@ int ff_cbs_init(CodedBitstreamContext **ctx_ptr,
         return AVERROR(ENOMEM);
 
     ctx->log_ctx = log_ctx;
-    ctx->codec   = type;
+    ctx->codec   = type; /* Must be before any error */
 
     if (type->priv_data_size) {
         ctx->priv_data = av_mallocz(ctx->codec->priv_data_size);
@@ -101,6 +102,10 @@ int ff_cbs_init(CodedBitstreamContext **ctx_ptr,
             av_freep(&ctx);
             return AVERROR(ENOMEM);
         }
+        if (type->priv_class) {
+            *(const AVClass **)ctx->priv_data = type->priv_class;
+            av_opt_set_defaults(ctx->priv_data);
+        }
     }
 
     ctx->decompose_unit_types = NULL;
@@ -112,6 +117,12 @@ int ff_cbs_init(CodedBitstreamContext **ctx_ptr,
     return 0;
 }
 
+void ff_cbs_flush(CodedBitstreamContext *ctx)
+{
+    if (ctx->codec->flush)
+        ctx->codec->flush(ctx);
+}
+
 void ff_cbs_close(CodedBitstreamContext **ctx_ptr)
 {
     CodedBitstreamContext *ctx = *ctx_ptr;
@@ -119,10 +130,14 @@ void ff_cbs_close(CodedBitstreamContext **ctx_ptr)
     if (!ctx)
         return;
 
-    if (ctx->codec && ctx->codec->close)
+    if (ctx->codec->close)
         ctx->codec->close(ctx);
 
     av_freep(&ctx->write_buffer);
+
+    if (ctx->codec->priv_class && ctx->priv_data)
+        av_opt_free(ctx->priv_data);
+
     av_freep(&ctx->priv_data);
     av_freep(ctx_ptr);
 }
@@ -187,6 +202,12 @@ static int cbs_read_fragment_content(CodedBitstreamContext *ctx,
             av_log(ctx->log_ctx, AV_LOG_VERBOSE,
                    "Decomposition unimplemented for unit %d "
                    "(type %"PRIu32").\n", i, unit->type);
+        } else if (err == AVERROR(EAGAIN)) {
+            av_log(ctx->log_ctx, AV_LOG_VERBOSE,
+                   "Skipping decomposition of unit %d "
+                   "(type %"PRIu32").\n", i, unit->type);
+            av_buffer_unref(&unit->content_ref);
+            unit->content = NULL;
         } else if (err < 0) {
             av_log(ctx->log_ctx, AV_LOG_ERROR, "Failed to read unit %d "
                    "(type %"PRIu32").\n", i, unit->type);
@@ -217,66 +238,67 @@ static int cbs_fill_fragment_data(CodedBitstreamFragment *frag,
     return 0;
 }
 
-int ff_cbs_read_extradata(CodedBitstreamContext *ctx,
-                          CodedBitstreamFragment *frag,
-                          const AVCodecParameters *par)
-{
-    int err;
-
-    err = cbs_fill_fragment_data(frag, par->extradata,
-                                 par->extradata_size);
-    if (err < 0)
-        return err;
-
-    err = ctx->codec->split_fragment(ctx, frag, 1);
-    if (err < 0)
-        return err;
-
-    return cbs_read_fragment_content(ctx, frag);
-}
-
-int ff_cbs_read_packet(CodedBitstreamContext *ctx,
-                       CodedBitstreamFragment *frag,
-                       const AVPacket *pkt)
+static int cbs_read_data(CodedBitstreamContext *ctx,
+                         CodedBitstreamFragment *frag,
+                         AVBufferRef *buf,
+                         const uint8_t *data, size_t size,
+                         int header)
 {
     int err;
 
-    if (pkt->buf) {
-        frag->data_ref = av_buffer_ref(pkt->buf);
+    if (buf) {
+        frag->data_ref = av_buffer_ref(buf);
         if (!frag->data_ref)
             return AVERROR(ENOMEM);
 
-        frag->data      = pkt->data;
-        frag->data_size = pkt->size;
+        frag->data      = (uint8_t *)data;
+        frag->data_size = size;
 
     } else {
-        err = cbs_fill_fragment_data(frag, pkt->data, pkt->size);
+        err = cbs_fill_fragment_data(frag, data, size);
         if (err < 0)
             return err;
     }
 
-    err = ctx->codec->split_fragment(ctx, frag, 0);
+    err = ctx->codec->split_fragment(ctx, frag, header);
     if (err < 0)
         return err;
 
     return cbs_read_fragment_content(ctx, frag);
 }
 
-int ff_cbs_read(CodedBitstreamContext *ctx,
-                CodedBitstreamFragment *frag,
-                const uint8_t *data, size_t size)
+int ff_cbs_read_extradata(CodedBitstreamContext *ctx,
+                          CodedBitstreamFragment *frag,
+                          const AVCodecParameters *par)
 {
-    int err;
+    return cbs_read_data(ctx, frag, NULL,
+                         par->extradata,
+                         par->extradata_size, 1);
+}
 
-    err = cbs_fill_fragment_data(frag, data, size);
-    if (err < 0)
-        return err;
+int ff_cbs_read_extradata_from_codec(CodedBitstreamContext *ctx,
+                                     CodedBitstreamFragment *frag,
+                                     const AVCodecContext *avctx)
+{
+    return cbs_read_data(ctx, frag, NULL,
+                         avctx->extradata,
+                         avctx->extradata_size, 1);
+}
 
-    err = ctx->codec->split_fragment(ctx, frag, 0);
-    if (err < 0)
-        return err;
+int ff_cbs_read_packet(CodedBitstreamContext *ctx,
+                       CodedBitstreamFragment *frag,
+                       const AVPacket *pkt)
+{
+    return cbs_read_data(ctx, frag, pkt->buf,
+                         pkt->data, pkt->size, 0);
+}
 
-    return cbs_read_fragment_content(ctx, frag);
+int ff_cbs_read(CodedBitstreamContext *ctx,
+                CodedBitstreamFragment *frag,
+                const uint8_t *data, size_t size)
+{
+    return cbs_read_data(ctx, frag, NULL,
+                         data, size, 0);
 }
 
 static int cbs_write_unit_data(CodedBitstreamContext *ctx,
@@ -324,7 +346,7 @@ static int cbs_write_unit_data(CodedBitstreamContext *ctx,
 
     flush_put_bits(&pbc);
 
-    ret = ff_cbs_alloc_unit_data(unit, put_bits_count(&pbc) / 8);
+    ret = ff_cbs_alloc_unit_data(unit, put_bytes_output(&pbc));
     if (ret < 0)
         return ret;