mirror of
https://github.com/signalwire/freeswitch.git
synced 2026-07-24 13:12:03 +00:00
fix sdp pass-thru of 200 OK in proxy mode aka (bypass_media=true)
git-svn-id: http://svn.freeswitch.org/svn/freeswitch/trunk@7717 d0543943-73ff-0310-b7d9-9358b9ac24b2
This commit is contained in:
@@ -80,7 +80,7 @@ static switch_status_t sofia_on_init(switch_core_session_t *session)
|
||||
tech_pvt->read_frame.buflen = SWITCH_RTP_MAX_BUF_LEN;
|
||||
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "%s SOFIA INIT\n", switch_channel_get_name(channel));
|
||||
if (switch_channel_test_flag(channel, CF_BYPASS_MEDIA)) {
|
||||
if (switch_channel_test_flag(channel, CF_PROXY_MODE) || switch_channel_test_flag(channel, CF_PROXY_MEDIA)) {
|
||||
sofia_glue_tech_absorb_sdp(tech_pvt);
|
||||
}
|
||||
|
||||
@@ -340,11 +340,17 @@ static switch_status_t sofia_answer_channel(switch_core_session_t *session)
|
||||
|
||||
switch_set_flag_locked(tech_pvt, TFLAG_ANS);
|
||||
|
||||
if (switch_channel_test_flag(channel, CF_BYPASS_MEDIA)) {
|
||||
if (switch_channel_test_flag(channel, CF_PROXY_MODE) || switch_channel_test_flag(channel, CF_PROXY_MEDIA)) {
|
||||
const char *sdp = NULL;
|
||||
if ((sdp = switch_channel_get_variable(channel, SWITCH_B_SDP_VARIABLE))) {
|
||||
tech_pvt->local_sdp_str = switch_core_session_strdup(session, sdp);
|
||||
}
|
||||
if (switch_channel_test_flag(channel, CF_PROXY_MEDIA)) {
|
||||
sofia_glue_tech_patch_sdp(tech_pvt);
|
||||
if (sofia_glue_activate_rtp(tech_pvt, 0) != SWITCH_STATUS_SUCCESS) {
|
||||
return SWITCH_STATUS_FALSE;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if (switch_test_flag(tech_pvt, TFLAG_LATE_NEGOTIATION)) {
|
||||
switch_clear_flag_locked(tech_pvt, TFLAG_LATE_NEGOTIATION);
|
||||
@@ -360,7 +366,7 @@ static switch_status_t sofia_answer_channel(switch_core_session_t *session)
|
||||
}
|
||||
}
|
||||
|
||||
if ((status = sofia_glue_tech_choose_port(tech_pvt)) != SWITCH_STATUS_SUCCESS) {
|
||||
if ((status = sofia_glue_tech_choose_port(tech_pvt, 0)) != SWITCH_STATUS_SUCCESS) {
|
||||
switch_channel_hangup(channel, SWITCH_CAUSE_DESTINATION_OUT_OF_ORDER);
|
||||
return status;
|
||||
}
|
||||
@@ -612,7 +618,7 @@ static switch_status_t sofia_write_frame(switch_core_session_t *session, switch_
|
||||
|
||||
switch_set_flag_locked(tech_pvt, TFLAG_WRITING);
|
||||
|
||||
if (!switch_test_flag(frame, SFF_CNG)) {
|
||||
if (!switch_test_flag(frame, SFF_CNG) && !switch_test_flag(frame, SFF_PROXY_PACKET)) {
|
||||
if (tech_pvt->read_codec.implementation->encoded_bytes_per_frame) {
|
||||
bytes = tech_pvt->read_codec.implementation->encoded_bytes_per_frame;
|
||||
frames = ((int) frame->datalen / bytes);
|
||||
@@ -758,7 +764,7 @@ static switch_status_t sofia_receive_message(switch_core_session_t *session, swi
|
||||
switch_channel_t *other_channel;
|
||||
const char *ip = NULL, *port = NULL;
|
||||
|
||||
switch_channel_set_flag(channel, CF_BYPASS_MEDIA);
|
||||
switch_channel_set_flag(channel, CF_PROXY_MODE);
|
||||
tech_pvt->local_sdp_str = NULL;
|
||||
if ((uuid = switch_channel_get_variable(channel, SWITCH_SIGNAL_BOND_VARIABLE))
|
||||
&& (other_session = switch_core_session_locate(uuid))) {
|
||||
@@ -790,11 +796,11 @@ static switch_status_t sofia_receive_message(switch_core_session_t *session, swi
|
||||
{
|
||||
uint32_t count = 0;
|
||||
|
||||
switch_channel_clear_flag(channel, CF_BYPASS_MEDIA);
|
||||
switch_channel_clear_flag(channel, CF_PROXY_MODE);
|
||||
tech_pvt->local_sdp_str = NULL;
|
||||
if (!switch_rtp_ready(tech_pvt->rtp_session)) {
|
||||
sofia_glue_tech_prepare_codecs(tech_pvt);
|
||||
if ((status = sofia_glue_tech_choose_port(tech_pvt)) != SWITCH_STATUS_SUCCESS) {
|
||||
if ((status = sofia_glue_tech_choose_port(tech_pvt, 0)) != SWITCH_STATUS_SUCCESS) {
|
||||
switch_channel_hangup(channel, SWITCH_CAUSE_DESTINATION_OUT_OF_ORDER);
|
||||
return status;
|
||||
}
|
||||
@@ -957,10 +963,10 @@ static switch_status_t sofia_receive_message(switch_core_session_t *session, swi
|
||||
|
||||
if (!switch_strlen_zero(((char *)msg->pointer_arg))) {
|
||||
nua_respond(tech_pvt->nh, code, reason, SIPTAG_CONTACT_STR(tech_pvt->reply_contact),
|
||||
SOATAG_USER_SDP_STR(msg->pointer_arg),
|
||||
SOATAG_AUDIO_AUX("cn telephone-event"),
|
||||
NUTAG_INCLUDE_EXTRA_SDP(1),
|
||||
TAG_END());
|
||||
SOATAG_USER_SDP_STR(msg->pointer_arg),
|
||||
SOATAG_AUDIO_AUX("cn telephone-event"),
|
||||
NUTAG_INCLUDE_EXTRA_SDP(1),
|
||||
TAG_END());
|
||||
} else {
|
||||
nua_respond(tech_pvt->nh, code, reason, SIPTAG_CONTACT_STR(tech_pvt->reply_contact), TAG_END());
|
||||
}
|
||||
@@ -986,11 +992,17 @@ static switch_status_t sofia_receive_message(switch_core_session_t *session, swi
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_INFO, "Asked to send early media by %s\n", msg->from);
|
||||
|
||||
/* Transmit 183 Progress with SDP */
|
||||
if (switch_channel_test_flag(channel, CF_BYPASS_MEDIA)) {
|
||||
if (switch_channel_test_flag(channel, CF_PROXY_MODE) || switch_channel_test_flag(channel, CF_PROXY_MEDIA)) {
|
||||
const char *sdp = NULL;
|
||||
if ((sdp = switch_channel_get_variable(channel, SWITCH_B_SDP_VARIABLE))) {
|
||||
tech_pvt->local_sdp_str = switch_core_session_strdup(session, sdp);
|
||||
}
|
||||
if (switch_channel_test_flag(channel, CF_PROXY_MEDIA)) {
|
||||
sofia_glue_tech_patch_sdp(tech_pvt);
|
||||
if (sofia_glue_activate_rtp(tech_pvt, 0) != SWITCH_STATUS_SUCCESS) {
|
||||
return SWITCH_STATUS_FALSE;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if (switch_test_flag(tech_pvt, TFLAG_LATE_NEGOTIATION)) {
|
||||
switch_clear_flag_locked(tech_pvt, TFLAG_LATE_NEGOTIATION);
|
||||
@@ -1008,7 +1020,7 @@ static switch_status_t sofia_receive_message(switch_core_session_t *session, swi
|
||||
}
|
||||
}
|
||||
|
||||
if ((status = sofia_glue_tech_choose_port(tech_pvt)) != SWITCH_STATUS_SUCCESS) {
|
||||
if ((status = sofia_glue_tech_choose_port(tech_pvt, 0)) != SWITCH_STATUS_SUCCESS) {
|
||||
switch_channel_hangup(channel, SWITCH_CAUSE_DESTINATION_OUT_OF_ORDER);
|
||||
return status;
|
||||
}
|
||||
|
||||
@@ -165,7 +165,8 @@ typedef enum {
|
||||
TFLAG_SDP = (1 << 25),
|
||||
TFLAG_VIDEO = (1 << 26),
|
||||
TFLAG_TPORT_LOG = (1 << 27),
|
||||
TFLAG_SENT_UPDATE = (1 << 28)
|
||||
TFLAG_SENT_UPDATE = (1 << 28),
|
||||
TFLAG_PROXY_MEDIA = (1 << 29)
|
||||
} TFLAGS;
|
||||
|
||||
struct mod_sofia_globals {
|
||||
@@ -341,6 +342,7 @@ struct private_object {
|
||||
char *fmtp_out;
|
||||
char *remote_sdp_str;
|
||||
char *local_sdp_str;
|
||||
char *orig_local_sdp_str;
|
||||
char *dest;
|
||||
char *dest_to;
|
||||
char *key;
|
||||
@@ -439,7 +441,7 @@ void sofia_glue_tech_prepare_codecs(private_object_t *tech_pvt);
|
||||
|
||||
void sofia_glue_attach_private(switch_core_session_t *session, sofia_profile_t *profile, private_object_t *tech_pvt, const char *channame);
|
||||
|
||||
switch_status_t sofia_glue_tech_choose_port(private_object_t *tech_pvt);
|
||||
switch_status_t sofia_glue_tech_choose_port(private_object_t *tech_pvt, int force);
|
||||
|
||||
switch_status_t sofia_glue_do_invite(switch_core_session_t *session);
|
||||
|
||||
@@ -584,3 +586,4 @@ char * sofia_glue_find_parameter(const char *str, const char *param);
|
||||
int sofia_glue_transport_has_tls(const sofia_transport_t tp);
|
||||
const char *sofia_glue_get_unknown_header(sip_t const *sip, const char *name);
|
||||
switch_status_t sofia_glue_build_crypto(private_object_t *tech_pvt, int index, switch_rtp_crypto_key_type_t type, switch_rtp_crypto_direction_t direction);
|
||||
void sofia_glue_tech_patch_sdp(private_object_t *tech_pvt);
|
||||
|
||||
@@ -971,6 +971,8 @@ switch_status_t config_sofia(int reload, char *profile_name)
|
||||
switch_set_flag(profile, TFLAG_INB_NOMEDIA);
|
||||
} else if (!strcasecmp(var, "inbound-late-negotiation") && switch_true(val)) {
|
||||
switch_set_flag(profile, TFLAG_LATE_NEGOTIATION);
|
||||
} else if (!strcasecmp(var, "inbound-proxy-media") && switch_true(val)) {
|
||||
switch_set_flag(profile, TFLAG_PROXY_MEDIA);
|
||||
} else if (!strcasecmp(var, "rfc2833-pt")) {
|
||||
profile->te = (switch_payload_t) atoi(val);
|
||||
} else if (!strcasecmp(var, "cng-pt")) {
|
||||
@@ -1316,7 +1318,7 @@ static void sofia_handle_sip_r_invite(switch_core_session_t *session, int status
|
||||
const char *uuid;
|
||||
switch_core_session_t *other_session;
|
||||
|
||||
if (switch_channel_test_flag(channel, CF_BYPASS_MEDIA)) {
|
||||
if (switch_channel_test_flag(channel, CF_PROXY_MODE) || switch_channel_test_flag(channel, CF_PROXY_MEDIA)) {
|
||||
private_object_t *tech_pvt = switch_core_session_get_private(session);
|
||||
switch_assert(tech_pvt != NULL);
|
||||
|
||||
@@ -1330,9 +1332,14 @@ static void sofia_handle_sip_r_invite(switch_core_session_t *session, int status
|
||||
const char *r_sdp = NULL;
|
||||
switch_core_session_message_t msg = { 0 };
|
||||
|
||||
if (sip->sip_payload && sip->sip_payload->pl_data &&
|
||||
sip->sip_content_type && sip->sip_content_type->c_subtype && switch_stristr("sdp", sip->sip_content_type->c_subtype)) {
|
||||
r_sdp = sip->sip_payload->pl_data;
|
||||
printf("WOOT\n%s\n", r_sdp);
|
||||
}
|
||||
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Passing %d %s to other leg\n", status, phrase);
|
||||
|
||||
tl_gets(tags, SOATAG_REMOTE_SDP_STR_REF(r_sdp), TAG_END());
|
||||
msg.message_id = SWITCH_MESSAGE_INDICATE_RESPOND;
|
||||
msg.from = __FILE__;
|
||||
msg.numeric_arg = status;
|
||||
@@ -1493,7 +1500,7 @@ static void sofia_handle_sip_i_state(switch_core_session_t *session, int status,
|
||||
if (status == 180) {
|
||||
switch_channel_mark_ring_ready(channel);
|
||||
if (!switch_channel_test_flag(channel, CF_GEN_RINGBACK)) {
|
||||
if (switch_channel_test_flag(channel, CF_BYPASS_MEDIA)) {
|
||||
if (switch_channel_test_flag(channel, CF_PROXY_MODE)) {
|
||||
if ((uuid = switch_channel_get_variable(channel, SWITCH_SIGNAL_BOND_VARIABLE))
|
||||
&& (other_session = switch_core_session_locate(uuid))) {
|
||||
switch_core_session_message_t msg;
|
||||
@@ -1510,10 +1517,15 @@ static void sofia_handle_sip_i_state(switch_core_session_t *session, int status,
|
||||
}
|
||||
|
||||
if (r_sdp) {
|
||||
if (switch_channel_test_flag(channel, CF_BYPASS_MEDIA)) {
|
||||
if (switch_channel_test_flag(channel, CF_PROXY_MODE) || switch_channel_test_flag(channel, CF_PROXY_MEDIA)) {
|
||||
switch_set_flag_locked(tech_pvt, TFLAG_EARLY_MEDIA);
|
||||
switch_channel_mark_pre_answered(channel);
|
||||
switch_set_flag(tech_pvt, TFLAG_SDP);
|
||||
if (switch_channel_test_flag(channel, CF_PROXY_MEDIA)) {
|
||||
if (sofia_glue_activate_rtp(tech_pvt, 0) != SWITCH_STATUS_SUCCESS) {
|
||||
goto done;
|
||||
}
|
||||
}
|
||||
if (!switch_channel_test_flag(channel, CF_GEN_RINGBACK) && (uuid = switch_channel_get_variable(channel, SWITCH_SIGNAL_BOND_VARIABLE))
|
||||
&& (other_session = switch_core_session_locate(uuid))) {
|
||||
other_channel = switch_core_session_get_channel(other_session);
|
||||
@@ -1526,7 +1538,9 @@ static void sofia_handle_sip_i_state(switch_core_session_t *session, int status,
|
||||
}
|
||||
goto done;
|
||||
} else {
|
||||
if (switch_test_flag(tech_pvt, TFLAG_LATE_NEGOTIATION) && !switch_channel_test_flag(tech_pvt->channel, CF_OUTBOUND)) {
|
||||
if (switch_channel_test_flag(channel, CF_PROXY_MEDIA) && !switch_channel_test_flag(tech_pvt->channel, CF_OUTBOUND)) {
|
||||
switch_channel_set_variable(channel, SWITCH_ENDPOINT_DISPOSITION_VARIABLE, "PROXY MEDIA");
|
||||
} else if (switch_test_flag(tech_pvt, TFLAG_LATE_NEGOTIATION) && !switch_channel_test_flag(tech_pvt->channel, CF_OUTBOUND)) {
|
||||
switch_channel_set_variable(channel, SWITCH_ENDPOINT_DISPOSITION_VARIABLE, "DELAYED NEGOTIATION");
|
||||
} else {
|
||||
if (sofia_glue_tech_media(tech_pvt, (char *) r_sdp) != SWITCH_STATUS_SUCCESS) {
|
||||
@@ -1546,7 +1560,7 @@ static void sofia_handle_sip_i_state(switch_core_session_t *session, int status,
|
||||
case nua_callstate_received:
|
||||
if (tech_pvt && !switch_test_flag(tech_pvt, TFLAG_SDP)) {
|
||||
if (r_sdp && !switch_test_flag(tech_pvt, TFLAG_SDP)) {
|
||||
if (switch_channel_test_flag(channel, CF_BYPASS_MEDIA)) {
|
||||
if (switch_channel_test_flag(channel, CF_PROXY_MODE)) {
|
||||
switch_channel_set_variable(channel, SWITCH_ENDPOINT_DISPOSITION_VARIABLE, "RECEIVED_NOMEDIA");
|
||||
switch_set_flag_locked(tech_pvt, TFLAG_READY);
|
||||
if (switch_channel_get_state(channel) == CS_NEW) {
|
||||
@@ -1554,6 +1568,12 @@ static void sofia_handle_sip_i_state(switch_core_session_t *session, int status,
|
||||
}
|
||||
switch_set_flag(tech_pvt, TFLAG_SDP);
|
||||
goto done;
|
||||
} else if (switch_channel_test_flag(tech_pvt->channel, CF_PROXY_MEDIA)) {
|
||||
switch_channel_set_variable(channel, SWITCH_ENDPOINT_DISPOSITION_VARIABLE, "PROXY MEDIA");
|
||||
switch_set_flag_locked(tech_pvt, TFLAG_READY);
|
||||
if (switch_channel_get_state(channel) == CS_NEW) {
|
||||
switch_channel_set_state(channel, CS_INIT);
|
||||
}
|
||||
} else if (switch_test_flag(tech_pvt, TFLAG_LATE_NEGOTIATION)) {
|
||||
switch_channel_set_variable(channel, SWITCH_ENDPOINT_DISPOSITION_VARIABLE, "DELAYED NEGOTIATION");
|
||||
switch_set_flag_locked(tech_pvt, TFLAG_READY);
|
||||
@@ -1627,16 +1647,19 @@ static void sofia_handle_sip_i_state(switch_core_session_t *session, int status,
|
||||
switch_channel_hangup(channel, SWITCH_CAUSE_INCOMPATIBLE_DESTINATION);
|
||||
}
|
||||
} else {
|
||||
if (switch_channel_test_flag(channel, CF_BYPASS_MEDIA)) {
|
||||
if (switch_channel_test_flag(channel, CF_PROXY_MODE) || switch_channel_test_flag(channel, CF_PROXY_MEDIA)) {
|
||||
goto done;
|
||||
} else {
|
||||
switch_channel_set_variable(channel, SWITCH_ENDPOINT_DISPOSITION_VARIABLE, "RECEIVED_NOSDP");
|
||||
sofia_glue_tech_choose_port(tech_pvt);
|
||||
sofia_glue_tech_choose_port(tech_pvt, 0);
|
||||
sofia_glue_set_local_sdp(tech_pvt, NULL, 0, NULL, 0);
|
||||
switch_channel_set_state(channel, CS_HIBERNATE);
|
||||
nua_respond(tech_pvt->nh, SIP_200_OK,
|
||||
SIPTAG_CONTACT_STR(tech_pvt->profile->url),
|
||||
SOATAG_USER_SDP_STR(tech_pvt->local_sdp_str), SOATAG_AUDIO_AUX("cn telephone-event"), NUTAG_INCLUDE_EXTRA_SDP(1), TAG_END());
|
||||
SOATAG_USER_SDP_STR(tech_pvt->local_sdp_str),
|
||||
SOATAG_AUDIO_AUX("cn telephone-event"),
|
||||
NUTAG_INCLUDE_EXTRA_SDP(1),
|
||||
TAG_END());
|
||||
goto done;
|
||||
}
|
||||
}
|
||||
@@ -1656,7 +1679,7 @@ static void sofia_handle_sip_i_state(switch_core_session_t *session, int status,
|
||||
uint8_t match = 0;
|
||||
|
||||
if (r_sdp) {
|
||||
if (switch_channel_test_flag(channel, CF_BYPASS_MEDIA)) {
|
||||
if (switch_channel_test_flag(channel, CF_PROXY_MODE) || switch_channel_test_flag(channel, CF_PROXY_MEDIA)) {
|
||||
if ((uuid = switch_channel_get_variable(channel, SWITCH_SIGNAL_BOND_VARIABLE))
|
||||
&& (other_session = switch_core_session_locate(uuid))) {
|
||||
switch_core_session_message_t msg = { 0 };
|
||||
@@ -1681,7 +1704,7 @@ static void sofia_handle_sip_i_state(switch_core_session_t *session, int status,
|
||||
}
|
||||
}
|
||||
if (match) {
|
||||
if (sofia_glue_tech_choose_port(tech_pvt) != SWITCH_STATUS_SUCCESS) {
|
||||
if (sofia_glue_tech_choose_port(tech_pvt, 0) != SWITCH_STATUS_SUCCESS) {
|
||||
goto done;
|
||||
}
|
||||
sofia_glue_set_local_sdp(tech_pvt, NULL, 0, NULL, 0);
|
||||
@@ -1713,7 +1736,7 @@ static void sofia_handle_sip_i_state(switch_core_session_t *session, int status,
|
||||
switch_set_flag_locked(tech_pvt, TFLAG_REINVITE);
|
||||
tech_pvt->nh = tech_pvt->nh2;
|
||||
tech_pvt->nh2 = NULL;
|
||||
if (sofia_glue_tech_choose_port(tech_pvt) == SWITCH_STATUS_SUCCESS) {
|
||||
if (sofia_glue_tech_choose_port(tech_pvt, 0) == SWITCH_STATUS_SUCCESS) {
|
||||
if (sofia_glue_activate_rtp(tech_pvt, 0) != SWITCH_STATUS_SUCCESS) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "Cheater Reinvite RTP Error!\n");
|
||||
switch_channel_hangup(channel, SWITCH_CAUSE_DESTINATION_OUT_OF_ORDER);
|
||||
@@ -1740,10 +1763,15 @@ static void sofia_handle_sip_i_state(switch_core_session_t *session, int status,
|
||||
r_sdp = (const char *) switch_channel_get_variable(channel, SWITCH_R_SDP_VARIABLE);
|
||||
}
|
||||
if (r_sdp && !switch_test_flag(tech_pvt, TFLAG_SDP)) {
|
||||
if (switch_channel_test_flag(channel, CF_BYPASS_MEDIA)) {
|
||||
if (switch_channel_test_flag(channel, CF_PROXY_MODE) || switch_channel_test_flag(channel, CF_PROXY_MEDIA)) {
|
||||
switch_set_flag_locked(tech_pvt, TFLAG_ANS);
|
||||
switch_set_flag_locked(tech_pvt, TFLAG_SDP);
|
||||
switch_channel_mark_answered(channel);
|
||||
if (switch_channel_test_flag(channel, CF_PROXY_MEDIA)) {
|
||||
if (sofia_glue_activate_rtp(tech_pvt, 0) != SWITCH_STATUS_SUCCESS) {
|
||||
goto done;
|
||||
}
|
||||
}
|
||||
if ((uuid = switch_channel_get_variable(channel, SWITCH_SIGNAL_BOND_VARIABLE))
|
||||
&& (other_session = switch_core_session_locate(uuid))) {
|
||||
other_channel = switch_core_session_get_channel(other_session);
|
||||
@@ -1770,7 +1798,7 @@ static void sofia_handle_sip_i_state(switch_core_session_t *session, int status,
|
||||
|
||||
if (match) {
|
||||
switch_set_flag_locked(tech_pvt, TFLAG_ANS);
|
||||
if (sofia_glue_tech_choose_port(tech_pvt) == SWITCH_STATUS_SUCCESS) {
|
||||
if (sofia_glue_tech_choose_port(tech_pvt, 0) == SWITCH_STATUS_SUCCESS) {
|
||||
if (sofia_glue_activate_rtp(tech_pvt, 0) == SWITCH_STATUS_SUCCESS) {
|
||||
switch_channel_mark_answered(channel);
|
||||
} else {
|
||||
@@ -1863,7 +1891,7 @@ void sofia_handle_sip_i_refer(nua_t *nua, sofia_profile_t *profile, nua_handle_t
|
||||
goto done;
|
||||
}
|
||||
|
||||
if (switch_channel_test_flag(channel_a, CF_BYPASS_MEDIA)) {
|
||||
if (switch_channel_test_flag(channel_a, CF_PROXY_MODE)) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_DEBUG, "Transfer on bypass media not allowed.\n");
|
||||
nua_notify(tech_pvt->nh, NUTAG_NEWSUB(1), SIPTAG_CONTENT_TYPE_STR("message/sipfrag"),
|
||||
NUTAG_SUBSTATE(nua_substate_terminated), SIPTAG_PAYLOAD_STR("SIP/2.0 403 Forbidden"), SIPTAG_EVENT_STR(etmp), TAG_END());
|
||||
@@ -2558,7 +2586,11 @@ void sofia_handle_sip_i_invite(nua_t *nua, sofia_profile_t *profile, nua_handle_
|
||||
switch_channel_set_variable(channel, SWITCH_ENDPOINT_DISPOSITION_VARIABLE, "INBOUND CALL");
|
||||
|
||||
if (switch_test_flag(tech_pvt, TFLAG_INB_NOMEDIA)) {
|
||||
switch_channel_set_flag(channel, CF_BYPASS_MEDIA);
|
||||
switch_channel_set_flag(channel, CF_PROXY_MODE);
|
||||
}
|
||||
|
||||
if (switch_test_flag(tech_pvt, TFLAG_PROXY_MEDIA)) {
|
||||
switch_channel_set_flag(channel, CF_PROXY_MEDIA);
|
||||
}
|
||||
|
||||
if (!tech_pvt->call_id && sip->sip_call_id && sip->sip_call_id->i_id) {
|
||||
|
||||
@@ -54,7 +54,7 @@ void sofia_glue_set_local_sdp(private_object_t *tech_pvt, const char *ip, uint32
|
||||
use_cng = 0;
|
||||
}
|
||||
|
||||
if (!force && !ip && !sr && switch_channel_test_flag(tech_pvt->channel, CF_BYPASS_MEDIA)) {
|
||||
if (!force && !ip && !sr && (switch_channel_test_flag(tech_pvt->channel, CF_PROXY_MODE) || switch_channel_test_flag(tech_pvt->channel, CF_PROXY_MEDIA))) {
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -321,7 +321,7 @@ void sofia_glue_tech_prepare_codecs(private_object_t *tech_pvt)
|
||||
const char *abs, *codec_string = NULL;
|
||||
const char *ocodec = NULL;
|
||||
|
||||
if (switch_channel_test_flag(tech_pvt->channel, CF_BYPASS_MEDIA)) {
|
||||
if (switch_channel_test_flag(tech_pvt->channel, CF_PROXY_MODE) || switch_channel_test_flag(tech_pvt->channel, CF_PROXY_MEDIA)) {
|
||||
goto end;
|
||||
}
|
||||
|
||||
@@ -475,15 +475,22 @@ const char *sofia_glue_get_unknown_header(sip_t const *sip, const char *name)
|
||||
return NULL;
|
||||
}
|
||||
|
||||
switch_status_t sofia_glue_tech_choose_port(private_object_t *tech_pvt)
|
||||
switch_status_t sofia_glue_tech_choose_port(private_object_t *tech_pvt, int force)
|
||||
{
|
||||
char *ip = tech_pvt->profile->rtpip;
|
||||
switch_port_t sdp_port;
|
||||
char tmp[50];
|
||||
|
||||
if (switch_channel_test_flag(tech_pvt->channel, CF_BYPASS_MEDIA) || tech_pvt->adv_sdp_audio_port) {
|
||||
return SWITCH_STATUS_SUCCESS;
|
||||
if (!force) {
|
||||
if (switch_channel_test_flag(tech_pvt->channel, CF_PROXY_MODE) ||
|
||||
switch_channel_test_flag(tech_pvt->channel, CF_PROXY_MEDIA) || tech_pvt->adv_sdp_audio_port) {
|
||||
return SWITCH_STATUS_SUCCESS;
|
||||
}
|
||||
}
|
||||
if (tech_pvt->adv_sdp_audio_port) {
|
||||
switch_rtp_release_port(tech_pvt->adv_sdp_audio_ip, tech_pvt->adv_sdp_audio_port);
|
||||
}
|
||||
|
||||
|
||||
tech_pvt->local_sdp_audio_ip = ip;
|
||||
if (!(tech_pvt->local_sdp_audio_port = switch_rtp_request_port(tech_pvt->profile->rtpip))) {
|
||||
@@ -515,7 +522,7 @@ switch_status_t sofia_glue_tech_choose_video_port(private_object_t *tech_pvt)
|
||||
switch_port_t sdp_port;
|
||||
char tmp[50];
|
||||
|
||||
if (switch_channel_test_flag(tech_pvt->channel, CF_BYPASS_MEDIA) || tech_pvt->adv_sdp_video_port) {
|
||||
if (switch_channel_test_flag(tech_pvt->channel, CF_PROXY_MODE) || switch_channel_test_flag(tech_pvt->channel, CF_PROXY_MEDIA) || tech_pvt->adv_sdp_video_port) {
|
||||
return SWITCH_STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
@@ -678,6 +685,119 @@ char *sofia_overcome_sip_uri_weakness(switch_core_session_t *session, const char
|
||||
return new_uri;
|
||||
}
|
||||
|
||||
static switch_status_t sofia_glue_tech_proxy_remote_addr(private_object_t *tech_pvt) {
|
||||
char rip[128] = "";
|
||||
char rp[128] = "";
|
||||
char *p, *ip_ptr = NULL, *port_ptr = NULL;
|
||||
int x;
|
||||
|
||||
if (switch_strlen_zero(tech_pvt->remote_sdp_str)) {
|
||||
return SWITCH_STATUS_FALSE;
|
||||
}
|
||||
|
||||
if ((p = (char *)switch_stristr("c=IN IP4 ", tech_pvt->remote_sdp_str))) {
|
||||
ip_ptr = p + 9;
|
||||
}
|
||||
|
||||
if ((p = (char *)switch_stristr("m=audio ", tech_pvt->remote_sdp_str))) {
|
||||
port_ptr = p + 8;
|
||||
}
|
||||
|
||||
if (!(ip_ptr && port_ptr)) {
|
||||
return SWITCH_STATUS_FALSE;
|
||||
}
|
||||
|
||||
p = ip_ptr;
|
||||
x = 0;
|
||||
while(x < sizeof(rip) && p && *p && ((*p >= '0' && *p <= '9') || *p == '.')) {
|
||||
rip[x++] = *p;
|
||||
p++;
|
||||
}
|
||||
|
||||
p = port_ptr;
|
||||
x = 0;
|
||||
while(x < sizeof(rp) && p && *p && (*p >= '0' && *p <= '9')) {
|
||||
rp[x++] = *p;
|
||||
p++;
|
||||
}
|
||||
|
||||
tech_pvt->remote_sdp_audio_ip = switch_core_session_strdup(tech_pvt->session, rip);
|
||||
tech_pvt->remote_sdp_audio_port = (switch_port_t) atoi(rp);
|
||||
|
||||
return SWITCH_STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
|
||||
void sofia_glue_tech_patch_sdp(private_object_t *tech_pvt)
|
||||
{
|
||||
switch_size_t len;
|
||||
char *p, *q, *ip_ptr = NULL, *port_ptr = NULL;
|
||||
int x;
|
||||
|
||||
if (switch_strlen_zero(tech_pvt->local_sdp_str)) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!switch_strlen_zero(tech_pvt->orig_local_sdp_str)) {
|
||||
return;
|
||||
}
|
||||
|
||||
len = strlen(tech_pvt->local_sdp_str) + 256;
|
||||
|
||||
if ((p = (char *)switch_stristr("c=IN IP4 ", tech_pvt->local_sdp_str))) {
|
||||
ip_ptr = p + 9;
|
||||
}
|
||||
|
||||
if ((p = (char *)switch_stristr("m=audio ", tech_pvt->local_sdp_str))) {
|
||||
port_ptr = p + 8;
|
||||
}
|
||||
|
||||
if (!(ip_ptr && port_ptr)) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (sofia_glue_tech_choose_port(tech_pvt, 1) != SWITCH_STATUS_SUCCESS) {
|
||||
return;
|
||||
}
|
||||
|
||||
tech_pvt->orig_local_sdp_str = tech_pvt->local_sdp_str;
|
||||
tech_pvt->local_sdp_str = switch_core_session_alloc(tech_pvt->session, len);
|
||||
|
||||
q = tech_pvt->local_sdp_str;
|
||||
p = tech_pvt->orig_local_sdp_str;
|
||||
|
||||
while (p && *p) {
|
||||
if (p == ip_ptr) {
|
||||
strncpy(q, tech_pvt->adv_sdp_audio_ip, strlen(tech_pvt->adv_sdp_audio_ip));
|
||||
q += strlen(tech_pvt->adv_sdp_audio_ip);
|
||||
x = 0;
|
||||
while(p && *p && ((*p >= '0' && *p <= '9') || *p == '.')) {
|
||||
p++;
|
||||
}
|
||||
|
||||
} else if (p == port_ptr) {
|
||||
char port_buf[25] = "";
|
||||
|
||||
switch_snprintf(port_buf, sizeof(port_buf), "%u", tech_pvt->adv_sdp_audio_port);
|
||||
strncpy(q, port_buf, strlen(port_buf));
|
||||
q += strlen(port_buf);
|
||||
x = 0;
|
||||
while(p && *p && (*p >= '0' && *p <= '9')) {
|
||||
p++;
|
||||
}
|
||||
}
|
||||
|
||||
*q++ = *p++;
|
||||
}
|
||||
|
||||
tech_pvt->iananame = switch_core_session_strdup(tech_pvt->session, "NO-NAME");
|
||||
|
||||
tech_pvt->rm_rate = 8000;
|
||||
tech_pvt->codec_ms = 20;
|
||||
|
||||
}
|
||||
|
||||
|
||||
switch_status_t sofia_glue_do_invite(switch_core_session_t *session)
|
||||
{
|
||||
char *alert_info = NULL;
|
||||
@@ -725,7 +845,7 @@ switch_status_t sofia_glue_do_invite(switch_core_session_t *session)
|
||||
|
||||
max_forwards = switch_channel_get_variable(channel, SWITCH_MAX_FORWARDS_VARIABLE);
|
||||
|
||||
if ((status = sofia_glue_tech_choose_port(tech_pvt)) != SWITCH_STATUS_SUCCESS) {
|
||||
if ((status = sofia_glue_tech_choose_port(tech_pvt, 0)) != SWITCH_STATUS_SUCCESS) {
|
||||
return status;
|
||||
}
|
||||
|
||||
@@ -793,17 +913,17 @@ switch_status_t sofia_glue_do_invite(switch_core_session_t *session)
|
||||
}
|
||||
}
|
||||
|
||||
if (!sofia_test_pflag(tech_pvt->profile, PFLAG_TLS) && sofia_glue_transport_has_tls(tech_pvt->transport)) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "TLS not supported by profile\n");
|
||||
if (!sofia_test_pflag(tech_pvt->profile, PFLAG_TLS) && sofia_glue_transport_has_tls(tech_pvt->transport)) {
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ERROR, "TLS not supported by profile\n");
|
||||
return SWITCH_STATUS_FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
if (switch_strlen_zero(tech_pvt->invite_contact))
|
||||
{
|
||||
if (sofia_glue_transport_has_tls(tech_pvt->transport))
|
||||
if (switch_strlen_zero(tech_pvt->invite_contact)) {
|
||||
if (sofia_glue_transport_has_tls(tech_pvt->transport)) {
|
||||
tech_pvt->invite_contact = tech_pvt->profile->tls_url;
|
||||
else
|
||||
} else {
|
||||
tech_pvt->invite_contact = tech_pvt->profile->url;
|
||||
}
|
||||
}
|
||||
|
||||
url_str = sofia_overcome_sip_uri_weakness(session, url, tech_pvt->transport, SWITCH_TRUE);
|
||||
@@ -835,6 +955,7 @@ switch_status_t sofia_glue_do_invite(switch_core_session_t *session)
|
||||
} else if (switch_test_flag(caller_profile, SWITCH_CPF_HIDE_NUMBER)) {
|
||||
priv = "full";
|
||||
}
|
||||
|
||||
if (switch_test_flag(caller_profile, SWITCH_CPF_SCREEN)) {
|
||||
screen = "yes";
|
||||
}
|
||||
@@ -908,6 +1029,10 @@ switch_status_t sofia_glue_do_invite(switch_core_session_t *session)
|
||||
}
|
||||
}
|
||||
|
||||
if (switch_channel_test_flag(channel, CF_PROXY_MEDIA)) {
|
||||
sofia_glue_tech_patch_sdp(tech_pvt);
|
||||
}
|
||||
|
||||
nua_invite(tech_pvt->nh,
|
||||
NUTAG_AUTOANSWER(0),
|
||||
NUTAG_SESSION_TIMER(session_timeout),
|
||||
@@ -1265,11 +1390,11 @@ switch_status_t sofia_glue_activate_rtp(private_object_t *tech_pvt, switch_rtp_f
|
||||
char tmp[50];
|
||||
uint32_t rtp_timeout_sec = tech_pvt->profile->rtp_timeout_sec;
|
||||
uint32_t rtp_hold_timeout_sec = tech_pvt->profile->rtp_hold_timeout_sec;
|
||||
|
||||
char *timer_name;
|
||||
|
||||
switch_assert(tech_pvt != NULL);
|
||||
|
||||
|
||||
if (switch_channel_test_flag(tech_pvt->channel, CF_BYPASS_MEDIA)) {
|
||||
if (switch_channel_test_flag(tech_pvt->channel, CF_PROXY_MODE)) {
|
||||
return SWITCH_STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
@@ -1346,6 +1471,16 @@ switch_status_t sofia_glue_activate_rtp(private_object_t *tech_pvt, switch_rtp_f
|
||||
goto video;
|
||||
}
|
||||
|
||||
if (switch_channel_test_flag(tech_pvt->channel, CF_PROXY_MEDIA)) {
|
||||
if ((status = sofia_glue_tech_proxy_remote_addr(tech_pvt)) != SWITCH_STATUS_SUCCESS) {
|
||||
return status;
|
||||
}
|
||||
flags = (switch_rtp_flag_t) (SWITCH_RTP_FLAG_PROXY_MEDIA | SWITCH_RTP_FLAG_AUTOADJ | SWITCH_RTP_FLAG_DATAWAIT);
|
||||
timer_name = NULL;
|
||||
} else {
|
||||
timer_name = tech_pvt->profile->timer_name;
|
||||
}
|
||||
|
||||
tech_pvt->rtp_session = switch_rtp_new(tech_pvt->local_sdp_audio_ip,
|
||||
tech_pvt->local_sdp_audio_port,
|
||||
tech_pvt->remote_sdp_audio_ip,
|
||||
@@ -1354,7 +1489,7 @@ switch_status_t sofia_glue_activate_rtp(private_object_t *tech_pvt, switch_rtp_f
|
||||
tech_pvt->read_codec.implementation->samples_per_frame,
|
||||
tech_pvt->codec_ms * 1000,
|
||||
(switch_rtp_flag_t) flags,
|
||||
tech_pvt->profile->timer_name,
|
||||
timer_name,
|
||||
&err,
|
||||
switch_core_session_get_pool(tech_pvt->session));
|
||||
|
||||
@@ -1519,7 +1654,7 @@ switch_status_t sofia_glue_tech_media(private_object_t *tech_pvt, const char *r_
|
||||
}
|
||||
|
||||
if (match) {
|
||||
if (sofia_glue_tech_choose_port(tech_pvt) != SWITCH_STATUS_SUCCESS) {
|
||||
if (sofia_glue_tech_choose_port(tech_pvt, 0) != SWITCH_STATUS_SUCCESS) {
|
||||
return SWITCH_STATUS_FALSE;
|
||||
}
|
||||
if (sofia_glue_activate_rtp(tech_pvt, 0) != SWITCH_STATUS_SUCCESS) {
|
||||
@@ -2006,7 +2141,7 @@ void sofia_glue_pass_sdp(private_object_t *tech_pvt, char *sdp)
|
||||
|
||||
if (!switch_test_flag(tech_pvt, TFLAG_CHANGE_MEDIA) && (switch_channel_test_flag(other_channel, CF_OUTBOUND) &&
|
||||
switch_channel_test_flag(tech_pvt->channel, CF_OUTBOUND) &&
|
||||
switch_channel_test_flag(tech_pvt->channel, CF_BYPASS_MEDIA))) {
|
||||
switch_channel_test_flag(tech_pvt->channel, CF_PROXY_MODE))) {
|
||||
switch_ivr_nomedia(val, SMF_FORCE);
|
||||
switch_set_flag_locked(tech_pvt, TFLAG_CHANGE_MEDIA);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user