参考链接
- FFmpeg源代码简单分析:avcodec_close()_雷霄骅的博客-CSDN博客_avcodec_close
avcodec_close()
- 该函数用于关闭编码器
- avcodec_close()函数的声明位于libavcodec\avcodec.h,如下所示。
- 该函数只有一个参数,就是需要关闭的编码器的AVCodecContext。
/*** Close a given AVCodecContext and free all the data associated with it* (but not the AVCodecContext itself).** Calling this function on an AVCodecContext that hasn't been opened will free* the codec-specific data allocated in avcodec_alloc_context3() with a non-NULL* codec. Subsequent calls will do nothing.** @note Do not use this function. Use avcodec_free_context() to destroy a* codec context (either open or closed). Opening and closing a codec context* multiple times is not supported anymore -- use multiple codec contexts* instead.*/
int avcodec_close(AVCodecContext *avctx);
av_cold int avcodec_close(AVCodecContext *avctx)
{int i;if (!avctx)return 0;if (avcodec_is_open(avctx)) {AVCodecInternal *avci = avctx->internal;if (CONFIG_FRAME_THREAD_ENCODER &&avci->frame_thread_encoder && avctx->thread_count > 1) {ff_frame_thread_encoder_free(avctx);}if (HAVE_THREADS && avci->thread_ctx)ff_thread_free(avctx);if (avci->needs_close && ffcodec(avctx->codec)->close)ffcodec(avctx->codec)->close(avctx);avci->byte_buffer_size = 0;av_freep(&avci->byte_buffer);av_frame_free(&avci->buffer_frame);av_packet_free(&avci->buffer_pkt);if (avci->pkt_props) {while (av_fifo_can_read(avci->pkt_props)) {av_packet_unref(avci->last_pkt_props);av_fifo_read(avci->pkt_props, avci->last_pkt_props, 1);}av_fifo_freep2(&avci->pkt_props);}av_packet_free(&avci->last_pkt_props);av_packet_free(&avci->in_pkt);av_frame_free(&avci->in_frame);av_buffer_unref(&avci->pool);if (avctx->hwaccel && avctx->hwaccel->uninit)avctx->hwaccel->uninit(avctx);av_freep(&avci->hwaccel_priv_data);av_bsf_free(&avci->bsf);av_channel_layout_uninit(&avci->initial_ch_layout);av_freep(&avctx->internal);}for (i = 0; i < avctx->nb_coded_side_data; i++)av_freep(&avctx->coded_side_data[i].data);av_freep(&avctx->coded_side_data);avctx->nb_coded_side_data = 0;av_buffer_unref(&avctx->hw_frames_ctx);av_buffer_unref(&avctx->hw_device_ctx);if (avctx->priv_data && avctx->codec && avctx->codec->priv_class)av_opt_free(avctx->priv_data);av_opt_free(avctx);av_freep(&avctx->priv_data);if (av_codec_is_encoder(avctx->codec)) {av_freep(&avctx->extradata);avctx->extradata_size = 0;} else if (av_codec_is_decoder(avctx->codec))av_freep(&avctx->subtitle_header);avctx->codec = NULL;avctx->active_thread_type = 0;return 0;
}
- 从avcodec_close()的定义可以看出,该函数释放AVCodecContext中有关的变量
- 并且调用了AVCodec的close()关闭了解码器
AVCodec->close()
- AVCodec的close()是一个函数指针,指向了特定编码器的关闭函数。
- 在这里我们以libx264为例,看一下它对应的AVCodec的结构体的定义,如下所示。
#if X264_BUILD >= 153
const
#endif
FFCodec ff_libx264_encoder = {.p.name = "libx264",.p.long_name = NULL_IF_CONFIG_SMALL("libx264 H.264 / AVC / MPEG-4 AVC / MPEG-4 part 10"),.p.type = AVMEDIA_TYPE_VIDEO,.p.id = AV_CODEC_ID_H264,.p.capabilities = AV_CODEC_CAP_DR1 | AV_CODEC_CAP_DELAY |AV_CODEC_CAP_OTHER_THREADS |AV_CODEC_CAP_ENCODER_REORDERED_OPAQUE,.p.priv_class = &x264_class,.p.wrapper_name = "libx264",.priv_data_size = sizeof(X264Context),.init = X264_init,FF_CODEC_ENCODE_CB(X264_frame),.close = X264_close,.defaults = x264_defaults,
#if X264_BUILD < 153.init_static_data = X264_init_static,
#else.p.pix_fmts = pix_fmts_all,
#endif.caps_internal = FF_CODEC_CAP_INIT_CLEANUP | FF_CODEC_CAP_AUTO_THREADS
#if X264_BUILD >= 158| FF_CODEC_CAP_INIT_THREADSAFE
#endif,
};
#endif
- 从ff_libx264_encoder的定义可以看出:close()函数对应的是X264_close()函数。
- 继续看一下X264_close()函数的定义,如下所示
-
从X264_close()的定义可以看出,该函数调用了libx264的x264_encoder_close()关闭了libx264编码器
static av_cold int X264_close(AVCodecContext *avctx)
{X264Context *x4 = avctx->priv_data;av_freep(&x4->sei);av_freep(&x4->reordered_opaque);#if X264_BUILD >= 161x264_param_cleanup(&x4->params);
#endifif (x4->enc) {x264_encoder_close(x4->enc);x4->enc = NULL;}return 0;
}