当前位置: 首页 > news >正文

音视频入门基础:FLV专题(5)——FFmpeg源码中,判断某文件是否为FLV文件的实现

一、引言

通过FFmpeg命令:

./ffmpeg -i XXX.flv

可以判断出某个文件是否为FLV文件:

所以FFmpeg是怎样判断出某个文件是否为FLV文件呢?它内部其实是通过flv_probe函数来判断的。从《FFmpeg源码:av_probe_input_format3函数和AVInputFormat结构体分析(FFmpeg源码5.0.3版本)》和《7.0.1版本的FFmpeg源码中av_probe_input_format3函数和AVInputFormat结构体的改变》中我们可以知道:

FFmpeg源码中实现容器格式检测的函数是av_probe_input_format3函数,其内部通过循环while ((fmt1 = av_demuxer_iterate(&i))) 拿到所有容器格式对应的AVInputFormat结构,然后通过score = fmt1->read_probe(&lpd)语句执行不同容器格式对应的解析函数,根据是否能被解析,以及匹配程度,来判断出这是哪种容器格式。而FLV文件对应的解析函数就是flv_probe函数。

二、flv_probe函数的定义

flv_probe函数定义在FFmpeg源码(本文演示用的FFmpeg源码版本为7.0.1)的源文件libavformat/flvdec.c中,可以看到flv_probe函数内部调用了probe函数:

static int flv_probe(const AVProbeData *p)
{return probe(p, 0);
}

三、probe函数的定义

probe函数也定义在libavformat/flvdec.c中:

static int probe(const AVProbeData *p, int live)
{const uint8_t *d = p->buf;unsigned offset = AV_RB32(d + 5);if (d[0] == 'F' &&d[1] == 'L' &&d[2] == 'V' &&d[3] < 5 && d[5] == 0 &&offset + 100 < p->buf_size &&offset > 8) {int is_live = !memcmp(d + offset + 40, "NGINX RTMP", 10);if (live == is_live)return AVPROBE_SCORE_MAX;}return 0;
}

probe函数的作用就是检测某个文件是否为flv文件或flv格式的直播流。

形参pd:输入型参数,为AVProbeData类型的指针。

AVProbeData结构体声明在libavformat/avformat.h中:

/*** This structure contains the data a format has to probe a file.*/
typedef struct AVProbeData {const char *filename;unsigned char *buf; /**< Buffer must have AVPROBE_PADDING_SIZE of extra allocated bytes filled with zero. */int buf_size;       /**< Size of buf except extra allocated bytes */const char *mime_type; /**< mime_type, when known. */
} AVProbeData;

p->filename为:需要被推测格式的文件/直播流的路径。

p->buf:指向“存放从路径为p->filename的FLV文件/直播流中读取出来的二进制数据”的缓冲区。

p->buf_size:缓冲区p->buf的大小,单位为字节。注:FFmpeg判断某个文件的格式时不会读取完整个文件,只会读取它前面的一部分,比如最开始的2048个字节。只要根据前面的这些字节就足够判断出它的格式了,所以p->buf_size的值一般就是2048。

p->mime_type:一般为NULL,可忽略。

返回值:返回一个类型为整形的分值。返回0表示该文件/直播流完全不符合FLV格式。返回AVPROBE_SCORE_MAX(100)表示该文件/直播流完全符合FLV格式。

形参live:值为1表示需要被推测格式的是直播流,值为0表示需要被推测格式的是本地媒体文件。

 

四、probe函数的内部实现原理

下面以需要被推测格式的是FLV文件为例,讲解probe函数的内部实现原理。FLV文件对应的解析函数是flv_probe函数,flv_probe函数内部调用了probe函数,这时probe函数的形参live的值为0。

probe函数内部,由于FLV文件的开头就是FLV header,所以指针d指向FLV header:

    const uint8_t *d = p->buf;

通过AV_RB32宏定义读取FLV header中的DataOffset属性,得到整个FLV header的以字节为单位的长度,赋值给局部变量offset。关于AV_RB32宏定义的用法可以参考:《FFmpeg源码:AV_RB32、AV_RB16、AV_RB8宏定义分析》:

    unsigned offset = AV_RB32(d + 5);

从《音视频入门基础:FLV专题(3)——FLV header简介》可以知道,FLV header的前3个字节固定为“FLV”,所有判断d[0] == 'F' && d[1] == 'L' && d[2] == 'V';FLV header的第4个字节为Version,对于FLV格式,值必须为1,所以判断d[3] < 5;整个FLV header的长度固定为9,所以判断offset > 8。不满足条件probe函数返回0,表示完全不符合FLV格式:

    if (d[0] == 'F' &&d[1] == 'L' &&d[2] == 'V' &&d[3] < 5 && d[5] == 0 &&offset + 100 < p->buf_size &&offset > 8) {//...}return 0;

判断是否为直播流,变量is_live的值为1表示是直播流,值为0表示是FLV文件:

        int is_live = !memcmp(d + offset + 40, "NGINX RTMP", 10);

返回AVPROBE_SCORE_MAX(100)表示该文件/直播流完全符合FLV格式。

        if (live == is_live)return AVPROBE_SCORE_MAX;

相关文章:

音视频入门基础:FLV专题(5)——FFmpeg源码中,判断某文件是否为FLV文件的实现

一、引言 通过FFmpeg命令&#xff1a; ./ffmpeg -i XXX.flv 可以判断出某个文件是否为FLV文件&#xff1a; 所以FFmpeg是怎样判断出某个文件是否为FLV文件呢&#xff1f;它内部其实是通过flv_probe函数来判断的。从《FFmpeg源码&#xff1a;av_probe_input_format3函数和AVI…...

Tomcat 乱码问题彻底解决

1. 终端乱码问题 找到 tomcat 安装目录下的 conf ---> logging.properties .修改ConsoleHandler.endcoding GBK &#xff08;如果在idea中设置了UTF-8字符集&#xff0c;这里就不需要修改&#xff09; 2. CMD命令窗口设置编码 参考&#xff1a;WIN10的cmd查看编码方式&am…...

RGB颜色模型

RGB颜色模型是一种广泛应用于数字图像和计算机图形领域的颜色表示方法 一、基本概念 RGB 代表红色&#xff08;Red&#xff09;、绿色&#xff08;Green&#xff09;和蓝色&#xff08;Blue&#xff09;三种基本颜色。这些颜色被视为加色模型中的原色&#xff0c;意味着它们可…...

智能工厂的软件设计 创新型原始制造商(“创新工厂“)的Creator原型(统一行为理论)之2

Q8、今天我们继续昨天开始的 “智能工厂的软件设计”以“统一行为理论”为指导原则的 创新型原始制造商的Creator伪代码--创新工厂“原型”。这是在前述将“程序program”问题的三个体现“方面”&#xff08;逻辑/语言/数学&#xff09; 视为符号学的三分支&#xff08;语用语义…...

【个人博客hexo版】hexo安装时会出现的一些问题

项目场景&#xff1a; 项目场景&#xff1a;在完成了GitHub仓库和git的连接之后&#xff0c;就要新建一个文件夹&#xff08;例如hexo blog&#xff09;进行下一步hexo的使用 问题描述 例如&#xff1a;如图所示 原因分析&#xff1a; 这些error不用看它到底是什么&#xf…...

道路裂缝,坑洼,病害数据集-包括无人机视角,摩托车视角,车辆视角覆盖道路

道路裂缝&#xff0c;坑洼&#xff0c;病害数据集 包括无人机视角&#xff0c;摩托车视角&#xff0c;车辆视角 覆盖道路所有问题 一共有八类16000张 1到7依次为: [横向裂缝, 纵向裂缝, 块状裂缝, 龟裂, 坑槽, 修补网状裂缝, 修补裂缝, 修补坑槽] 道路病害&#xff08;如裂缝、…...

java接口文档配置

接口文档配置 一. swagger与knife4j 配置 1. 导入依赖 <!--swagger接口文档说明--> <dependency><groupId>io.springfox</groupId><artifactId>springfox-swagger2</artifactId> </dependency> <dependency><groupId>…...

【服务器第二期】mobaxterm软件下载及连接

【服务器第二期】mobaxterm软件下载及连接 前言什么是SSH什么是FTP/SFTP mobaxterm软件介绍mobaxterm软件下载SSH登录使用方法1-新建ssh连接方法2-打开已有的ssh连接方法3-通过ssh命令建立连接 SFTP数据传输方法1-建立ssh连接后直接拖拽方法2-建立sftp连接再拖拽方法3-直接使用…...

排序-----计数排序(非比较排序)

原理&#xff1a; 存在的问题&#xff1a;数组空间浪费 所以要相对映射&#xff0c;不要绝对映射 calloc()函数的功能是:为num个大小为size的元素开辟一块空间,并且把空间的每个字节初始化为0. // 时间复杂度:O(Nrange) // 只适合整数/适合范围集中 // 空间范围度&#xff1a;…...

[Python]案例驱动最佳入门:Python数据可视化在气候研究中的应用

在全球气候问题日益受到关注的今天&#xff0c;气温变化成为了科学家、政府、公众讨论的热门话题。然而&#xff0c;全球气温究竟是如何变化的&#xff1f;我们能通过数据洞察到哪些趋势&#xff1f;本文将通过真实模拟的气温数据&#xff0c;结合Python数据分析和可视化技术&a…...

PyQt5 导入ui文件报错 AttributeError: type object ‘Qt‘ has no attribute

问题描述&#xff1a; 利用 PyQt5 编写可视化界面是较为普遍的做法&#xff0c;但是使用全新UI版本的 Pycharm 修改之前正常的UI文件时&#xff0c;在没有动其他代码的情况下发现出现以下报错 AttributeError: type object Qt has no attribute Qt::ContextMenuPolicy::Defaul…...

Unity中Rigidbody 刚体组件和Rigidbody类是什么?

Rigidbody 刚体组件 Rigidbody 是 Unity 中的一个组件&#xff0c;它可以让你的游戏对象像真实世界中的物体一样移动和碰撞。想象一下&#xff0c;你有一个小球&#xff0c;你希望它像真实世界中的球一样滚动、弹跳和碰撞&#xff0c;那么你就可以给这个小球添加一个 Rigidbod…...

MySQL学习笔记(持续更新中)

1、Mysql概述 1.1 数据库相关概念 三个概念&#xff1a;数据库、数据库管理系统、SQL 名称全称简称数据库存储数据的仓库&#xff0c;数据是有组织的进行存储DataBase&#xff08;DB&#xff09;数据库管理系统操纵和管理数据库的大型软件DataBase Mangement System&#xf…...

sqlserver插入数据删除数据

1、插入数据 1.1 直接插入 1.1.1 方式一 insert into test values(001,黎明,1),(002,冯绍峰,1),(003,菲菲,2);1.1.2 方式二 insert into test(ID,Name,Sex) values(004,丽丽,2),(005,凌晨,2),(006,虾米,1);1.2 插入部分行 insert into test(ID,Name) values(007,红)2、删除…...

[51单片机] 简单介绍 (一)

文章目录 1.单片机介绍2.单片机内部三大资源3.单片机最小系统4.STC89C52单片机 1.单片机介绍 兼容Intel的MCS-51体系架构的一系列单片机。 STC89C52&#xff1a;8K FLASH、512字节RAM、32个IO口、3个定时器、1个UART、8个中断源。 单片机简称MCU单片机内部集成了CPU、RAM、RO…...

6个岗位抢1个人,百万年薪抢毕业生?大厂打响AI人才战

前言 “24岁毕业时年薪50万元&#xff0c;到了30岁大概能升到P7(注&#xff1a;职级名称&#xff09;&#xff0c;那时就能年薪百万了。” 从上海交大硕士毕业后&#xff0c;出生于2000年的赵宏在今年入职腾讯&#xff0c;担任AI算法工程师&#xff0c;成为AI风口下第一批就业…...

erlang学习:Linux命令学习3

shell基本输出 创建一个test.sh文件&#xff0c;并开放他的权限&#xff0c;之后向其中编辑以下内容 touch test.sh chmod 777 test.sh vim test.shecho "hello linux"之后运行相应shell程序得到输出 ./test.sh变量 单引号特点&#xff1a; 单引号里的任何字符都…...

力扣41 缺失的第一个正数 Java版本

文章目录 题目描述代码 题目描述 给你一个整数数组 nums&#xff0c;返回 数组 answer &#xff0c;其中 answer[i] 等于 nums 中除 nums[i] 之外其余各元素的乘积 。 题目数据 保证 数组 nums之中任意元素的全部前缀元素和后缀的乘积都在 32 位 整数范围内。 请 不要使用除…...

第五篇:Linux进程的相关知识总结(1)

目录 第四章&#xff1a;进程 4.1进程管理 4.1.1进程管理需要的学习目标 4.1.1.1了解进程的相关信息 4.1.1.2僵尸进程的概念和处理方法&#xff1a; 4.1.1.3PID、PPID的概念以及特性&#xff1a; 4.1.1.4进程状态 4.1.2进程管理PS 4.1.2.1静态查看进程 4.1.2.1.1自定义…...

企业级Windows server服务器技术(1)

windows server服务器安装 准备工作&#xff1a; 1.准备安装的镜像 2.安装好虚拟机VMware或者virtual box 3.准备安装的位置&#xff08;选择你的电脑的磁盘上比较空闲的位置&#xff0c;新建一个文件夹并命名&#xff09; 4.开始安装&#xff08;按步骤&#xff09;----…...

智慧工地云平台源码,基于微服务架构+Java+Spring Cloud +UniApp +MySql

智慧工地管理云平台系统&#xff0c;智慧工地全套源码&#xff0c;java版智慧工地源码&#xff0c;支持PC端、大屏端、移动端。 智慧工地聚焦建筑行业的市场需求&#xff0c;提供“平台网络终端”的整体解决方案&#xff0c;提供劳务管理、视频管理、智能监测、绿色施工、安全管…...

大型活动交通拥堵治理的视觉算法应用

大型活动下智慧交通的视觉分析应用 一、背景与挑战 大型活动&#xff08;如演唱会、马拉松赛事、高考中考等&#xff09;期间&#xff0c;城市交通面临瞬时人流车流激增、传统摄像头模糊、交通拥堵识别滞后等问题。以演唱会为例&#xff0c;暖城商圈曾因观众集中离场导致周边…...

根据万维钢·精英日课6的内容,使用AI(2025)可以参考以下方法:

根据万维钢精英日课6的内容&#xff0c;使用AI&#xff08;2025&#xff09;可以参考以下方法&#xff1a; 四个洞见 模型已经比人聪明&#xff1a;以ChatGPT o3为代表的AI非常强大&#xff0c;能运用高级理论解释道理、引用最新学术论文&#xff0c;生成对顶尖科学家都有用的…...

SAP学习笔记 - 开发26 - 前端Fiori开发 OData V2 和 V4 的差异 (Deepseek整理)

上一章用到了V2 的概念&#xff0c;其实 Fiori当中还有 V4&#xff0c;咱们这一章来总结一下 V2 和 V4。 SAP学习笔记 - 开发25 - 前端Fiori开发 Remote OData Service(使用远端Odata服务)&#xff0c;代理中间件&#xff08;ui5-middleware-simpleproxy&#xff09;-CSDN博客…...

初探Service服务发现机制

1.Service简介 Service是将运行在一组Pod上的应用程序发布为网络服务的抽象方法。 主要功能&#xff1a;服务发现和负载均衡。 Service类型的包括ClusterIP类型、NodePort类型、LoadBalancer类型、ExternalName类型 2.Endpoints简介 Endpoints是一种Kubernetes资源&#xf…...

【Nginx】使用 Nginx+Lua 实现基于 IP 的访问频率限制

使用 NginxLua 实现基于 IP 的访问频率限制 在高并发场景下&#xff0c;限制某个 IP 的访问频率是非常重要的&#xff0c;可以有效防止恶意攻击或错误配置导致的服务宕机。以下是一个详细的实现方案&#xff0c;使用 Nginx 和 Lua 脚本结合 Redis 来实现基于 IP 的访问频率限制…...

如何应对敏捷转型中的团队阻力

应对敏捷转型中的团队阻力需要明确沟通敏捷转型目的、提升团队参与感、提供充分的培训与支持、逐步推进敏捷实践、建立清晰的奖励和反馈机制。其中&#xff0c;明确沟通敏捷转型目的尤为关键&#xff0c;团队成员只有清晰理解转型背后的原因和利益&#xff0c;才能降低对变化的…...

Visual Studio Code 扩展

Visual Studio Code 扩展 change-case 大小写转换EmmyLua for VSCode 调试插件Bookmarks 书签 change-case 大小写转换 https://marketplace.visualstudio.com/items?itemNamewmaurer.change-case 选中单词后&#xff0c;命令 changeCase.commands 可预览转换效果 EmmyLua…...

Android写一个捕获全局异常的工具类

项目开发和实际运行过程中难免会遇到异常发生&#xff0c;系统提供了一个可以捕获全局异常的工具Uncaughtexceptionhandler&#xff0c;它是Thread的子类&#xff08;就是package java.lang;里线程的Thread&#xff09;。本文将利用它将设备信息、报错信息以及错误的发生时间都…...

前端高频面试题2:浏览器/计算机网络

本专栏相关链接 前端高频面试题1&#xff1a;HTML/CSS 前端高频面试题2&#xff1a;浏览器/计算机网络 前端高频面试题3&#xff1a;JavaScript 1.什么是强缓存、协商缓存&#xff1f; 强缓存&#xff1a; 当浏览器请求资源时&#xff0c;首先检查本地缓存是否命中。如果命…...