FFmpeg5.0源码阅读—— av_read_frame

news2024/9/21 4:28:17

  摘要:本文主要描述了FFmpeg中用于打开编解码器接口av_read_frame的具体调用流程,详细描述了该接口被调用时所作的具体工作。
  关键字ffmpegav_read_frame
  读者须知:读者需要了解FFmpeg的基本使用流程,以及一些FFmpeg的基本常识,了解FFmpegIO相关的内容,以及大致的解码流程。
  使用FFmpeg解码视频时需要主动打开解码器获得解码器相关的Context,然后直接调用av_read_frame读取AVPacket码流数据送到FFmpeg中进行解码即可。本文主要通过源码了解FFmpeg搜索和打开解码器的基本实现原理和FFmpeg具体的解码流程。

2 av_read_frame

在这里插入图片描述

  av_read_frame用于从已经打开的文件中读取未经过解码的码流AVPacket,对于视频帧就是一帧的压缩帧,对于音频帧如果音频是固定大小的话则可以是多帧,否则也是一帧。av_read_frame内部读取码流时调用avpriv_packet_list_getav_read_frame_internal
  avpriv_packet_list_get比较简单就是从当前媒体的PackList中取出一帧。av_read_frame的函数实现比较长,其大致流程为:

  1. 调用ff_read_packet读取一帧码流;
  2. 如果1步骤失败则调用parse_packet刷新解析器,否则继续到步骤3;
  3. 如果当前context需要更新解码器context,则将internal的解码器context更新到stream的解码器context;
  4. 如果成功拿到预期的帧则下一步,否则跳转到步骤1;
  5. 后续的工作就是解析元数据,计算需要丢弃的数据大小等。

  ff_read_packet会先检查缓冲区是否有帧没有的话就会调用s->iformat->read_packet即对应个是的解析码流的函数进行解码。每个FFmpeg支持的格式都有一个FormatContext描述对应格式的信息以及解析对应格式的函数指针,比如下面是mov的格式描述:

static const AVClass mov_class = {
    .class_name = "mov,mp4,m4a,3gp,3g2,mj2",
    .item_name  = av_default_item_name,
    .option     = mov_options,
    .version    = LIBAVUTIL_VERSION_INT,
};

const AVInputFormat ff_mov_demuxer = {
    .name           = "mov,mp4,m4a,3gp,3g2,mj2",
    .long_name      = NULL_IF_CONFIG_SMALL("QuickTime / MOV"),
    .priv_class     = &mov_class,
    .priv_data_size = sizeof(MOVContext),
    .extensions     = "mov,mp4,m4a,3gp,3g2,mj2,psp,m4b,ism,ismv,isma,f4v",
    .flags_internal = FF_FMT_INIT_CLEANUP,
    .read_probe     = mov_probe,
    .read_header    = mov_read_header,
    .read_packet    = mov_read_packet,
    .read_close     = mov_read_close,
    .read_seek      = mov_read_seek,
    .flags          = AVFMT_NO_BYTE_SEEK | AVFMT_SEEK_TO_PTS,
};

  从上面的过程能够看出av_read_frame完全是同步的操作,可能是比较耗时的,因为如果一直拿不到帧就会一直遍历当前媒体文件的buffer,因此一般建议开一个线程读取Packet。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/733462.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

JVM理论(二)类加载子系统

类加载流程 类加载流程 类加载器子系统负责从文件系统或者网络中加载class文件,class文件的文件头有特定的文件标识(CAFEBABE是JVM识别class文件是否合法的依据)classLoader只负责文件的加载,而执行引擎决定它是否被执行加载类的信息存放在运行时数据区的方法区中,方法区还包括…

【终端增强工具】这次,我把Terminal(终端)也接入ChatGPT了...

大家好,我是萌新程序员豆小匠。 为terminal(终端)增加自定义命令这个想法从开始学编程的时候就有了,但是一直没有付诸行动。 这次,终于抽时间完成了,且代码开源! 实现的功能 先说下实现的功能…

Idea社区版创建SpringBoot

一 下载Spring Initalizr and Assistant插件 选择左上角的File->Settings->Plugins,在搜索框中输入Spring,出现的第一个Spring Boot Helper插件,点击Installed,下载插件。(这里已经下载) 二 创建Spr…

Python学习笔记【01-基础语法】

文章目录 第一章输入输出print转义字符字符编码标识符和保留字变量数据类型整形浮点型布尔类型字符串类型数据类型转换 注释 第二章input()函数运算符算术运算符赋值运算符比较运算符布尔运算符(逻辑运算符)位运算符运算符的优先级 第三章顺序结构对象的布尔值单分支结构双分支…

dSYM文件是什么 ?

Overview 概述 dSYM的全称是debug symbol, 所以dSYM文件就是debug symbol (dSYM) file, dSYM文件中的每个 debug symbol, 对应了一个关系, 这个关系一端是源代码里真实的符号(类名称、全局变量以及方法和函数名称), 另一端则是其定义的文件号和行号. Apple Documentation 苹果…

word批量替换时使用通配符

替换这个好操作,打开替换功能: 弹出窗口中分别输入要替换的对象和替换的结果: 这里主要介绍特殊的替换: 可以看到点击“更多”之后,会出现下面的选项 像是【区分大小写】、【全字匹配】、【同音】、【查找单词的所有形…

三张表学会MySQL的单表操作!

表单一信息 1、查询表中所有学生的信息 mysql> select * from student; 2、 查询表中所有学生的姓名和英语成绩 mysql> select name,english from student; 3、过滤表中的重复数据 mysql> select DISTINCT * from student; 4、统计每个学生的总分 mysql> sele…

大语言模型高效训练基础知识:优化器AdamW和Adafator

Prerequsite:Adam优化算法 Adam优化算法很长一段时间都是比较主流的参数更新算法,也有很多变种,本文介绍在大模型训练过程中使用的AdamW和Adafator AdamW 原论文:Decoupled Weight Decay Regularization AdamW指的是Adam Weight Decay&#…

Mysql中默认自动事务autocommit关闭和开启方式、rollback回滚恢复数据的使用方法

文章目录 autocommit自动提交事物一、查看autocommit状态二、修改autocommit 状态的方式1、第一种方式2、修改mysql配置文件my.cnf 二、rollback回滚1、autocommit 开启1、autocommit 关闭 autocommit自动提交事物 MySQL 默认开启事务自动提交模式,每条 SOL 语句都…

深度神经网络知识蒸馏算法基础理论

知识蒸馏作为一种压缩方法,与剪枝、量化中直接在原模型上进行参数的剪枝或数据位宽的降低来压缩不同,知识蒸馏方法往往是通过将大模型上的精度转移到一个相对更小的模型上来完成对大模型的压缩。此处所说的大模型即知识蒸馏中的教师模型,而相…

【C语言】深入学习数组

👦个人主页:Weraphael ✍🏻作者简介:目前正在回炉重造C语言(2023暑假) ✈️专栏:【C语言航路】 🐋 希望大家多多支持,咱一起进步!😁 如果文章对你…

进程间通信方法——匿名管道

什么是管道&#xff1f; 管道是Unix中最古老的进程间通信的形式。我们把从一个进程连接到另一个进程的一个数据流称为一个“管道” 什么是匿名管道 就是一个没有名字的管道。 #include <unistd.h> 功能:创建一无名管道 原型 int pipe(int fd[2]); 参数 fd&#xff1a;文…

韩信谋反解密-使用命名空间

开机故事&#xff1a; 另一个韩信 什么是命名空间 c里面也有这种困扰&#xff0c;名字的冲突&#xff0c; 特意使用命名空间&#xff0c;开发的时候都要给函数命名 就会有名字相同的时候。这样就会出现混乱 区分相同名字相同函数的这样一个功能 用法1. #include<string…

openGauss学习笔记-04 openGauss极简版单机主备安装部署

文章目录 openGauss学习笔记-04 openGauss极简版单机主备安装部署4.1 获取安装包4.1.1 下载对应平台的安装包4.1.2 解压安装包4.1.3 查看目录结构 4.2 准备软硬件安装环境4.2.1 硬件环境要求4.2.2 软件环境要求4.2.3 软件依赖要求 4.3 单机主备安装部署4.3.1 安装前准备4.3.2 单…

【网络安全带你练爬虫-100练】第11练:xpath快速定位提取数据

目录 一、目标1&#xff1a;使用etree解析数据 二、目标2&#xff1a;使用xpath爬取指定数据 三、目标3&#xff1a;提取指定数据 四、网络安全小圈子 一、目标1&#xff1a;使用etree解析数据 其余的不用过多介绍&#xff0c;前面的练习都给大家已经过了一遍 def get_page…

【沐风老师】3DMAX砖石墙地面生成工具插件使用方法详解

3dMax砖石墙地面生成工具插件&#xff0c;收集了一些用于创建石墙、石头路面和不规则石头图案的实用工具&#xff0c;以模拟墙壁和地面。脚本会自动烘焙法线贴图、AO贴图和高度贴图以供实时使用。 【主要特点】 1.可以生成真实的石墙、地面、不规则石块及石灰墙面&#xff0c;是…

4.5 x64dbg 探索钩子劫持技术

钩子劫持技术是计算机编程中的一种技术&#xff0c;它们可以让开发者拦截系统函数或应用程序函数的调用&#xff0c;并在函数调用前或调用后执行自定义代码&#xff0c;钩子劫持技术通常用于病毒和恶意软件&#xff0c;也可以让开发者扩展或修改系统函数的功能&#xff0c;从而…

oracle启动/关闭/查看监听+启动/关闭/查看数据库实例命令

启动oracle第一步启动监听&#xff0c;第二步启动数据库实例 &#xff08;1&#xff09;输入su oracle进入oracle用户状态 &#xff08;2&#xff09;这里的密码是你的root密码 1 启动/关闭/查看监听命令 &#xff08;1&#xff09;启动监听—— lsnrctl start &am…

C#学习之路-封装

封装 被定义为"把一个或多个项目封闭在一个物理的或者逻辑的包中"。在面向对象程序设计方法论中&#xff0c;封装是为了防止对实现细节的访问。 抽象和封装是面向对象程序设计的相关特性。抽象允许相关信息可视化&#xff0c;封装则使开发者实现所需级别的抽象。 C…

编码和调制

编码与调制 消息是以二进制的形式存放在数据当中的&#xff0c;这种数据的表现形式是信号&#xff0c;而信源发出的原始信号就叫做基带信号&#xff0c;基带信号又可以分为数字基带信号和模拟基带信号。 信号需要在信道中进行传输&#xff0c;信道分为模拟信道和数字信…