FreeSWITCH - mod_xml_rpc源码分析七server.c

下面分析过程中函数先后次序,采用mod_xml_rpc.c文件内SWITCH_MODULE_RUNTIME_FUNCTION(mod_xml_rpc_runtime)函数里abyss库函数的出现顺序。

ServerCreate

abyss_bool
ServerCreate(TServer *       const serverP,
             const char *    const name,
             xmlrpc_uint16_t const portNumber,
             const char *    const filesPath,
             const char *    const logFileName)
这应该是使用abyss库的客户代码首要调用的函数。函数内代码很容易理解,首先调用createServer进行初始化操作,如果初始化成功则再调用setNamePathLog函数初始化主目录以及日志文件等信息。客户代码内的TServer定义其实没什么实质内容,内部只是一个指向_TServer的指针。这个结构体内部的信息都只由库代码访问。

typedef struct {
    /* Before Xmlrpc-c 1.04, the internal server representation,
       struct _TServer, was exposed to users and was the only way to
       set certain parameters of the server.  Now, use the (new)
       ServerSet...() functions.  Use the HAVE_ macros to determine
       which method you have to use.
    */
    struct _TServer * srvP;
} TServer;

createServer

在这个函数内,果然看到了为_TServer变量申请内存初始化变量的代码。创建完变量后,并没有做其他更多的处理,只是为三个函数指针赋上了相应的函数。HandlerCreate和HandlerDefaultBuiltin函数均在handler.c函数内定义。

setNamePathLog

ServerCreate函数内另一个被调用的函数是setNamePathLog。这个函数内一次调用了另三个函数:ServerSetName、ServerSetFilesPath和ServerSetLogFileName。第一个函数只是为_TServer变量的内部name属性赋值。ServerSetLogFileName函数的作用也只是给_TServer变量的logfilename赋值。ServerSetFilesPath函数是对另一个函数的封装:HandlerSetFilesPath。并且向HandlerSetFilesPath函数传递了_TServer的builtinHandlerP函数指针。这个函数指针值在createServer函数内被赋值,指向的是HandlerCreate。HandlerSetFilesPath也是在handler.c文件中定义。突然发现刚才分析代码时出错了,createServer函数内并不是将HandlerCreate函数赋给_TServer结构体内的属性,而是调用HandlerCreate函数创建一个BIHandler变量。这个被创建的BIHandler变量将赋给_TServer结构体内的builtinHandlerP属性。BIHandler结构体见下图:

struct BIHandler {
    const char * filesPath;
    TList defaultFileNames;
    MIMEType * mimeTypeP;
        /* NULL means to use the global MIMEType object */
};
HandlerCreate函数内会初始化这个结构体内部的TList。这个结构体在分析data.c代码时曾经研究过。HandlerSetFilesPath这个函数其实也不复杂,只是将主目录赋给BIHandler结构体的filesPath属性。


ServerInit

客户代码调用完ServerCreate函数后,就应该接着调用ServerInit函数了。第一步就是要创建一个TChanSwitch变量,并赋给_TServer的chanSwitchP属性。为了达到这个目的,最终调用的是ChanSwitchWinCreate函数,此函数在socket_win.c文件内,曾经研究过。这个函数不但创建了TChanSwitch变量,而且还生成了一个socket,并且与特定的port端口绑定成功。第一步完成后,接着就是调用ChanSwitchListen函数。

void
ChanSwitchListen(TChanSwitch * const chanSwitchP,
                 uint32_t      const backlog,
                 const char ** const errorP) {

    if (SwitchTraceIsActive)
        fprintf(stderr, "Channel switch %p listening.\n", chanSwitchP);

    (*chanSwitchP->vtbl.listen)(chanSwitchP, backlog, errorP);
}
代码显示最终访问了vtbl下
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值