流媒体学习笔记2(live555中的Session)
来源:互联网 发布:系统备份还原软件 编辑:程序博客网 时间:2024/04/30 12:57
毕业课题打算从最原始的地方做起。好吧,那就从live555采集转发本地摄像头视频开始吧。首先从源码开始吧,今天看了点liveMedia中的session,这里做个总结。
整个源码中的继承顺序为
H264VideoFileServerMediaSubsession::FileServerMediaSubsession:: OnDemandServerMediaSubsession::ServerMediaSubsession ::Medium
ServerMediaSession ::Medium
Medium:抽象了基本的接口,包括环境,task和媒体名和媒体查找函数以及一些辅助函数,几乎所有得处理单元都继承自Medium类。
ServerMediaSession:添加了子会话链表,SDP(Session Description Protocol 会话协议)描述以及一些媒体相关处理函数。其中静态成员函数lookupByName可以从session链表中找到对应的媒体
ServerMediaSubsession:定义了指向ServerMediaSession的父指针,指向下个一个对象的指针。该媒体的SDP信息,该媒体的读取定位函数等。
ServerMediaSubsessionIterator:一个迭代器类,用来遍历subsession链表。
程序为容器中的每一个流建立一个subseesion,然后通过 ServerMediaSession::addSubsession 函数,将subsession 加入到ServerMediaSession。具体代码如下
ServerMediaSession::addSubsession(ServerMediaSubsession* subsession) { if (subsession->fParentSession != NULL) return False; // it's already used if (fSubsessionsTail == NULL) { fSubsessionsHead = subsession; } else { fSubsessionsTail->fNext = subsession; } fSubsessionsTail = subsession; subsession->fParentSession = this; subsession->fTrackNumber = ++fSubsessionCounter; return True;}
ServerMediaSession与流名字所指定与文件是没有关系的,也就是说它不会操作文件,而文件的操作是放在 ServerMediaSubsession中的。具体应该是在ServerMediaSubsession的sdpLines()函数中打开。sdpLines()是在派生类OnDemandServerMediaSubsession中实现,代码如下
char const*OnDemandServerMediaSubsession::sdpLines() { if (fSDPLines == NULL) { // We need to construct a set of SDP lines that describe this // subsession (as a unicast stream). To do so, we first create // dummy (unused) source and "RTPSink" objects, // whose parameters we use for the SDP lines://构建一套SDP行来描述这个Subsession。创建未使用的source和RTPSink对象 unsigned estBitrate; FramedSource* inputSource = createNewStreamSource(0, estBitrate); if (inputSource == NULL) return NULL; // file not found struct in_addr dummyAddr; dummyAddr.s_addr = 0; Groupsock dummyGroupsock(envir(), dummyAddr, 0, 0); unsigned char rtpPayloadType = 96 + trackNumber()-1; // if dynamic RTPSink* dummyRTPSink = createNewRTPSink(&dummyGroupsock, rtpPayloadType, inputSource);//Sink中的到SDP setSDPLinesFromRTPSink(dummyRTPSink, inputSource, estBitrate); Medium::close(dummyRTPSink); closeStreamSource(inputSource); } return fSDPLines;}
OnDemandServerMediaSubsession类继承 ServerMediaSubsession类,OnDemand实际上用来描述需求,Subsession表示只是一种类型媒体的会话。所以可以通过继承OnDemandServerMediaSubsession来实现不同类型的媒体转发,比如OnDemandServerMediaSubsession的两个子类
1.ProxyServerMediaSubsession:用于实现一个单播RTSP的服务器代理另一个RTSP流
2.FileServerMediaSubsession:虚基类,不同类型媒体通过继承它来实现对于需求,比如音频,视频,比如h263,h264编解码。FileServerMediaSubsession类只是添加了两个成员变量 fFileName,fFileSize用来描述转发的媒体。构造函数如下:
FileServerMediaSubsession::FileServerMediaSubsession(UsageEnvironment& env, char const* fileName, Boolean reuseFirstSource) : OnDemandServerMediaSubsession(env, reuseFirstSource), fFileSize(0) { fFileName = strDup(fileName);}
而H264VideoFileServerMediaSubsession类继承了FileServerMediaSubsession,它将构造函数放入protected中,并用静态的成员方法createNew来实例对象,这是设计模式的工厂模式。createNew(env, fileName, reuseSource)是每一种类型的流媒体自己的subsession实现。如果 reuseSource == True,则多个客户端共享 StreamState 对象,也即意味着多个客户端播放同一流文件时,服务器端使用同一FileSource 对象对该流文件进行数据读取操作,使用同一RTPSink 对象对流数据进行封装发送操作,这时,多个客户端播放的内容就是同步的,这适合于实时数据播放;如果reuseSource==False,则对每个客户端,服务器端单独维护一个StreamState 对象进行播放操作,此时,多个客户端播放的内容就是独立的,这适合于数据回放。
当然,单看session看不出什么门道来,那看下面
SDP消息组装过程:
ServerMediaSession负责产生会话公共描述信息,子会话描述由H264VideoFileServerMediaSubsession产生。 H264VideoFileServerMediaSubsession在其父类成员函数OnDemandServerMediaSubsession::sdpLines()中生成会话描述信息。在sdpLines()实现里面,创建一个FramedSource(具体实现类为H264VideoStreamFramer)和RTPSink(具体实现类为H264VideoRTPSink),最后调用OnDemandServerMediaSubsession::setSDPLinesFromRTPSink(...)成员函数生成子会话描述。
好吧,这样思路基本清楚了点,以后要写自己需要的编解码类,那就继承OnDemandServerMediaSubsession吧。对于souce-sink 机制下次讲了....
- 流媒体学习笔记2(live555中的Session)
- 流媒体Live555学习(一)
- 流媒体Live555学习(二)
- 流媒体Live555学习(三)
- 流媒体Live555学习(一)
- 流媒体Live555学习(二)
- 流媒体Live555学习(三)
- 流媒体学习笔记1(live555+vs2010编译)
- 流媒体学习笔记3(live555的source-sink)
- live555学习笔记2
- live555学习笔记(二)
- 【流媒体学习】live555学习(二):基础类
- Live555学习笔记(一)—— live555概述
- 流媒体学习笔记(一)
- live555搭建流媒体服务器2--live555源码分析2
- 【流媒体学习】live555学习(一):live555—VS2010 /VS2013 下live555编译、使用及测试
- live555搭建流媒体服务器2--live555源码分析
- live555学习笔记2-基础类
- Gesture透过view传递到上层的view
- H.264 extradata (partially) explained
- C语言 结构体的内存对齐问题与位域
- 提高程序运行效率的10个简单方法
- 用Ajax实现无刷新分页类
- 流媒体学习笔记2(live555中的Session)
- verilog实现的红外解码(详细注释)
- RDIFramework.NET(.NET快速信息化系统开发框架) Web版介绍
- 视频图像标准:D1/D2/D3/D4/D5
- CVT在线测试题
- .NET日期格式化
- android中,如果使用imageButton可以在drawable 中设置一个selector,但是imageView设置不起作用
- 8.5内部排序法---分配类排序(基数排序)
- ExtJs关于grid高度自适应浏览器的问题解决办法