FFmpeg调研报告
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了FFmpeg调研报告相关的知识,希望对你有一定的参考价值。
参考技术A FFmpeg 是非常强大的多媒体编解码框架,堪称多媒体处理的瑞士军刀,是集录制,转码,流的完整的跨平台多媒体解决方案。本身涵盖了大量的多媒体处理工具。而我们常说的视频,其实是包含的视频,音频甚至还有字幕的一个整体。因为视频本身是三维的数据,在计算中直接存储空间非常大,通常无法接受,所以,会对其进行一些编码和压缩,这个过程通常是有损的,但却极大了降低了它的存储空间。
视频数据相比位图数据多了一维,但其本身还是由像素点组成。
编码、压缩在流媒体领域是一项非常重要的技术:从 H264码流 到 YUV流 的过程称为 解码 ,反之称为 编码 。
帧是流的基本元素,即视频流中的图像。在原始流里,各帧都一样。但经过编码压缩后的帧,通常分为下面几种:
注意:I、P、B帧,并不是依据视频帧数据内部的元素的不同来区分的,从解码后的帧本身而言,它们没有任何区别。仅仅是在编码时,对帧处理的方式不同而已。
首先视频文件与视频编码格式是两个概念。
一般包括以下部分:
FFmpeg 处理视频转码时的常规过程如下:
各自状态的数据产物如下:
视频中会有音频,视频,它们在文件有各自的编码压缩方式,但为了传输过程方便,将压缩过的音频和视频捆绑在一起进行传输。首先就需要将媒体文件中的各个音频,视频,字幕流等分开。
这一步叫Demux(解复用)。总结就是把不同的流从某种容器(文件)中解析出来。如上图所示,并且,一个媒体文件中,还可以分别有不止一个音频,视频和字幕流。
媒体数据为了降低存储量,针对里面的音频,视频,字幕等都会采取特定方式的编码压缩。
这一步便对各自的流采用其对应的解码算法进行处理。得到原始流。
即这一步是以帧为单位实现压缩数据到原始数据转换。
这一步再按照目标的编码方式对流进行编码。即这一步是以帧为单位实现原始数据到压缩数据转换。
Demux的逆操作,把不同的流按照某种容器的规则放入容器
按照编解码器的位置划分:
FFmpeg中filter分为:
因其仅有解码部分的硬件加速,缺少编码部分的加速。且Nvidia有单身以NVENC和NVDEC替代掉这一块的意思,这里不多做细节介绍。细节请看 文档
支持的格式有:
优点:
各种型号的设计支持情况请看 Video Encode and Decode GPU Support Matrix
查看硬件支持:
使用CUDA解码:
使用CUVID解码:
转码,使用NVDEC和NVENC
可以使用 -hwaccel_device <id> 指定GPU。GPU id可以通过 nvidia-smi 查看
该方案一般通过QSV来进行加速。QSV(Quick Sync Video)即Intel的集成加速器,该方便优缺点如下:
优点:
查看CPU是否支持的方法如下:
该方案支持h264,h265,mjpeg,mpeg2video,vp8,vp9的编解码,和vc1的解码。
更细节的支持情况如下:
解码支持情况:
编码支持情况:
QuickSync对于编码解码在CPU使用率上都有着非常不错的提升。编码提升效果特别明显。
关于抽帧的各种表现,待之后测试补上。TODO
更多细节可以参考官方 文档
FFmpeg使用QSV加速的一些命令行参数可 参考
使用ffprobe提取出IPB帧的时间
抽取IPB帧到jpg图片:
抽帧流程其实与转码类似,一样是输入视频文件,对视频文件进行Demux,解码视频流,得到原始视频帧,然后挑选相应的视频帧按jpeg编码,mux输出到一个个文件中。
那么要加快抽帧的效率,便是想办法加快上面这各个阶段的速率
抽帧会伴随着大量的文件输出。在有很多抽帧任务并行时,理论上会对磁盘造成大量的随机写入。
其他途径优化:
结合以上各节点,这里列出一些进一步的调研方向:
此方案针对加快解码,加快编码。基于目前的信息来看:
该方案会有非常大的优化效果,若有足够支持QSV的CPU机器,那么该方案可行性非常大。
待进一步补充相关测试数据
同上,针对解码编码方面尝试加快进行优化。目前情况:
该方案理论上也应该会有不错的优化效果。但就目前的一些简单测试来看,即使能达到好的加速效果,其成本也未必能够接受
待进一步补充相关测试数据
该方案针对加快数据读取和数据输出。考虑的点主要是整个抽帧过程中是否对视频文件有不小量的随机读取,大量抽帧任务并行时,会有巨量的图片输出。这块是否会产生大量的随机写入,降低效率。
待进一步补充相关测试数据
该方案针对加解码(更确切地说是减少不必要的解码操作)
例如对于一秒一帧的均匀抽帧,我们针对这种情况,修改为,尽量抽取每一秒中的关键帧。做个伪的一秒一帧的均匀抽帧。这种模式不一定能为所有抽帧情况加速,但若能为大头的需求加速也不错
待进一步测试验证可行性及补充相关测试数据
针对解码编码方面尝试加快进行优化。
ffmpeg中,同样格式可能有多个编码解码器,比如jpeg的就会有mjpeg,libjpeg等。不同的库实现,性能,质量会有一些差距,通过测试实验,改善参数,或许一定程度上能优化性能。
待进一步补充相关测试数据
针对流程的优化。如前面的单帧抽帧, -ss 参数的不同位置会影响 ffmpeg 抽取的时间。理论上,ffmpeg 本身设计是为了通用,而对于专用于抽帧的场景,ffmpeg本身可能存在一些没必要的工作,尝试通过参数和源码级别来优化,或许能省掉这部分的资源消耗。
待进一步补充相关测试数据
TODO
FFmpeg官网
3GP/MP4 视频文件格式解析及其播放原理(转)
FFmpeg视频抽帧那些事
FFmpeg原理和架构
FFmpeg 硬件加速方案概览 (上)
FFmpeg 硬件加速方案概览 (下)
FFmpeg wiki HWAccelIntro
视频和视频帧:FFMPEG+Intel QSV硬解的环境安装篇
视频和视频帧:视频和帧基础知识整理
FFmpeg使用 FFmpeg 处理音视频格式转换流程 ( 解复用 | 解码 | 帧处理 | 编码 | 复用 )
FFmpeg 系列文章目录
【FFmpeg】Windows 搭建 FFmpeg 命令行运行环境
【FFmpeg】FFmpeg 相关术语简介
【FFmpeg】FFmpeg 相关术语简介 二
【FFmpeg】FFmpeg 帮助文档使用
一、视频格式转换
1、x264 视频格式转换
使用 x264 压缩格式 , 将原始 大小 1920x1040 大小的 mp4 格式的视频转为 960x520 的 flv 格式的视频 ;
进入视频所在目录 , 执行如下命令 :
ffmpeg -i 1920x1040.mp4 -acodec copy -vcodec libx264 -s 960x520 960x520.flv
命令执行过程 :
转换前的视频信息 :
转换后的视频信息 :
2、x265 视频格式转换
使用 x265 压缩格式 , 将原始 大小 1920x1040 大小的 mp4 格式的视频转为 960x520 的 mkv 格式的视频 ;
进入视频所在目录 , 执行如下命令 :
ffmpeg -i 1920x1040.mp4 -acodec copy -vcodec libx265 -s 960x520 960x520.mkv
命令执行结果 :
转换前的视频信息 :
转换后的视频信息 :
二、视频格式转换流程
分析如下命令的详细流程 :
ffmpeg -i 1920x1040.mp4 -acodec copy -vcodec libx264 -s 960x520 960x520.flv
将 1920x1040 大小的 mp4 格式的视频文件 , 使用 x264 编解码器 , 转为 960x520 大小的 flv 格式的视频文件 ;
蓝色的是 文件 / 中间产物 , 红色的是过程 ;
输入文件 : 输入 1920x1040 大小的 mp4 格式文件 , 1920x1040.mp4 ;
解复用 : 使用 demuxer 解复用器 , 将输入文件进行解复用操作 , 从容器中分别将 AVC 视频流 , AAC LC 音频流取出 , 得到编码数据包 ;
编码数据包 : 该数据包中的音视频数据都是编码后的数据 , 不能直接使用 ; 编码数据包中的视频流数据是 AVC 编码格式的 , 音频流数据是 AAC LC 编码格式的 ;
解码 : 使用 decoder 解码器 , 解码 AVC 编码的视频流数据 , AAC LC 编码的音频流数据 , 得到解码后的数据 ;
解码后的数据帧 : 音频数据是 PCM 采样 , 视频帧 数据是一张张 YUV 格式的图片 ;
帧处理 : 使用 filter 过滤器 处理 解码后的数据帧 , 将其转为 处理后的数据帧 ; 该过程中将视频的分辨率进行了修改 , 分辨率从 1920x1040 转为 960x520 ;
如果要修改视频的相关参数 , 如 时间 , 帧率 , 都在该步骤进行操作 , 操作的主体一定是解码后的数据帧 ;
处理后的数据帧 : 该数据帧是可以直接用于播放 ; 音频数据是 PCM 采样 , 视频帧 数据是一张张 YUV 格式的图片 ;
编码 : 使用 encoder 编码器 , 将处理后的数据帧进行编码 , 音频从 PCM 采样转为 AAC LC 编码格式 , 视频从 YUV 图片编码为 AVC 编码格式 ,
编码数据包 : 音频数据是 AAC LC 编码格式 , 视频数据是 AVC 编码格式 ;
复用 : 使用 muxer 复用器 , 将编码后的 视频流 和 音频流 封装到 容器中 , 即 flv 格式的视频文件 , 得到输出文件 ;
输出文件 : 格式转换完毕的 960x520.flv 视频文件 ;
以上是关于FFmpeg调研报告的主要内容,如果未能解决你的问题,请参考以下文章
在Mono / Linux中使用FFmpeg.Autogen 4.1.0.2时找不到Kernel32 https://github.com/Ruslan-B/FFmpeg.AutoGen/issues