MRCP UA的创建及SIP信令处理

在mrcp_sofia_task_initialize中调用nua_create一个UA(User agent)这个跟freeswitch SIP信令的接收,是一样的。在nua_create的时候会设置回调函数:mrcp_sofia_event_callback()。接下来的处理都是一样的,只是有事件的时候的回调不一样。现在调用的是mrcp_sofia_event_callback()。

/** This callback will be called by SIP stack to process incoming events */
static void mrcp_sofia_event_callback( 
                        nua_event_t           nua_event,
                        int                   status,
                        char const           *phrase,
                        nua_t                *nua,
                        mrcp_sofia_agent_t   *sofia_agent,
                        nua_handle_t         *nh,
                        mrcp_sofia_session_t *sofia_session,
                        sip_t const          *sip,
                        tagi_t                tags[])
{
    apt_log(APT_LOG_MARK,APT_PRIO_INFO,"Receive SIP Event [%s] Status %d %s [%s]",
        nua_event_name(nua_event),
        status,
        phrase,
        sofia_agent->sig_agent->id);

    switch(nua_event) {
        case nua_i_state:
            mrcp_sofia_on_state_change(status,sofia_agent,nh,sofia_session,sip,tags);
            break;
            if(status >= 200) {
                        /* break main loop of sofia thread */
                        su_root_break(sofia_agent->root);
                    }
                    break;
                default: 
                    break;
            }
        }
        case nua_r_invite:
            if(status >= 300 && status < 400) {
                mrcp_sofia_on_session_redirect(status,sofia_agent,nh,sofia_session,sip,tags);
            }
            break;
        case nua_r_options:
            mrcp_sofia_on_resource_discover(status,sofia_agent,nh,sofia_session,sip,tags);
            break;
        case nua_r_shutdown:
            /* if status < 200, shutdown still in progress */

我们这里分析一下nua_i_state的时候的处理,这个时候会调用mrcp_sofia_on_state_change()。

nua_callstate的描述是一个枚举类型,定义为:
enum nua_callstate {
nua_callstate_init, /*< Initial state /
nua_callstate_authenticating, /*< 401/407 received /
nua_callstate_calling, /*< INVITE sent /
nua_callstate_proceeding, /*< 18X received /
nua_callstate_completing, /*< 2XX received /
nua_callstate_received, /*< INVITE received /
nua_callstate_early, /*< 18X sent (w/SDP) /
nua_callstate_completed, /*< 2XX sent /
nua_callstate_ready, /*< 2XX received, ACK sent, or vice versa /
nua_callstate_terminating, /*< BYE sent /
nua_callstate_terminated /*< BYE complete /
};

接下来看下mrcp_sofia_on_state_change的具体实现

static void mrcp_sofia_on_state_change(
                        int                   status,
                        mrcp_sofia_agent_t   *sofia_agent,
                        nua_handle_t         *nh,
                        mrcp_sofia_session_t *sofia_session,
                        sip_t const          *sip,
                        tagi_t                tags[])
{
    int nua_state = nua_callstate_init;
    tl_gets(tags,
            NUTAG_CALLSTATE_REF(nua_state),
            TAG_END());

    if(!sofia_session || !sofia_session->session) {
        apt_log(APT_LOG_MARK,APT_PRIO_WARNING,"SIP Call State [%s]", nua_callstate_name(nua_state));
        return;
    }
    apt_obj_log(APT_LOG_MARK,APT_PRIO_NOTICE,sofia_session->session->log_obj,"SIP Call State %s [%s]",
        sofia_session->session->name,
        nua_callstate_name(nua_state));

    if(nua_state == nua_callstate_terminated) {
        mrcp_sofia_on_session_terminate(status,sofia_agent,nh,sofia_session,sip,tags);
        return;
    }

    if(nua_state == nua_callstate_ready) {
        mrcp_sofia_on_session_ready(status,sofia_agent,nh,sofia_session,sip,tags);
    }
    sofia_session->nua_state = nua_state;
}

你可能感兴趣的:(freeswitch)