本文转自雷霄骅大神的博客,仅供学习,更多内容请阅读原文:https://blog.youkuaiyun.com/leixiaohua1020/article/details/44226355
函数调用关系图
首先呈现分析的结果,如图所示。这张图的尺寸很大(大于4000x4000),因此需要打开图片链接之后将图片保存为本地文件,然后才能查看。它表明了FFmpeg在编码一个视频的时候的函数调用流程。为了保证结构清晰,其中仅列出了最关键的函数,剔除了其它不是特别重要的函数。

下面解释一下图中关键标记的含义。
函数背景色
函数在图中以方框的形式表现出来。不同的背景色标志了该函数不同的作用:
粉红色背景函数:FFmpeg的API函数。
白色背景的函数:FFmpeg的内部函数。
黄色背景的函数:URLProtocol结构体中的函数,包含了读写各种协议的功能。
绿色背景的函数:AVOutputFormat结构体中的函数,包含了读写各种封装格式的功能。
蓝色背景的函数:AVCodec结构体中的函数,包含了编解码的功能。
区域
整个关系图可以分为以下几个区域:
左边区域——架构函数区域:这些函数并不针对某一特定的视频格式。
右上方黄色区域——协议处理函数区域:不同的协议(RTP,RTMP,FILE)会调用不同的协议处理函数。
右边中间绿色区域——封装格式处理函数区域:不同的封装格式(MKV,FLV,MPEG2TS,AVI)会调用不同的封装格式处理函数。
右边下方蓝色区域——编解码函数区域:不同的编码标准(HEVC,H.264,MPEG2)会调用不同的编解码函数。
箭头线
为了把调用关系表示的更明显,图中的箭头线也使用了不同的颜色:
红色的箭头线:标志了编码的流程。
其他颜色的箭头线:标志了函数之间的调用关系。其中:
调用URLProtocol结构体中的函数用黄色箭头线标识;
调用AVOutputFormat结构体中的函数用绿色箭头线标识;
调用AVCodec结构体中的函数用蓝色箭头线标识。
函数所在的文件
每个函数标识了它所在的文件路径。
函数功能简述
下面简单列出几个区域中函数之间的调用关系(函数之间的调用关系使用缩进的方式表现出来)。详细的函数分析可以参考相关的《FFmpeg源代码分析》系列文章。
左边区域(架构函数)
1. av_register_all()【函数简单分析】
1) avcodec_register_all()
(a) REGISTER_HWACCEL()
(b) REGISTER_ENCODER()
(c) REGISTER_DECODER()
(d) REGISTER_PARSER()
(e) REGISTER_BSF()
2) REGISTER_MUXER()
3) REGISTER_DEMUXER()
4) REGISTER_PROTOCOL()
2. avformat_alloc_output_context2()【函数简单分析】
1) avformat_alloc_context()
(a) av_malloc(sizeof(AVFormatContext))
(b) avformat_get_context_defaults()
a) av_opt_set_defaults()
2) av_guess_format()
(a) av_oformat_next()
(b) av_match_name()
(c) av_match_ext()
3. avio_open2()【函数简单分析】
1) ffurl_open()
(a) ffurl_alloc()
a) url_find_protocol()
b) url_alloc_for_protocol()
(b) ffurl_connect()
a) URLProtocol->url_open()
2) ffio_fdopen()
(a) av_malloc(buffer_size)
(b) avio_alloc_context()
a) av_mallocz(sizeof(AVIOContext))
b) ffio_init_context()
4. avformat_new_stream()【函数简单分析】
1) av_mallocz(sizeof(AVStream))
2) avcodec_alloc_context3()
(a) av_malloc(sizeof(AVCodecContext))
(b) avcodec_get_context_defaults3()
5. avcodec_find_encoder()【函数简单分析】
1) find_encdec()
6. avcodec_open2()【函数简单分析】
1) AVCodec->init()
7. avformat_write_header()【函数简单分析】
1) init_muxer()
2) AVOutputFormat->write_header()
3) init_pts()
8. avcodec_encode_video2()【函数简单分析】
1) AVCodec->encode2()
9. av_write_frame()【函数简单分析】
1) check_packet()
2) compute_pkt_fields2()
3) write_packet()
(a) AVOutputFormat->write_packet()
10. av_write_trailer()【函数简单分析】
1) write_packet()
2) AVOutputFormat->write_trailer()
11. avcodec_close()【函数简单分析】
1) AVCodec->close()
12. avformat_free_context()【函数简单分析】
1) ff_free_stream()
13. avio_close()【函数简单分析】
1) avio_flush()
(a) flush_buffer()
2) ffurl_close()
(a) ffurl_closep()
a) URLProtocol->url_close()
本文详细解析了FFmpeg在视频编码过程中的函数调用流程,通过一张庞大的函数调用关系图,展示了从架构函数到编解码函数的全过程。图中以不同颜色区分FFmpeg的API函数、内部函数及与协议、封装格式、编解码相关的函数,并用箭头线表示调用关系。
298

被折叠的 条评论
为什么被折叠?



