网上开源的RTP库普遍采用C++编写,主要有CCRtp库和JRtplib库,这两个库baidu搜索jrtplib量非常大,感觉国内大部分采用 JRtplib 而用google搜索CCRtp比较多,但是jrtplib也不少。还有oRTP以c 作为编程语言, 多媒体处理可以直接采用ffserver中的处理,非常简单。Mplayer中使用Live555库。

以前练习时用过jrtplib,现在的项目使用oRTP。

最近使用RTP传语音,使用的是ortp协议栈,没想到在接收的时候收不到数据包,调了半天也没有结果,一怒之下索性废掉了ortp,直接实现rtp。

老实说,自己实现rtp还是比较简单的。分为接收和发送,接收的时候直接去掉12个字节的报头,然后向下送。而发送的时候稍微麻烦点,我的实现手法如下:

初始化报头:
      char rtppacket[172] = {0x80, 0x08};//PCMA 0x08 PCMU 0x00
srand((int)time(0));
unsigned short seq = 0, tmp = 0;
unsigned int timestamp = htonl(0);
unsigned int ssrc = htonl(rand());

memcpy(rtppacket+ 4, &timestamp, 4);
memcpy(rtppacket+ 8, &ssrc, 4);

发送报文(在一个循环中):
memcpy(rtppacket+ 2, &tmp, 2);
seq++;
tmp = htons(seq);
memcpy(rtppacket+ 12, &voicedata, 160);
直接UDP send报文。

在这里面,timestamp是我全部赋值为0的,并且这个实现是只能承载G711A。但是在ZTE的网关上运行正常。实际测试的时候,使用ADSL上行 的网络,从上海打到香港的VOIP电话,比在深圳用skype打过去还要清晰,效果让人振奋。(应该是网络的条件非常好,个人估计大部分路径都是走的电路 交换)

效果是基本实现了,但是又来了一个疑问,既然这么简单就可以实现rtp的功能,那么怎么会需要100多页的RFC3550,又何必需要ortp那么多的代码呢?

仔细看了一下ortp的介绍,来自linephone:

Written in C, works under Linux (and probably any Unix) and Windows. Implement the RFC3550 (RTP) with a easy to use API with high and low level access. Includes support for multiples profiles, AV profile (RFC3551) being the one by default. Includes a packet scheduler for to send and recv packet "on time", according to their timestamp. Scheduling is optionnal, rtp sessions can remain not scheduled. Supports mutiplexing IO, so that hundreds of RTP sessions can be scheduled by a single thread. Features an adaptive jitter algorithm for a receiver to adapt to the clockrate of the sender. Supports part of RFC2833 for telephone events over RTP. The API is well documented using gtk-doc. Licensed under the Lesser Gnu Public License. RTCP messages sent periodically since 0.7.0 (compound packet including sender report or receiver report + SDES) Includes an API to parse incoming RTCP packets.

从以上介绍可以看出,ortp所标榜的是:多种RTP格式支持;发送接收的实时调度;单线程支持多路媒体流;自适应的缓冲区算法;实现了RTCP。

既然是Opensource,那么我们就来一个个的看它的实现。

首先是多种RTP格式支持

ortp有一个RtpProfile的全局变量,该变量在ortp初始化的时候赋值,该变量中有一个PayloadType的数组,每个PayloadType对应一种媒体流,PayloadType中包含了媒体流的特性,包括名称,采样率,声音位数,静音格式,占用带宽等。这些定义都在avprofile.c中。

其中的几个参数中,采样率用的比较多,主要用来计算实时性,还有就是计算jitter。

发送接收的实时调度

ortp中发送和接收主要是两个函数rtp_session_send_with_ts和rtp_session_recv_with_ts。以 rtp_session_recv_with_ts为例:内部接收数据使用的是rtp_session_recvm_with_ts,首先,会接收所有 scoket上的数据,然后将rtp包存放在一个队列之中,一系列处理之后,有一个pthread_mutex_lock的线程锁,将线程锁住。此时,由 rtp_scheduler_schedule线程进行调度(该线程在协议栈初始化)时创建。rtp_scheduler_schedule会遍历所有的 media session(媒体流),然后判断其中的timestamp(时间戳),如果计算的时间到达,则让rtp_session_recvm_with_ts 继续处理。

时间戳的算法是以第一个打到的rtp数据包为准,然后根据其中的时间,进行推算。假如第一个包是10点整来的,然后ptime又是20ms,那么下一个包的时间就是10点又20毫秒。

media session是一个RtpSession对象,包含多种属性和方法。RtpScheduler中包含一个RtpSession的队列,用来支持多媒体流。

值得一提的是,rtp_scheduler_schedule中有一个独特的"sleep",该sleep可以停顿10ms。并且这个时间是绝对的,如果 中间因为处理或者其他原因延迟了2ms,那么这个sleep停顿的就是8ms。具体函数可以看一下posixtimer.c中的 posix_timer_do实现。精确的计时使用select,精确时间的取得很多使用gettimeofday这个函数,该函数在精确计时的时候非常 有用。

单线程支持多路媒体流

对外是有一个sessionset,完全模拟了select的做法,对外提供的接口,也和标准select几乎一样。主要的处理实现,还是在rtp_scheduler里面完成。模拟select的唤醒,使用了pthread_cond_wait。

自适应的缓冲区算法

主要的实现都在jitterctl.c里面,也不算很复杂,没有太仔细看。从注释中看到算法如下:
      The algorithm computes two values:
slide: an average of difference between the expected and the socket-received timestamp
jitter: an average of the absolute value of the difference between socket-received timestamp and slide.
slide is used to make clock-slide detection and correction.

RTCP的实现

rtcp是不算很复杂的东西。ortp中,在RtpSession里面,即包含了rtcp的一些相关属性。需要的时候,直接取出然后组包发送就可以了。不过还要涉及到SDES,东西倒也是不少。

后记

大概读了一下ortp,一共大约14K的代码量,确实算是一款优秀的作品,作者对于线程,实时性的一些处理,都相当的深入。对于数据结构的组织,也非常不 错,大部分数据,均适用了自己的封装。采用了链表的结构,声明在str_utils.h里面,这些数据结构的具体使用,就没有太仔细看了。

读完以后,再回头看看自己的项目,确实没有必要用ortp这样的“庞然大物”了:多种rtp格式?我只需要G711A;实时性?我有底层硬件保证了;多路 媒体流?不需要,我只要VOIP语音;自适应的jitter?也不用,底层硬件有保证;至于RTCP,不是必须项,也可以不要。在单用途的终端上,协议栈 的实现可以简化非常多。

最后感叹一下,老外的计算机水平确实比国内高出很多。我看的这份ortp的实现,设计,实现几近炉火纯青,方方面面考虑周详仔细,并且实现了Linux平 台和Windows平台的通用。显示在程序结构,数据组织,操作系统,网络协议方面不凡的功力。国内程序员,写程序很多是为了混口饭,不会去精益求精,能 实现功能,就已经很不错,是老板眼中的红人。国内写代码要达到ortp这样的艺术水准,还有非常长的路要走。

附:ortp版本为0.13.1,下载地址为:http://download.savannah.gnu.org/releases/linphone/ortp/sources/

ORTP协议栈【ZT】相关推荐

  1. oSIP协议栈(及eXoSIP、Ortp等)使用入门

    http://ghj19850926.blog.163.com/blog/static/18591560201241410033429/ 一直没空仔细研究下oSIP,最近看到其版本已经到了3.x版本, ...

  2. oSIP协议栈(及eXoSIP、Ortp等)使用入门(转)

    oSIP协议栈(及eXoSIP.Ortp等)使用入门(转) 转自http://mbstudio.spaces.live.com/blog/cns!C898C3C40396DC11!955.entry ...

  3. oSIP协议栈(及eXoSIP,Ortp等)使用入门

    http://blog.csdn.net/lhsxsh/article/details/4593908 文档最新版本及文中提到的相关源码及VC6工程文件请在本站找,嘿嘿~~ (首页的SkyDriver ...

  4. ortp流媒体协议 [1]

    http://blog.csdn.net/flyhawk007j2me/article/details/6830354 RTP(Real-time transport Protocol)用于在网路上多 ...

  5. [ZT]640-801中文读书笔记

    [原创]640-801中文读书笔记 作者:红头发 03-22-2004                               打包下载 Noko#sh run ! Written by 红头发 ...

  6. 2021年大数据ELK(一):集中式日志协议栈Elastic Stack简介

    全网最详细的大数据ELK文章系列,强烈建议收藏加关注! 新文章都已经列出历史文章目录,帮助大家回顾前面的知识重点. 目录 系列历史文章 一.简介 二.ELK 协议栈介绍及体系结构 三.集中式日志协议栈 ...

  7. mac 思科 链路聚合_TCP/IP协议栈-之-数据链路层分析

    数据链路层 一.数据链路层的概述 1.1 概述 数据链路层是TCP/IP协议栈的第二层! 数据链路层的传输单元:帧(也就是传输单位) 1.2 帧结构 帧结构分析如下: 帧结构的构成:MAC子层 + 上 ...

  8. TCP/IP 协议栈4层结构及3次握手4次挥手

    TCP/IP 协议栈是一系列网络协议的总和,是构成网络通信的核心骨架,它定义了电子设备如何连入因特网,以及数据如何在它们之间进行传输.TCP/IP 协议采用4层结构,分别是应用层.传输层.网络层和链路 ...

  9. Linux TCP/IP协议栈笔记

    数据包的接收 作者:kendo Kernel:2.6.12 一.从网卡说起 这并非是一个网卡驱动分析的专门文档,只是对网卡处理数据包的流程进行一个重点的分析.这里以Intel的e100驱动为例进行分析 ...

最新文章

  1. Java学习总结:42(字节流和字符流)
  2. 收藏 | 提高数据处理效率的 Pandas 函数方法
  3. 剑指offer 24:二叉搜索树的后序遍历序列
  4. 听李宏毅点评GPT-3:来自猎人暗黑大陆的模型
  5. 【整理】SYSCOMMAND的wParam值的宏定义
  6. QTableView中修改某个单元格或者行或者列内容颜色
  7. 制度化规范化标准化精细化_精细化管理ORTCC模型在管理中的运用(下)
  8. zookeeper基本原理及适用场景 转:http://blog.chinaunix.net/uid-26748613-id-4536290.html
  9. 手写自己的MyBatis框架-Configuration
  10. 网站维护页面_营销型企业网站有哪些功能?
  11. TensorFlow7-多元线性回归模型
  12. [MFC]关于Visual studio 2012的AfxGetMainWnd
  13. 如何在PHP7中安装mysql的扩展
  14. 【重识云原生】第四章云网络第二节——相关基础知识准备
  15. relocation R_ARM_THM_MOVW_ABS_NC against `a local symbol' can not be used when making a shared objec
  16. python抓取豆瓣电影
  17. 公司最大的内卷,是“管理错位”
  18. 信息系统安全等级保护(简称“等保”)
  19. 解决笔记本电脑外接显示器后声音播放不了的问题
  20. 《三体》中的经典名句

热门文章

  1. MTK 驱动开发(18)---LCD 参数理解
  2. Java中的时间和日期(下)
  3. php程序yii是什么意思,yii是啥意思?
  4. 都是套路!HR谈及薪资时的12种套路
  5. ARM, MIPS, Power PC
  6. 马斯克:大部分人没必要活那么长!活太久会让社会“陷入窒息”
  7. 大动作!今日头条、西瓜视频并入抖音,字节梁汝波正式接任CEO
  8. 滴滴否认柳青计划卸任:目前正积极全面配合网络安全审查
  9. 苹果也开始打价格战了
  10. 马斯克发全员信 呼吁员工6月底全力以赴