blackstar

V1

2023/04/28阅读:61主题:默认主题

RTP数据包剖析和实践

网络中的RTP数据包

我们使用ffmpeg命令行工具推送一个RTP流,通过Wirshark工具抓包可以看到RTP数据包的结构如下:

那么,数据包中的这些字段分别表示什么含义呢?在实际应用中又该注意哪些问题呢?

RTP数据包组成

RTP固定头

  • V:version,标识RTP版本号,占2位;目前RFC 3350规定的版本号为2
  • P:padding,填充位,占1位;当该字段设置为1RTP数据包的末尾包含一个字节的填充数据,该数据不是有效载荷(见下文)的一部分,在解析的时候应该忽略。某些具有固定块大小的加密算法或在较低层协议数据单元中承载多个RTP数据包可能需要填充。
  • X:extension,扩展位,占1位;当该字段设置为1RTP固定头后必须紧跟一个扩展头(见下文)。
  • CC:RTP固定头后面SSRC标识符的数量,占4位。
  • M:marker,占1位,由不同有效载荷类型说明。用来标记诸如帧边界之类的重要事件。例如:对于视频,标记一帧的结束;对于音频,标记会话的开始。
  • PT:playload type,RTP有效载荷类型,占7位;RFC 3551中定义了一组音频和视频的类型(见下文)。
  • timestamp:RTP数据包采样点时间戳,占32位;标准中规定,该采样时间戳必须从时间上单调线性递增的时钟中计算出来;第一个数据包的时间戳应该是随机值,后面的包时间戳按照采样频率递增(见下文)。
  • SSRC:同步源标识,占32位;随机选择该标识,确保同一RTP会话中的两个同步源不会相同;
  • CSRC:标识此数据包中包含的有效负载的贡献源标识列表,表最多有15项,每项占32位;主要用于混音器产生数据。

RTP扩展头

RTP协议提供一种扩展机制,以允许单个实现试验新的有效载荷格式的独立的功能,这些功能需要在RTP数据包报头中携带附加信息。相关扩展头信息格式如下:

  • defined by profile:由配置文件定义,占2个字节。
  • length:扩展信息头字节数,占2个字节。

有关RTP扩展头机制详情,可参考RFC 8285

RTP有效载荷

RTP在流媒体传输协议中常用的有效载荷数据流有两类:

  • 音频流
  • 视频流

RFC 3551中规定了音频和视频流的有效载荷格式的技术参数。

有效载荷类型定义:

  • 静态有效负载类型,PT值范围:0~95。
  • 动态有效载荷类型,PT值范围:96~127。

音视频的RTP时间戳频率

RFC 3551中规定了音频和视频的RTP时间戳频率的参数要求,其中:

  • 音频的RTP时间戳频率:一般采用音频自身采样率,例如:8000、11025、16000、22050、24000、32000、44100和48000 Hz;但是也有例外,在实际运用中需要参考规范要求。
  • 视频的RTP时间戳频率:固定90000Hz频率。

常见音频有效载荷格式的技术参数

有效载荷类型 编码名称 通道数 时钟频率 参考 描述
0 PCMU 1 8000 RFC 3551 ITU-T G.711 PCM μ-Law audio
8 PCMA 1 8000 RFC 3551 ITU-T G.711 PCM A-Law audio
动态或配置 opus 1,2 48000 RFC 7587 Opus audio
动态或配置 MP4A-LATM 90000或其他 RFC 6416 MPEG-4 Audio(包括AAC)
动态或配置 L24 1,2,3,4... 44100,48000,... RFC 3190 Linear PCM 24-bit audio

常见视频有效载荷格式的技术参数

有效载荷类型 编码名称 时钟频率 参考 描述
26 JPEG 90000 RFC 2435 JPEG video
动态或配置 H264 AVC 90000 RFC 6184, previously RFC 3984 H.264 video (MPEG-4 Part 10)
动态或配置 H264 SVC 90000 RFC 6190 H.264 video
动态或配置 H265 90000 RFC 7798 H.265 video (HEVC)
动态 VP8 90000 RFC 7741 VP8 video
动态 VP9 90000 Draft VP9 video

RTP数据包封装格式

一个完整的RTP数据包由如下部分组成:

  • RTP Fixed Header
  • RTP Extension Header
  • Playload
  • RTP Padding

包格式如下:

一般情况下,RTP数包不包含RTP Extension HeaderRTP Padding,即:RTP固定头中的XP标识为0。包格式如下:

RTP时间戳计算

RFC 3551中规定了音频和视频的RTP时间戳频率的参数要求,那么如何根据音视频参数计算出每帧音视频的RTP时间戳?

概念

时间戳:是用时钟频率计算而来表示的时间。

时间戳增量:相邻两个RTP包之间的时间差。

采样率:一秒钟的样本数,一般描述音频。例如:48000HZ,表示1秒钟有48000个样本。

帧率:一秒钟传输的视频帧数,一般描述视频。例如:25FPS,表示每秒钟传输25帧视频图像。

包时间:一个RTP包的毫秒数。例如:48000HZ音频数据,1秒钟传输1000帧,包时间为1000 / 1000 = 1ms;25FPS视频帧,包时间为1000 / 25 = 40ms。

音频的RTP时间戳

公式推导

1.Frames = 1000 / PacketTime
 
2.TimestampInc = Samplerate / Frames
 
3.Timestamp(n) = T0 + TimestampInc * (n - 1)

==> Timestamp(n) = T0 + (Samplerate*  PacketTime / 1000) * (n - 1)

举个例子

编码为L24,采样率为48000Hz,包时间为1ms的`RTP`流,每帧的`RTP`包时间戳计算如下:

1. 帧数:1000 / 1 = 1000。
2. 时间戳增量:48000 / 1000 = 48。
3. Timestamp(n) = T0 + 48 * (n - 1)。

第一帧(A1):T0

第二帧(A2): T0 + 48

第三帧(A3):T0 + 48 * 2

... ...

第1000帧(A1000):T0 + 48 * 999

视频的RTP时间戳

公式推导

1.TimestampInc = Samplerate / FPS
 
2.Timestamp(n) = T0 + TimestampInc * (n - 1)
 
==> Timestamp(n) = T0 + (Samplerate/ FPS) * (n - 1)

举个例子

帧率为25FPS的`RTP`视频流,每帧的`RTP`包时间戳计算如下:

1. 帧数:25
2. 包时间:1000 / 25 = 40
3. 时间戳增量:90000 / 40 = 2250
4. Timestamp(n) = T0 + 2550 * (n - 1)

第一帧(P1):T0

第二帧(P2):T0 + 2250

第三帧(P3):T0 + 2250 * 2

... ...

第25帧(P25):T0 + 2250 + 24

案例实践

L24音频流的RTP有效载荷格式

RFC 3190规定了使用RTP封装12位非线性、20位线性和24位线性音频数据流的打包方案,以及SDP参数格式。下面,我们主要介绍24位线性音频数据流的打包方案

L24编码

L24是24位线性音频有效负载格式被赋予编码名称。它的SDP音频媒体描述示例如下:

 m=audio 49230 RTP/AVP 99 100
 a=rtpmap:100 L24/48000

L24打包

RFC 3551中对L16的描述是:L16表示未压缩的音频数据样本,使用16位有符号表示,范围从-32768~32767。该值以2的补码表示,并以网络字节顺序传输。

RFC 3190中的描述是:L24线性编码只是L16线性音频编码的扩展。24位未压缩音频数据样本以2的补码表示法表示有符号值。样本以最高有效位开始连续打包到有效负载八位字节中。

上述描述翻译就是:

  • 未压缩的线性PCM音频数据
  • 以网络字节顺序传输,即大端存储

那么,RTP中的L24封装格式:

其中,2通道L24的数据格式:

一般每帧的音频包数据比较小,不进行分包处理,所以RTPMarker标志位设置是0

使用SDP文件播放RTP流

启动一个RTP推流端,我们该如何拉取这个RTP流呢?没错,就是SDP协议,它描述了RTP流中对应媒体信息的参数,拉流端需要先进行媒体参数的解析。有关SDP协议,可参考相关的RFC。下面结合之前的学习到的知识,编写一个L24编码格式的RTP推流端,使用FFMPEG命令行拉流。

启动RTP推流端

通过抓包,我们可以看到RTP包间隔是480

编写SDP会话描述协议文件L24.sdp

v=0
o=- 0 0 IN IP4 127.0.0.1
s=No Name
m=audio 5004 RTP/AVP 96 
a=rtpmap:96 L24/48000/1
c=IN IP4 239.69.5.2 

执行 ffplay命令拉流

ffplay -protocol_whitelist 'rtp,file,udp' L24.sdp

弹出一个播放窗口,拉流播放音频

以上是作者根据实践应用中对RTP数据包的一些理解,进行归纳总结,希望对了解RTP的同学有一定帮助。

参考文献

分类:

后端

标签:

C++

作者介绍

blackstar
V1

一个常年混迹于摸鱼网站的码农