近期在研究crtmpserver,这里记录下学习过程,首先我们先分析下基本流程。

1、初始化流程

InitNetworking---初始化网络

Initialize

Logger::Init()---初始化日志

lowerCase(extension) == "lua"---载入.lua后缀配置文件

LoadLuaFile

Normalize

NormalizeLogAppenders
初始化日志配置

NormalizeApplications
初始化监听配置





gRs.pConfigFile->ConfigLogAppenders()依据配置初始化

IOHandlerManager::Initialize()
初始化IO,读写队列清零

gRs.pConfigFile->ConfigModules()
载入动态库appselector.dll

ProtocolFactoryManager::RegisterProtocolFactory(gRs.pProtocolFactory) 载入默认支持的协议集合

gRs.pConfigFile->ConfigAcceptors()
依据IP和port开启监听器

gRs.pConfigFile->ConfigInstances()
配置多实例,win下不支持

gRs.pConfigFile->ConfigApplications()
将监听器与实例绑定

installQuitSignal
设置程序退出机制





Run

IOHandlerManager::Pulse()
对socket资源进行轮询,查询是否有须要进行读写的socket操作













2、接收client的连接请求之connect

Pulse()

FD_ISSET(MAP_VAL(i)->GetInboundFd(), &_readFdsCopy)

MAP_VAL(i)->OnEvent(_currentEvent)

TCPAcceptor::Accept()
进入accept进行连接的创建

BaseProtocol *pProtocol = ProtocolFactoryManager::CreateProtocolChain
为连接创建相应配置的协议,比方tcp && rtmp,或者udp && rtcp==





TCPCarrier *pTCPCarrier = new TCPCarrier(fd)
为连接创建一个tcp交互对象,并将其和刚创建的协议对象绑定,创建时构造函数中就注冊了读请求





FD_ISSET(MAP_VAL(i)->GetInboundFd(), &_readFdsCopy)

MAP_VAL(i)->OnEvent(_currentEvent)

TCPCarrier::OnEvent(select_event &event)
进入读分支读取数据,根据相应的协议分析读取的数据根据结果填充_outputBuffer发送缓冲区,并设置发送信号TCPCarrier::SignalOutputData()--->ENABLE_WRITE_DATA,通知Pulse轮询socket状态须要发送数据,然后再次进入TCPCarrier::OnEvent(select_event &event)写分支进行真正的数据发送操作





RTMP消息类型为:RM_INVOKE_FUNCTION_CONNECT





3、接收client的公布流之Publish

这一段属于rtmp协议交互的部分





RM_INVOKE_FUNCTION_RELEASESTREAM
这里没有获得stream名称,发送名称请求

RM_INVOKE_FUNCTION_FCPUBLISH
这里获得stream名称

RM_INVOKE_FUNCTION_CREATESTREAM

ProcessInvokeCreateStream

pFrom->CreateNeutralStream(id) == NULL

RTMPStream *pStream = new RTMPStream
这里创建一个rtmpstream流控制对象  RTMPStream ---> BaseStream

RM_INVOKE_FUNCTION_PUBLISH

ProcessInvokePublish

GetApplication()->GetAllowDuplicateInboundNetworkStreams()这里推断是否存在同名情况

InNetRTMPStream *pInNetRTMPStream = pFrom->CreateINS(VH_CI(request) 创建network inbound stream

GetApplication()->GetStreamsManager()->GetWaitingSubscribers 查询是否有请求这路流的连接并绑定pBaseOutStream->Link(pInNetRTMPStream);

pInNetRTMPStream->SendOnStatusStreamPublished()
发送准备接收流请求

BaseOutFileStream *pOutFileStream = CreateOutFileStream(pFrom, meta, appending);另外,假设须要录像,这里创建文件流连接





4、接收client请求实时流

这一段属于rtmp协议交互的部分





RM_INVOKE_FUNCTION_PLAY

ProcessInvokePlay

pFrom->CloseStream(VH_SI(request), true)
关闭该连接之前请求的流

TryLinkToLiveStream(pFrom, VH_SI(request), streamName, linked)
将该连接绑定

FOR_MAP(inboundStreams, uint32_t, BaseStream *, i)
通过streamName查询找到流输入

BaseOutNetRTMPStream * pBaseOutNetRTMPStream = pFrom->CreateONS(streamId, 先创建流输出

pBaseInNetStream->Link(pBaseOutNetRTMPStream)
然后将流输出绑定至流输入

crtmpserver 基本流程分析的更多相关文章

  1. 8、Struts2 运行流程分析

    1.流程分析: 请求发送给 StrutsPrepareAndExecuteFilter StrutsPrepareAndExecuteFilter 询问 ActionMapper: 该请求是否是一个 ...

  2. freeswitch呼叫流程分析

    今天翻文档时发现之前整理的关于freeswitch呼叫相关的内容,写成博文分享出来也方便我以后查阅. 整体结构图 FreeswitchCore 模块加载过程 freeswitch主程序初始化时会从mo ...

  3. u-boot 流程分析

    u-boot 介绍: 对于计算机来说 , 从一开始上机通电是无法直接启动操作系统的 , 这中间需要一个引导过程 , 嵌入式Linux系统同样离不开引导程序 ,  这个启动程序就叫启动加载程序(Boot ...

  4. thttpd和cgilua安装与运行流程分析

    安装 参考如下博文安装thttpd软件 http://blog.csdn.net/21aspnet/article/details/7045845 http://blog.csdn.net/drago ...

  5. 【转】Hostapd工作流程分析

    [转]Hostapd工作流程分析 转自:http://blog.chinaunix.net/uid-30081165-id-5290531.html Hostapd是一个运行在用户态的守护进程,可以通 ...

  6. u-boot中nandflash初始化流程分析(转)

    u-boot中nandflash初始化流程分析(转) 原文地址http://zhuairlunjj.blog.163.com/blog/static/80050945201092011249136/ ...

  7. Android7.0 Phone应用源码分析(二) phone来电流程分析

    接上篇博文:Android7.0 Phone应用源码分析(一) phone拨号流程分析 今天我们再来分析下Android7.0 的phone的来电流程 1.1TelephonyFramework 当有 ...

  8. runc start container流程分析

    1.runc/start.go Action: func(context *cli.Context) error 该函数首先调用container, err := getContainer(conte ...

  9. 从注册流程 分析如何安全退出多个Activity 多种方式(附DEMO)

      退出Activity注册Android遍历   目录(?)[+] 前言 知识结构 具体方案 方案1 方法采用FLAG_ACTIVITY_CLEAR_TOP退出整个程序多activity 方案2 方 ...

随机推荐

  1. Hadoop配置项整理(mapred-site.xml)【转】

    本文转自:http://slaytanic.blog.51cto.com/2057708/1101360 name value Description hadoop.job.history.locat ...

  2. Sqlite 错误码

    #define SQLITE_OK 0 /* 成功 | Successful result */ /* 错误码开始 */ #define SQLITE_ERROR 1 /* SQL错误 或 丢失数据库 ...

  3. 【转】教你爱上Blocks(闭包)

    Block 与传统代码相比较更加轻量,调用简洁方便,而且可以返回多个参数,使用Block可以让代码更加具有易读性,而我们在写回调时,也可以直接写在函数内部,而不用再去写一个回调函数 Block 闭包 ...

  4. [转]Delphi 关键字详解

    全文链接地址:http://www.cnblogs.com/del/archive/2008/06/23/1228562.html

  5. 你好,C++(33)对象生死两茫茫 6.2.3 一个对象的生与死:构造函数和析构函数

    6.2.2  使用类创建对象 完成某个类的声明并且定义其成员函数之后,这个类就可以使用了.一个定义完成的类就相当于一种新的数据类型,我们可以用它来定义变量,也就是创建这个类所描述的对象,表示现实世界中 ...

  6. 你好,C++(7)第三部分 C++世界众生相 3.2.1 变量的定义与初始化

    第3部分 C++世界众生相 在听过了HelloWorld.exe的自我介绍,完成了与C++世界的第一次亲密接触后,大家是不是都急不可待地想要一试身手,开始编写C++程序了呢?程序的两大任务是描述数据和 ...

  7. 最短路径算法——Dijkstra,Bellman-Ford,Floyd-Warshall,Johnson

    根据DSqiu的blog整理出来 :http://dsqiu.iteye.com/blog/1689163 PS:模板是自己写的,如有错误欢迎指出~ 本文内容框架: §1 Dijkstra算法 §2 ...

  8. Java学习----你的选择是什么-条件结构

    import java.util.Scanner; public class Student { public static void main(String[] args) { byte money ...

  9. (git fetch git push git pull)远程本地分支互相推送更新

    git push origin bug_huiyuan:mobile_attribution 把bug_huiyuan(本地分支) 推送到 远程mobile_attribution分支 git pus ...

  10. 日期选择器(Query+bootstrap和js两种方式)

    日期选择是在下拉列表中选择年.月.日,年显示前后的五年,12个月,日就是有30.31.29.28天的区别,随着月份的变而变 一.js方式的日期选择 (1)首先就是三个下拉列表了,点击年.月.日显示列表 ...