Chinaunix首页 | 论坛 | 博客
  • 博客访问: 9463786
  • 博文数量: 1750
  • 博客积分: 12961
  • 博客等级: 上将
  • 技术积分: 20091
  • 用 户 组: 普通用户
  • 注册时间: 2009-01-09 11:25
个人简介

偷得浮生半桶水(半日闲), 好记性不如抄下来(烂笔头). 信息爆炸的时代, 学习是一项持续的工作.

文章分类

全部博文(1750)

文章存档

2024年(26)

2023年(26)

2022年(112)

2021年(217)

2020年(157)

2019年(192)

2018年(81)

2017年(78)

2016年(70)

2015年(52)

2014年(40)

2013年(51)

2012年(85)

2011年(45)

2010年(231)

2009年(287)

分类: Android平台

2015-05-08 17:45:28

http://blog.csdn.net/fhxpp_27/article/details/9234069

ubuntu下jthread 和jrtplib的安装
http://blog.csdn.net/chenyu123123/article/details/8743362

一、简述

RTP 是目前解决流媒体实时传输问题的最好办法,而JRTPLIB 是一个用C++语言实现的RTP库,包括UDP通讯。刚使用JRTPLIB,对JRTPLIB的理解还不够深,当做使用时,积累的一些经验写个笔记吧。

二、RTP协议

实时传送协议(Real-time Transport Protocol或简写RTP,也可以写成RTTP)是一个网络传输协议,RTP协议详细说明了在互联网上传递音频和视频的标准数据包格式。它一开始被设计为一个多播协议,但后来被用在很多单播应用中。RTP协议常用于流媒体系统(配合RTCP协议或者RTSP协议)。因为RTP自身具有Time stamp所以在ffmpeg 中被用做一种formate。

RTP协议的详细介绍,请参考这篇文章

三、RTPSession类

这里不介绍jrtplib的编译安装,这个很简单,网上很多地方都有讲解。

jrtplib的使用中,主要是围绕这个类来实现的,因此大家有必要去查看源码,看这类的实现。为了方便使用,我在这做了RTPSession的继承封装,下面直接贴代码了。

RTPSessionUtils.h

  1. #include "rtpsession.h"  
  2. #include "rtppacket.h"  
  3. #include "rtpudpv4transmitter.h"  
  4. #include "rtpipv4address.h"  
  5. #include "rtpsessionparams.h"  
  6. #include "rtperrors.h"  
  7. #ifndef WIN32  
  8. #include   
  9. #include   
  10. #else  
  11. #include   
  12. #endif // WIN32  
  13. #include "rtpsourcedata.h"  
  14. #include   
  15. #include   
  16. #include   
  17. #include   
  18.   
  19. //jrtplib应用需链接的lib  
  20. #pragma comment(lib,"ws2_32.lib")  
  21. #pragma comment(lib, "jrtplib_d.lib")  
  22. #pragma comment(lib,"jthread_d.lib")  
  23.   
  24. namespace jrtplib  
  25. {  
  26.     class RTPSessionUtils : public RTPSession  
  27.     {  
  28.         typedef RTPSession base_type;  
  29.     public:  
  30.         RTPSessionUtils();  
  31.         ~RTPSessionUtils();  
  32.   
  33.         int AddDestination(const std::string& ip, uint16_t port);  
  34.         int DeleteDestination(const std::string& ip, uint16_t port);  
  35.         int CreateDefault(uint16_t port);  
  36.     protected:  
  37.         void OnNewSource(RTPSourceData *dat);  
  38.         void OnBYEPacket(RTPSourceData *dat);  
  39.         void OnRemoveSource(RTPSourceData *dat);  
  40.         void OnRTPPacket(RTPPacket *pack,const RTPTime &receivetime,  
  41.             const RTPAddress *senderaddress);  
  42.         void OnRTCPCompoundPacket(RTCPCompoundPacket *pack,const RTPTime &receivetime,  
  43.             const RTPAddress *senderaddress);  
  44.         void OnPollThreadStep();  
  45.     private:  
  46.         int GetAddrFromSource(RTPSourceData *dat, uint32_t& ip, uint16_t& port);  
  47.     };  
  48. }  
  49.   
  50. //整形的ip转成字符串ip  
  51. static std::string IPToString(const unsigned int iIP)  
  52. {  
  53.     struct in_addr inaddr;  
  54.     inaddr.s_addr = htonl(iIP);  
  55.     return std::string(inet_ntoa(inaddr));  
  56. }  
  57.   
  58. //字符串ip转成整形ip  
  59. static unsigned int IPToInt(const std::string& sIP)  
  60. {  
  61.     return inet_addr(sIP.c_str());  
  62. }  

RTPSessionUtils.cpp


  1. #include "RTPSessionUtils.h"  
  2.   
  3. namespace jrtplib{  
  4.     RTPSessionUtils::RTPSessionUtils()  
  5.     {  
  6. #ifdef WIN32  
  7.         WSADATA dat;  
  8.         WSAStartup(MAKEWORD(2,2),&dat);  
  9. #endif // WIN32  
  10.     }  
  11.   
  12.     RTPSessionUtils::~RTPSessionUtils()  
  13.     {  
  14. #ifdef WIN32  
  15.         WSACleanup();  
  16. #endif // WIN32  
  17.     }  
  18.   
  19.     int RTPSessionUtils::CreateDefault(uint16_t port)  
  20.     {  
  21.         RTPUDPv4TransmissionParams transparams;  
  22.         RTPSessionParams sessparams;  
  23.         sessparams.SetOwnTimestampUnit(1.0/10.0);//必须设置  
  24.         transparams.SetPortbase(port);//port必须是偶数  
  25.         return base_type::Create(sessparams, &transparams);  
  26.   
  27.         base_type::SetDefaultPayloadType(0);  
  28.         base_type::SetDefaultTimestampIncrement(0);  
  29.         base_type::SetDefaultMark(false);  
  30.     }  
  31.   
  32.     int RTPSessionUtils::AddDestination(const std::string& ip, uint16_t port)  
  33.     {  
  34.         return base_type::AddDestination(RTPIPv4Address(ntohl(inet_addr(ip.c_str())), port));  
  35.     }  
  36.   
  37.     int RTPSessionUtils::DeleteDestination(const std::string& ip, uint16_t port)  
  38.     {  
  39.         return base_type::DeleteDestination(RTPIPv4Address(ntohl(inet_addr(ip.c_str())), port));  
  40.     }  
  41.   
  42.     int RTPSessionUtils::GetAddrFromSource(RTPSourceData *dat, uint32_t& ip, uint16_t& port)  
  43.     {  
  44.         if (dat->IsOwnSSRC())  
  45.             return -1;  
  46.   
  47.         if (dat->GetRTPDataAddress() != 0)  
  48.         {  
  49.             const RTPIPv4Address *addr = (const RTPIPv4Address *)(dat->GetRTPDataAddress());  
  50.             ip = addr->GetIP();  
  51.             port = addr->GetPort();  
  52.         }  
  53.         else if (dat->GetRTCPDataAddress() != 0)  
  54.         {  
  55.             const RTPIPv4Address *addr = (const RTPIPv4Address *)(dat->GetRTCPDataAddress());  
  56.             ip = addr->GetIP();  
  57.             port = addr->GetPort()-1;  
  58.         }  
  59.   
  60.         return 0;  
  61.     }  
  62.   
  63.     void RTPSessionUtils::OnNewSource(RTPSourceData *dat)  
  64.     {  
  65.         uint32_t ip;  
  66.         uint16_t port;  
  67.   
  68.         if (GetAddrFromSource(dat, ip, port))  
  69.             return;  
  70.           
  71.   
  72.         RTPIPv4Address dest(ip,port);  
  73.         base_type::AddDestination(dest);  
  74.   
  75.         std::cout << "OnNewSource Adding destination " << IPToString(ip) << ":" << port << std::endl;  
  76.     }  
  77.   
  78.     void RTPSessionUtils::OnRemoveSource(RTPSourceData *dat)  
  79.     {  
  80.         if (dat->ReceivedBYE())  
  81.             return;  
  82.   
  83.         uint32_t ip;  
  84.         uint16_t port;  
  85.   
  86.         if (GetAddrFromSource(dat, ip, port))  
  87.             return;  
  88.   
  89.         RTPIPv4Address dest(ip,port);  
  90.         base_type::DeleteDestination(dest);  
  91.   
  92.         std::cout << "OnRemoveSource Deleting destination " << IPToString(ip) << ":" << port << std::endl;  
  93.     }  
  94.   
  95.     void RTPSessionUtils::OnBYEPacket(RTPSourceData *dat)  
  96.     {  
  97.         uint32_t ip;  
  98.         uint16_t port;  
  99.   
  100.         if (GetAddrFromSource(dat, ip, port))  
  101.             return;  
  102.   
  103.         RTPIPv4Address dest(ip,port);  
  104.         base_type::DeleteDestination(dest);  
  105.   
  106.         std::cout << "OnBYEPacket Deleting destination " << IPToString(ip) << ":" << port << std::endl;  
  107.     }  
  108.   
  109.     //只要有rtp包就会触发  
  110.     void RTPSessionUtils::OnRTPPacket(RTPPacket *pack,const RTPTime &receivetime,  
  111.         const RTPAddress *senderaddress)  
  112.     {  
  113.         std::cout << "OnRTPPacket: data:" << pack->GetPayloadData() << std::endl;  
  114.     }  
  115.   
  116.     //收到rtcp包触发  
  117.     void RTPSessionUtils::OnRTCPCompoundPacket(RTCPCompoundPacket *pack,const RTPTime &receivetime,  
  118.         const RTPAddress *senderaddress)  
  119.     {  
  120.         std::cout << "OnRTCPCompoundPacket: data:" << pack->GetCompoundPacketData() << std::endl;  
  121.     }  
  122.   
  123.     //隔段时间就会触发,也可以用于收包回调函数  
  124.     //void RTPSessionUtils::OnPollThreadStep()  
  125.     //{  
  126.     //  BeginDataAccess();  
  127.   
  128.     //  // check incoming packets  
  129.     //  if (GotoFirstSourceWithData())  
  130.     //  {  
  131.     //      do  
  132.     //      {  
  133.     //          RTPPacket *pack;  
  134.     //          RTPSourceData *srcdat;  
  135.   
  136.     //          srcdat = GetCurrentSourceInfo();  
  137.   
  138.     //          while ((pack = GetNextPacket()) != NULL)  
  139.     //          {  
  140.     //              std::cout << "Got packet " << pack->GetExtendedSequenceNumber() << " from SSRC " << srcdat->GetSSRC() << std::endl;  
  141.     //              DeletePacket(pack);  
  142.     //          }  
  143.     //      } while (GotoNextSourceWithData());  
  144.     //  }  
  145.   
  146.     //  EndDataAccess();  
  147.     //}  
  148. }  

server.cpp


  1. #include   
  2. #include "RTPSessionUtils.h"  
  3. using namespace jrtplib;  
  4. void main()  
  5. {  
  6.     int status;  
  7.     RTPSessionUtils sess;  
  8.     status = sess.CreateDefault(8888);  
  9.     if(status)  
  10.     {  
  11.         std::cout << "RTP error:" << RTPGetErrorString(status) << std::endl;  
  12.         return;  
  13.     }  
  14.   
  15.     while (1)  
  16.     {  
  17.         std::string buf;  
  18.         std::cout << "Input send data:" ;  
  19.         std::cin >> buf;  
  20.   
  21.         sess.SendPacket((void*)buf.c_str(), buf.length(), 0, false, 0);  
  22.         if(status)  
  23.         {  
  24.             std::cout << "RTP error:" << RTPGetErrorString(status) << std::endl;  
  25.             continue;  
  26.         }  
  27.     }  
  28.   
  29.     system("pause");  
  30. }  

client.cpp


  1. #include   
  2. #include "RTPSessionUtils.h"  
  3. using namespace jrtplib;  
  4.   
  5. void main()  
  6. {  
  7.     int status;  
  8.     RTPSessionUtils sess;  
  9.     status = sess.CreateDefault(6666);  
  10.     if(status)  
  11.     {  
  12.         std::cout << "RTP error:" << RTPGetErrorString(status) << std::endl;  
  13.         return;  
  14.     }  
  15.     status = sess.AddDestination("127.0.0.1", 8888);  
  16.     if(status)  
  17.     {  
  18.         std::cout << "RTP error:" << RTPGetErrorString(status) << std::endl;  
  19.         return;  
  20.     }  
  21.   
  22.     while (1)  
  23.     {  
  24.         std::string buf;  
  25.         std::cout << "Input send data:" ;  
  26.         std::cin >> buf;  
  27.   
  28.         sess.SendPacket((void*)buf.c_str(), buf.length(), 0, false, 0);  
  29.         if(status)  
  30.         {  
  31.             std::cout << "RTP error:" << RTPGetErrorString(status) << std::endl;  
  32.             continue;  
  33.         }  
  34.     }  
  35.   
  36.     system("pause");  
  37. }  
阅读(4981) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~