Changeset 5241


Ignore:
Timestamp:
Feb 5, 2016 4:29:17 AM (8 years ago)
Author:
nanang
Message:

Fixed #1902:

  • Crash when endpoint has multiple worker threads and SIP TCP transport is disconnected during incoming call handling.
  • Deprecated pjsip_dlg_create_uas(), replaced by pjsip_dlg_create_uas_and_inc_lock().
  • Serialized transaction state notifications (of 'terminated' and 'destroyed') in case of transport error.
Location:
pjproject/trunk
Files:
14 edited

Legend:

Unmodified
Added
Removed
  • pjproject/trunk/pjsip-apps/src/samples/footprint.c

    r3553 r5241  
    342342    pjsip_ua_destroy(); 
    343343    pjsip_dlg_create_uac(NULL, NULL, NULL, NULL, NULL, NULL); 
    344     pjsip_dlg_create_uas(NULL, NULL, NULL, NULL); 
     344    pjsip_dlg_create_uas_and_inc_lock(NULL, NULL, NULL, NULL); 
    345345    pjsip_dlg_terminate(NULL); 
    346346    pjsip_dlg_set_route_set(NULL, NULL); 
  • pjproject/trunk/pjsip-apps/src/samples/pjsip-perf.c

    r5170 r5241  
    476476 
    477477    /* Create UAS dialog */ 
    478     status = pjsip_dlg_create_uas( pjsip_ua_instance(), rdata, 
    479                                    &app.local_contact, &dlg); 
     478    status = pjsip_dlg_create_uas_and_inc_lock( pjsip_ua_instance(), rdata, 
     479                                                &app.local_contact, &dlg); 
    480480    if (status != PJ_SUCCESS) { 
    481481        const pj_str_t reason = pj_str("Unable to create dialog"); 
     
    503503        pjsip_dlg_create_response(dlg, rdata, 500, NULL, &tdata); 
    504504        pjsip_dlg_send_response(dlg, pjsip_rdata_get_tsx(rdata), tdata); 
     505        pjsip_dlg_dec_lock(dlg); 
    505506        return PJ_TRUE; 
    506507    } 
    507508     
     509    /* Invite session has been created, decrement & release dialog lock. */ 
     510    pjsip_dlg_dec_lock(dlg); 
     511 
    508512    /* Send 100/Trying if needed */ 
    509513    if (app.server.send_trying) { 
  • pjproject/trunk/pjsip-apps/src/samples/simpleua.c

    r4815 r5241  
    726726     * Create UAS dialog. 
    727727     */ 
    728     status = pjsip_dlg_create_uas( pjsip_ua_instance(),  
    729                                    rdata, 
    730                                    &local_uri, /* contact */ 
    731                                    &dlg); 
     728    status = pjsip_dlg_create_uas_and_inc_lock( pjsip_ua_instance(), 
     729                                                rdata, 
     730                                                &local_uri, /* contact */ 
     731                                                &dlg); 
    732732    if (status != PJ_SUCCESS) { 
    733733        pjsip_endpt_respond_stateless(g_endpt, rdata, 500, NULL, 
     
    742742    status = pjmedia_endpt_create_sdp( g_med_endpt, rdata->tp_info.pool, 
    743743                                       MAX_MEDIA_CNT, g_sock_info, &local_sdp); 
    744     PJ_ASSERT_RETURN(status == PJ_SUCCESS, PJ_TRUE); 
     744    pj_assert(status == PJ_SUCCESS); 
     745    if (status != PJ_SUCCESS) { 
     746        pjsip_dlg_dec_lock(dlg); 
     747        return PJ_TRUE; 
     748    } 
    745749 
    746750 
     
    750754     */ 
    751755    status = pjsip_inv_create_uas( dlg, rdata, local_sdp, 0, &g_inv); 
    752     PJ_ASSERT_RETURN(status == PJ_SUCCESS, PJ_TRUE); 
     756    pj_assert(status == PJ_SUCCESS); 
     757    if (status != PJ_SUCCESS) { 
     758        pjsip_dlg_dec_lock(dlg); 
     759        return PJ_TRUE; 
     760    } 
     761 
     762    /* 
     763     * Invite session has been created, decrement & release dialog lock. 
     764     */ 
     765    pjsip_dlg_dec_lock(dlg); 
    753766 
    754767 
  • pjproject/trunk/pjsip-apps/src/samples/sipecho.c

    r4537 r5241  
    418418    char temp[80], hostip[PJ_INET6_ADDRSTRLEN]; 
    419419    pj_str_t local_uri; 
    420     pjsip_dialog *dlg; 
     420    pjsip_dialog *dlg = NULL; 
    421421    pjsip_rdata_sdp_info *sdp_info; 
    422422    pjmedia_sdp_session *answer = NULL; 
     
    499499    local_uri = pj_str(temp); 
    500500 
    501     status = pjsip_dlg_create_uas( pjsip_ua_instance(), rdata, 
    502                                    &local_uri, &dlg); 
     501    status = pjsip_dlg_create_uas_and_inc_lock( pjsip_ua_instance(), rdata, 
     502                                                &local_uri, &dlg); 
    503503 
    504504    if (status == PJ_SUCCESS) 
    505505        answer = create_answer((int)(call-app.call), dlg->pool, sdp_info->sdp); 
     506 
    506507    if (status == PJ_SUCCESS) 
    507508        status = pjsip_inv_create_uas( dlg, rdata, answer, 0, &call->inv); 
     509 
     510    if (dlg) 
     511        pjsip_dlg_dec_lock(dlg); 
     512 
    508513    if (status == PJ_SUCCESS) 
    509514        status = pjsip_inv_initial_answer(call->inv, rdata, 100, 
  • pjproject/trunk/pjsip-apps/src/samples/siprtp.c

    r5170 r5241  
    638638 
    639639    /* Create UAS dialog */ 
    640     status = pjsip_dlg_create_uas( pjsip_ua_instance(), rdata, 
    641                                    &app.local_contact, &dlg); 
     640    status = pjsip_dlg_create_uas_and_inc_lock( pjsip_ua_instance(), rdata, 
     641                                                &app.local_contact, &dlg); 
    642642    if (status != PJ_SUCCESS) { 
    643643        const pj_str_t reason = pj_str("Unable to create dialog"); 
     
    656656        pjsip_dlg_create_response(dlg, rdata, 500, NULL, &tdata); 
    657657        pjsip_dlg_send_response(dlg, pjsip_rdata_get_tsx(rdata), tdata); 
     658        pjsip_dlg_dec_lock(dlg); 
    658659        return; 
    659660    } 
    660661     
     662    /* Invite session has been created, decrement & release dialog lock */ 
     663    pjsip_dlg_dec_lock(dlg); 
    661664 
    662665    /* Attach call data to invite session */ 
  • pjproject/trunk/pjsip/include/pjsip-ua/sip_replaces.h

    r3553 r5241  
    139139    // Create UAS Invite session as usual. 
    140140    // 
    141     status = pjsip_dlg_create_uas(.., rdata, .., &dlg); 
     141    status = pjsip_dlg_create_uas_and_inc_lock(.., rdata, .., &dlg); 
    142142    .. 
    143143    status = pjsip_inv_create_uas(dlg, .., &inv); 
  • pjproject/trunk/pjsip/include/pjsip/sip_dialog.h

    r4173 r5241  
    6161PJ_BEGIN_DECL 
    6262 
     63 
     64/* Deprecated API pjsip_dlg_create_uas() due to a fatal bug of possible 
     65 * premature dialog destroy. Application should not change this setting, 
     66 * unless it uses single worker thread. 
     67 * See also https://trac.pjsip.org/repos/ticket/1902. 
     68 */ 
     69#ifndef DEPRECATED_FOR_TICKET_1902 
     70#  define DEPRECATED_FOR_TICKET_1902      1 
     71#endif 
    6372 
    6473/** 
     
    241250 
    242251 
     252#if !DEPRECATED_FOR_TICKET_1902 
    243253/** 
    244254 * Initialize UAS dialog from the information found in the incoming request  
     
    280290                                            const pj_str_t *contact, 
    281291                                            pjsip_dialog **p_dlg); 
     292#endif 
     293 
     294 
     295/** 
     296 * Initialize UAS dialog from the information found in the incoming request  
     297 * that creates a dialog (such as INVITE, REFER, or SUBSCRIBE), and set the  
     298 * local Contact to contact. If contact is not specified, the local contact  
     299 * is initialized from the URI in the To header in the request.  
     300 * 
     301 * This function will also create UAS transaction for the incoming request, 
     302 * and associate the transaction to the rdata. Application can query the 
     303 * transaction used to handle this request by calling #pjsip_rdata_get_tsx() 
     304 * after this function returns. 
     305 * 
     306 * Note that initially, the session count in the dialog will be initialized  
     307 * to 1 (one), and the dialog is locked. Application needs to explicitly call 
     308 * #pjsip_dlg_dec_lock() to release the lock and decrease the session count. 
     309 * 
     310 * 
     311 * @param ua                The user agent module instance. 
     312 * @param rdata             The incoming request that creates the dialog, 
     313 *                          such as INVITE, SUBSCRIBE, or REFER. 
     314 * @param contact           Optional dialog local Contact to be put as Contact 
     315 *                          header value, hence the format must follow 
     316 *                          RFC 3261 Section 20.10: 
     317 *                          When the header field value contains a display  
     318 *                          name, the URI including all URI parameters is  
     319 *                          enclosed in "<" and ">".  If no "<" and ">" are  
     320 *                          present, all parameters after the URI are header 
     321 *                          parameters, not URI parameters.  The display name  
     322 *                          can be tokens, or a quoted string, if a larger  
     323 *                          character set is desired. 
     324 *                          If this argument is NULL, the local contact will be 
     325 *                          initialized from the value of To header in the 
     326 *                          request. 
     327 * @param p_dlg             Pointer to receive the dialog. 
     328 * 
     329 * @return                  PJ_SUCCESS on success. 
     330 */ 
     331PJ_DECL(pj_status_t) 
     332pjsip_dlg_create_uas_and_inc_lock(    pjsip_user_agent *ua, 
     333                                      pjsip_rx_data *rdata, 
     334                                      const pj_str_t *contact, 
     335                                      pjsip_dialog **p_dlg); 
    282336 
    283337 
     
    362416 * established, the route set can not be changed. 
    363417 * 
    364  * For UAS dialog,the route set will be initialized in pjsip_dlg_create_uas() 
    365  * from the Record-Route headers in the incoming request. 
     418 * For UAS dialog, the route set will be initialized in 
     419 * pjsip_dlg_create_uas_and_inc_lock() from the Record-Route headers in 
     420 * the incoming request. 
    366421 * 
    367422 * The route_set argument is standard list of Route headers (i.e. with  
  • pjproject/trunk/pjsip/src/pjsip/sip_dialog.c

    r5180 r5241  
    312312 * Create UAS dialog. 
    313313 */ 
    314 PJ_DEF(pj_status_t) pjsip_dlg_create_uas(   pjsip_user_agent *ua, 
    315                                             pjsip_rx_data *rdata, 
    316                                             const pj_str_t *contact, 
    317                                             pjsip_dialog **p_dlg) 
     314pj_status_t create_uas_dialog( pjsip_user_agent *ua, 
     315                               pjsip_rx_data *rdata, 
     316                               const pj_str_t *contact, 
     317                               pj_bool_t inc_lock, 
     318                               pjsip_dialog **p_dlg) 
    318319{ 
    319320    pj_status_t status; 
     
    511512        goto on_error; 
    512513 
     514    /* Increment the dialog's lock since tsx may cause the dialog to be 
     515     * destroyed prematurely (such as in case of transport error). 
     516     */ 
     517    if (inc_lock) 
     518        pjsip_dlg_inc_lock(dlg); 
     519 
    513520    /* Create UAS transaction for this request. */ 
    514521    status = pjsip_tsx_create_uas(dlg->ua, rdata, &tsx); 
     
    553560    } 
    554561 
    555     destroy_dialog(dlg, PJ_FALSE); 
     562    if (inc_lock) { 
     563        pjsip_dlg_dec_lock(dlg); 
     564    } else { 
     565        destroy_dialog(dlg, PJ_FALSE); 
     566    } 
     567     
    556568    return status; 
     569} 
     570 
     571 
     572#if !DEPRECATED_FOR_TICKET_1902 
     573/* 
     574 * Create UAS dialog. 
     575 */ 
     576PJ_DEF(pj_status_t) pjsip_dlg_create_uas(   pjsip_user_agent *ua, 
     577                                            pjsip_rx_data *rdata, 
     578                                            const pj_str_t *contact, 
     579                                            pjsip_dialog **p_dlg) 
     580{ 
     581    return create_uas_dialog(ua, rdata, contact, PJ_FALSE, p_dlg); 
     582} 
     583#endif 
     584 
     585 
     586/* 
     587 * Create UAS dialog and increase its session count. 
     588 */ 
     589PJ_DEF(pj_status_t) 
     590pjsip_dlg_create_uas_and_inc_lock(    pjsip_user_agent *ua, 
     591                                      pjsip_rx_data *rdata, 
     592                                      const pj_str_t *contact, 
     593                                      pjsip_dialog **p_dlg) 
     594{ 
     595    return create_uas_dialog(ua, rdata, contact, PJ_TRUE, p_dlg); 
    557596} 
    558597 
  • pjproject/trunk/pjsip/src/pjsip/sip_transaction.c

    r5147 r5241  
    139139#define TRANSPORT_ERR_TIMER     3 
    140140 
     141/* Flags for tsx_set_state() */ 
     142enum 
     143{ 
     144    NO_NOTIFY = 1, 
     145    NO_SCHEDULE_HANDLER = 2, 
     146}; 
    141147 
    142148/* Prototypes. */ 
     
    170176                                  pjsip_tsx_state_e state, 
    171177                                  pjsip_event_id_e event_src_type, 
    172                                   void *event_src ); 
    173 static void        tsx_set_state_no_notify( pjsip_transaction *tsx, 
    174                                             pjsip_tsx_state_e state, 
    175                                             pjsip_event_id_e event_src_type, 
    176                                             void *event_src ); 
     178                                  void *event_src, 
     179                                  int flag); 
    177180static void        tsx_set_status_code(pjsip_transaction *tsx, 
    178181                                       int code, const pj_str_t *reason); 
     
    11041107        if (tsx->state < PJSIP_TSX_STATE_TERMINATED) { 
    11051108            pjsip_tsx_state_e prev_state; 
     1109            pj_time_val timeout = { 0, 0 }; 
    11061110 
    11071111            pj_grp_lock_acquire(tsx->grp_lock); 
     
    11231127             * https://trac.pjsip.org/repos/ticket/1646 
    11241128             */ 
    1125             tsx_set_state_no_notify( tsx, PJSIP_TSX_STATE_TERMINATED, 
    1126                                      PJSIP_EVENT_TRANSPORT_ERROR, NULL); 
     1129            /* Also don't schedule tsx handler, otherwise we'll get race 
     1130             * condition of TU notifications due to delayed TERMINATED 
     1131             * state TU notification. It happened in multiple worker threads 
     1132             * environment between TERMINATED & DESTROYED! See: 
     1133             * https://trac.pjsip.org/repos/ticket/1902 
     1134             */ 
     1135            tsx_set_state( tsx, PJSIP_TSX_STATE_TERMINATED, 
     1136                           PJSIP_EVENT_TRANSPORT_ERROR, NULL, 
     1137                           NO_NOTIFY | NO_SCHEDULE_HANDLER); 
    11271138            pj_grp_lock_release(tsx->grp_lock); 
    11281139 
     
    11391150                (*tsx->tsx_user->on_tsx_state)(tsx, &e); 
    11401151            } 
     1152 
     1153            /* Now let's schedule the tsx handler */ 
     1154            tsx_schedule_timer(tsx, &tsx->timeout_timer, &timeout, 
     1155                               TIMEOUT_TIMER); 
    11411156        } 
    11421157    } else { 
     
    11681183                           pjsip_tsx_state_e state, 
    11691184                           pjsip_event_id_e event_src_type, 
    1170                            void *event_src ) 
     1185                           void *event_src, 
     1186                           int flag) 
    11711187{ 
    11721188    pjsip_tsx_state_e prev_state = tsx->state; 
     
    11931209     * rx event. 
    11941210     */ 
    1195     if (event_src_type==PJSIP_EVENT_RX_MSG && tsx->tsx_user) { 
     1211    if (event_src_type==PJSIP_EVENT_RX_MSG && tsx->tsx_user && 
     1212        (flag & NO_NOTIFY)==0) 
     1213    { 
    11961214        pjsip_rx_data *rdata = (pjsip_rx_data*) event_src; 
    11971215 
     
    12071225 
    12081226    /* Inform TU about state changed. */ 
    1209     if (tsx->tsx_user && tsx->tsx_user->on_tsx_state) { 
     1227    if (tsx->tsx_user && tsx->tsx_user->on_tsx_state && 
     1228        (flag & NO_NOTIFY) == 0) 
     1229    { 
    12101230        pjsip_event e; 
    12111231        PJSIP_EVENT_INIT_TSX_STATE(e, tsx, event_src_type, event_src, 
     
    12191239     */ 
    12201240    if (state == PJSIP_TSX_STATE_TERMINATED) { 
    1221         pj_time_val timeout = {0, 0}; 
     1241        pj_time_val timeout = { 0, 0 }; 
    12221242 
    12231243        /* If we're still waiting for a message to be sent.. */ 
     
    12371257        lock_timer(tsx); 
    12381258        tsx_cancel_timer(tsx, &tsx->timeout_timer); 
    1239         tsx_schedule_timer( tsx, &tsx->timeout_timer, &timeout, TIMEOUT_TIMER); 
     1259        if ((flag & NO_SCHEDULE_HANDLER) == 0) { 
     1260            tsx_schedule_timer(tsx, &tsx->timeout_timer, &timeout, 
     1261                               TIMEOUT_TIMER); 
     1262        } 
    12401263        unlock_timer(tsx); 
    12411264 
     
    12501273 
    12511274    pj_log_pop_indent(); 
    1252 } 
    1253  
    1254 /* Set transaction state without notifying tsx_user */ 
    1255 static void tsx_set_state_no_notify( pjsip_transaction *tsx, 
    1256                                      pjsip_tsx_state_e state, 
    1257                                      pjsip_event_id_e event_src_type, 
    1258                                      void *event_src ) 
    1259 { 
    1260     pjsip_module *tsx_user = tsx->tsx_user; 
    1261     tsx->tsx_user = NULL; 
    1262     tsx_set_state(tsx, state, event_src_type, event_src); 
    1263     tsx->tsx_user = tsx_user; 
    12641275} 
    12651276 
     
    16271638    if (tsx->state < PJSIP_TSX_STATE_TERMINATED) { 
    16281639        tsx_set_status_code(tsx, code, NULL); 
    1629         tsx_set_state( tsx, PJSIP_TSX_STATE_TERMINATED, PJSIP_EVENT_USER, NULL); 
     1640        tsx_set_state( tsx, PJSIP_TSX_STATE_TERMINATED, PJSIP_EVENT_USER, 
     1641                       NULL, 0); 
    16301642    } 
    16311643    pj_grp_lock_release(tsx->grp_lock); 
     
    18381850        if (tsx->transport_flag & TSX_HAS_PENDING_DESTROY) { 
    18391851            tsx_set_state( tsx, PJSIP_TSX_STATE_DESTROYED,  
    1840                            PJSIP_EVENT_UNKNOWN, NULL ); 
     1852                           PJSIP_EVENT_UNKNOWN, NULL, 0 ); 
    18411853            pj_grp_lock_release(tsx->grp_lock); 
    18421854            return; 
     
    19131925            { 
    19141926                tsx_set_state( tsx, PJSIP_TSX_STATE_TERMINATED,  
    1915                                PJSIP_EVENT_TRANSPORT_ERROR, send_state->tdata); 
     1927                               PJSIP_EVENT_TRANSPORT_ERROR, 
     1928                               send_state->tdata, 0); 
    19161929            }  
    19171930            /* Don't forget to destroy if we have pending destroy flag 
     
    19211934            { 
    19221935                tsx_set_state( tsx, PJSIP_TSX_STATE_DESTROYED,  
    1923                                PJSIP_EVENT_TRANSPORT_ERROR, send_state->tdata); 
     1936                               PJSIP_EVENT_TRANSPORT_ERROR, 
     1937                               send_state->tdata, 0); 
    19241938            } 
    19251939 
     
    21232137        tsx_set_status_code(tsx, PJSIP_SC_TSX_TRANSPORT_ERROR, &err); 
    21242138        tsx_set_state( tsx, PJSIP_TSX_STATE_TERMINATED,  
    2125                        PJSIP_EVENT_TRANSPORT_ERROR, NULL ); 
     2139                       PJSIP_EVENT_TRANSPORT_ERROR, NULL, 0 ); 
    21262140 
    21272141        return status; 
     
    23552369                    PJSIP_REQUEST_MSG); 
    23562370        tsx_set_state( tsx, PJSIP_TSX_STATE_TRYING, PJSIP_EVENT_RX_MSG, 
    2357                        event->body.rx_msg.rdata); 
     2371                       event->body.rx_msg.rdata, 0); 
    23582372 
    23592373    } else { 
     
    24102424        /* Move state. */ 
    24112425        tsx_set_state( tsx, PJSIP_TSX_STATE_CALLING,  
    2412                        PJSIP_EVENT_TX_MSG, tdata); 
     2426                       PJSIP_EVENT_TX_MSG, tdata, 0); 
    24132427    } 
    24142428 
     
    24512465        /* Inform TU. */ 
    24522466        tsx_set_state( tsx, PJSIP_TSX_STATE_TERMINATED, 
    2453                        PJSIP_EVENT_TIMER, &tsx->timeout_timer); 
     2467                       PJSIP_EVENT_TIMER, &tsx->timeout_timer, 0); 
    24542468 
    24552469        /* Transaction is destroyed */ 
     
    25702584 
    25712585        tsx_set_state( tsx, PJSIP_TSX_STATE_PROCEEDING,  
    2572                        PJSIP_EVENT_TX_MSG, event->body.tx_msg.tdata); 
     2586                       PJSIP_EVENT_TX_MSG, event->body.tx_msg.tdata, 0); 
    25732587 
    25742588    } 
     
    26512665 
    26522666            tsx_set_state( tsx, PJSIP_TSX_STATE_PROCEEDING,  
    2653                            PJSIP_EVENT_TX_MSG, tdata ); 
     2667                           PJSIP_EVENT_TX_MSG, tdata, 0 ); 
    26542668 
    26552669            /* Retransmit provisional response every 1 minute if this is 
     
    26852699                 */ 
    26862700                tsx_set_state( tsx, PJSIP_TSX_STATE_TERMINATED,  
    2687                                PJSIP_EVENT_TX_MSG, tdata ); 
     2701                               PJSIP_EVENT_TX_MSG, tdata, 0 ); 
    26882702 
    26892703                /* Transaction is destroyed. */ 
     
    27432757                /* Set state to "Completed" */ 
    27442758                tsx_set_state( tsx, PJSIP_TSX_STATE_COMPLETED,  
    2745                                PJSIP_EVENT_TX_MSG, tdata ); 
     2759                               PJSIP_EVENT_TX_MSG, tdata, 0 ); 
    27462760            } 
    27472761 
     
    28022816            /* Inform TU */ 
    28032817            tsx_set_state( tsx, PJSIP_TSX_STATE_COMPLETED,  
    2804                            PJSIP_EVENT_TX_MSG, tdata ); 
     2818                           PJSIP_EVENT_TX_MSG, tdata, 0 ); 
    28052819 
    28062820        } else { 
     
    28362850 
    28372851        tsx_set_state( tsx, PJSIP_TSX_STATE_TERMINATED, 
    2838                        PJSIP_EVENT_TIMER, &tsx->timeout_timer); 
     2852                       PJSIP_EVENT_TIMER, &tsx->timeout_timer, 0); 
    28392853 
    28402854        return PJ_EBUG; 
     
    29012915        /* Inform the message to TU. */ 
    29022916        tsx_set_state( tsx, PJSIP_TSX_STATE_PROCEEDING,  
    2903                        PJSIP_EVENT_RX_MSG, event->body.rx_msg.rdata ); 
     2917                       PJSIP_EVENT_RX_MSG, event->body.rx_msg.rdata, 0 ); 
    29042918 
    29052919    } else if (PJSIP_IS_STATUS_IN_CLASS(tsx->status_code,200)) { 
     
    29152929        if (tsx->method.id == PJSIP_INVITE_METHOD) { 
    29162930            tsx_set_state( tsx, PJSIP_TSX_STATE_TERMINATED,  
    2917                            PJSIP_EVENT_RX_MSG, event->body.rx_msg.rdata ); 
     2931                           PJSIP_EVENT_RX_MSG, event->body.rx_msg.rdata, 0 ); 
    29182932            //return PJSIP_ETSXDESTROYED; 
    29192933 
     
    29422956            /* Move state to Completed, inform TU. */ 
    29432957            tsx_set_state( tsx, PJSIP_TSX_STATE_COMPLETED,  
    2944                            PJSIP_EVENT_RX_MSG, event->body.rx_msg.rdata ); 
     2958                           PJSIP_EVENT_RX_MSG, event->body.rx_msg.rdata, 0 ); 
    29452959        } 
    29462960 
     
    29502964        /* Inform TU. */ 
    29512965        tsx_set_state( tsx, PJSIP_TSX_STATE_TERMINATED, 
    2952                        PJSIP_EVENT_TIMER, &tsx->timeout_timer); 
     2966                       PJSIP_EVENT_TIMER, &tsx->timeout_timer, 0); 
    29532967 
    29542968 
     
    30413055        /* Inform TU. */ 
    30423056        tsx_set_state( tsx, PJSIP_TSX_STATE_COMPLETED,  
    3043                        PJSIP_EVENT_RX_MSG, event->body.rx_msg.rdata); 
     3057                       PJSIP_EVENT_RX_MSG, event->body.rx_msg.rdata, 0); 
    30443058 
    30453059        /* Generate and send ACK for INVITE. */ 
     
    31523166            /* Move state to "Confirmed" */ 
    31533167            tsx_set_state( tsx, PJSIP_TSX_STATE_CONFIRMED,  
    3154                            PJSIP_EVENT_RX_MSG, event->body.rx_msg.rdata ); 
     3168                           PJSIP_EVENT_RX_MSG, event->body.rx_msg.rdata, 0 ); 
    31553169        }        
    31563170 
     
    31763190 
    31773191                tsx_set_state( tsx, PJSIP_TSX_STATE_TERMINATED,  
    3178                                PJSIP_EVENT_TIMER, &tsx->timeout_timer ); 
     3192                               PJSIP_EVENT_TIMER, &tsx->timeout_timer, 0 ); 
    31793193 
    31803194                //return PJSIP_ETSXDESTROYED; 
     
    31833197                /* Transaction terminated, it can now be deleted. */ 
    31843198                tsx_set_state( tsx, PJSIP_TSX_STATE_TERMINATED,  
    3185                                PJSIP_EVENT_TIMER, &tsx->timeout_timer ); 
     3199                               PJSIP_EVENT_TIMER, &tsx->timeout_timer, 0 ); 
    31863200                //return PJSIP_ETSXDESTROYED; 
    31873201            } 
     
    32163230        /* Move to Terminated state. */ 
    32173231        tsx_set_state( tsx, PJSIP_TSX_STATE_TERMINATED, 
    3218                        PJSIP_EVENT_TIMER, event->body.timer.entry ); 
     3232                       PJSIP_EVENT_TIMER, event->body.timer.entry, 0 ); 
    32193233 
    32203234        /* Transaction has been destroyed. */ 
     
    32913305            /* Move to Terminated state. */ 
    32923306            tsx_set_state( tsx, PJSIP_TSX_STATE_TERMINATED, 
    3293                            PJSIP_EVENT_TIMER, &tsx->timeout_timer ); 
     3307                           PJSIP_EVENT_TIMER, &tsx->timeout_timer, 0 ); 
    32943308 
    32953309            /* Transaction has been destroyed. */ 
     
    33223336    /* Destroy this transaction */ 
    33233337    tsx_set_state(tsx, PJSIP_TSX_STATE_DESTROYED,  
    3324                   event->type, event->body.user.user1 ); 
     3338                  event->type, event->body.user.user1, 0 ); 
    33253339 
    33263340    return PJ_SUCCESS; 
  • pjproject/trunk/pjsip/src/pjsip/sip_ua_layer.c

    r4537 r5241  
    278278/* 
    279279 * Register new dialog. Called by pjsip_dlg_create_uac() and 
    280  * pjsip_dlg_create_uas(); 
     280 * pjsip_dlg_create_uas_and_inc_lock(); 
    281281 */ 
    282282PJ_DEF(pj_status_t) pjsip_ua_register_dlg( pjsip_user_agent *ua, 
  • pjproject/trunk/pjsip/src/pjsua-lib/pjsua_call.c

    r5232 r5241  
    983983    pjsip_tx_data *response = NULL; 
    984984    unsigned options = 0; 
     985    pjsip_dialog *dlg = call->async_call.dlg; 
    985986    int sip_err_code = (info? info->sip_err_code: 0); 
    986987    pj_status_t status = (info? info->status: PJ_SUCCESS); 
    987988 
    988989    PJSUA_LOCK(); 
     990     
     991    /* Increment the dialog's lock to prevent it to be destroyed prematurely, 
     992     * such as in case of transport error. 
     993     */ 
     994    pjsip_dlg_inc_lock(dlg); 
     995 
     996    /* Decrement dialog session. */ 
     997    pjsip_dlg_dec_session(dlg, &pjsua_var.mod);     
    989998 
    990999    if (status != PJ_SUCCESS) { 
     
    9971006        pjsua_media_channel_deinit(call->index); 
    9981007        call->med_ch_cb = NULL; 
     1008        pjsip_dlg_dec_lock(dlg); 
    9991009        PJSUA_UNLOCK(); 
    10001010        return PJ_SUCCESS; 
     
    10681078        } 
    10691079    } 
    1070  
     1080     
     1081    pjsip_dlg_dec_lock(dlg); 
     1082     
    10711083    PJSUA_UNLOCK(); 
    10721084    return status; 
     
    13521364 
    13531365    /* Create dialog: */ 
    1354     status = pjsip_dlg_create_uas( pjsip_ua_instance(), rdata, 
    1355                                    &contact, &dlg); 
     1366    status = pjsip_dlg_create_uas_and_inc_lock( pjsip_ua_instance(), rdata, 
     1367                                                &contact, &dlg); 
    13561368    if (status != PJ_SUCCESS) { 
    13571369        pjsip_endpt_respond_stateless(pjsua_var.endpt, rdata, 500, NULL, 
     
    14601472    call->async_call.dlg = dlg; 
    14611473    pj_list_init(&call->async_call.call_var.inc_call.answers); 
     1474 
     1475    pjsip_dlg_inc_session(dlg, &pjsua_var.mod); 
    14621476 
    14631477    /* Init media channel, only when there is offer or call replace request. 
     
    15021516            pjsip_dlg_dec_lock(dlg); 
    15031517 
     1518            pjsip_dlg_dec_session(dlg, &pjsua_var.mod); 
     1519 
    15041520            call->inv = NULL; 
    15051521            call->async_call.dlg = NULL; 
     
    16191635    /* This INVITE request has been handled. */ 
    16201636on_return: 
     1637    if (dlg) { 
     1638        pjsip_dlg_dec_lock(dlg); 
     1639    } 
     1640     
    16211641    pj_log_pop_indent(); 
    16221642    PJSUA_UNLOCK(); 
  • pjproject/trunk/pjsip/src/pjsua-lib/pjsua_core.c

    r5170 r5241  
    11061106 
    11071107        for (ii=0; ii<pjsua_var.ua_cfg.thread_cnt; ++ii) { 
    1108             status = pj_thread_create(pjsua_var.pool, "pjsua", &worker_thread, 
     1108            char thread_name[16]; 
     1109            pj_ansi_snprintf(thread_name, 16, "pjsua_%d", ii); 
     1110            status = pj_thread_create(pjsua_var.pool, thread_name, &worker_thread, 
    11091111                                      NULL, 0, 0, &pjsua_var.thread[ii]); 
    11101112            if (status != PJ_SUCCESS) 
  • pjproject/trunk/pjsip/src/pjsua-lib/pjsua_pres.c

    r5224 r5241  
    856856 
    857857    /* Create UAS dialog: */ 
    858     status = pjsip_dlg_create_uas(pjsip_ua_instance(), rdata,  
    859                                   &contact, &dlg); 
     858    status = pjsip_dlg_create_uas_and_inc_lock(pjsip_ua_instance(), rdata, 
     859                                               &contact, &dlg); 
    860860    if (status != PJ_SUCCESS) { 
    861861        pjsua_perror(THIS_FILE,  
     
    922922        } 
    923923 
     924        pjsip_dlg_dec_lock(dlg); 
    924925        PJSUA_UNLOCK(); 
    925926        pj_log_pop_indent(); 
    926927        return PJ_TRUE; 
    927928    } 
     929 
     930    /* Subscription has been created, decrement & release dlg lock */ 
     931    pjsip_dlg_dec_lock(dlg); 
    928932 
    929933    /* If account is locked to specific transport, then lock dialog 
     
    10361040 
    10371041    /* Done: */ 
    1038  
    10391042    PJSUA_UNLOCK(); 
    10401043    pj_log_pop_indent(); 
  • pjproject/trunk/pjsip/src/test/inv_offer_answer_test.c

    r3553 r5241  
    309309         */ 
    310310        uri = pj_str(CONTACT); 
    311         status = pjsip_dlg_create_uas(pjsip_ua_instance(), rdata, 
    312                                       &uri, &dlg); 
     311        status = pjsip_dlg_create_uas_and_inc_lock(pjsip_ua_instance(), rdata, 
     312                                                   &uri, &dlg); 
    313313        pj_assert(status == PJ_SUCCESS); 
    314314 
     
    322322        status = pjsip_inv_create_uas(dlg, rdata, sdp, inv_test.param.inv_option, &inv_test.uas); 
    323323        pj_assert(status == PJ_SUCCESS); 
     324        pjsip_dlg_dec_lock(dlg); 
    324325 
    325326        TRACE_((THIS_FILE, "    Sending 183 with SDP")); 
Note: See TracChangeset for help on using the changeset viewer.