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

FFmpeg 4.3 音视频-多路H265监控录放C++开发十三.2:avpacket中包含多个 NALU如何解析头部分析

前提:

注意的是:我们这里是从avframe转换成avpacket 后,从avpacket中查看NALU。

在实际开发中,我们有可能是从摄像头中拿到 RGB 或者 PCM,然后将pcm打包成avframe,然后将avframe转换成avpacket,然后直接就通过网络传播avpacket了,

那么在网络传输的过程中如何传送这个avpacket呢?这就要用到 NALU 了。

关于NALU是啥?可以参考这个:

音视频开发14 FFmpeg 视频 相关格式分析 -- H264 NALU格式分析-CSDN博客

为了方便在网络上传输的一种抽象层。一般网络上传输的数据包有大小限制,而AVC(H264)的一帧大小远远大于网络传输的字节大小限制。因此要对AVC的数据流进行拆包,将一帧数据拆分为多个包传输。和NAL层相对是VAL层,即视频编码层(Video Coding Layer)

NALU就是经过分组后的一个一个数据包。

发I帧之前,⾄少要发⼀次SPS和PPS。当分辨率变化的时候,要重新发送一次SPS和PPS(类似在视频网站上,我们将分辨率从720p变成1080p的时候)

这个很重要,如果遇到我们显示不了图片或者视频的时候,应该第一个检查的就是 SPS 和PPS是否有正确的发送。

SPS:序列参数集,SPS中保存了⼀组编码视频序列(Coded video sequence)的全局参数。

PPS:图像参数集,对应的是⼀个序列中某⼀幅图像或者某⼏幅图像的参数。

I帧:帧内编码帧,可独⽴解码⽣成完整的图⽚。

P帧: 前向预测编码帧,需要参考其前⾯的⼀个I 或者B 来⽣成⼀张完整的图⽚。

B帧: 双向预测内插编码帧,则要参考其前⼀个I或者P帧及其后⾯的⼀个P帧来⽣成⼀张完整的图⽚。

每个NALU = StartCode + 由一个1字节的NALU头部 + 一个包含控制信息或编码视频数据的字节流组成。

NALU 结构单元的主体结构如下所示;⼀个原始的 H.264 NALU 单元 通常由 [StartCode] [NALU
Header] [NALU Payload] 三部分组成。

Start Code ⽤于标示这是⼀个 NALU 单元的开始,
必须是"00 00 00 01" 或 "00 00 01" ,
H.264 标准指出,当数据流是储存在介质上时,在每个 NALU 前添加起始码: 0x000001 或
0x00000001 ,⽤来指示⼀个 NALU 的起始和终⽌位置:
在这样的机制下,在码流中检测起始码,作为⼀个 NALU 得起始标识,当检测到下⼀个起始码时,当前NALU 结束。
3 字节的 0x000001 只有⼀种场合下使⽤,就是⼀个完整的帧被编为多个 slice (⽚)的时
候,包含这些 slice 的 NALU 使⽤ 3 字节起始码。其余场合都是 4 字节 0x00000001 的。
NALU Header :
NALU Header占位8Bit,其中三个字段分别为

F 为禁⽌位,占 1bit  
forbidden_zero_bit: 在 H.264 规范中规定了这⼀位必须为 0。
R为重要性指示位,占 2个 bit 
nal_ref_idc :取 00~11, 似乎指示这个 NALU 的重要性 , 如 00 的 NALU 解码器可以丢弃它⽽不影响图像的回放,0 ~ 3 ,取值越⼤,表示当前 NAL 越重要,需要优先受到保护。如果当前 NAL是属于参考帧的⽚,或是序列参数集,或是图像参数集这些重要的单位时,本句法元 素必需⼤于0 。
T 为负荷 数据类型 ,占 5 bit
nal_unit_type:这个 NALU 单元的类型 ,1 ~ 12 由 H.264 使⽤, 24 ~ 31 由 H.264 以外的应⽤
其值如下:重点是 5,6,7,8
5      Coded slice of an IDR picture                                  VCL
        IDR图像的编码条带(⽚) slice_layer_without_partitioning_rbsp( )
6      Supplemental enhancement information (SEI)                     non-VCL
        辅助增强信息 (SEI)sei_rbsp( )
7      Sequence parameter set                                         non-VCL
        序列参数集 seq_parameter_set_rbsp( )
8      Picture parameter set                                          non-VCL
        图像参数集 pic_parameter_set_rbsp( )

0      Unspecified                                                    non-VCL未指定
1      Coded slice of a non-IDR picture                               VCL⼀个⾮IDR图像的编码条带slice_layer_without_partitioning_rbsp()
2      Coded slice data partition A                                   VCL编码条带数据分割块A slice_data_partition_a_layer_rbsp()
3      Coded slice data partition B                                   VCL编码条带数据分割块B slice_data_partition_b_layer_rbsp( )
4      Coded slice data partition C                                   VCL编码条带数据分割块C slice_data_partition_c_layer_rbsp( )
5      Coded slice of an IDR picture                                  VCLIDR图像的编码条带(⽚) slice_layer_without_partitioning_rbsp( )
6      Supplemental enhancement information (SEI)                     non-VCL辅助增强信息 (SEI)sei_rbsp( )
7      Sequence parameter set                                         non-VCL序列参数集 seq_parameter_set_rbsp( )
8      Picture parameter set                                          non-VCL图像参数集 pic_parameter_set_rbsp( )
9      Access unit delimiter                                          non-VCL访问单元分隔符 access_unit_delimiter_rbsp( )
10     End of sequence                                                non-VCL序列结尾 end_of_seq_rbsp( )
11     End of stream                                                  non-VCL流结尾end_of_stream_rbsp( )
12     Filler data                                                    non-VCL填充数据filler_data_rbsp( )
13     Sequence parameter set extension                               non-VCL序列参数集扩展seq_parameter_set_extension_rbsp( )
14     Prefix NAL unit                                                non-VCLNAL 单元前缀
15     Subset sequence parameter set                                  non-VCL子集序列参数集
16     Depth parameter set                                            non-VCL深度参数集
17..18 Reserved                                                       non-VCL保留
19     Coded slice of an auxiliary coded picture without partitioning non-VCL未分割的辅助编码图像的编码条带slice_layer_without_partitioning_rbsp( )
20     Coded slice extension                                          non-VCL编码切片扩展
21     Coded slice extension for depth view components                non-VCL深度视图组件的编码切片扩展
22..23 Reserved                                                       non-VCL保留
24..31 Unspecified                                                    non-VCL未定义

这里只是将之前的博客弄了一部分过来,请完全阅读。

从一个avpacket中获取 NALU,解析NALU头部。

我们这里从传递的avpacket中获取NALU,并获取头部。要研究的是通过 h264编码器后,avpacket中NALU 的头部信息,看是否发送了 PPS 和 SPS 等重要信息。

如下代码中打印的 nal_unit_type 就是每个NALU 头部字节的后5位,得到这个值就可以对比5,6,7,8,看发送的是啥,有没有发送PPS,SPS等。

	///通过h264编码器后的avpacket,解析avpacket里面的NALU///第一个问题是 如何从 avpacket如何分离出 每个 NALU呢?/// 一个avpacket 的NALU  和 下一个avpacket 的NALU 是以 0001间隔/// 但是一个avpacket中是有多个 NALU组成的,一个avpacket之内是以 001间隔的。avpacketcount++;//计算总共有多少个avpacketunsigned char naluheader = *(avpacket->data + 4);//跳过0001个字节/// naluheader这一个字节 8位是这样的:第一位是禁用位; 2,3位表示该NALU的重要性,4-7位标识是个啥类型的NALU:SPS,PPS,IDR 等,int nal_unit_type = naluheader & 0X1F;cout << "   nal_unit_type = " << nal_unit_type;//然后呢一个 avpacket中可能有多个 NALU,以001间隔开的,还需要找到这些头部for (int i = 4; i < avpacket->size - 4; i++) //一个data中由多条nalu{if (avpacket->data[i] == 0 &&avpacket->data[i + 1] == 0 &&avpacket->data[i + 2] == 1) {   ///001nal_unit_type = avpacket->data[i + 3] & 0x1f;avpacketcount++;cout << "(" << nal_unit_type << ")" << flush;}}

相关文章:

FFmpeg 4.3 音视频-多路H265监控录放C++开发十三.2:avpacket中包含多个 NALU如何解析头部分析

前提&#xff1a; 注意的是&#xff1a;我们这里是从avframe转换成avpacket 后&#xff0c;从avpacket中查看NALU。 在实际开发中&#xff0c;我们有可能是从摄像头中拿到 RGB 或者 PCM&#xff0c;然后将pcm打包成avframe&#xff0c;然后将avframe转换成avpacket&#xff0…...

【MATLAB】目标检测初探

文章目录 0 前言1 目标检测概述2 算法实践2.1 YOLO v22.2 YOLO v3 3 项目实践3.1 项目背景和数据集3.2 实践结果3.3 算法对比 4 工具箱与数据标注5 总结 0 前言 之前因为项目原因&#xff0c;做了一个基于YOLOv5实现目标检测的程序&#xff0c;是基于Python做的&#xff0c;直接…...

SpringCloud 微服务消息队列灰度方案 (RocketMQ 4.x)

目录 背景遇到的问题 RocketMQ 基础基础消息模型扩展后的消息模型部署模型相关概念点 方案对比影子Topic的方案Tag的方案UserProperty的方案影子Group的方案灰度分区的方案方案对比 灰度分区方案设计适配只有部分灰度的情况所做的功能扩展消费者&#xff08;无灰度&#xff09;…...

厘清标准差和标准误:因果推断的统计学基础

标准差&#xff0c;指 一次抽样中 个体取值间的离散程度&#xff0c;反映了 个体取值对样本均值的代表性。 标准误&#xff0c;指 多次抽样中 样本均值间的离散程度&#xff0c;反映了 样本均值对总体均值的代表性。 公众号原文-厘清标准差和标准误&#xff1a;因果推断的统计…...

GESP4级考试语法知识(贪心算法(二))

排队接水2代码&#xff1a; #include<iostream> #include<cstdio> #include<algorithm> using namespace std; struct people {int num;int time; }; people s[1001]; int n,r,a[1001]; double sum,ave; bool cmp(people x,people y) {return x.time<y.t…...

MATLAB 使用教程 —— 命令窗口输入命令,工作区显示变量

命令在命令窗口输入变量在工作区显示 MATLAB 桌面包含的面板如下&#xff1a; 当前文件夹 - 此面板允许访问项目文件夹和文件。命令窗口 - 这是主要区域&#xff0c;用户在命令行中输入命令&#xff0c;命令提示符(>>).工作区 - 工作区显示所有变量&#xff0c;无论是创…...

LeetCode 热题100(八)【二叉树】(3)

目录 8.11二叉树展开为链表&#xff08;中等&#xff09; 8.12从前序与中序遍历序列构造二叉树&#xff08;中等&#xff09; 8.13路径总和III&#xff08;中等&#xff09; 8.14二叉树的最近公共祖先&#xff08;中等&#xff09; 8.15二叉树中的最大路径和&#xff08;困…...

uniapp h5实现录音

使用npm安装 npm install recorder-core引入Recorder库 可以使用import、require、html script等你适合的方式来引入js文件&#xff0c;下面的以import为主要参考&#xff0c;其他引入方式根据文件路径自行调整一下就可以了。 //必须引入的Recorder核心&#xff08;文件路径是…...

字节跳动Android面试题汇总及参考答案(80+面试题,持续更新)

Android 四大组件是什么? Android 四大组件分别是 Activity、Service、Broadcast Receiver 和 Content Provider。 Activity 是 Android 应用中最基本的组件,用于实现用户界面。它可以包含各种视图控件,如按钮、文本框等。一个 Activity 通常对应一个屏幕的内容。用户可以通…...

【go从零单排】通道select、通道timeout、Non-Blocking Channel Operations非阻塞通道操作

&#x1f308;Don’t worry , just coding! 内耗与overthinking只会削弱你的精力&#xff0c;虚度你的光阴&#xff0c;每天迈出一小步&#xff0c;回头时发现已经走了很远。 &#x1f4d7;概念 select 语句是 Go 的一种控制结构&#xff0c;用于等待多个通道操作。它类似于 s…...

PSRR仿真笔记

1.首先打开bandgap的testbench电路&#xff0c;选择schematic 2.打开电路后,选择VDD模块&#xff0c;然后按键盘Q&#xff0c;进行编辑&#xff0c;将AC magnitude改为1 V 3.修改完成后&#xff0c;点击左上角Launch > ADE Explorer 4.在出现的窗口中&#xff0c;选择Creat…...

AUTOSAR_EXP_ARAComAPI的7章笔记(3)

☞返回总目录 相关总结&#xff1a;AutoSar AP简单多绑定总结 7.3 多绑定 如在 5.4.3 小节中简要讨论的&#xff0c;某个代理类 / 骨架类的不同实例之间的技术传输是不同的&#xff0c;多绑定描述了这种情况的解决方案。多种技术原因都可能导致这种情况出现&#xff1a; 代…...

WSADATA 关键字详细介绍

WSADATA 是 Windows Sockets API&#xff08;Winsock&#xff09;中用于存储 Winsock 库的初始化信息的结构体。在使用 Winsock API 之前&#xff0c;必须通过调用 WSAStartup() 函数进行初始化&#xff0c;WSADATA 结构体用于接收有关 Winsock 库版本的信息。Winsock 是 Windo…...

Day44 | 动态规划 :状态机DP 买卖股票的最佳时机IV买卖股票的最佳时机III

Day44 | 动态规划 &#xff1a;状态机DP 买卖股票的最佳时机IV&&买卖股票的最佳时机III&&309.买卖股票的最佳时机含冷冻期 动态规划应该如何学习&#xff1f;-CSDN博客 本次题解参考自灵神的做法&#xff0c;大家也多多支持灵神的题解 买卖股票的最佳时机【…...

Area-Composition模型部署指南

一、介绍 本模型可以通过输入不同的提示词&#xff0c;然后根据各部分提示词进行融合生成图片。如下图&#xff1a; 此图像包含 4 个不同的区域&#xff1a;夜晚、傍晚、白天、早晨 二、部署 环境要求&#xff1a; 最低显存&#xff1a;10G 1. 部署ComfyUI 本篇的模型部署…...

策略模式、状态机详细解读

策略模式 (Strategy Pattern) 策略模式 (Strategy Pattern) 是一种行为型设计模式&#xff0c;旨在将一组算法封装成独立的类&#xff0c;使得它们可以相互替换。这种模式让算法的变化不会影响到使用算法的客户&#xff0c;减少了类之间的耦合。策略模式通常用于处理一类问题&…...

OpenWrt广播DNS到客户端

OpenWrt广播DNS到客户端 Network -> Interfaces -> lan ->DHCP Server -> Advanced Settings -> DHCP-Options 设置 6,dns1,dns2 如下图 也可以直接编辑 /etc/config/dhcp config dhcp lan list dhcp_option 6,119.29.29.29,223.5.5.5 #ipv4 option dns 2402:4…...

C++编程技巧与规范-类和对象

类和对象 1. 静态对象的探讨与全局对象的构造顺序 静态对象的探讨 类中的静态成员变量(类类型静态成员) 类中静态变量的声明与定义&#xff08;类中声明类外定义&#xff09; #include<iostream> using namespace std;namespace _nmspl {class A{public:A():m_i(5){…...

AutoHotKey自动热键AHK-正则表达式

在这个软件的操作中,基本都是需要即时的解决一些问题,所以对字符串的操作是比较多的,所以正则的使用还是比较重要的,接下来我们用一个例子来了解正则表达式的使用 str "7654321" RegExMatch(str, "65(43)(21)", SubPat)str ( str %str% SubPat %SubPa…...

【3D Slicer】的小白入门使用指南四

开源解剖影像浏览工具Open Anatomy Browser使用及介绍 和3D slicer米有太大关系,该工具是网页版影像数据的浏览工具(可以简单理解为网页版的3D slicer) 介绍 ● 开放解剖(OA)浏览器是由神经影像分析中心开发的,基于网络浏览器技术构建的图谱查看器。 ● OA浏览器将解剖模…...

使用docker在3台服务器上搭建基于redis 6.x的一主两从三台均是哨兵模式

一、环境及版本说明 如果服务器已经安装了docker,则忽略此步骤,如果没有安装,则可以按照一下方式安装: 1. 在线安装(有互联网环境): 请看我这篇文章 传送阵>> 点我查看 2. 离线安装(内网环境):请看我这篇文章 传送阵>> 点我查看 说明&#xff1a;假设每台服务器已…...

最新SpringBoot+SpringCloud+Nacos微服务框架分享

文章目录 前言一、服务规划二、架构核心1.cloud的pom2.gateway的异常handler3.gateway的filter4、admin的pom5、admin的登录核心 三、code-helper分享总结 前言 最近有个活蛮赶的&#xff0c;根据Excel列的需求预估的工时直接打骨折&#xff0c;不要问我为什么&#xff0c;主要…...

python执行测试用例,allure报乱码且未成功生成报告

allure执行测试用例时显示乱码&#xff1a;‘allure’ &#xfffd;&#xfffd;&#xfffd;&#xfffd;&#xfffd;ڲ&#xfffd;&#xfffd;&#xfffd;&#xfffd;ⲿ&#xfffd;&#xfffd;&#xfffd;Ҳ&#xfffd;&#xfffd;&#xfffd;ǿ&#xfffd;&am…...

LeetCode - 199. 二叉树的右视图

题目 199. 二叉树的右视图 - 力扣&#xff08;LeetCode&#xff09; 思路 右视图是指从树的右侧看&#xff0c;对于每一层&#xff0c;只能看到该层最右边的节点。实现思路是&#xff1a; 使用深度优先搜索(DFS)按照"根-右-左"的顺序遍历树记录每个节点的深度对于…...

深入浅出深度学习基础:从感知机到全连接神经网络的核心原理与应用

文章目录 前言一、感知机 (Perceptron)1.1 基础介绍1.1.1 感知机是什么&#xff1f;1.1.2 感知机的工作原理 1.2 感知机的简单应用&#xff1a;基本逻辑门1.2.1 逻辑与 (Logic AND)1.2.2 逻辑或 (Logic OR)1.2.3 逻辑与非 (Logic NAND) 1.3 感知机的实现1.3.1 简单实现 (基于阈…...

基于IDIG-GAN的小样本电机轴承故障诊断

目录 🔍 核心问题 一、IDIG-GAN模型原理 1. 整体架构 2. 核心创新点 (1) ​梯度归一化(Gradient Normalization)​​ (2) ​判别器梯度间隙正则化(Discriminator Gradient Gap Regularization)​​ (3) ​自注意力机制(Self-Attention)​​ 3. 完整损失函数 二…...

【安全篇】金刚不坏之身:整合 Spring Security + JWT 实现无状态认证与授权

摘要 本文是《Spring Boot 实战派》系列的第四篇。我们将直面所有 Web 应用都无法回避的核心问题&#xff1a;安全。文章将详细阐述认证&#xff08;Authentication) 与授权&#xff08;Authorization的核心概念&#xff0c;对比传统 Session-Cookie 与现代 JWT&#xff08;JS…...

VSCode 使用CMake 构建 Qt 5 窗口程序

首先,目录结构如下图: 运行效果: cmake -B build cmake --build build 运行: windeployqt.exe F:\testQt5\build\Debug\app.exe main.cpp #include "mainwindow.h"#include <QAppli...

Qt的学习(二)

1. 创建Hello Word 两种方式&#xff0c;实现helloworld&#xff1a; 1.通过图形化的方式&#xff0c;在界面上创建出一个控件&#xff0c;显示helloworld 2.通过纯代码的方式&#xff0c;通过编写代码&#xff0c;在界面上创建控件&#xff0c; 显示hello world&#xff1b; …...

用鸿蒙HarmonyOS5实现国际象棋小游戏的过程

下面是一个基于鸿蒙OS (HarmonyOS) 的国际象棋小游戏的完整实现代码&#xff0c;使用Java语言和鸿蒙的Ability框架。 1. 项目结构 /src/main/java/com/example/chess/├── MainAbilitySlice.java // 主界面逻辑├── ChessView.java // 游戏视图和逻辑├── …...