Ignore:
Timestamp:
May 20, 2011 8:47:14 AM (9 years ago)
Author:
nanang
Message:

Fix #1235: fixed lock codec to check all active media (previously only checked one media: first active audio).

File:
1 edited

Legend:

Unmodified
Added
Removed
  • pjproject/branches/projects/2.0-dev/pjsip/src/pjsua-lib/pjsua_call.c

    r3531 r3573  
    31753175    const pj_str_t STR_UPDATE = {"UPDATE", 6}; 
    31763176    const pjmedia_sdp_session *local_sdp = NULL, *new_sdp; 
    3177     const pjmedia_sdp_media *ref_m; 
    3178     pjmedia_sdp_media *m; 
    3179     pjsua_call_media *call_med = &call->media[call->audio_idx]; 
    3180     unsigned i, codec_cnt = 0; 
     3177    unsigned i; 
    31813178    pj_bool_t rem_can_update; 
     3179    pj_bool_t need_lock_codec = PJ_FALSE; 
    31823180    pjsip_tx_data *tdata; 
    31833181    pj_status_t status; 
     
    32113209        return PJMEDIA_SDP_EINVER; 
    32123210 
    3213     /* Verify if media is deactivated */ 
    3214     if (call_med->state == PJSUA_CALL_MEDIA_NONE || 
    3215         call_med->state == PJSUA_CALL_MEDIA_ERROR || 
    3216         call_med->dir == PJMEDIA_DIR_NONE) 
    3217     { 
    3218         return PJ_EINVALIDOP; 
    3219     } 
    3220  
    32213211    PJ_LOG(3, (THIS_FILE, "Updating media session to use only one codec..")); 
    32223212 
     
    32263216     */ 
    32273217    new_sdp = pjmedia_sdp_session_clone(call->inv->pool_prov, local_sdp); 
    3228     m = new_sdp->media[call->audio_idx]; 
    3229     ref_m = local_sdp->media[call->audio_idx]; 
    3230     pj_assert(ref_m->desc.port); 
    3231     codec_cnt = 0; 
    3232     i = 0; 
    3233     while (i < m->desc.fmt_count) { 
    3234         pjmedia_sdp_attr *a; 
    3235         pj_str_t *fmt = &m->desc.fmt[i]; 
    3236  
    3237         if (is_non_av_fmt(m, fmt) || (++codec_cnt == 1)) { 
    3238             ++i; 
     3218 
     3219    for (i = 0; i < call->med_cnt; ++i) { 
     3220        unsigned j = 0, codec_cnt = 0; 
     3221        const pjmedia_sdp_media *ref_m; 
     3222        pjmedia_sdp_media *m; 
     3223        pjsua_call_media *call_med = &call->media[i]; 
     3224 
     3225        /* Verify if media is deactivated */ 
     3226        if (call_med->state == PJSUA_CALL_MEDIA_NONE || 
     3227            call_med->state == PJSUA_CALL_MEDIA_ERROR || 
     3228            call_med->dir == PJMEDIA_DIR_NONE) 
     3229        { 
    32393230            continue; 
    32403231        } 
    32413232 
    3242         /* Remove format */ 
    3243         a = pjmedia_sdp_attr_find2(m->attr_count, m->attr, "rtpmap", fmt); 
    3244         if (a) pjmedia_sdp_attr_remove(&m->attr_count, m->attr, a); 
    3245         a = pjmedia_sdp_attr_find2(m->attr_count, m->attr, "fmtp", fmt); 
    3246         if (a) pjmedia_sdp_attr_remove(&m->attr_count, m->attr, a); 
    3247         pj_array_erase(m->desc.fmt, sizeof(m->desc.fmt[0]), 
    3248                        m->desc.fmt_count, i); 
    3249         --m->desc.fmt_count; 
     3233        ref_m = local_sdp->media[i]; 
     3234        m = new_sdp->media[i]; 
     3235 
     3236        /* Verify that media must be active. */ 
     3237        pj_assert(ref_m->desc.port); 
     3238 
     3239        while (j < m->desc.fmt_count) { 
     3240            pjmedia_sdp_attr *a; 
     3241            pj_str_t *fmt = &m->desc.fmt[j]; 
     3242 
     3243            if (is_non_av_fmt(m, fmt) || (++codec_cnt == 1)) { 
     3244                ++j; 
     3245                continue; 
     3246            } 
     3247 
     3248            /* Remove format */ 
     3249            a = pjmedia_sdp_attr_find2(m->attr_count, m->attr, "rtpmap", fmt); 
     3250            if (a) pjmedia_sdp_attr_remove(&m->attr_count, m->attr, a); 
     3251            a = pjmedia_sdp_attr_find2(m->attr_count, m->attr, "fmtp", fmt); 
     3252            if (a) pjmedia_sdp_attr_remove(&m->attr_count, m->attr, a); 
     3253            pj_array_erase(m->desc.fmt, sizeof(m->desc.fmt[0]), 
     3254                           m->desc.fmt_count, j); 
     3255            --m->desc.fmt_count; 
     3256        } 
     3257         
     3258        need_lock_codec |= (ref_m->desc.fmt_count > m->desc.fmt_count); 
    32503259    } 
    32513260 
     
    32543263     * increase the SDP version (should not happen!). 
    32553264     */ 
    3256     if (ref_m->desc.fmt_count == m->desc.fmt_count) 
     3265    if (!need_lock_codec) 
    32573266        return PJ_SUCCESS; 
    32583267 
     
    33023311    pjsip_inv_session *inv = call->inv; 
    33033312    const pjmedia_sdp_session *local_sdp, *remote_sdp; 
    3304     const pjmedia_sdp_media *rem_m, *loc_m; 
    3305     unsigned codec_cnt=0, i; 
    3306     pjsua_call_media *call_med = &call->media[call->audio_idx]; 
    33073313    pj_time_val delay = {0, 0}; 
    33083314    const pj_str_t st_update = {"UPDATE", 6}; 
     3315    unsigned i; 
     3316    pj_bool_t has_mult_fmt = PJ_FALSE; 
    33093317    pj_status_t status; 
    33103318 
     
    33183326    /* Skip this if we are the answerer */ 
    33193327    if (!inv->neg || !pjmedia_sdp_neg_was_answer_remote(inv->neg)) { 
    3320         return PJ_SUCCESS; 
    3321     } 
    3322  
    3323     /* Skip this if the media is inactive or error */ 
    3324     if (call_med->state == PJSUA_CALL_MEDIA_NONE || 
    3325         call_med->state == PJSUA_CALL_MEDIA_ERROR || 
    3326         call_med->dir == PJMEDIA_DIR_NONE) 
    3327     { 
    33283328        return PJ_SUCCESS; 
    33293329    } 
     
    33473347        return status; 
    33483348 
    3349     PJ_ASSERT_RETURN(call->audio_idx>=0 && 
    3350                      call->audio_idx < (int)remote_sdp->media_count, 
    3351                      PJ_EINVALIDOP); 
    3352  
    3353     rem_m = remote_sdp->media[call->audio_idx]; 
    3354     loc_m = local_sdp->media[call->audio_idx]; 
    3355  
    3356     /* Verify that media must be active. */ 
    3357     pj_assert(loc_m->desc.port && rem_m->desc.port); 
    3358  
    3359     /* Count the formats in the answer. */ 
    3360     if (rem_m->desc.fmt_count==1) { 
    3361         codec_cnt = 1; 
    3362     } else { 
    3363         for (i=0; i<rem_m->desc.fmt_count && codec_cnt <= 1; ++i) { 
    3364             if (!is_non_av_fmt(rem_m, &rem_m->desc.fmt[i])) 
    3365                 ++codec_cnt; 
    3366         } 
    3367     } 
    3368     if (codec_cnt <= 1) { 
    3369         /* Answer contains single codec. */ 
    3370         call->lock_codec.retry_cnt = 0; 
     3349    /* Find multiple codecs answer in all media */ 
     3350    for (i = 0; i < call->med_cnt; ++i) { 
     3351        pjsua_call_media *call_med = &call->media[i]; 
     3352        const pjmedia_sdp_media *rem_m, *loc_m; 
     3353        unsigned codec_cnt = 0; 
     3354 
     3355        /* Skip this if the media is inactive or error */ 
     3356        if (call_med->state == PJSUA_CALL_MEDIA_NONE || 
     3357            call_med->state == PJSUA_CALL_MEDIA_ERROR || 
     3358            call_med->dir == PJMEDIA_DIR_NONE) 
     3359        { 
     3360            continue; 
     3361        } 
     3362 
     3363        /* Remote may answer with less media lines. */ 
     3364        if (i >= remote_sdp->media_count) 
     3365            continue; 
     3366 
     3367        rem_m = remote_sdp->media[i]; 
     3368        loc_m = local_sdp->media[i]; 
     3369 
     3370        /* Verify that media must be active. */ 
     3371        pj_assert(loc_m->desc.port && rem_m->desc.port); 
     3372 
     3373        /* Count the formats in the answer. */ 
     3374        if (rem_m->desc.fmt_count==1) { 
     3375            codec_cnt = 1; 
     3376        } else { 
     3377            unsigned j; 
     3378            for (j=0; j<rem_m->desc.fmt_count && codec_cnt <= 1; ++j) { 
     3379                if (!is_non_av_fmt(rem_m, &rem_m->desc.fmt[j])) 
     3380                    ++codec_cnt; 
     3381            } 
     3382        } 
     3383 
     3384        if (codec_cnt > 1) { 
     3385            has_mult_fmt = PJ_TRUE; 
     3386            break; 
     3387        } 
     3388    } 
     3389 
     3390    /* Each media in the answer already contains single codec. */ 
     3391    if (!has_mult_fmt) { 
     3392        call->lock_codec.retry_cnt = 0; 
    33713393        return PJ_SUCCESS; 
    33723394    } 
Note: See TracChangeset for help on using the changeset viewer.