版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
1、live555学习之RTSP连接建立以及请求消息处理过程1, RTSP连接的建立过程RTSPServer类用于构建一个 RTSP服务器,该类同时在 其内部定义了一个 RTSPClientSession类,用于处理单独的客 户会话。首先创建RTSP服务器(具体实现类是 DynamicRTSPServer),在创建过程中,先建立 Socket(ourSocket)在TCP的554端口进行监听,然后把连接 处理函数句柄(RTSPServer: incomingConnectionHandler)和 socket句柄传给 任务调度器(taskScheduler)。任务调度器把socket句柄放入后面s
2、elect调用中用到的 socket句柄集(fReadSet)中,同时将 socket句柄和 incomingConnectionHandler句柄关联起来。接着,主程序开 始进入任务调度器的主循环(doEventLoop ),在主循环中调 用系统函数select阻塞,等待网络连接。当 RTSP 客户端输入(rtsp:/09/1.mpg)连接服 务器时,select返回对应的scoket,进而根据前面保存的对应 关系,可找到对应处理函数句柄,这里就是前面提到的 incomingConnectionHandler 了。在incomingConnectionHandler 中创建了 RTSPCli
3、entSession,开 始对这个客户端的会话进行处理。具体分析如下:DynamicRTSPServer:creatnew():.调用继承自 RTPSever:setUpOurSocket:.调用 GroupsockHelper 的 setupStreamSocket仓建 个socket连接,并绑定,.设置socket的发送缓存大小,.调用listen开始监听端口,设置同时最大能处理连 接数LISTEN_BACKLOG_SIZE=20 ,如果达至U这个上限贝U client端将收至U ECONNERREFUSED的错误.测试绑定端口是否为 0,为0的话重新绑定断口, 并返回系统自己选择的新的端
4、口。.返回建立的socket文件描述符.调用自己和 RTPSever的构造函数:RTPSever构造函数:.用一个UsageEnvironment对象的引用构造其父类 Medium.设置最大等待回收连接时间reclamationTestSeconds,超过这个时间从客户端没有RTSP命令或者 RTSP的RR包则收回其 RTSPClientSession.建立一个HashTable (实际上是一个BasicHashTable) ,fServerMediaSessions 指向这个表。.调用参数UsageEnvironment对象env的成员,一个 TaskScheduler指针所指对象(实际就是
5、一个 BasicTaskScheduler对象)的成员函数turnOnBackgroundReadHandling():.调用一个 HandlerSet:assignHandler()创建 一个Handler,把socketNum【此处为服务器监听的socket描述符】和处理函数RTSPServer:incomingConnectionHandler(),还有指向 RTSPSever的指针绑定在一起。incomingConnectionHandler 作用:.调用accept返回服务器与客户 端连接的socket描述符.设置客户端描述符为非阻塞.增加客户端socket描述符的发 送缓存为50*
6、1024.为此客户端随机分配一个 sessionId.用客户端socket描述符clientSocket,sessionId,和客户端地址 clientAddr 调用creatNewClientSession 创建一个 clientSession。2,请求消息处理过程上节我们谈到RTSP服务器收到客户端的连接请求,建 立了 RTSPClientSession类,处理单独的客户会话。在建立RTSPClientSession的过程中,将新建立的socket句柄(clientSocket)和RTSP请求处理函数句柄RTSPClientSession二incomingRequestHandler 传给
7、任务调度器,由任务调度器对两者进行一对一关联。当客户端发生RTSP请求后,服务器主循环中的select调用返回,根据socket 句柄找到对应的incomingRequestHandler ,开始消息处理。 先进行消息的解析。RTSPClientSession二RTSPClientSession。构造函数:.重置请求缓存.调用envir().taskScheduler().turnOnBackgroundReadHandling(), 这 次socketnumber为客户端socket描述符这次的处理函数是RTSPServer:RTSPClientSession:incomingRequest
8、Handler()RTSPServer:RTSPClientSession:incomingRequestHandler(): 调用 handleAlternativeRequestByte1(uint8_trequestByte):1.fRequestBufferfRequestBytesAlreadySeen=requestByte;把请求字符放入请求缓存fRequestBuffer2.调用 handleRequestBytes(l)处理请求缓handleRequestBytes(int newBytesRead): 1.调用 noteLiveness()查看请求是 否到I期,如果服务器的
9、 reclamationTestSeconds 0 ,调用 taskScheduler 对象的 rescheduleDelayedTask 函数:参数为 (fLivenessCheckTask,fOurServer.fReclamationTestSeconds*10 00000,(TaskFunc*)livenessTimeoutTask, this ) 其中livenessTimeoutTask()函数作用是删除 new由来的 clientSession.调用unscheduleDelayedTask(TaskToken&prevTask): 从DelayQueue中删除 prevTask
10、 项, prevTask 置空.调用 scheduleDelayedTask(int64_t microseconds,TaskFunc* proc, void*clientData):.仓1J建一个 DelayInterval 对象 timeToDelay ,用 microseconds 初始化。.创建一个AlarmHandler 对象,用 proc, clientData, timeToDelay 初始化.调用 fDelayQueue.addEntry(),把这个 AlarmHandler 对象加入到延 迟队列中.返回 AlarmHandler 对 象的tokenlong类型的指针.如果请
11、求的的长度超过请求缓存 可读长度fRequestBufferBytesLeft ,结束这个连接。.找到请求消息的结尾:。.如果找到消息结尾,调用 RTSPServer:RTSPClientSession:handleRequestBytes()值得 关注此函数把请求字符串转换成命令各部分包括: cmdName方法,urlPreSuffixurl 地址,urlSuffix要读取的 文件名,sceq消息的Cseq,否则函数返回需要继续从连接 中读取请求。分别存入对应的数组。.如果转换成功,调用 handleCmd_xxx()处 理对应的cmdName: xxx此处实现了 : OPTIONS , D
12、ESCRIBE , SETUP, TEARDOWN , PLAY, PAUSE, GET_PARAMETER SET_PARAMETER其中 PLAY , PAUSE, GET_PARAMETER , SET_PARAMETER 调用 handleCmd_withinSession(cmdName,urlPreSuffix, urlSuffix,cseq,(char const*)fRequestBuffer);.清空 RequestBuffer比如:消息解析后,如果发现客户端的请求是DESCRIBE则进入handleCmd_DESCR旧E函数。RTSP服务器收到客户端 的DESCRIBE请求
13、后,根据请求URL(rtsp:/09/1.mpg),找到对应的流媒体资源, 返回响应消息。live555中的ServerMediaSession类用来处理 会话中描述,它包含多个(音频或视频)的子会话描述 (ServerMediaSubsession)o根据客户端请求 URL的后缀(例如 是1.mpg),调用成员函数 DynamicRTSPServer:lookupServerMediaSession 查找对应的 流媒体信息 ServerMediaSession。(根据 urlSuffix 查找)。 如果ServerMediaSession不存在,查找文件是否存在,若文 件不存在,则判断 Se
14、rverMediaSession(即smsExists)是否存在,如果存在则将其remove (调用removeServerMediaSession 方法)。但是如果本地存在 1.mpg 文件,则根据文件名创建一个新的ServerMediaSession (调用createNewSMS方法,若在该方法中找不到对应的文件扩 展名,则将返回 NULL )。如果通过lookupServerMediaSession返回的是 NULL,则向客 户端发送响应消息并将 fSessionIsActive置为FALSE;否则, 为该session组装一个SDP描述信息(调用generateSDPDescript
15、ion 方法,该方法在 ServerMediaSession 类中),组装完成后,生成一个 RTSP URL (调用rtspURL方 法,该方法在 RTSPServer类中)。在创建ServerMediaSession过程中,根据文件后缀.mpg,创 建媒体MPEG-1or2的解复用器 (MPEG1or2FileServerDemux)。再由 MPEG1or2FileServerDemux创建一个子会话描述 MPEG1or2DemuxedServerMediaSubsession。最后由ServerMediaSession完成组装响应消息中的SDP信息(SDP组装过程见下面的描述),然后将响应
16、消息发给客户端,完 成一次消息交互。RTSP服务器处理客户端点播的基本流程处理连接请求的基本流程:l Step 1:与客户端建立 RTSP连接(调用incomingConnectionHandler 方法),创建 ClientSession 并关联 fClientSocket 与 incomingRequestHandler (调用 incomingConnectionHandler1 )。l Step 2:接收客户端t#求(调用 incomingRequestHandler 方法)。l Step 3:从客户端Socket读取数据,并对请求数据(即the request string)进行转换
17、(调用 parseRTSPRequestString方法, 该方法在 RTSPCommon类中)。l Step 4:根据分离由来的指令进行分别处理:n OPTIONS f handleCmd_OPTIONSn DESCRIBE f handleCmd_DESCRIBE handleCmd_DESCRIBE这一个方法比较重要,首先根据 urlSuffix 查找 ServerMediaSession 是否存在(调用 lookupServerMediaSession 方法,该方法中通过 HashTable 来 查找)。在testOnDemandRTSPServer项目工程中,仅仅是通过 stream
18、Name来确认session是否为NULL。而在完整的 live555MediaServer项目工程中,则是通过DynamicRTSPServer类来处理,其首先是查找文件是否存在, 若文件不存在,则判断ServerMediaSession (即smsExists)是否存在,如果存在则将其remove (调用removeServerMediaSession方法);若文件存在,则根据文件名创建一个 ServerMediaSession (调用 createNewSMS 方法,若在该方法中找不到对应的文件扩展名,则将返回NULL )。如果通过lookupServerMediaSession返回的是
19、 NULL,则向客 户端发送响应消息并将 fSessionIsActive置为FALSE;否则, 为该session组装一个SDP描述信息(调用 generateSDPDescription 方法,该方法在 ServerMediaSession 类中),组装完成后,生成一个RTSP URL (调用rtspURL方法,该方法在 RTSPServer类中)。n SETUP fhandleCmd_SETUPhandleCmd_SETUP方法中,有两个关键的名词,一个是 urlPreSuffix , 代表了 session name(即 stream name); 一个是 urlSuffix , 代表
20、了 subsession name (即 track name), 后面经 常用到的streamName和trackId分别与这两个名词有关。接下来会创建 sessions state,包括 incrementReferenceCount 等。紧接着,会针对确定的subsession (track)查找相应的信息。接着,在 request string 查找一个 Transport: header, 目的是为了从中提取客户端请求的一些参数(调用 parseTransportHeader方法,该方法在 RTSPServer类中),如 clientsDestinationAddressStr、Cl
21、ientRTPPortNum 等。再接着是 getStreamParameters(该方法在 ServerMediaSession 类中被定义为纯虚函数并在OnDemandServerMediaSubsession 类中被重定义),然后通过fIsMulticast和streamingMode来组装不同的响应消息。n PLAY f handleCmd_PLAY :处理播放请求,具体的实现 流程请参见后面的步骤。n PAUSEfhandleCmd_PAUSE :处理暂停请求,在执行了 该请求后,最终会调用 StopPlaying方法,并将 fAreCurrentlyPlaying 置为 FALSE
22、。n TEARDOWN f handleCmd_TEARDOWN :处理停止请 求,将 fSessionIsActive 置为 FALSE。n GET_PARAMETER f handleCmd_GET_PARAMETER :该 方法主要是维持客户端与服务器通信的生存状态,just forkeep alive on SET_PARAMETER f handleCmd_SET_PARAMETER :该 方法未针对SET_PARAMETER作实现,使用该方法会调用 handleCmd_notSupported方法,并将最终引发与客户端断开 连接。l Step 5:根据Step 4的不同指令进行消息
23、响应(调用 send方法),该消息响应是即时的l Step 6:处理客户端发送“ SETUP”指令后即开始播放的 特殊情况。l Step 7:将RequestBuffer进行重置,以便于为之后到来的 请求做好准备。l Step 8:检查fSessionIsActive是否为FALSE ,如果是则删 除当前的 ClientSession。处理PLAY的基本流程:l Step 1:对rtspURL及相关header的处理,涉及较多的细 节。l Step 2:根据不同的header对流进行缩放比例或定位的处 理。如果为sawScaleHeader,则进行缩放比例的处理(调用setStreamScal
24、e方法,该方法在OnDemandServerMediaSubsession 类中实现)。如果为sawRangeHeader,则进行寻找流的处理(即是对流进 行定位,调用seekStream方法,该方法在OnDemandServerMediaSubsession 类中实现;同时,该方法 的调用是在初始播放前及播放过程中由于用户拖动播放进 度条而产生的系列请求)。在 OnDemandServerMediaSubsession 类中,seekStream方法 中调用了 seekStreamSource方法,该方法在对应的媒体格式 文件的FileServerMediaSubsession类中实现(如针
25、对 WAV格 式,贝U在 WAVAudioFileServerMediaSubsession 类中实现;针 对 MP3 格式,贝U在 MP3AudioFileServerMediaSubsession 类 中实现)。同理,OnDemandServerMediaSubsession 类中的 setStreamScale 方法中所调用的 setStreamSourceScale 方法亦 是类似的实现机制。l Step 3:开始进行流式播放(调用 startStream方法,该方 法在 OnDemandServerMediaSubsession 类中实现)。n Step 3.1:根据 clientS
26、essionId 从 fDestinationsHashTable 中查找到destinations(包括了客户端的IP地址、RTP端口号、 RTCP端口号等信息)。n Step 3.2:调用startPlaying方法,在该方法中根据 RTPSink 或UDPSink分别调用startPlaying方法。如果是调用 RTPSink的startPlaying方法,则接着会调用 MediaSink类中的startPlaying方法,并在该方法中调用 MultiFramedRTPSink 类中的 continuePlaying 方法,之后便是 buildAndSendPacket 了。这里已经来到重点了,即是关于不 断读取Frame并Send的要点。在MultiFramedRTPSink类中, 通过 buildAndSendPacket、 packFrame、 afterGettingFrame、 afterGettingFrame1、 sendPacketIfNecessary 和 sendNext 构成 了一个循环圈,数据包的读取和发送在这里循环进行着。特 别注意
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
最新文档
- 2026 学龄前自闭症同伴自理课件
- 企业生产管理办法
- 化肥农药减量增效方案
- 经济适用房消防安全管理规定
- 会议策划流程
- 2026 育儿中的情绪疏导课件
- 单位协同合作教育
- 露营安全教育大班
- 2026年个人能力自我检测试题集
- 2026年石油行业采购英语面试模拟题
- 重庆机场集团有限公司招聘考试试题及答案
- 2026上海中考语文知识点背诵清单练习含答案
- 腹股沟疝术后感染的风险与应对
- 2026广东佛山市南海区大沥镇镇属企业员工招聘9人建设笔试模拟试题及答案解析
- 2026综合版《安全员手册》
- 2025年陕西高中学业水平合格性考试化学试卷真题(含答案)
- 人教版九年级化学 实验活动2 水的组成及变化的探究(学习、上课课件)
- 国家义务教育质量监测(2024年) 中小学生心理健康测试试卷
- 大学生的生理特点与体育运动以及体育卫生保健
- 【高中语文】《屈原列传》课件++统编版+高中语文选择性必修中册
- 重庆理工809数据结构考纲
评论
0/150
提交评论