ffmpeg-nvenc
nvenc.c是一个用nvidia来执行的代码,下面简单分析nvenc编码的基本流程,
主要关注与nvenc底层相关的接口调用,nvenc底层代码的关键调用如下图所示的8个步骤
AVCodec ff_nvenc_h264_encoder = {.name = "nvenc_h264",.long_name = NULL_IF_CONFIG_SMALL("NVIDIA NVENC H.264 encoder"),.type = AVMEDIA_TYPE_VIDEO,.id = AV_CODEC_ID_H264,/*关键的三个接口函数*/.init = nvenc_old_init,.encode2 = ff_nvenc_encode_frame,.close = ff_nvenc_encode_close,.priv_data_size = sizeof(NvencContext),.priv_class = &nvenc_h264_class,.defaults = defaults,.capabilities = AV_CODEC_CAP_DELAY,.caps_internal = FF_CODEC_CAP_INIT_CLEANUP,.pix_fmts = ff_nvenc_pix_fmts,
};
#endif
主要是分析 ff_nvenc_encode_frame和ff_nvenc_encode_init
ff_nvenc_encode_init关键部分
/*加载函数库*关键err = nvenc_create_instance(&dl_fn->nvenc_funcs);*/if ((ret = nvenc_load_libraries(avctx)) < 0)return ret;if ((ret = nvenc_setup_device(avctx)) < 0)return ret;if ((ret = nvenc_setup_encoder(avctx)) < 0)return ret;if ((ret = nvenc_setup_surfaces(avctx)) < 0)return ret;
1.nvenc_load_libraries
加载函数库,经过这样的处理后就可以使用nvenc底层的函数接口
err = nvenc_create_instance(&dl_fn->nvenc_funcs);//关键调用
2.nvenc_setup_device
获取GPU使用资源(可以理解成要想使用nvidia,需要获取GPU的使用权限),打开段,检测设备兼容性等性能
这个函数的流程会有两个分支,一个是从显卡(显存)传来的数据,另一个是从CPU传来的数据(内存)。这两个流程的区别就是
假设数据从内存传来,为了开启显卡,需要获取显卡的相关资源,因此需要调用一系列获取显卡信息资源的接口,这类接口主要有:
(dl_fn->cu_init(0)) dl_fn->cu_device_get_count(&nb_devices) //获取设备数量cu_res =dl_fn->cu_device_get(&cu_device, idx);//获取idx指定的设备入口cu_res =dl_fn->cu_ctx_create(&ctx->cu_context_internal, 0, cu_device);//在这个设备创建相关资源ctx->cu_context =ctx->cu_context_internal; //ctx->cu_context会在被open_session使用
假设数据是从显存传过来,代表之前已经用显卡做了解码相关的操作,显卡相关的信息资源就可以直接获取到了
frames_ctx = (AVHWFramesContext*)avctx->hw_frames_ctx->data;device_hwctx = frames_ctx->device_ctx->hwctx;ctx->cu_context = device_hwctx->cuda_ctx;
这个函数里面有两个重要的接口调用nvenc_open_session和nvenc_check_capabilities
`nvenc_open_session` ---------必须有这个操作,后续的接口调用操作才能成功
ret = p_nvenc->nvEncOpenEncodeSessionEx(¶ms, &ctx->nvencoder); //关键调用
nvenc_check_capabilities
————-支持的编码参数检测
3.nvenc_setup_encoder—-设置编码参数
摘取与nvenc底层相关的关键代码:
static av_cold int nvenc_setup_encoder(AVCodecContext *avctx)
{.... /*这里涉及到-preset的设置*/nvenc_map_preset(ctx);nv_status = nv_status = p_nvenc->nvEncGetEncodePresetConfig(ctx->nvencoder,ctx->init_encode_params.encodeGUID,ctx->init_encode_params.presetGUID,&preset_config);
.... /*码率控制设置,大多数nvenc的参数的设置都和码率控制相关*/ nvenc_setup_rate_control(avctx);
.........../*设置h264和hevc的编码参数,level等级*/res = nvenc_setup_codec_config(avctx);
..... /*初始化编码器*/nv_status = p_nvenc->nvEncInitializeEncoder(ctx->nvencoder, &ctx->init_encode_params);}
4.nvenc_setup_surfaces ——–分配必要显存的地方
底层库关键调用nv_status = p_nvenc->nvEncCreateInputBuffer(ctx->nvencoder, &allocSurf); -----分配输入nv_status = p_nvenc->nvEncCreateBitstreamBuffer(ctx->nvencoder, &allocOut); -----分配输出
ff_nvenc_encode_frame的简单分析:
{....inSurf = get_free_frame(ctx);//从获取空余空间if (!inSurf) {av_log(avctx, AV_LOG_ERROR, "No free surfaces\n");return AVERROR_BUG;}/* 把解码之后的数据加载进来*nvenc_upload_frame两个分支*/res = nvenc_upload_frame(avctx, frame, inSurf);if (res) {inSurf->lockCount = 0;return res;}....... nv_status = p_nvenc->nvEncEncodePicture(ctx->nvencoder, &pic_params);//开始编码...../*接下来就是编码数据的读写操作*数据放到surface --fifo*读写fifo*av_fifo_generic_read*av_fifo_generic_write*处理数据,变成pkt---process_output_surface*/......
}
nvenc_upload_frame两个分支:
如果数据是从显存传来
ret = p_nvenc->nvEncRegisterResource(ctx->nvencoder, ®);nv_status = p_nvenc->nvEncMapInputResource(ctx->nvencoder, &nvenc_frame->in_map);
如果数据从内存传过来
v_status = p_nvenc->nvEncLockInputBuffer(ctx->nvencoder, &lockBufferParams);nv_status = p_nvenc->nvEncUnlockInputBuffer(ctx->nvencoder, nvenc_frame->input_surface);
ffmpeg-nvenc相关推荐
- ffmpeg nvenc编码
花时间研究了一些ffmpeg的nvenc,本来想我已经有了cuvid,然后又搞出来了nvenc,应该可以做个全套的英伟达的转码了,没想到ffmpeg官网下载的动态库没有cuvid,windows上编译 ...
- 【视频开发】【CUDA开发】ffmpeg nvenc编码
花时间研究了一些ffmpeg的nvenc,本来想我已经有了cuvid,然后又搞出来了nvenc,应该可以做个全套的英伟达的转码了,没想到ffmpeg官网下载的动态库没有cuvid,windows上编译 ...
- Nvidia nvenc cuvid + ffmpeg 硬编解码
ffmpeg 命令行,可指定GPU运算:ffmpeg -hwaccel_output_format cuda -vcodec h264_cuvid -i input.mp4 -vcodec h264_ ...
- centos7 如何编译ffmpeg 带x265和nvenc
如果不想编译nvenc 或者你的显卡不是英伟达 可以 不卸载驱动 编译的时候 把nvenc这个参数给去掉 # 下载英伟达驱动 https://www.geforce.cn/drivers 卸载默认驱动 ...
- NVIDIA FFmpeg 转码技术分析
NVIDIA FFmpeg 转码技术分析 所有从 Kepler 一代开始的 NVIDIA GPUs 都支持完全加速的硬件视频编码,而从费米一代开始的所有 GPUs 都支持完全加速的硬件视频解码.截至 ...
- 从 FFmpeg 性能加速到端云一体媒体系统优化
简介:7 月 31 日,阿里云视频云受邀参加由开放原子开源基金会.Linux 基金会亚太区.开源中国共同举办的全球开源技术峰会 GOTC 2021 ,在大会的音视频性能优化专场上,分享了开源 FFmp ...
- 音视频技术开发周刊:FFmpeg内置的一个无中生有的音视频输入数据 | 214
每周一期,纵览音视频技术领域的干货. 新闻投稿:contribute@livevideostack.com 火山引擎视频云:坚持基础技术创新,打造极致用户体验 从toC到toB,作为抖音背后的视频技术 ...
- FFmpeg在Intel GPU上的硬件加速与优化
英特尔提供了一套基于VA-API/Media SDK的硬件加速方案,通过在FFmpeg中集成Intel GPU的媒体硬件加速能力,为用户提供更多的收益.本文来自英特尔资深软件开发工程师赵军在LiveV ...
- FFmpeg 硬件加速方案概览 (下)
被称为"多媒体技术领域的瑞士军刀",FFmpeg拥有广泛的应用基础.不过,当(实时)处理海量视频时,需要借助各种方法提升效率.比如,短视频平台Revvel将视频转码服务迁移到AWS ...
- linux 显卡转码,ffmpeg用GPU转码
8种机械键盘轴体对比 本人程序员,要买一个写代码的键盘,请问红轴和茶轴怎么选? 有些视频编码太屌,播放起来对CPU消耗巨大,而在电视上或者电视盒子上看视频,编码就需要合适,楼主用的FireTV Sti ...
最新文章
- apache ant 安装_SAP Hybris使用recipe进行安装时,是如何执行ant命令的?
- 机器学习之支持向量机
- 读取文档时出现问题129_springboot读取配置文件的自定义内容时出现中文乱码
- 计算机组网配置,计算机组网技术与配置教案..doc
- 【小程序】【Tips】等待服务器的反馈的定时、间隔运行的正确方法
- linux窗口黑边,解决deepin-scrot在gnome3截图顶部出现黑边问题
- 拉格朗日乘子法几何意义
- 常用工具——Rsync
- 关于IE浏览器以及Firefox下冒泡事件的响应层级
- 在线代理和缓存工具(转)
- QCustomplot 实现鼠标追踪定位线以及坐标
- 移动通信网络规划:5G业务解析
- Fandis COSTECH A17M23SWB MT0 AC220V 50HZ 42W
- ES使用Ngram分词器实现wildcard高性能替代方案
- update语句执行卡死现象原因及解决方案
- 前端面试题整理 (ES6篇)
- 行星碰撞(C语言实现)
- python爬取王者荣耀皮肤高清图
- 算术运算符:取余(取模)%
- Android音量调节的实现(RingtoneManager和RingerVolumePreference)
热门文章
- 小程序canvans一键截屏纯前端实现
- 16天记住7000考研单词(第一天)
- c语言负数与正数判断大小,c语言编程,输入一些整数,判断其中正数与负数的个数,并分别求出正数与负数的平均值...
- linux怎么发送邮件到qq邮箱,centos7命令行下用QQ邮箱发送邮件教程
- ATP 系列无线测温集中采集触摸屏
- python汇率的转换程序_如何实现python汇率转换代码
- 李宏毅2021春季机器学习课程视频笔记1:Introduction, Colab PyTorch Tutorials, HW1
- 虚拟机无法在更新服务器,今win10更新导致VMware workstation pro无法打开的解决方法...
- 笔试题:计算机网络 (1)
- 苹果系统 虚拟机_大连win10远程双系统重装电脑维修7苹果笔记本安装做虚拟机服务mac8...