diff --git a/daemon/sdp.c b/daemon/sdp.c index 8a0531bd9..91e82da72 100644 --- a/daemon/sdp.c +++ b/daemon/sdp.c @@ -621,19 +621,16 @@ static int skip_over(struct sdp_chopper *chop, str *where) { return 0; } -static int replace_media_port(struct sdp_chopper *chop, struct sdp_media *media, GList *m, int off) { - struct callstream *cs; - struct streamrelay *sr; - str *port = &media->port; - int cons; - - if (!m) { - mylog(LOG_ERROR, "BUG! Ran out of streams"); - return -1; - } +static void fill_relays(struct streamrelay **rtp, struct streamrelay **rtcp, GList *m, int off, struct stream_input *sip) { + *rtp = &((struct callstream *) m->data)->peers[off].rtps[0]; + if (rtcp) + *rtcp = &((struct callstream *) m->data)->peers[off].rtps[1]; + if (sip && sip->has_rtcp && m->next) + *rtcp = &((struct callstream *) m->next->data)->peers[off].rtps[0]; +} - cs = m->data; - sr = &cs->peers[off].rtps[0]; +static int replace_media_port(struct sdp_chopper *chop, struct sdp_media *media, struct streamrelay *sr) { + str *port = &media->port; if (copy_up_to(chop, port)) return -1; @@ -643,6 +640,15 @@ static int replace_media_port(struct sdp_chopper *chop, struct sdp_media *media, if (skip_over(chop, port)) return -1; + return 0; +} + +static int replace_consecutive_port_count(struct sdp_chopper *chop, struct sdp_media *media, + struct streamrelay *rtp, GList *m, int off) +{ + int cons; + struct streamrelay *sr; + if (media->port_count == 1) return 0; @@ -650,8 +656,8 @@ static int replace_media_port(struct sdp_chopper *chop, struct sdp_media *media, m = m->next; if (!m) goto warn; - cs = m->data; - if (cs->peers[off].rtps[0].fd.localport != sr->fd.localport + cons * 2) { + fill_relays(&sr, NULL, m, off, NULL); + if (sr->fd.localport != rtp->fd.localport + cons * 2) { warn: mylog(LOG_WARN, "Failed to handle consecutive ports"); break; @@ -680,21 +686,11 @@ static int insert_ice_address(struct sdp_chopper *chop, struct sdp_ng_flags *fla } static int replace_network_address(struct sdp_chopper *chop, struct network_address *address, - GList *m, int off, struct sdp_ng_flags *flags) + struct streamrelay *sr, struct sdp_ng_flags *flags) { - struct callstream *cs; - struct peer *peer; char buf[64]; int len; - if (!m) { - mylog(LOG_ERROR, "BUG! Ran out of streams"); - return -1; - } - - cs = m->data; - peer = &cs->peers[off]; - if (copy_up_to(chop, &address->address_type)) return -1; @@ -704,7 +700,7 @@ static int replace_network_address(struct sdp_chopper *chop, struct network_addr chopper_append_str(chop, &flags->received_from_address); } else { - call_stream_address(buf, peer, SAF_NG, &len); + call_stream_address(buf, sr->up, SAF_NG, &len); chopper_append_dup(chop, buf, len); } @@ -798,6 +794,15 @@ strip: return 0; } +static GList *find_stream_num(GList *m, int num) { + /* XXX use a hash instead? must link input streams to output streams */ + while (m && ((struct callstream *) m->data)->num < num) + m = m->next; + while (m && ((struct callstream *) m->data)->num > num) + m = m->prev; + return m; +} + int sdp_replace(struct sdp_chopper *chop, GQueue *sessions, struct call *call, enum call_opmode opmode, struct sdp_ng_flags *flags, GHashTable *streamhash) { @@ -814,12 +819,14 @@ int sdp_replace(struct sdp_chopper *chop, GQueue *sessions, struct call *call, for (l = sessions->head; l; l = l->next) { session = l->data; + fill_relays(&rtp, &rtcp, m, off, NULL); + if (session->origin.parsed && flags->replace_origin) { - if (replace_network_address(chop, &session->origin.address, m, off, flags)) + if (replace_network_address(chop, &session->origin.address, rtp, flags)) goto error; } if (session->connection.parsed) { - if (replace_network_address(chop, &session->connection.address, m, off, flags)) + if (replace_network_address(chop, &session->connection.address, rtp, flags)) goto error; } @@ -848,25 +855,18 @@ int sdp_replace(struct sdp_chopper *chop, GQueue *sessions, struct call *call, sip = g_hash_table_lookup(streamhash, &si); if (!sip) goto error; - /* XXX use a hash instead? must link input streams to output streams */ + m = find_stream_num(m, sip->stream.num); if (!m) - m = call->callstreams->head; - while (m && ((struct callstream *) m->data)->num < sip->stream.num) - m = m->next; - while (m && ((struct callstream *) m->data)->num > sip->stream.num) - m = m->prev; - - /* XXX use those in function calls exclusively */ - rtp = &((struct callstream *) m->data)->peers[off].rtps[0]; - rtcp = &((struct callstream *) m->data)->peers[off].rtps[1]; - if (sip->has_rtcp && m->next) - rtcp = &((struct callstream *) m->next->data)->peers[off].rtps[0]; - - if (replace_media_port(chop, media, m, off)) + goto error; + fill_relays(&rtp, &rtcp, m, off, sip); + + if (replace_media_port(chop, media, rtp)) + goto error; + if (replace_consecutive_port_count(chop, media, rtp, m, off)) goto error; if (media->connection.parsed && flags->replace_sess_conn) { - if (replace_network_address(chop, &media->connection.address, m, off, flags)) + if (replace_network_address(chop, &media->connection.address, rtp, flags)) goto error; }