trying to get mozilla to work using sipml5, got stun/dtls/rtp flowing and its dead silent. c'mon guys... why do you have to do everything differently?????

This commit is contained in:
Anthony Minessale 2013-02-15 21:27:49 -06:00
parent 05dd02d0a6
commit c4b221c750
8 changed files with 211 additions and 99 deletions

View File

@ -1387,7 +1387,9 @@ void sdp_media_transport(sdp_media_t *m, char const *s)
else if (su_casematch(s, "RTP/SAVP"))
m->m_proto = sdp_proto_srtp, m->m_proto_name = "RTP/SAVP";
else if (su_casematch(s, "RTP/SAVPF"))
m->m_proto = sdp_proto_extended_srtp, m->m_proto_name = "RTP/SAVPF";
m->m_proto = sdp_proto_extended_srtp, m->m_proto_name = "RTP/SAVPF";
else if (su_casematch(s, "UDP/TLS/RTP/SAVPF"))
m->m_proto = sdp_proto_extended_srtp, m->m_proto_name = "UDP/TLS/RTP/SAVPF";
else if (su_casematch(s, "udptl"))
/* Lower case - be compatible with people living by T.38 examples */
m->m_proto = sdp_proto_udptl, m->m_proto_name = "udptl";

View File

@ -3,11 +3,17 @@
#define SHA1_HASH_SIZE 20
struct globals_s globals;
#ifndef PTHREAD
#ifndef WSS_STANDALONE
void init_ssl(void)
{
SSL_library_init();
}
void deinit_ssl(void)
{
return;
}
#else
static unsigned long pthreads_thread_id(void);
static void pthreads_locking_callback(int mode, int type, const char *file, int line);
@ -68,23 +74,24 @@ static unsigned long pthreads_thread_id(void)
void init_ssl(void) {
SSL_library_init();
// OpenSSL_add_all_algorithms(); /* load & register cryptos */
// SSL_load_error_strings(); /* load all error messages */
//globals.ssl_method = SSLv23_server_method(); /* create server instance */
//globals.ssl_ctx = SSL_CTX_new(globals.ssl_method); /* create context */
//assert(globals.ssl_ctx);
OpenSSL_add_all_algorithms(); /* load & register cryptos */
SSL_load_error_strings(); /* load all error messages */
globals.ssl_method = TLSv1_server_method(); /* create server instance */
globals.ssl_ctx = SSL_CTX_new(globals.ssl_method); /* create context */
assert(globals.ssl_ctx);
/* set the local certificate from CertFile */
//SSL_CTX_use_certificate_file(globals.ssl_ctx, globals.cert, SSL_FILETYPE_PEM);
SSL_CTX_use_certificate_file(globals.ssl_ctx, globals.cert, SSL_FILETYPE_PEM);
/* set the private key from KeyFile */
//SSL_CTX_use_PrivateKey_file(globals.ssl_ctx, globals.key, SSL_FILETYPE_PEM);
SSL_CTX_use_PrivateKey_file(globals.ssl_ctx, globals.key, SSL_FILETYPE_PEM);
/* verify private key */
//if ( !SSL_CTX_check_private_key(globals.ssl_ctx) ) {
// abort();
//}
if ( !SSL_CTX_check_private_key(globals.ssl_ctx) ) {
abort();
}
thread_setup();
}
@ -215,7 +222,7 @@ int ws_handshake(wsh_t *wsh)
if (wsh->sock == ws_sock_invalid) {
return -3;
}
while((bytes = ws_raw_read(wsh, wsh->buffer + wsh->datalen, wsh->buflen - wsh->datalen)) > 0) {
wsh->datalen += bytes;
if (strstr(wsh->buffer, "\r\n\r\n") || strstr(wsh->buffer, "\n\n")) {
@ -272,7 +279,7 @@ int ws_handshake(wsh_t *wsh)
//printf("ERR:\n%s\n", respond);
send(wsh->sock, respond, strlen(respond), 0);
ws_raw_write(wsh, respond, strlen(respond));
ws_close(wsh, WS_NONE);
@ -300,7 +307,7 @@ ssize_t ws_raw_read(wsh_t *wsh, void *data, size_t bytes)
} while (r == -1 && (errno == EAGAIN || errno == EINTR) && x < 100);
//if (r<0) {
//printf("READ FAIL: %s\n", strerror(errno));
// printf("READ FAIL: %s\n", strerror(errno));
//}
return r;
@ -334,6 +341,10 @@ int ws_init(wsh_t *wsh, ws_socket_t sock, size_t buflen, SSL_CTX *ssl_ctx, int c
memset(wsh, 0, sizeof(*wsh));
wsh->sock = sock;
if (!ssl_ctx) {
ssl_ctx = globals.ssl_ctx;
}
if (close_sock) {
wsh->close_sock = 1;
}
@ -352,13 +363,16 @@ int ws_init(wsh_t *wsh, ws_socket_t sock, size_t buflen, SSL_CTX *ssl_ctx, int c
if (wsh->secure) {
int code;
wsh->ssl = SSL_new(ssl_ctx);
assert(wsh->ssl);
SSL_set_fd(wsh->ssl, wsh->sock);
do {
code = SSL_accept(wsh->ssl);
} while (code == -1 && SSL_get_error(wsh->ssl, code) == SSL_ERROR_WANT_READ);
}
while (!wsh->down && !wsh->handshake) {

View File

@ -1,6 +1,8 @@
#ifndef _WS_H
#define _WS_H
//#define WSS_STANDALONE 1
#define MAXLEN 0x10000
#define WEBSOCKET_GUID "258EAFA5-E914-47DA-95CA-C5AB0DC85B11"
#define B64BUFFLEN 1024

View File

@ -1297,6 +1297,7 @@ typedef enum {
CF_AUTOFLUSH_DURING_BRIDGE,
CF_RTP_NOTIMER_DURING_BRIDGE,
CF_WEBRTC,
CF_WEBRTC_MOZ,
CF_ICE,
CF_DTLS,
/* WARNING: DO NOT ADD ANY FLAGS BELOW THIS LINE */

View File

@ -663,6 +663,7 @@ static switch_status_t sofia_answer_channel(switch_core_session_t *session)
if (switch_channel_test_flag(channel, CF_CONFERENCE)) {
tech_pvt->reply_contact = switch_core_session_sprintf(session, "%s;isfocus", tech_pvt->reply_contact);
}
//switch_core_media_set_local_sdp
if(sofia_test_flag(tech_pvt, TFLAG_3PCC_INVITE)) {
// SNARK: complete hack to get final ack sent when a 3pcc invite has been passed from the other leg in bypass_media mode.
@ -688,7 +689,7 @@ static switch_status_t sofia_answer_channel(switch_core_session_t *session)
}
if (sofia_test_flag(tech_pvt, TFLAG_ANS) || switch_channel_direction(channel) == SWITCH_CALL_DIRECTION_OUTBOUND) {
return SWITCH_STATUS_SUCCESS;
printf("BALLZ %d\n", __LINE__);return SWITCH_STATUS_SUCCESS;
}
@ -702,7 +703,7 @@ static switch_status_t sofia_answer_channel(switch_core_session_t *session)
if (switch_channel_test_flag(channel, CF_PROXY_MEDIA)) {
switch_core_media_patch_sdp(tech_pvt->session);
if (sofia_media_activate_rtp(tech_pvt) != SWITCH_STATUS_SUCCESS) {
return SWITCH_STATUS_FALSE;
printf("BALLZ %d\n", __LINE__);return SWITCH_STATUS_FALSE;
}
}
} else {
@ -721,7 +722,7 @@ static switch_status_t sofia_answer_channel(switch_core_session_t *session)
if (switch_channel_test_flag(channel, CF_PROXY_MEDIA)) {
switch_core_media_patch_sdp(tech_pvt->session);
if (sofia_media_activate_rtp(tech_pvt) != SWITCH_STATUS_SUCCESS) {
return SWITCH_STATUS_FALSE;
printf("BALLZ %d\n", __LINE__);return SWITCH_STATUS_FALSE;
}
}
}
@ -776,7 +777,7 @@ static switch_status_t sofia_answer_channel(switch_core_session_t *session)
}
switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(session), SWITCH_LOG_DEBUG, "3PCC-PROXY, Done waiting for ACK\n");
return SWITCH_STATUS_SUCCESS;
printf("BALLZ %d\n", __LINE__);return SWITCH_STATUS_SUCCESS;
}
if ((is_proxy && !b_sdp) || sofia_test_flag(tech_pvt, TFLAG_LATE_NEGOTIATION) ||
@ -799,14 +800,14 @@ static switch_status_t sofia_answer_channel(switch_core_session_t *session)
//switch_mutex_lock(tech_pvt->sofia_mutex);
//nua_respond(tech_pvt->nh, SIP_488_NOT_ACCEPTABLE, TAG_END());
//switch_mutex_unlock(tech_pvt->sofia_mutex);
return SWITCH_STATUS_FALSE;
printf("BALLZ %d\n", __LINE__);return SWITCH_STATUS_FALSE;
}
}
}
if ((status = switch_core_media_choose_port(tech_pvt->session, SWITCH_MEDIA_TYPE_AUDIO, 0)) != SWITCH_STATUS_SUCCESS) {
switch_channel_hangup(channel, SWITCH_CAUSE_DESTINATION_OUT_OF_ORDER);
return status;
printf("BALLZ %d\n", __LINE__);return status;
}
switch_core_media_gen_local_sdp(session, NULL, 0, NULL, 0);

View File

@ -77,20 +77,20 @@ switch_status_t sofia_media_tech_media(private_object_t *tech_pvt, const char *r
switch_assert(r_sdp != NULL);
if (zstr(r_sdp)) {
return SWITCH_STATUS_FALSE;
printf("BALLZ %d\n", __LINE__);return SWITCH_STATUS_FALSE;
}
if ((match = sofia_media_negotiate_sdp(tech_pvt->session, r_sdp))) {
if (switch_core_media_choose_port(tech_pvt->session, SWITCH_MEDIA_TYPE_AUDIO, 0) != SWITCH_STATUS_SUCCESS) {
return SWITCH_STATUS_FALSE;
printf("BALLZ %d\n", __LINE__);return SWITCH_STATUS_FALSE;
}
if (sofia_media_activate_rtp(tech_pvt) != SWITCH_STATUS_SUCCESS) {
return SWITCH_STATUS_FALSE;
printf("BALLZ %d\n", __LINE__);return SWITCH_STATUS_FALSE;
}
switch_channel_set_variable(tech_pvt->channel, SWITCH_ENDPOINT_DISPOSITION_VARIABLE, "EARLY MEDIA");
sofia_set_flag_locked(tech_pvt, TFLAG_EARLY_MEDIA);
switch_channel_mark_pre_answered(tech_pvt->channel);
return SWITCH_STATUS_SUCCESS;
printf("BALLZ %d\n", __LINE__);return SWITCH_STATUS_SUCCESS;
}

View File

@ -1804,7 +1804,7 @@ static void generate_local_fingerprint(switch_media_handle_t *smh, switch_media_
//?
static void check_ice(switch_media_handle_t *smh, switch_media_type_t type, sdp_media_t *m)
static void check_ice(switch_media_handle_t *smh, switch_media_type_t type, sdp_session_t *sdp, sdp_media_t *m)
{
switch_rtp_engine_t *engine = &smh->engines[type];
sdp_attribute_t *attr;
@ -1814,8 +1814,13 @@ static void check_ice(switch_media_handle_t *smh, switch_media_type_t type, sdp_
engine->ice_in.chosen[1] = 0;
engine->ice_in.cand_idx = 0;
if (m) {
attr = m->m_attributes;
} else {
attr = sdp->sdp_attributes;
}
for (attr = m->m_attributes; attr; attr = attr->a_next) {
for (; attr; attr = attr->a_next) {
char *data;
char *fields[15];
int argc = 0, j = 0;
@ -2187,6 +2192,8 @@ SWITCH_DECLARE(uint8_t) switch_core_media_negotiate_sdp(switch_core_session_t *s
switch_core_media_find_zrtp_hash(session, sdp);
switch_core_media_pass_zrtp_hash(session);
check_ice(smh, SWITCH_MEDIA_TYPE_AUDIO, sdp, NULL);
for (m = sdp->sdp_media; m; m = m->m_next) {
sdp_connection_t *connection;
switch_core_session_t *other_session;
@ -2199,6 +2206,10 @@ SWITCH_DECLARE(uint8_t) switch_core_media_negotiate_sdp(switch_core_session_t *s
switch_core_session_set_ice(session);
}
if (m->m_proto_name && !strcasecmp(m->m_proto_name, "UDP/TLS/RTP/SAVPF")) {
switch_channel_set_flag(session->channel, CF_WEBRTC_MOZ);
}
if (m->m_proto == sdp_proto_srtp || m->m_proto == sdp_proto_extended_srtp) {
if (m->m_type == sdp_media_audio) {
got_savp++;
@ -2633,7 +2644,7 @@ SWITCH_DECLARE(uint8_t) switch_core_media_negotiate_sdp(switch_core_session_t *s
if (match) {
if (switch_core_media_set_codec(session, 1, smh->mparams->codec_flags) == SWITCH_STATUS_SUCCESS) {
got_audio = 1;
check_ice(smh, SWITCH_MEDIA_TYPE_AUDIO, m);
check_ice(smh, SWITCH_MEDIA_TYPE_AUDIO, sdp, m);
} else {
match = 0;
}
@ -2810,8 +2821,8 @@ SWITCH_DECLARE(uint8_t) switch_core_media_negotiate_sdp(switch_core_session_t *s
switch_channel_set_variable(session->channel, "sip_video_recv_pt", tmp);
if (!match && vmatch) match = 1;
check_ice(smh, SWITCH_MEDIA_TYPE_VIDEO, m);
check_ice(smh, SWITCH_MEDIA_TYPE_VIDEO, sdp, m);
check_ice(smh, SWITCH_MEDIA_TYPE_VIDEO, sdp, NULL);
break;
} else {
vmatch = 0;
@ -3753,23 +3764,7 @@ SWITCH_DECLARE(switch_status_t) switch_core_media_activate_rtp(switch_core_sessi
}
if (!zstr(a_engine->local_dtls_fingerprint.str) && switch_rtp_has_dtls()) {
dtls_type_t xtype, dtype = switch_channel_direction(smh->session->channel) == SWITCH_CALL_DIRECTION_INBOUND ? DTLS_TYPE_CLIENT : DTLS_TYPE_SERVER;
xtype = DTLS_TYPE_RTP;
if (a_engine->rtcp_mux > 0) xtype |= DTLS_TYPE_RTCP;
switch_rtp_add_dtls(a_engine->rtp_session, &a_engine->local_dtls_fingerprint, &a_engine->remote_dtls_fingerprint, dtype | xtype);
if (a_engine->rtcp_mux < 1) {
xtype = DTLS_TYPE_RTCP;
switch_rtp_add_dtls(a_engine->rtp_session, &a_engine->local_dtls_fingerprint, &a_engine->remote_dtls_fingerprint, dtype | xtype);
}
}
if (a_engine->ice_in.cands[a_engine->ice_in.chosen[0]][0].ready) {
gen_ice(session, SWITCH_MEDIA_TYPE_AUDIO, NULL, 0);
@ -3843,6 +3838,24 @@ SWITCH_DECLARE(switch_status_t) switch_core_media_activate_rtp(switch_core_sessi
}
if (!zstr(a_engine->local_dtls_fingerprint.str) && switch_rtp_has_dtls()) {
dtls_type_t xtype, dtype = switch_channel_direction(smh->session->channel) == SWITCH_CALL_DIRECTION_INBOUND ? DTLS_TYPE_CLIENT : DTLS_TYPE_SERVER;
xtype = DTLS_TYPE_RTP;
if (a_engine->rtcp_mux > 0) xtype |= DTLS_TYPE_RTCP;
switch_rtp_add_dtls(a_engine->rtp_session, &a_engine->local_dtls_fingerprint, &a_engine->remote_dtls_fingerprint, dtype | xtype);
if (a_engine->rtcp_mux < 1) {
xtype = DTLS_TYPE_RTCP;
switch_rtp_add_dtls(a_engine->rtp_session, &a_engine->local_dtls_fingerprint, &a_engine->remote_dtls_fingerprint, dtype | xtype);
}
}
if ((val = switch_channel_get_variable(session->channel, "jitterbuffer_msec")) || (val = smh->mparams->jb_msec)) {
int jb_msec = atoi(val);
int maxlen = 0, max_drift = 0;
@ -4179,7 +4192,7 @@ SWITCH_DECLARE(switch_status_t) switch_core_media_activate_rtp(switch_core_sessi
if ((val = switch_channel_get_variable(session->channel, "rtcp_video_interval_msec")) || (val = smh->mparams->rtcp_video_interval_msec)) {
const char *rport = switch_channel_get_variable(session->channel, "sip_remote_video_rtcp_port");
switch_port_t remote_port = 0;
switch_port_t remote_port = v_engine->remote_rtcp_port;
if (rport) {
remote_port = (switch_port_t)atoi(rport);
}
@ -4198,21 +4211,6 @@ SWITCH_DECLARE(switch_status_t) switch_core_media_activate_rtp(switch_core_sessi
}
if (!zstr(v_engine->local_dtls_fingerprint.str) && switch_rtp_has_dtls()) {
dtls_type_t xtype,
dtype = switch_channel_direction(smh->session->channel) == SWITCH_CALL_DIRECTION_INBOUND ? DTLS_TYPE_CLIENT : DTLS_TYPE_SERVER;
xtype = DTLS_TYPE_RTP;
if (v_engine->rtcp_mux > 0) xtype |= DTLS_TYPE_RTCP;
switch_rtp_add_dtls(v_engine->rtp_session, &v_engine->local_dtls_fingerprint, &v_engine->remote_dtls_fingerprint, dtype | xtype);
if (v_engine->rtcp_mux < 1) {
xtype = DTLS_TYPE_RTCP;
switch_rtp_add_dtls(v_engine->rtp_session, &v_engine->local_dtls_fingerprint, &v_engine->remote_dtls_fingerprint, dtype | xtype);
}
}
if (v_engine->ice_in.cands[v_engine->ice_in.chosen[1]][1].ready) {
switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(session), SWITCH_LOG_INFO, "Activating VIDEO RTCP ICE\n");
switch_rtp_activate_ice(v_engine->rtp_session,
@ -4236,7 +4234,20 @@ SWITCH_DECLARE(switch_status_t) switch_core_media_activate_rtp(switch_core_sessi
}
if (!zstr(v_engine->local_dtls_fingerprint.str) && switch_rtp_has_dtls()) {
dtls_type_t xtype,
dtype = switch_channel_direction(smh->session->channel) == SWITCH_CALL_DIRECTION_INBOUND ? DTLS_TYPE_CLIENT : DTLS_TYPE_SERVER;
xtype = DTLS_TYPE_RTP;
if (v_engine->rtcp_mux > 0) xtype |= DTLS_TYPE_RTCP;
switch_rtp_add_dtls(v_engine->rtp_session, &v_engine->local_dtls_fingerprint, &v_engine->remote_dtls_fingerprint, dtype | xtype);
if (v_engine->rtcp_mux < 1) {
xtype = DTLS_TYPE_RTCP;
switch_rtp_add_dtls(v_engine->rtp_session, &v_engine->local_dtls_fingerprint, &v_engine->remote_dtls_fingerprint, dtype | xtype);
}
}
if ((val = switch_channel_get_variable(session->channel, "rtp_manual_video_rtp_bugs"))) {
@ -4293,6 +4304,26 @@ SWITCH_DECLARE(switch_status_t) switch_core_media_activate_rtp(switch_core_sessi
}
static const char *get_media_profile_name(switch_core_session_t *session, int secure)
{
switch_assert(session);
if (switch_channel_test_flag(session->channel, CF_WEBRTC)) {
if (switch_channel_test_flag(session->channel, CF_WEBRTC_MOZ)) {
return "UDP/TLS/RTP/SAVPF";
} else {
return "RTP/SAVPF";
}
}
if ((!secure && switch_channel_test_flag(session->channel, CF_SECURE)) || secure) {
return "RTP/SAVP";
}
return "RTP/AVP";
}
//?
static void generate_m(switch_core_session_t *session, char *buf, size_t buflen,
switch_port_t port, const char *family, const char *ip,
@ -4315,9 +4346,10 @@ static void generate_m(switch_core_session_t *session, char *buf, size_t buflen,
a_engine = &smh->engines[SWITCH_MEDIA_TYPE_AUDIO];
switch_snprintf(buf + strlen(buf), buflen - strlen(buf), "m=audio %d RTP/%sAVP%s",
port, secure ? "S" : "", switch_channel_test_flag(session->channel, CF_WEBRTC) ? "F" : "");
//switch_snprintf(buf + strlen(buf), buflen - strlen(buf), "m=audio %d RTP/%sAVP%s",
//port, secure ? "S" : "", switch_channel_test_flag(session->channel, CF_WEBRTC) ? "F" : "");
switch_snprintf(buf + strlen(buf), buflen - strlen(buf), "m=audio %d %s", port, get_media_profile_name(session, secure));
for (i = 0; i < smh->mparams->num_codecs; i++) {
@ -4477,9 +4509,11 @@ static void generate_m(switch_core_session_t *session, char *buf, size_t buflen,
switch_snprintf(buf + strlen(buf), buflen - strlen(buf), "a=ssrc:%u mslabel:%s\n", a_engine->ssrc, smh->msid);
switch_snprintf(buf + strlen(buf), buflen - strlen(buf), "a=ssrc:%u label:%sa0\n", a_engine->ssrc, smh->msid);
switch_snprintf(buf + strlen(buf), buflen - strlen(buf), "a=ice-ufrag:%s\n", ice_out->ufrag);
switch_snprintf(buf + strlen(buf), buflen - strlen(buf), "a=ice-pwd:%s\n", ice_out->pwd);
switch_snprintf(buf + strlen(buf), buflen - strlen(buf), "a=candidate:%s 1 %s %u %s %d typ host generation 0\n",
tmp1, ice_out->cands[0][0].transport, c1,
ice_out->cands[0][0].con_addr, ice_out->cands[0][0].con_port
@ -4850,18 +4884,28 @@ SWITCH_DECLARE(void) switch_core_media_gen_local_sdp(switch_core_session_t *sess
"%s",
username, smh->owner_id, smh->session_id, family, ip, username, family, ip, srbuf);
if (switch_channel_test_flag(smh->session->channel, CF_ICE)) {
gen_ice(session, SWITCH_MEDIA_TYPE_AUDIO, ip, port);
switch_snprintf(buf + strlen(buf), SDPBUFLEN - strlen(buf), "a=msid-semantic: WMS %s\n", smh->msid);
}
if (a_engine->codec_params.rm_encoding) {
/*
switch_snprintf(buf + strlen(buf), SDPBUFLEN - strlen(buf), "m=audio %d RTP/%sAVP%s",
port, ((!zstr(local_audio_crypto_key) || switch_channel_test_flag(session->channel, CF_DTLS)) &&
switch_channel_test_flag(session->channel, CF_SECURE)) ? "S" : "",
switch_channel_test_flag(session->channel, CF_WEBRTC) ? "F" : "");
*/
switch_snprintf(buf + strlen(buf), SDPBUFLEN - strlen(buf), "m=audio %d %s", port,
get_media_profile_name(session,
((!zstr(local_audio_crypto_key) || switch_channel_test_flag(session->channel, CF_DTLS)) &&
switch_channel_test_flag(session->channel, CF_SECURE))
));
switch_snprintf(buf + strlen(buf), SDPBUFLEN - strlen(buf), " %d", a_engine->codec_params.pt);
if ((smh->mparams->dtmf_type == DTMF_2833 || switch_media_handle_test_media_flag(smh, SCMF_LIBERAL_DTMF) ||
@ -4960,15 +5004,17 @@ SWITCH_DECLARE(void) switch_core_media_gen_local_sdp(switch_core_session_t *sess
ice_out = &a_engine->ice_out;
switch_snprintf(buf + strlen(buf), SDPBUFLEN - strlen(buf), "a=ssrc:%u cname:%s\n", a_engine->ssrc, smh->cname);
switch_snprintf(buf + strlen(buf), SDPBUFLEN - strlen(buf), "a=ssrc:%u msid:%s a0\n", a_engine->ssrc, smh->msid);
switch_snprintf(buf + strlen(buf), SDPBUFLEN - strlen(buf), "a=ssrc:%u mslabel:%s\n", a_engine->ssrc, smh->msid);
switch_snprintf(buf + strlen(buf), SDPBUFLEN - strlen(buf), "a=ssrc:%u label:%sa0\n", a_engine->ssrc, smh->msid);
switch_snprintf(buf + strlen(buf), SDPBUFLEN - strlen(buf), "a=ice-ufrag:%s\n", ice_out->ufrag);
switch_snprintf(buf + strlen(buf), SDPBUFLEN - strlen(buf), "a=ice-pwd:%s\n", ice_out->pwd);
switch_snprintf(buf + strlen(buf), SDPBUFLEN - strlen(buf), "a=candidate:%s 1 %s %u %s %d typ host generation 0\n",
tmp1, ice_out->cands[0][0].transport, c1,
ice_out->cands[0][0].con_addr, ice_out->cands[0][0].con_port
@ -5122,12 +5168,19 @@ SWITCH_DECLARE(void) switch_core_media_gen_local_sdp(switch_core_session_t *sess
if (switch_channel_test_flag(smh->session->channel, CF_ICE)) {
gen_ice(session, SWITCH_MEDIA_TYPE_VIDEO, ip, v_port);
}
/*
switch_snprintf(buf + strlen(buf), SDPBUFLEN - strlen(buf), "m=video %d RTP/%sAVP%s",
v_port, ((!zstr(local_video_crypto_key) || switch_channel_test_flag(session->channel, CF_DTLS))
&& switch_channel_test_flag(session->channel, CF_SECURE)) ? "S" : "",
switch_channel_test_flag(session->channel, CF_WEBRTC) ? "F" : "");
*/
switch_snprintf(buf + strlen(buf), SDPBUFLEN - strlen(buf), "m=video %d %s",
v_port, get_media_profile_name(session,
(!zstr(local_video_crypto_key) || switch_channel_test_flag(session->channel, CF_DTLS))
&& switch_channel_test_flag(session->channel, CF_SECURE)));
/*****************************/
if (v_engine->codec_params.rm_encoding) {
@ -5283,14 +5336,18 @@ SWITCH_DECLARE(void) switch_core_media_gen_local_sdp(switch_core_session_t *sess
ice_out = &v_engine->ice_out;
switch_snprintf(buf + strlen(buf), SDPBUFLEN - strlen(buf), "a=ssrc:%u cname:%s\n", v_engine->ssrc, smh->cname);
switch_snprintf(buf + strlen(buf), SDPBUFLEN - strlen(buf), "a=ssrc:%u msid:%s v0\n", v_engine->ssrc, smh->msid);
switch_snprintf(buf + strlen(buf), SDPBUFLEN - strlen(buf), "a=ssrc:%u mslabel:%s\n", v_engine->ssrc, smh->msid);
switch_snprintf(buf + strlen(buf), SDPBUFLEN - strlen(buf), "a=ssrc:%u label:%sv0\n", v_engine->ssrc, smh->msid);
switch_snprintf(buf + strlen(buf), SDPBUFLEN - strlen(buf), "a=ice-ufrag:%s\n", ice_out->ufrag);
switch_snprintf(buf + strlen(buf), SDPBUFLEN - strlen(buf), "a=ice-pwd:%s\n", ice_out->pwd);
switch_snprintf(buf + strlen(buf), SDPBUFLEN - strlen(buf), "a=candidate:%s 1 %s %u %s %d typ host generation 0\n",
tmp1, ice_out->cands[0][0].transport, c1,
ice_out->cands[0][0].con_addr, ice_out->cands[0][0].con_port

View File

@ -177,6 +177,7 @@ typedef struct {
uint8_t sending;
uint8_t ready;
uint8_t rready;
int missed_count;
} switch_rtp_ice_t;
struct switch_rtp;
@ -678,12 +679,9 @@ static switch_status_t ice_out(switch_rtp_t *rtp_session, switch_rtp_ice_t *ice)
if (ice == &rtp_session->rtcp_ice) {
sock_output = rtp_session->rtcp_sock_output;
//remote_addr = rtp_session->rtcp_remote_addr;
}
switch_assert(rtp_session != NULL);
switch_assert(ice->ice_user != NULL);
@ -775,6 +773,7 @@ static void handle_ice(switch_rtp_t *rtp_session, switch_rtp_ice_t *ice, void *d
int xlen = 0;
int ok = 1;
uint32_t *pri = NULL;
int is_rtcp = ice == &rtp_session->rtcp_ice;
if (!switch_rtp_ready(rtp_session) || zstr(ice->user_ice) || zstr(ice->ice_user)) {
return;
@ -800,8 +799,6 @@ static void handle_ice(switch_rtp_t *rtp_session, switch_rtp_ice_t *ice, void *d
}
#if 0
if (ice->sending && (packet->header.type == SWITCH_STUN_BINDING_RESPONSE || packet->header.type == SWITCH_STUN_BINDING_ERROR_RESPONSE)) {
ice->sending = 0;
@ -847,19 +844,23 @@ static void handle_ice(switch_rtp_t *rtp_session, switch_rtp_ice_t *ice, void *d
ok = !strcmp(ice->user_ice, username);
}
if (ice->type == ICE_VANILLA) {
if ((ice->type & ICE_VANILLA)) {
if (!ok && ice == &rtp_session->ice && pri &&
*pri == rtp_session->rtcp_ice.ice_params->cands[rtp_session->rtcp_ice.ice_params->chosen[1]][1].priority) {
ice = &rtp_session->rtcp_ice;
ok = 1;
}
if (!ok) {
if (ok) {
ice->missed_count = 0;
} else {
uint32_t elapsed = (unsigned int) ((switch_micro_time_now() - rtp_session->last_stun) / 1000);
switch_rtp_ice_t *icep[2] = { &rtp_session->ice, &rtp_session->rtcp_ice };
switch_port_t port = 0;
char *host = NULL;
ice->missed_count++;
if (elapsed > 20000 && pri) {
int i, j;
uint32_t old;
@ -936,7 +937,7 @@ static void handle_ice(switch_rtp_t *rtp_session, switch_rtp_ice_t *ice, void *d
}
if (ok) {
if (ok || ice->missed_count > 1) {
if ((packet->header.type == SWITCH_STUN_BINDING_RESPONSE)) {
if (rtp_session->flags[SWITCH_RTP_FLAG_RTCP_MUX]) {
rtp_session->ice.rready = 1;
@ -953,7 +954,7 @@ static void handle_ice(switch_rtp_t *rtp_session, switch_rtp_ice_t *ice, void *d
switch_sockaddr_t *from_addr = rtp_session->from_addr;
switch_socket_t *sock_output = rtp_session->sock_output;
if (ice == &rtp_session->rtcp_ice && !rtp_session->flags[SWITCH_RTP_FLAG_RTCP_MUX]) {
if (is_rtcp && !rtp_session->flags[SWITCH_RTP_FLAG_RTCP_MUX]) {
from_addr = rtp_session->rtcp_from_addr;
sock_output = rtp_session->rtcp_sock_output;
}
@ -968,7 +969,7 @@ static void handle_ice(switch_rtp_t *rtp_session, switch_rtp_ice_t *ice, void *d
}
remote_ip = switch_get_addr(ipbuf, sizeof(ipbuf), from_addr);
switch_stun_packet_attribute_add_binded_address(rpacket, (char *) remote_ip, switch_sockaddr_get_port(from_addr));
switch_stun_packet_attribute_add_xor_binded_address(rpacket, (char *) remote_ip, switch_sockaddr_get_port(from_addr));
if ((ice->type & ICE_VANILLA)) {
switch_stun_packet_attribute_add_integrity(rpacket, ice->pass);
@ -988,7 +989,7 @@ static void handle_ice(switch_rtp_t *rtp_session, switch_rtp_ice_t *ice, void *d
port = switch_sockaddr_get_port(from_addr);
switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(rtp_session->session), SWITCH_LOG_INFO,
"Auto Changing stun/rtp/dtls port to %s:%u\n", host, port);
"Auto Changing stun/%s/dtls port to %s:%u\n", is_rtcp ? "rtcp" : "rtp", host, port);
ice->ice_params->cands[ice->ice_params->chosen[ice->proto]][ice->proto].con_addr = switch_core_strdup(rtp_session->pool, host);
ice->ice_params->cands[ice->ice_params->chosen[ice->proto]][ice->proto].con_port = port;
@ -1001,8 +1002,15 @@ static void handle_ice(switch_rtp_t *rtp_session, switch_rtp_ice_t *ice, void *d
switch_sockaddr_info_get(&rtp_session->dtls->remote_addr, host, SWITCH_UNSPEC, port, 0, rtp_session->pool);
}
if (ice == &rtp_session->rtcp_ice && !rtp_session->flags[SWITCH_RTP_FLAG_RTCP_MUX] && rtp_session->rtcp_dtls) {
switch_sockaddr_info_get(&rtp_session->rtcp_dtls->remote_addr, host, SWITCH_UNSPEC, port, 0, rtp_session->pool);
if (is_rtcp && !rtp_session->flags[SWITCH_RTP_FLAG_RTCP_MUX]) {
switch_sockaddr_info_get(&rtp_session->rtcp_remote_addr, host, SWITCH_UNSPEC, port, 0, rtp_session->pool);
if (rtp_session->rtcp_dtls) {
//switch_sockaddr_info_get(&rtp_session->rtcp_dtls->remote_addr, host, SWITCH_UNSPEC, port, 0, rtp_session->pool);
rtp_session->rtcp_dtls->remote_addr = rtp_session->rtcp_remote_addr;
rtp_session->rtcp_dtls->sock_output = rtp_session->rtcp_sock_output;
}
}
}
@ -2179,6 +2187,7 @@ SWITCH_DECLARE(switch_status_t) switch_rtp_add_dtls(switch_rtp_t *rtp_session, d
{
switch_dtls_t *dtls;
int ret;
const char *kind = "";
#ifndef HAVE_OPENSSL_DTLS_SRTP
return SWITCH_STATUS_FALSE;
@ -2192,8 +2201,16 @@ SWITCH_DECLARE(switch_status_t) switch_rtp_add_dtls(switch_rtp_t *rtp_session, d
switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(rtp_session->session), SWITCH_LOG_CRIT, "INVALID TYPE!\n");
}
if ((type & DTLS_TYPE_RTP) && (type & DTLS_TYPE_RTCP)) {
kind = "RTP/RTCP";
} else if ((type & DTLS_TYPE_RTP)) {
kind = "RTP";
} else {
kind = "RTCP";
}
switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(rtp_session->session), SWITCH_LOG_INFO,
"Activate %s DTLS %s\n", rtp_type(rtp_session), (type & DTLS_TYPE_SERVER) ? "server" : "client");
"Activate %s %s DTLS %s\n", kind, rtp_type(rtp_session), (type & DTLS_TYPE_SERVER) ? "server" : "client");
if (((type & DTLS_TYPE_RTP) && rtp_session->dtls) || ((type & DTLS_TYPE_RTCP) && rtp_session->rtcp_dtls)) {
switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(rtp_session->session), SWITCH_LOG_WARNING, "DTLS ALREADY INIT\n");
@ -2395,7 +2412,7 @@ SWITCH_DECLARE(switch_status_t) switch_rtp_add_crypto_key(switch_rtp_t *rtp_sess
case SWITCH_RTP_CRYPTO_RECV:
policy->ssrc.type = ssrc_any_inbound;
if (rtp_session->flags[SWITCH_RTP_FLAG_SECURE_RECV] && idx == 0) {
if (rtp_session->flags[SWITCH_RTP_FLAG_SECURE_RECV] && idx == 0 && rtp_session->recv_ctx[idx]) {
rtp_session->flags[SWITCH_RTP_FLAG_SECURE_RECV_RESET] = 1;
} else {
if ((stat = srtp_create(&rtp_session->recv_ctx[idx], policy))) {
@ -2403,8 +2420,8 @@ SWITCH_DECLARE(switch_status_t) switch_rtp_add_crypto_key(switch_rtp_t *rtp_sess
}
if (status == SWITCH_STATUS_SUCCESS) {
switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(rtp_session->session), SWITCH_LOG_INFO, "Activating %s Secure RTP RECV\n",
rtp_session->flags[SWITCH_RTP_FLAG_VIDEO] ? "Video" : "Audio");
switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(rtp_session->session), SWITCH_LOG_INFO, "Activating %s Secure %s RECV\n",
rtp_session->flags[SWITCH_RTP_FLAG_VIDEO] ? "Video" : "Audio", idx ? "RTCP" : "RTP");
rtp_session->flags[SWITCH_RTP_FLAG_SECURE_RECV] = 1;
} else {
switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(rtp_session->session), SWITCH_LOG_ERROR, "Error allocating srtp [%d]\n", stat);
@ -2417,7 +2434,7 @@ SWITCH_DECLARE(switch_status_t) switch_rtp_add_crypto_key(switch_rtp_t *rtp_sess
//policy->ssrc.type = ssrc_specific;
//policy->ssrc.value = rtp_session->ssrc;
if (rtp_session->flags[SWITCH_RTP_FLAG_SECURE_SEND] && idx == 0) {
if (rtp_session->flags[SWITCH_RTP_FLAG_SECURE_SEND] && idx == 0 && rtp_session->send_ctx[idx]) {
rtp_session->flags[SWITCH_RTP_FLAG_SECURE_SEND_RESET] = 1;
} else {
if ((stat = srtp_create(&rtp_session->send_ctx[idx], policy))) {
@ -2425,8 +2442,8 @@ SWITCH_DECLARE(switch_status_t) switch_rtp_add_crypto_key(switch_rtp_t *rtp_sess
}
if (status == SWITCH_STATUS_SUCCESS) {
switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(rtp_session->session), SWITCH_LOG_INFO, "Activating %s Secure RTP SEND\n",
rtp_session->flags[SWITCH_RTP_FLAG_VIDEO] ? "Video" : "Audio");
switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(rtp_session->session), SWITCH_LOG_INFO, "Activating %s Secure %s SEND\n",
rtp_session->flags[SWITCH_RTP_FLAG_VIDEO] ? "Video" : "Audio", idx ? "RTCP" : "RTP");
rtp_session->flags[SWITCH_RTP_FLAG_SECURE_SEND] = 1;
} else {
switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(rtp_session->session), SWITCH_LOG_ERROR, "Error allocating SRTP [%d]\n", stat);
@ -3041,8 +3058,8 @@ SWITCH_DECLARE(switch_status_t) switch_rtp_activate_ice(switch_rtp_t *rtp_sessio
return SWITCH_STATUS_FALSE;
}
switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(rtp_session->session), SWITCH_LOG_NOTICE, "Activating %s ICE: %s %s:%d\n",
rtp_type(rtp_session), ice_user, host, port);
switch_log_printf(SWITCH_CHANNEL_SESSION_LOG(rtp_session->session), SWITCH_LOG_NOTICE, "Activating %s %s ICE: %s %s:%d\n",
proto == IPR_RTP ? "RTP" : "RTCP", rtp_type(rtp_session), ice_user, host, port);
if (ice->ice_user) {
@ -3679,6 +3696,13 @@ static switch_status_t read_rtp_packet(switch_rtp_t *rtp_session, switch_size_t
}
if (rtp_session->dtls) {
if (rtp_session->rtcp_dtls && rtp_session->rtcp_dtls != rtp_session->dtls) {
rtp_session->rtcp_dtls->bytes = 0;
rtp_session->rtcp_dtls->data = NULL;
do_dtls(rtp_session, rtp_session->rtcp_dtls);
}
rtp_session->dtls->bytes = 0;
if (*bytes) {
@ -4002,10 +4026,12 @@ static switch_status_t process_rtcp_packet(switch_rtp_t *rtp_session, switch_siz
}
static switch_status_t read_rtcp_packet(switch_rtp_t *rtp_session, switch_size_t *bytes, switch_frame_flag_t *flags)
{
switch_status_t status = SWITCH_STATUS_FALSE;
if (!rtp_session->flags[SWITCH_RTP_FLAG_ENABLE_RTCP]) {
return SWITCH_STATUS_FALSE;
}
@ -4019,21 +4045,30 @@ static switch_status_t read_rtcp_packet(switch_rtp_t *rtp_session, switch_size_t
*bytes = 0;
}
if (rtp_session->rtcp_dtls) {
char *b = (char *) &rtp_session->rtcp_recv_msg;
//printf("RECV2 %d %ld\n", *b, *bytes);
if ((*b >= 20) && (*b <= 64)) {
if (*b == 0 || *b == 1) {
if (rtp_session->rtcp_ice.ice_user) {
handle_ice(rtp_session, &rtp_session->rtcp_ice, (void *) &rtp_session->rtcp_recv_msg, *bytes);
}
*bytes = 0;
}
if (*bytes && (*b >= 20) && (*b <= 64)) {
rtp_session->rtcp_dtls->bytes = *bytes;
rtp_session->rtcp_dtls->data = (void *) &rtp_session->rtcp_recv_msg;
} else {
rtp_session->rtcp_dtls->bytes = 0;
rtp_session->rtcp_dtls->data = NULL;
}
do_dtls(rtp_session, rtp_session->rtcp_dtls);
if (rtp_session->rtcp_dtls->bytes) {
*bytes = 0;
@ -4327,7 +4362,7 @@ static int rtp_common_read(switch_rtp_t *rtp_session, switch_payload_t *payload_
if (bytes && rtp_session->flags[SWITCH_RTP_FLAG_ENABLE_RTCP]) {
if (rtp_session->flags[SWITCH_RTP_FLAG_ENABLE_RTCP]) {
rtcp_poll_status = SWITCH_STATUS_FALSE;
if (rtp_session->flags[SWITCH_RTP_FLAG_RTCP_MUX] && has_rtcp) {