From 8f0e8dc03b4d20a17ec8d15125b0996db6227cc1 Mon Sep 17 00:00:00 2001 From: Benny Prijono Date: Mon, 6 Mar 2006 13:30:39 +0000 Subject: [PATCH] Fixed bug if payload type for rx and tx is different (i.e. dyn pt) git-svn-id: https://svn.pjsip.org/repos/pjproject/trunk@290 74dad513-b988-da41-8d7b-12977e46ad98 --- pjmedia/include/pjmedia/stream.h | 3 +- pjmedia/src/pjmedia/session.c | 48 +++++++++++++++++++++++++++++--- pjmedia/src/pjmedia/stream.c | 21 ++++++++------ 3 files changed, 58 insertions(+), 14 deletions(-) diff --git a/pjmedia/include/pjmedia/stream.h b/pjmedia/include/pjmedia/stream.h index 679755667..91f50dc3c 100644 --- a/pjmedia/include/pjmedia/stream.h +++ b/pjmedia/include/pjmedia/stream.h @@ -70,7 +70,8 @@ struct pjmedia_stream_info pjmedia_dir dir; /**< Media direction. */ pjmedia_sock_info sock_info; /**< Media transport (RTP/RTCP sockets) */ pj_sockaddr_in rem_addr; /**< Remote RTP address */ - pjmedia_codec_info fmt; /**< Codec format info. */ + pjmedia_codec_info fmt; /**< Incoming codec format info. */ + unsigned tx_pt; /**< Outgoing codec paylaod type. */ int tx_event_pt;/**< Outgoing pt for telephone-events. */ int rx_event_pt;/**< Incoming pt for telephone-events. */ pj_uint32_t ssrc; /**< RTP SSRC. */ diff --git a/pjmedia/src/pjmedia/session.c b/pjmedia/src/pjmedia/session.c index 6f37d3b0e..ab9e5e953 100644 --- a/pjmedia/src/pjmedia/session.c +++ b/pjmedia/src/pjmedia/session.c @@ -95,7 +95,7 @@ static pj_status_t create_stream_info_from_sdp(pj_pool_t *pool, } else { si->type = PJMEDIA_TYPE_UNKNOWN; - + return PJMEDIA_EINVALIMEDIATYPE; } /* Media direction: */ @@ -141,10 +141,13 @@ static pj_status_t create_stream_info_from_sdp(pj_pool_t *pool, } /* And codec must be numeric! */ - if (!pj_isdigit(*local_m->desc.fmt[0].ptr)) + if (!pj_isdigit(*local_m->desc.fmt[0].ptr) || + !pj_isdigit(*rem_m->desc.fmt[0].ptr)) + { return PJMEDIA_EINVALIDPT; + } - /* Get the payload number. */ + /* Get the payload number for receive channel. */ pt = pj_strtoul(&local_m->desc.fmt[0]); /* Get codec info. @@ -161,8 +164,10 @@ static pj_status_t create_stream_info_from_sdp(pj_pool_t *pool, if (status != PJ_SUCCESS) return status; - } else { + /* For static payload type, pt's are symetric */ + si->tx_pt = pt; + } else { attr = pjmedia_sdp_media_find_attr(local_m, &ID_RTPMAP, &local_m->desc.fmt[0]); if (attr == NULL) @@ -178,8 +183,43 @@ static pj_status_t create_stream_info_from_sdp(pj_pool_t *pool, si->fmt.pt = pj_strtoul(&local_m->desc.fmt[0]); pj_strdup(pool, &si->fmt.encoding_name, &rtpmap->enc_name); si->fmt.sample_rate = rtpmap->clock_rate; + + /* Determine payload type for outgoing channel, by finding + * dynamic payload type in remote SDP that matches the answer. + */ + si->tx_pt = 0xFFFF; + for (i=0; idesc.fmt_count; ++i) { + unsigned rpt; + pjmedia_sdp_attr *r_attr; + pjmedia_sdp_rtpmap r_rtpmap; + + rpt = pj_strtoul(&rem_m->desc.fmt[i]); + if (rpt < 96) + continue; + + r_attr = pjmedia_sdp_media_find_attr(rem_m, &ID_RTPMAP, + &rem_m->desc.fmt[i]); + if (!r_attr) + continue; + + if (pjmedia_sdp_attr_get_rtpmap(attr, &r_rtpmap) != PJ_SUCCESS) + continue; + + if (!pj_stricmp(&rtpmap->enc_name, &r_rtpmap.enc_name) && + rtpmap->clock_rate == r_rtpmap.clock_rate) + { + /* Found matched codec. */ + si->tx_pt = rpt; + break; + } + } + + if (si->tx_pt == 0xFFFF) + return PJMEDIA_EMISSINGRTPMAP; } + + /* Get local DTMF payload type */ si->tx_event_pt = -1; for (i=0; iattr_count; ++i) { diff --git a/pjmedia/src/pjmedia/stream.c b/pjmedia/src/pjmedia/stream.c index 6526d5cd6..5c9268dde 100644 --- a/pjmedia/src/pjmedia/stream.c +++ b/pjmedia/src/pjmedia/stream.c @@ -131,7 +131,7 @@ static void stream_perror(const char *sender, const char *title, char errmsg[PJ_ERR_MSG_SIZE]; pj_strerror(status, errmsg, sizeof(errmsg)); - PJ_LOG(3,(sender, "%s: %s [err:%d]", title, errmsg, status)); + PJ_LOG(4,(sender, "%s: %s [err:%d]", title, errmsg, status)); } @@ -509,7 +509,10 @@ static int PJ_THREAD_FUNC jitter_buffer_thread (void*arg) status != PJMEDIA_RTP_ESESSPROBATION && status != PJMEDIA_RTP_ESESSRESTART) { - TRACE_((THIS_FILE, "RTP session_update error", status)); + TRACE_((THIS_FILE, "RTP session_update error (details follows)", + status)); + PJ_LOG(4,(THIS_FILE,"RTP packet detail: pt=%d, seq=%d", + hdr->pt, pj_ntohs(hdr->seq))); continue; } pj_rtcp_rx_rtp(&stream->rtcp, pj_ntohs(hdr->seq), pj_ntohl(hdr->ts)); @@ -557,6 +560,7 @@ static void init_snd_param( pj_snd_stream_info *snd_param, static pj_status_t create_channel( pj_pool_t *pool, pjmedia_stream *stream, pjmedia_dir dir, + unsigned pt, const pjmedia_stream_info *param, const pjmedia_codec_param *codec_param, pjmedia_channel **p_channel) @@ -574,7 +578,7 @@ static pj_status_t create_channel( pj_pool_t *pool, channel->stream = stream; channel->dir = dir; channel->paused = 1; - channel->pt = param->fmt.pt; + channel->pt = pt; /* Allocate buffer for incoming packet. */ @@ -608,8 +612,7 @@ static pj_status_t create_channel( pj_pool_t *pool, /* Create RTP and RTCP sessions: */ - status = pjmedia_rtp_session_init(&channel->rtp, param->fmt.pt, - param->ssrc); + status = pjmedia_rtp_session_init(&channel->rtp, pt, param->ssrc); if (status != PJ_SUCCESS) return status; @@ -748,16 +751,16 @@ PJ_DEF(pj_status_t) pjmedia_stream_create( pjmedia_endpt *endpt, /* Create decoder channel: */ - status = create_channel( pool, stream, PJMEDIA_DIR_DECODING, info, - &codec_param, &stream->dec); + status = create_channel( pool, stream, PJMEDIA_DIR_DECODING, + info->fmt.pt, info, &codec_param, &stream->dec); if (status != PJ_SUCCESS) goto err_cleanup; /* Create encoder channel: */ - status = create_channel( pool, stream, PJMEDIA_DIR_ENCODING, info, - &codec_param, &stream->enc); + status = create_channel( pool, stream, PJMEDIA_DIR_ENCODING, + info->tx_pt, info, &codec_param, &stream->enc); if (status != PJ_SUCCESS) goto err_cleanup;