44 #include <openssl/opensslconf.h> 45 #include <openssl/opensslv.h> 46 #if !defined(OPENSSL_NO_SRTP) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) 47 #include <openssl/ssl.h> 48 #include <openssl/err.h> 49 #include <openssl/bio.h> 50 #if !defined(OPENSSL_NO_ECDH) && (OPENSSL_VERSION_NUMBER >= 0x10000000L) 51 #include <openssl/bn.h> 54 #include <openssl/dh.h> 61 #include <pjlib-util.h> 92 #define MAX_TIMESTAMP_SKEW 640 94 #define RTP_SEQ_MOD (1<<16) 95 #define RTCP_DEFAULT_INTERVALMS 5000 96 #define RTCP_MIN_INTERVALMS 500 97 #define RTCP_MAX_INTERVALMS 60000 99 #define DEFAULT_RTP_START 5000 100 #define DEFAULT_RTP_END 31000 102 #define MINIMUM_RTP_PORT 1024 103 #define MAXIMUM_RTP_PORT 65535 105 #define DEFAULT_TURN_PORT 3478 107 #define TURN_STATE_WAIT_TIME 2000 109 #define DEFAULT_RTP_SEND_BUFFER_SIZE 250 110 #define MAXIMUM_RTP_SEND_BUFFER_SIZE (DEFAULT_RTP_SEND_BUFFER_SIZE + 200) 111 #define DEFAULT_RTP_RECV_BUFFER_SIZE 20 112 #define MAXIMUM_RTP_RECV_BUFFER_SIZE (DEFAULT_RTP_RECV_BUFFER_SIZE + 20) 113 #define OLD_PACKET_COUNT 1000 114 #define MISSING_SEQNOS_ADDED_TRIGGER 2 116 #define SEQNO_CYCLE_OVER 65536 119 #define RTCP_PT_FUR 192 121 #define RTCP_PT_SR AST_RTP_RTCP_SR 123 #define RTCP_PT_RR AST_RTP_RTCP_RR 125 #define RTCP_PT_SDES 202 127 #define RTCP_PT_BYE 203 129 #define RTCP_PT_APP 204 132 #define RTCP_PT_PSFB AST_RTP_RTCP_PSFB 135 #define DTMF_SAMPLE_RATE_MS 8 137 #define DEFAULT_DTMF_TIMEOUT (150 * (8000 / 1000)) 139 #define ZFONE_PROFILE_ID 0x505a 141 #define DEFAULT_LEARNING_MIN_SEQUENTIAL 4 154 #define CALC_LEARNING_MIN_DURATION(count) (((count) - 1) * 9 - 5) 155 #define DEFAULT_LEARNING_MIN_DURATION CALC_LEARNING_MIN_DURATION(DEFAULT_LEARNING_MIN_SEQUENTIAL) 157 #define SRTP_MASTER_KEY_LEN 16 158 #define SRTP_MASTER_SALT_LEN 14 159 #define SRTP_MASTER_LEN (SRTP_MASTER_KEY_LEN + SRTP_MASTER_SALT_LEN) 161 #define RTP_DTLS_ESTABLISHED -37 182 #define STRICT_RTP_LEARN_TIMEOUT 5000 184 #define DEFAULT_STRICT_RTP STRICT_RTP_YES 185 #define DEFAULT_SRTP_REPLAY_PROTECTION 1 186 #define DEFAULT_ICESUPPORT 1 187 #define DEFAULT_STUN_SOFTWARE_ATTRIBUTE 1 188 #define DEFAULT_DTLS_MTU 1200 204 static int nochecksums;
210 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 213 #ifdef HAVE_PJPROJECT 283 #define FLAG_3389_WARNING (1 << 0) 284 #define FLAG_NAT_ACTIVE (3 << 1) 285 #define FLAG_NAT_INACTIVE (0 << 1) 286 #define FLAG_NAT_INACTIVE_NOWARN (1 << 1) 287 #define FLAG_NEED_MARKER_BIT (1 << 3) 288 #define FLAG_DTMF_COMPENSATE (1 << 4) 289 #define FLAG_REQ_LOCAL_BRIDGE_BIT (1 << 5) 291 #define TRANSPORT_SOCKET_RTP 0 292 #define TRANSPORT_SOCKET_RTCP 1 293 #define TRANSPORT_TURN_RTP 2 294 #define TRANSPORT_TURN_RTCP 3 299 struct timeval start;
300 struct timeval received;
307 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 308 struct dtls_details {
318 #ifdef HAVE_PJPROJECT 340 struct timeval received;
350 unsigned int last_seqno;
352 unsigned int last_extended_seqno;
354 unsigned int feedback_count;
387 unsigned short seedrxseqno;
388 unsigned int seedrxts;
389 unsigned int rxcount;
390 unsigned int rxoctetcount;
391 unsigned int txcount;
392 unsigned int txoctetcount;
401 unsigned int last_seqno;
403 unsigned int dtmf_duration;
404 unsigned int dtmf_timeout;
405 unsigned int dtmfsamples;
408 unsigned int lastdigitts;
414 struct timeval rxcore;
415 struct timeval txcore;
417 struct timeval dtmfmute;
419 unsigned short seqno;
422 unsigned int asymmetric_codec;
445 #ifdef HAVE_PJPROJECT 450 pj_turn_sock *turn_rtp;
451 pj_turn_sock *turn_rtcp;
452 pj_turn_state_t turn_state;
453 unsigned int passthrough:1;
454 unsigned int rtp_passthrough:1;
455 unsigned int rtcp_passthrough:1;
456 unsigned int ice_port;
462 char remote_ufrag[256];
463 char remote_passwd[256];
465 char local_ufrag[256];
466 char local_passwd[256];
472 unsigned int ice_num_components;
473 unsigned int ice_media_started:1;
476 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 481 char local_fingerprint[160];
483 unsigned char remote_fingerprint[EVP_MAX_MD_SIZE];
486 struct dtls_details dtls;
508 struct timeval rxlsr;
509 struct timeval txlsr;
555 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 556 struct dtls_details dtls;
578 unsigned char t140red_data[64000];
579 unsigned char buf_data[64000];
623 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 627 static int dtls_bio_write(BIO *bio,
const char *
buf,
int len);
628 static long dtls_bio_ctrl(BIO *bio,
int cmd,
long arg1,
void *arg2);
629 static int dtls_bio_new(BIO *bio);
630 static int dtls_bio_free(BIO *bio);
632 #ifndef HAVE_OPENSSL_BIO_METHOD 633 static BIO_METHOD dtls_bio_methods = {
634 .type = BIO_TYPE_BIO,
636 .bwrite = dtls_bio_write,
637 .ctrl = dtls_bio_ctrl,
638 .create = dtls_bio_new,
639 .destroy = dtls_bio_free,
642 static BIO_METHOD *dtls_bio_methods;
648 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 649 static int dtls_bio_new(BIO *bio)
651 #ifdef HAVE_OPENSSL_BIO_METHOD 652 BIO_set_init(bio, 1);
653 BIO_set_data(bio,
NULL);
654 BIO_set_shutdown(bio, 0);
663 static int dtls_bio_free(BIO *bio)
669 #ifdef HAVE_OPENSSL_BIO_METHOD 670 BIO_set_data(bio,
NULL);
677 static int dtls_bio_write(BIO *bio,
const char *
buf,
int len)
679 #ifdef HAVE_OPENSSL_BIO_METHOD 694 if (rtp->rtcp && rtp->rtcp->dtls.write_bio == bio) {
705 bytes_sent =
__rtp_sendto(instance, (
char *)buf, len, 0, &remote_address, rtcp, &ice, 0);
708 ast_debug(0,
"(%p) DTLS - sent %s packet to %s%s (len %-6.6d)\n",
710 ice ?
" (via ICE)" :
"", bytes_sent);
716 static long dtls_bio_ctrl(BIO *bio,
int cmd,
long arg1,
void *arg2)
721 case BIO_CTRL_DGRAM_QUERY_MTU:
723 case BIO_CTRL_WPENDING:
724 case BIO_CTRL_PENDING:
733 #ifdef HAVE_PJPROJECT 752 char address[PJ_INET6_ADDRSTRLEN];
754 if (component < 1 || !ice->comp[component - 1].valid_check) {
759 pj_sockaddr_print(&ice->comp[component - 1].valid_check->rcand->addr, address,
760 sizeof(address), 0), 0);
762 pj_sockaddr_get_port(&ice->comp[component - 1].valid_check->rcand->addr));
783 int ice_attrb_reset = 0;
786 if (!
ast_strlen_zero(rtp->remote_ufrag) && strcmp(ufrag, rtp->remote_ufrag)) {
793 if (!
ast_strlen_zero(rtp->remote_passwd) && strcmp(password, rtp->remote_passwd)) {
796 ast_copy_string(rtp->remote_passwd, password,
sizeof(rtp->remote_passwd));
800 if (ice_attrb_reset) {
810 if (strcmp(candidate1->
foundation, candidate2->foundation) ||
811 candidate1->
id != candidate2->id ||
812 candidate1->
type != candidate2->type ||
827 if (strcasecmp(candidate->
transport,
"udp")) {
831 if (!rtp->ice_proposed_remote_candidates) {
834 if (!rtp->ice_proposed_remote_candidates) {
849 remote_candidate->
id = candidate->
id;
854 remote_candidate->
type = candidate->
type;
856 ast_debug_ice(2,
"(%p) ICE add remote candidate\n", instance);
858 ao2_link(rtp->ice_proposed_remote_candidates, remote_candidate);
867 pj_thread_desc *
desc;
870 if (pj_thread_is_registered() == PJ_TRUE) {
876 ast_log(
LOG_ERROR,
"Could not get thread desc from thread-local storage. Expect awful things to occur\n");
879 pj_bzero(*desc,
sizeof(*desc));
881 if (pj_thread_register(
"Asterisk Thread", *desc, &thread) != PJ_SUCCESS) {
931 *pj_role = PJ_ICE_SESS_ROLE_CONTROLLED;
934 *pj_role = PJ_ICE_SESS_ROLE_CONTROLLING;
942 case PJ_ICE_SESS_ROLE_CONTROLLED:
945 case PJ_ICE_SESS_ROLE_CONTROLLING:
948 case PJ_ICE_SESS_ROLE_UNKNOWN:
965 if (!rtp->ice->real_ice->is_nominating && !rtp->ice->real_ice->is_complete) {
966 ast_debug_ice(3,
" (%p) ICE nevermind, not ready for a reset\n", instance);
970 ast_debug_ice(3,
"(%p) ICE recreating ICE session %s (%d)\n",
972 res =
ice_create(instance, &rtp->ice_original_rtp_addr, rtp->ice_port, 1);
975 enum pj_ice_sess_role role = PJ_ICE_SESS_ROLE_UNKNOWN;
977 pj_ice_sess_change_role(rtp->ice->real_ice, role);
983 if (rtp->ice_num_components == 1 && rtp->turn_rtcp) {
985 struct timespec ts = { .tv_sec = wait.tv_sec, .tv_nsec = wait.tv_usec * 1000, };
987 rtp->turn_state = PJ_TURN_STATE_NULL;
991 pj_turn_sock_destroy(rtp->turn_rtcp);
993 while (rtp->turn_state != PJ_TURN_STATE_DESTROYING) {
998 rtp->ice_media_started = 0;
1016 if (!left_candidate) {
1034 pj_str_t ufrag = pj_str(rtp->remote_ufrag), passwd = pj_str(rtp->remote_passwd);
1035 pj_ice_sess_cand candidates[PJ_ICE_MAX_CAND];
1038 int cand_cnt = 0, has_rtp = 0, has_rtcp = 0;
1040 if (!rtp->ice || !rtp->ice_proposed_remote_candidates) {
1045 if (rtp->ice_active_remote_candidates &&
1047 ast_debug_ice(2,
"(%p) ICE proposed equals active candidates\n", instance);
1049 rtp->ice_proposed_remote_candidates =
NULL;
1057 rtp->ice_active_remote_candidates = rtp->ice_proposed_remote_candidates;
1058 rtp->ice_proposed_remote_candidates =
NULL;
1064 ast_log(
LOG_NOTICE,
"(%p) ICE failed to create replacement session\n", instance);
1079 pj_strdup2(rtp->ice->real_ice->pool, &candidates[cand_cnt].foundation,
1081 candidates[cand_cnt].comp_id = candidate->
id;
1082 candidates[cand_cnt].prio = candidate->
priority;
1091 candidates[cand_cnt].type = PJ_ICE_CAND_TYPE_HOST;
1093 candidates[cand_cnt].type = PJ_ICE_CAND_TYPE_SRFLX;
1095 candidates[cand_cnt].type = PJ_ICE_CAND_TYPE_RELAYED;
1102 pj_turn_sock_set_perm(rtp->turn_rtp, 1, &candidates[cand_cnt].addr, 1);
1108 pj_turn_sock_set_perm(rtp->turn_rtcp, 1, &candidates[cand_cnt].addr, 1);
1119 ast_log(
LOG_WARNING,
"(%p) ICE lost %d candidates. Consider increasing PJ_ICE_MAX_CAND in PJSIP\n",
1128 if (!has_rtcp && rtp->ice_num_components > 1) {
1132 if (rtp->ice && has_rtp && (has_rtcp || rtp->ice_num_components == 1)) {
1141 res = pj_ice_sess_create_check_list(ice->
real_ice, &ufrag, &passwd, cand_cnt, &candidates[0]);
1142 if (res == PJ_SUCCESS) {
1143 ast_debug_ice(2,
"(%p) ICE successfully created checklist\n", instance);
1145 pj_ice_sess_start_check(ice->
real_ice);
1155 pj_strerror(res, reason,
sizeof(reason));
1156 ast_log(
LOG_WARNING,
"(%p) ICE failed to create session check list: %s\n", instance, reason);
1165 ao2_ref(rtp->ice_active_remote_candidates, -1);
1166 rtp->ice_active_remote_candidates =
NULL;
1168 rtp->ice->real_ice->rcand_cnt = rtp->ice->real_ice->clist.count = 0;
1177 return rtp->local_ufrag;
1185 return rtp->local_passwd;
1193 if (rtp->ice_local_candidates) {
1194 ao2_ref(rtp->ice_local_candidates, +1);
1197 return rtp->ice_local_candidates;
1211 pj_ice_sess_change_role(rtp->ice->real_ice, PJ_ICE_SESS_ROLE_CONTROLLING);
1220 ast_debug_ice(3,
"(%p) ICE set role failed; no ice instance\n", instance);
1226 if (!rtp->ice->real_ice->is_nominating && !rtp->ice->real_ice->is_complete) {
1231 PJ_ICE_SESS_ROLE_CONTROLLED : PJ_ICE_SESS_ROLE_CONTROLLING);
1233 ast_debug_ice(2,
"(%p) ICE not setting role because state is %s\n",
1234 instance, rtp->ice->real_ice->is_nominating ?
"nominating" :
"complete");
1240 unsigned comp_id,
unsigned transport_id, pj_ice_cand_type
type, pj_uint16_t local_pref,
1241 const pj_sockaddr_t *addr,
const pj_sockaddr_t *base_addr,
const pj_sockaddr_t *rel_addr,
1244 pj_str_t foundation;
1247 char address[PJ_INET6_ADDRSTRLEN];
1256 pj_ice_calc_foundation(rtp->ice->real_ice->pool, &foundation, type, addr);
1258 if (!rtp->ice_local_candidates) {
1261 if (!rtp->ice_local_candidates) {
1271 candidate->
id = comp_id;
1282 if (type == PJ_ICE_CAND_TYPE_HOST) {
1284 }
else if (type == PJ_ICE_CAND_TYPE_SRFLX) {
1286 }
else if (type == PJ_ICE_CAND_TYPE_RELAYED) {
1300 status = pj_ice_sess_add_cand(ice->
real_ice, comp_id, transport_id, type, local_pref,
1301 &foundation, addr, base_addr, rel_addr, addr_len,
NULL);
1304 if (!rtp->ice || status != PJ_SUCCESS) {
1312 candidate->
priority = rtp->ice->real_ice->lcand[rtp->ice->real_ice->lcand_cnt - 1].prio;
1317 ao2_link(rtp->ice_local_candidates, candidate);
1337 if (status != PJ_SUCCESS) {
1340 pj_strerror(status, buf,
sizeof(buf));
1342 instance, (
int)status, buf);
1345 if (!rtp->rtp_passthrough) {
1348 rtp->rtp_passthrough = 0;
1351 ast_sendto(rtp->
s, pkt, pkt_len, 0, &rtp->rtp_loop);
1370 rtp->turn_state = new_state;
1373 if (new_state == PJ_TURN_STATE_DESTROYING) {
1374 pj_turn_sock_set_user_data(rtp->turn_rtp,
NULL);
1375 rtp->turn_rtp =
NULL;
1403 if (status != PJ_SUCCESS) {
1406 pj_strerror(status, buf,
sizeof(buf));
1411 if (!rtp->rtcp_passthrough) {
1414 rtp->rtcp_passthrough = 0;
1417 ast_sendto(rtp->rtcp->
s, pkt, pkt_len, 0, &rtp->rtcp_loop);
1436 rtp->turn_state = new_state;
1439 if (new_state == PJ_TURN_STATE_DESTROYING) {
1440 pj_turn_sock_set_user_data(rtp->turn_rtcp,
NULL);
1441 rtp->turn_rtcp =
NULL;
1459 const pj_time_val delay = {0, 10};
1461 pj_ioqueue_poll(ioqueue->
ioqueue, &delay);
1474 pj_thread_join(ioqueue->
thread);
1475 pj_thread_destroy(ioqueue->
thread);
1478 if (ioqueue->
pool) {
1482 pj_pool_t *temp_pool = ioqueue->
pool;
1485 pj_pool_release(temp_pool);
1498 if ((ioqueue->
count - 2) == 0) {
1521 if ((ioqueue->
count + 2) < PJ_IOQUEUE_MAX_HANDLES) {
1528 ioqueue->
count += 2;
1542 if (pj_timer_heap_create(ioqueue->
pool, 4, &ioqueue->
timerheap) != PJ_SUCCESS) {
1546 if (pj_lock_create_recursive_mutex(ioqueue->
pool,
"rtp%p", &lock) != PJ_SUCCESS) {
1550 pj_timer_heap_set_lock(ioqueue->
timerheap, lock, PJ_TRUE);
1552 if (pj_ioqueue_create(ioqueue->
pool, PJ_IOQUEUE_MAX_HANDLES, &ioqueue->
ioqueue) != PJ_SUCCESS) {
1578 enum ast_transport transport,
const char *server,
unsigned int port,
const char *username,
const char *
password)
1581 pj_turn_sock **turn_sock;
1582 const pj_turn_sock_cb *turn_cb;
1583 pj_turn_tp_type conn_type;
1585 pj_stun_auth_cred cred = { 0, };
1588 pj_stun_config stun_config;
1590 struct timespec ts = { .tv_sec = wait.tv_sec, .tv_nsec = wait.tv_usec * 1000, };
1591 pj_turn_session_info
info;
1594 pj_turn_sock_cfg turn_sock_cfg;
1606 turn_sock = &rtp->turn_rtp;
1611 turn_sock = &rtp->turn_rtcp;
1620 conn_type = PJ_TURN_TP_UDP;
1622 conn_type = PJ_TURN_TP_TCP;
1631 rtp->turn_state = PJ_TURN_STATE_NULL;
1635 pj_turn_sock_destroy(*turn_sock);
1637 while (rtp->turn_state != PJ_TURN_STATE_DESTROYING) {
1651 if (!rtp->ioqueue) {
1656 pj_stun_config_init(&stun_config, &
cachingpool.factory, 0, rtp->ioqueue->ioqueue, rtp->ioqueue->timerheap);
1658 stun_config.software_name = pj_str(
NULL);
1662 pj_turn_sock_cfg_default(&turn_sock_cfg);
1665 turn_sock_cfg.grp_lock = ice->
real_ice->grp_lock;
1671 status = pj_turn_sock_create(&stun_config,
1673 turn_cb, &turn_sock_cfg, instance, turn_sock);
1675 if (status != PJ_SUCCESS) {
1681 cred.type = PJ_STUN_AUTH_CRED_STATIC;
1682 pj_strset2(&cred.data.static_cred.username, (
char*)username);
1683 cred.data.static_cred.data_type = PJ_STUN_PASSWD_PLAIN;
1684 pj_strset2(&cred.data.static_cred.data, (
char*)password);
1686 pj_turn_sock_alloc(*turn_sock, pj_cstr(&turn_addr, server), port,
NULL, &cred,
NULL);
1688 ast_debug_ice(2,
"(%p) ICE request TURN %s %s candidate\n", instance,
1698 while (rtp->turn_state < PJ_TURN_STATE_READY) {
1703 if (rtp->turn_state != PJ_TURN_STATE_READY) {
1707 pj_turn_sock_get_info(*turn_sock, &info);
1710 PJ_ICE_CAND_TYPE_RELAYED, 65535, &info.relay_addr, &info.relay_addr,
1711 &info.mapped_addr, pj_sockaddr_get_len(&info.relay_addr));
1725 for (x=0; x<4; x++) {
1728 snprintf(buf, size,
"%08lx%08lx%08lx%08lx", (
long unsigned)val[0], (
long unsigned)val[1], (
long unsigned)val[2], (
long unsigned)val[3]);
1741 if (!
icesupport || !rtp->ice || rtp->ice_num_components == num_components) {
1745 ast_debug_ice(2,
"(%p) ICE change number of components %u -> %u\n", instance,
1746 rtp->ice_num_components, num_components);
1748 rtp->ice_num_components = num_components;
1768 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 1769 static int dtls_verify_callback(
int preverify_ok, X509_STORE_CTX *ctx)
1775 static int dtls_details_initialize(
struct dtls_details *dtls,
SSL_CTX *ssl_ctx,
1778 dtls->dtls_setup = setup;
1780 if (!(dtls->ssl = SSL_new(ssl_ctx))) {
1785 if (!(dtls->read_bio = BIO_new(BIO_s_mem()))) {
1789 BIO_set_mem_eof_return(dtls->read_bio, -1);
1791 #ifdef HAVE_OPENSSL_BIO_METHOD 1792 if (!(dtls->write_bio = BIO_new(dtls_bio_methods))) {
1793 ast_log(
LOG_ERROR,
"Failed to allocate memory for outbound SSL traffic\n");
1797 BIO_set_data(dtls->write_bio, instance);
1799 if (!(dtls->write_bio = BIO_new(&dtls_bio_methods))) {
1800 ast_log(
LOG_ERROR,
"Failed to allocate memory for outbound SSL traffic\n");
1803 dtls->write_bio->ptr = instance;
1805 SSL_set_bio(dtls->ssl, dtls->read_bio, dtls->write_bio);
1808 SSL_set_accept_state(dtls->ssl);
1810 SSL_set_connect_state(dtls->ssl);
1817 if (dtls->read_bio) {
1818 BIO_free(dtls->read_bio);
1819 dtls->read_bio =
NULL;
1822 if (dtls->write_bio) {
1823 BIO_free(dtls->write_bio);
1824 dtls->write_bio =
NULL;
1828 SSL_free(dtls->ssl);
1838 if (!rtp->ssl_ctx || !rtp->rtcp) {
1843 return dtls_details_initialize(&rtp->rtcp->dtls, rtp->ssl_ctx, rtp->dtls.dtls_setup, instance);
1846 static const SSL_METHOD *get_dtls_method(
void)
1848 #if OPENSSL_VERSION_NUMBER < 0x10002000L || defined(LIBRESSL_VERSION_NUMBER) 1849 return DTLSv1_method();
1851 return DTLS_method();
1855 struct dtls_cert_info {
1856 EVP_PKEY *private_key;
1862 #if !defined(OPENSSL_NO_ECDH) && (OPENSSL_VERSION_NUMBER >= 0x10000000L) && (OPENSSL_VERSION_NUMBER < 0x10100000L) 1866 #ifndef OPENSSL_NO_DH 1868 BIO *bio = BIO_new_file(dtls_cfg->
pvtfile,
"r");
1872 if (SSL_CTX_set_tmp_dh(rtp->ssl_ctx, dh)) {
1873 long options = SSL_OP_CIPHER_SERVER_PREFERENCE |
1874 SSL_OP_SINGLE_DH_USE | SSL_OP_SINGLE_ECDH_USE;
1875 options = SSL_CTX_set_options(rtp->ssl_ctx, options);
1876 ast_verb(2,
"DTLS DH initialized, PFS enabled\n");
1885 #if !defined(OPENSSL_NO_ECDH) && (OPENSSL_VERSION_NUMBER >= 0x10000000L) && (OPENSSL_VERSION_NUMBER < 0x10100000L) 1887 ecdh = EC_KEY_new_by_curve_name(NID_X9_62_prime256v1);
1889 if (SSL_CTX_set_tmp_ecdh(rtp->ssl_ctx, ecdh)) {
1890 #ifndef SSL_CTRL_SET_ECDH_AUTO 1891 #define SSL_CTRL_SET_ECDH_AUTO 94 1895 ast_verb(2,
"DTLS ECDH initialized (automatic), faster PFS enabled\n");
1897 ast_verb(2,
"DTLS ECDH initialized (secp256r1), faster PFS enabled\n");
1905 #if !defined(OPENSSL_NO_ECDH) && (OPENSSL_VERSION_NUMBER >= 0x10000000L) 1907 static int create_ephemeral_ec_keypair(EVP_PKEY **keypair)
1909 EC_KEY *eckey =
NULL;
1912 group = EC_GROUP_new_by_curve_name(NID_X9_62_prime256v1);
1917 EC_GROUP_set_asn1_flag(group, OPENSSL_EC_NAMED_CURVE);
1918 EC_GROUP_set_point_conversion_form(group, POINT_CONVERSION_UNCOMPRESSED);
1920 eckey = EC_KEY_new();
1925 if (!EC_KEY_set_group(eckey, group)) {
1929 if (!EC_KEY_generate_key(eckey)) {
1933 *keypair = EVP_PKEY_new();
1938 EVP_PKEY_assign_EC_KEY(*keypair, eckey);
1939 EC_GROUP_free(group);
1945 EC_GROUP_free(group);
1951 #define SERIAL_RAND_BITS 159 1953 static int create_ephemeral_certificate(EVP_PKEY *keypair, X509 **certificate)
1956 BIGNUM *serial =
NULL;
1964 if (!X509_set_version(cert, 2)) {
1969 X509_set_pubkey(cert, keypair);
1972 if (!(serial = BN_new())
1973 || !BN_rand(serial, SERIAL_RAND_BITS, -1, 0)
1974 || !BN_to_ASN1_INTEGER(serial, X509_get_serialNumber(cert))) {
1982 #if OPENSSL_VERSION_NUMBER < 0x10100000L 1983 if (!X509_time_adj_ex(X509_get_notBefore(cert), -1, 0,
NULL)
1984 || !X509_time_adj_ex(X509_get_notAfter(cert), 30, 0,
NULL)) {
1988 if (!X509_time_adj_ex(X509_getm_notBefore(cert), -1, 0,
NULL)
1989 || !X509_time_adj_ex(X509_getm_notAfter(cert), 30, 0,
NULL)) {
1995 if (!(name = X509_get_subject_name(cert))
1996 || !X509_NAME_add_entry_by_NID(name, NID_commonName, MBSTRING_ASC,
1997 (
unsigned char *)
"asterisk", -1, -1, 0)
1998 || !X509_set_issuer_name(cert, name)) {
2003 if (!X509_sign(cert, keypair, EVP_sha256())) {
2007 *certificate = cert;
2020 struct dtls_cert_info *cert_info)
2023 cert_info->private_key =
NULL;
2024 cert_info->certificate =
NULL;
2026 if (create_ephemeral_ec_keypair(&cert_info->private_key)) {
2031 if (create_ephemeral_certificate(cert_info->private_key, &cert_info->certificate)) {
2039 X509_free(cert_info->certificate);
2040 EVP_PKEY_free(cert_info->private_key);
2049 struct dtls_cert_info *cert_info)
2051 ast_log(
LOG_ERROR,
"Your version of OpenSSL does not support ECDSA keys\n");
2059 struct dtls_cert_info *cert_info)
2062 BIO *certbio =
NULL;
2063 EVP_PKEY *private_key =
NULL;
2067 fp = fopen(private_key_file,
"r");
2069 ast_log(
LOG_ERROR,
"Failed to read private key from file '%s': %s\n", private_key_file, strerror(
errno));
2073 if (!PEM_read_PrivateKey(fp, &private_key,
NULL,
NULL)) {
2074 ast_log(
LOG_ERROR,
"Failed to read private key from PEM file '%s'\n", private_key_file);
2080 ast_log(
LOG_ERROR,
"Failed to close private key file '%s': %s\n", private_key_file, strerror(
errno));
2084 certbio = BIO_new(BIO_s_file());
2086 ast_log(
LOG_ERROR,
"Failed to allocate memory for certificate fingerprinting on RTP instance '%p'\n",
2091 if (!BIO_read_filename(certbio, dtls_cfg->
certfile)
2092 || !(cert = PEM_read_bio_X509(certbio,
NULL, 0,
NULL))) {
2097 cert_info->private_key = private_key;
2098 cert_info->certificate = cert;
2100 BIO_free_all(certbio);
2106 BIO_free_all(certbio);
2107 EVP_PKEY_free(private_key);
2114 struct dtls_cert_info *cert_info)
2117 return create_certificate_ephemeral(instance, dtls_cfg, cert_info);
2119 return create_certificate_from_file(instance, dtls_cfg, cert_info);
2129 struct dtls_cert_info cert_info = { 0 };
2139 ast_log(
LOG_ERROR,
"SRTP support module is not loaded or available. Try loading res_srtp.so.\n");
2147 rtp->ssl_ctx = SSL_CTX_new(get_dtls_method());
2148 if (!rtp->ssl_ctx) {
2152 SSL_CTX_set_read_ahead(rtp->ssl_ctx, 1);
2154 configure_dhparams(rtp, dtls_cfg);
2156 rtp->dtls_verify = dtls_cfg->
verify;
2160 dtls_verify_callback :
NULL);
2163 SSL_CTX_set_tlsext_use_srtp(rtp->ssl_ctx,
"SRTP_AES128_CM_SHA1_80");
2165 SSL_CTX_set_tlsext_use_srtp(rtp->ssl_ctx,
"SRTP_AES128_CM_SHA1_32");
2167 ast_log(
LOG_ERROR,
"Unsupported suite specified for DTLS-SRTP on RTP instance '%p'\n", instance);
2171 rtp->local_hash = dtls_cfg->
hash;
2173 if (!load_dtls_certificate(instance, dtls_cfg, &cert_info)) {
2175 unsigned int size, i;
2176 unsigned char fingerprint[EVP_MAX_MD_SIZE];
2177 char *local_fingerprint = rtp->local_fingerprint;
2179 if (!SSL_CTX_use_certificate(rtp->ssl_ctx, cert_info.certificate)) {
2180 ast_log(
LOG_ERROR,
"Specified certificate for RTP instance '%p' could not be used\n",
2185 if (!SSL_CTX_use_PrivateKey(rtp->ssl_ctx, cert_info.private_key)
2186 || !SSL_CTX_check_private_key(rtp->ssl_ctx)) {
2187 ast_log(
LOG_ERROR,
"Specified private key for RTP instance '%p' could not be used\n",
2195 type = EVP_sha256();
2197 ast_log(
LOG_ERROR,
"Unsupported fingerprint hash type on RTP instance '%p'\n",
2202 if (!X509_digest(cert_info.certificate, type, fingerprint, &size) || !size) {
2203 ast_log(
LOG_ERROR,
"Could not produce fingerprint from certificate for RTP instance '%p'\n",
2208 for (i = 0; i < size; i++) {
2209 sprintf(local_fingerprint,
"%02hhX:", fingerprint[i]);
2210 local_fingerprint += 3;
2213 *(local_fingerprint - 1) = 0;
2215 EVP_PKEY_free(cert_info.private_key);
2216 X509_free(cert_info.certificate);
2220 if (!SSL_CTX_set_cipher_list(rtp->ssl_ctx, dtls_cfg->
cipher)) {
2221 ast_log(
LOG_ERROR,
"Invalid cipher specified in cipher list '%s' for RTP instance '%p'\n",
2222 dtls_cfg->
cipher, instance);
2228 if (!SSL_CTX_load_verify_locations(rtp->ssl_ctx,
S_OR(dtls_cfg->
cafile, NULL),
S_OR(dtls_cfg->
capath, NULL))) {
2229 ast_log(
LOG_ERROR,
"Invalid certificate authority file '%s' or path '%s' specified for RTP instance '%p'\n",
2235 rtp->rekey = dtls_cfg->
rekey;
2236 rtp->suite = dtls_cfg->
suite;
2238 res = dtls_details_initialize(&rtp->dtls, rtp->ssl_ctx, dtls_cfg->
default_setup, instance);
2240 dtls_setup_rtcp(instance);
2251 return !rtp->ssl_ctx ? 0 : 1;
2258 SSL *ssl = rtp->dtls.ssl;
2262 dtls_srtp_stop_timeout_timer(instance, rtp, 0);
2266 SSL_CTX_free(rtp->ssl_ctx);
2267 rtp->ssl_ctx =
NULL;
2270 if (rtp->dtls.ssl) {
2271 SSL_free(rtp->dtls.ssl);
2272 rtp->dtls.ssl =
NULL;
2277 dtls_srtp_stop_timeout_timer(instance, rtp, 1);
2280 if (rtp->rtcp->dtls.ssl) {
2281 if (rtp->rtcp->dtls.ssl != ssl) {
2282 SSL_free(rtp->rtcp->dtls.ssl);
2284 rtp->rtcp->dtls.ssl =
NULL;
2294 if (SSL_is_init_finished(rtp->dtls.ssl)) {
2295 SSL_shutdown(rtp->dtls.ssl);
2299 if (rtp->rtcp && SSL_is_init_finished(rtp->rtcp->dtls.ssl)) {
2300 SSL_shutdown(rtp->rtcp->dtls.ssl);
2310 return rtp->dtls.connection;
2318 return rtp->dtls.dtls_setup;
2347 if (old == *dtls_setup) {
2357 SSL_set_connect_state(ssl);
2359 SSL_set_accept_state(ssl);
2370 if (rtp->dtls.ssl) {
2371 dtls_set_setup(&rtp->dtls.dtls_setup, setup, rtp->dtls.ssl);
2374 if (rtp->rtcp && rtp->rtcp->dtls.ssl) {
2375 dtls_set_setup(&rtp->rtcp->dtls.dtls_setup, setup, rtp->rtcp->dtls.ssl);
2390 rtp->remote_hash = hash;
2392 while ((
value =
strsep(&tmp,
":")) && (pos != (EVP_MAX_MD_SIZE - 1))) {
2393 sscanf(
value,
"%02hhx", &rtp->remote_fingerprint[pos++]);
2402 return rtp->local_hash;
2406 static const char *ast_rtp_dtls_get_fingerprint(
struct ast_rtp_instance *instance)
2410 return rtp->local_fingerprint;
2416 .active = ast_rtp_dtls_active,
2417 .stop = ast_rtp_dtls_stop,
2418 .reset = ast_rtp_dtls_reset,
2419 .get_connection = ast_rtp_dtls_get_connection,
2420 .get_setup = ast_rtp_dtls_get_setup,
2421 .set_setup = ast_rtp_dtls_set_setup,
2422 .set_fingerprint = ast_rtp_dtls_set_fingerprint,
2423 .get_fingerprint_hash = ast_rtp_dtls_get_fingerprint_hash,
2424 .get_fingerprint = ast_rtp_dtls_get_fingerprint,
2429 #ifdef TEST_FRAMEWORK 2434 if (rtp && rtp->recv_buffer) {
2445 if (rtp && rtp->recv_buffer) {
2456 if (rtp && rtp->send_buffer) {
2467 if (rtp && rtp->rtcp) {
2468 rtp->rtcp->schedid =
id;
2509 #ifdef HAVE_PJPROJECT 2512 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 2513 .dtls = &ast_rtp_dtls,
2514 .activate = ast_rtp_activate,
2522 #ifdef TEST_FRAMEWORK 2527 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 2529 static void dtls_perform_handshake(
struct ast_rtp_instance *instance,
struct dtls_details *dtls,
int rtcp)
2533 ast_debug_dtls(3,
"(%p) DTLS perform handshake - ssl = %p, setup = %d\n",
2534 rtp, dtls->ssl, dtls->dtls_setup);
2544 SSL_do_handshake(dtls->ssl);
2554 dtls_srtp_start_timeout_timer(instance, rtp, rtcp);
2558 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 2559 static void dtls_perform_setup(
struct dtls_details *dtls)
2561 if (!dtls->ssl || !SSL_is_init_finished(dtls->ssl)) {
2565 SSL_clear(dtls->ssl);
2567 SSL_set_accept_state(dtls->ssl);
2569 SSL_set_connect_state(dtls->ssl);
2577 #ifdef HAVE_PJPROJECT 2588 if (status == PJ_SUCCESS) {
2605 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 2607 if (rtp->ice_media_started) {
2613 "(%p) ICE starting media - perform DTLS - (%p)\n", instance, rtp);
2627 dtls_perform_handshake(instance, &rtp->dtls, 0);
2630 dtls_perform_handshake(instance, &rtp->rtcp->dtls, 1);
2634 rtp->ice_media_started = 1;
2641 ast_verb(4,
"%p -- Strict RTP learning after ICE completion\n", rtp);
2646 #ifdef HAVE_PJPROJECT_ON_VALID_ICE_PAIR_CALLBACK 2650 ast_debug_ice(2,
"(%p) ICE valid pair, start media\n", ice->user_data);
2658 ast_debug_ice(2,
"(%p) ICE complete, start media\n", ice->user_data);
2663 static void ast_rtp_on_ice_rx_data(pj_ice_sess *ice,
unsigned comp_id,
unsigned transport_id,
void *pkt, pj_size_t size,
const pj_sockaddr_t *src_addr,
unsigned src_addr_len)
2671 rtp->passthrough = 1;
2673 rtp->rtp_passthrough = 1;
2675 rtp->rtcp_passthrough = 1;
2680 static pj_status_t
ast_rtp_on_ice_tx_pkt(pj_ice_sess *ice,
unsigned comp_id,
unsigned transport_id,
const void *pkt, pj_size_t size,
const pj_sockaddr_t *dst_addr,
unsigned dst_addr_len)
2684 pj_status_t
status = PJ_EINVALIDOP;
2685 pj_ssize_t _size = (pj_ssize_t)size;
2689 status = pj_sock_sendto(rtp->
s, pkt, &_size, 0, dst_addr, dst_addr_len);
2691 ast_assert(_size == size || status != PJ_SUCCESS);
2695 status = pj_sock_sendto(rtp->rtcp->
s, pkt, &_size, 0, dst_addr, dst_addr_len);
2697 ast_assert(_size == size || status != PJ_SUCCESS);
2699 status = PJ_SUCCESS;
2703 if (rtp->turn_rtp) {
2704 status = pj_turn_sock_sendto(rtp->turn_rtp, pkt, size, dst_addr, dst_addr_len);
2708 if (rtp->turn_rtcp) {
2709 status = pj_turn_sock_sendto(rtp->turn_rtcp, pkt, size, dst_addr, dst_addr_len);
2718 #ifdef HAVE_PJPROJECT_ON_VALID_ICE_PAIR_CALLBACK 2731 if (pj_ioqueue_create(
pool, 1, &ioqueue) != PJ_SUCCESS) {
2736 const pj_time_val delay = {0, 10};
2739 pj_ioqueue_poll(ioqueue, &delay);
2778 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 2780 static int dtls_srtp_handle_timeout(
struct ast_rtp_instance *instance,
int rtcp)
2783 struct dtls_details *dtls = !rtcp ? &rtp->dtls : &rtp->rtcp->dtls;
2784 struct timeval dtls_timeout;
2786 ast_debug_dtls(3,
"(%p) DTLS srtp - handle timeout - rtcp=%d\n", instance, rtcp);
2787 DTLSv1_handle_timeout(dtls->ssl);
2790 if (!DTLSv1_get_timeout(dtls->ssl, &dtls_timeout)) {
2791 dtls->timeout_timer = -1;
2795 return dtls_timeout.tv_sec * 1000 + dtls_timeout.tv_usec / 1000;
2799 static int dtls_srtp_handle_rtp_timeout(
const void *data)
2805 reschedule = dtls_srtp_handle_timeout(instance, 0);
2815 static int dtls_srtp_handle_rtcp_timeout(
const void *data)
2821 reschedule = dtls_srtp_handle_timeout(instance, 1);
2832 struct dtls_details *dtls = !rtcp ? &rtp->dtls : &rtp->rtcp->dtls;
2833 struct timeval dtls_timeout;
2835 if (DTLSv1_get_timeout(dtls->ssl, &dtls_timeout)) {
2836 int timeout = dtls_timeout.tv_sec * 1000 + dtls_timeout.tv_usec / 1000;
2841 if ((dtls->timeout_timer =
ast_sched_add(rtp->sched, timeout,
2842 !rtcp ? dtls_srtp_handle_rtp_timeout : dtls_srtp_handle_rtcp_timeout, instance)) < 0) {
2844 ast_log(
LOG_WARNING,
"Scheduling '%s' DTLS retransmission for RTP instance [%p] failed.\n",
2845 !rtcp ?
"RTP" :
"RTCP", instance);
2847 ast_debug_dtls(3,
"(%p) DTLS srtp - scheduled timeout timer for '%d'\n", instance, timeout);
2855 struct dtls_details *dtls = !rtcp ? &rtp->dtls : &rtp->rtcp->dtls;
2858 ast_debug_dtls(3,
"(%p) DTLS srtp - stopped timeout timer'\n", instance);
2862 static int dtls_srtp_renegotiate(
const void *data)
2870 SSL_renegotiate(rtp->dtls.ssl);
2871 SSL_do_handshake(rtp->dtls.ssl);
2873 if (rtp->rtcp && rtp->rtcp->dtls.ssl && rtp->rtcp->dtls.ssl != rtp->dtls.ssl) {
2874 SSL_renegotiate(rtp->rtcp->dtls.ssl);
2875 SSL_do_handshake(rtp->rtcp->dtls.ssl);
2886 static int dtls_srtp_add_local_ssrc(
struct ast_rtp *rtp,
struct ast_rtp_instance *instance,
int rtcp,
unsigned int ssrc,
int set_remote_policy)
2889 unsigned char *local_key, *local_salt, *remote_key, *remote_salt;
2892 struct dtls_details *dtls = !rtcp ? &rtp->dtls : &rtp->rtcp->dtls;
2894 ast_debug_dtls(3,
"(%p) DTLS srtp - add local ssrc - rtcp=%d, set_remote_policy=%d'\n",
2895 instance, rtcp, set_remote_policy);
2898 if (!SSL_export_keying_material(dtls->ssl, material,
SRTP_MASTER_LEN * 2,
"EXTRACTOR-dtls_srtp", 19,
NULL, 0, 0)) {
2899 ast_log(
LOG_WARNING,
"Unable to extract SRTP keying material from DTLS-SRTP negotiation on RTP instance '%p'\n",
2906 local_key = material;
2911 remote_key = material;
2917 if (!(local_policy = res_srtp_policy->
alloc())) {
2922 ast_log(
LOG_WARNING,
"Could not set key/salt information on local policy of '%p' when setting up DTLS-SRTP\n", rtp);
2926 if (res_srtp_policy->
set_suite(local_policy, rtp->suite)) {
2927 ast_log(
LOG_WARNING,
"Could not set suite to '%u' on local policy of '%p' when setting up DTLS-SRTP\n", rtp->suite, rtp);
2931 res_srtp_policy->
set_ssrc(local_policy, ssrc, 0);
2933 if (set_remote_policy) {
2934 if (!(remote_policy = res_srtp_policy->
alloc())) {
2939 ast_log(
LOG_WARNING,
"Could not set key/salt information on remote policy of '%p' when setting up DTLS-SRTP\n", rtp);
2943 if (res_srtp_policy->
set_suite(remote_policy, rtp->suite)) {
2944 ast_log(
LOG_WARNING,
"Could not set suite to '%u' on remote policy of '%p' when setting up DTLS-SRTP\n", rtp->suite, rtp);
2948 res_srtp_policy->
set_ssrc(remote_policy, 0, 1);
2952 ast_log(
LOG_WARNING,
"Could not set policies when setting up DTLS-SRTP on '%p'\n", rtp);
2960 res_srtp_policy->
destroy(local_policy);
2962 if (remote_policy) {
2963 res_srtp_policy->
destroy(remote_policy);
2971 struct dtls_details *dtls = !rtcp ? &rtp->dtls : &rtp->rtcp->dtls;
2974 ast_debug_dtls(3,
"(%p) DTLS setup SRTP rtp=%p'\n", instance, rtp);
2980 if (!(certificate = SSL_get_peer_certificate(dtls->ssl))) {
2981 ast_log(
LOG_WARNING,
"No certificate was provided by the peer on RTP instance '%p'\n", instance);
2986 if (rtp->remote_fingerprint[0]) {
2988 unsigned char fingerprint[EVP_MAX_MD_SIZE];
2994 type = EVP_sha256();
2996 ast_log(
LOG_WARNING,
"Unsupported fingerprint hash type on RTP instance '%p'\n", instance);
3000 if (!X509_digest(certificate, type, fingerprint, &size) ||
3002 memcmp(fingerprint, rtp->remote_fingerprint, size)) {
3003 X509_free(certificate);
3004 ast_log(
LOG_WARNING,
"Fingerprint provided by remote party does not match that of peer certificate on RTP instance '%p'\n",
3010 X509_free(certificate);
3018 for (index = 0; index <
AST_VECTOR_SIZE(&rtp->ssrc_mapping); ++index) {
3028 if ((rtp->rekeyid =
ast_sched_add(rtp->sched, rtp->rekey * 1000, dtls_srtp_renegotiate, instance)) < 0) {
3041 return elem -
value;
3047 return elem ==
value;
3060 version = (packet[0] & 0XC0) >> 6;
3075 m = packet[1] & 0x80;
3076 pt = packet[1] & 0x7F;
3077 if (m && pt >= 64 && pt <= 95) {
3088 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 3091 #ifdef HAVE_PJPROJECT 3092 struct ast_sockaddr *loop = rtcp ? &rtp->rtcp_loop : &rtp->rtp_loop;
3094 #ifdef TEST_FRAMEWORK 3098 if ((len =
ast_recvfrom(rtcp ? rtp->rtcp->
s : rtp->
s, buf, size, flags, sa)) < 0) {
3102 #ifdef TEST_FRAMEWORK 3109 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 3112 if ((*in >= 20) && (*in <= 63)) {
3113 struct dtls_details *dtls = !rtcp ? &rtp->dtls : &rtp->rtcp->dtls;
3118 ast_log(
LOG_ERROR,
"Received SSL traffic on RTP instance '%p' without an SSL session\n",
3123 ast_debug_dtls(3,
"(%p) DTLS - __rtp_recvfrom rtp=%p - Got SSL packet '%d'\n", instance, rtp, *in);
3135 dtls_srtp_stop_timeout_timer(instance, rtp, rtcp);
3141 SSL_set_accept_state(dtls->ssl);
3144 BIO_write(dtls->read_bio, buf, len);
3146 len = SSL_read(dtls->ssl, buf, len);
3148 if ((len < 0) && (SSL_get_error(dtls->ssl, len) == SSL_ERROR_SSL)) {
3149 unsigned long error = ERR_get_error();
3150 ast_log(
LOG_ERROR,
"DTLS failure occurred on RTP instance '%p' due to reason '%s', terminating\n",
3151 instance, ERR_reason_error_string(error));
3155 if (SSL_is_init_finished(dtls->ssl)) {
3159 if ((res = dtls_srtp_setup(rtp, instance, rtcp))) {
3165 ast_debug_dtls(3,
"(%p) DTLS - __rtp_recvfrom rtp=%p - established'\n", instance, rtp);
3168 dtls_srtp_start_timeout_timer(instance, rtp, rtcp);
3175 #ifdef HAVE_PJPROJECT 3185 }
else if (rtp->ice) {
3193 pj_sockaddr_parse(pj_AF_UNSPEC(), 0, &combined, &address);
3199 status = pj_ice_sess_on_rx_pkt(ice->
real_ice,
3202 pj_sockaddr_get_len(&address));
3205 if (status != PJ_SUCCESS) {
3208 pj_strerror(status, err_buf,
sizeof(err_buf));
3210 (
int)status, err_buf);
3213 if (!rtp->passthrough) {
3218 if (!rtp->ice_active_remote_candidates && !rtp->ice_proposed_remote_candidates) {
3227 rtp->passthrough = 0;
3252 struct ast_rtp_instance *transport = rtp->bundled ? rtp->bundled : instance;
3259 if (use_srtp && res_srtp && srtp && res_srtp->
protect(srtp, &temp, &len, rtcp) < 0) {
3263 #ifdef HAVE_PJPROJECT 3264 if (transport_rtp->ice) {
3270 if (rtcp && rtp->rtcp->
s == rtp->
s) {
3277 ice = transport_rtp->ice;
3279 if (instance == transport) {
3282 status = pj_ice_sess_send_data(ice->
real_ice, component, temp, len);
3284 if (instance == transport) {
3287 if (status == PJ_SUCCESS) {
3294 res =
ast_sendto(rtcp ? transport_rtp->rtcp->
s : transport_rtp->
s, temp, len, flags, sa);
3305 return __rtp_sendto(instance, buf, size, flags, sa, 1, ice, 1);
3315 if ((res =
__rtp_sendto(instance, buf, size, flags, sa, 0, ice, 1)) > 0) {
3317 rtp->txoctetcount += (res - hdrlen);
3325 unsigned int interval;
3338 double last_sum_of_squares = (*std_dev) * (*std_dev) * (*count ?: 1);
3340 if (++(*count) == 0) {
3352 delta1 = new_sample - *mean;
3353 *mean += (delta1 / *
count);
3354 delta2 = new_sample - *mean;
3357 *std_dev = sqrt((last_sum_of_squares + (delta1 * delta2)) / *count);
3371 setsockopt(sock, SOL_SOCKET, SO_NO_CHECK, &nochecksums,
sizeof(nochecksums));
3405 if (seq == (uint16_t) (info->
max_seq + 1)) {
3456 memset(&rtp->rtp_source_learn.proposed_address, 0,
3457 sizeof(rtp->rtp_source_learn.proposed_address));
3458 rtp->rtp_source_learn.start =
ast_tvnow();
3462 #ifdef HAVE_PJPROJECT 3525 unsigned int count = 0;
3526 struct ifaddrs *ifa, *ia;
3530 int af_inet_ok = 0, af_inet6_ok = 0;
3535 af_inet_ok = af_inet6_ok = 1;
3540 if (getifaddrs(&ifa) < 0) {
3542 ast_log(
LOG_ERROR,
"(%p) ICE Error obtaining list of local addresses: %s\n",
3543 instance, strerror(
errno));
3545 ast_debug_ice(2,
"(%p) ICE add system candidates\n", instance);
3549 for (ia = ifa; ia && count < PJ_ICE_MAX_CAND; ia = ia->ifa_next) {
3552 if (!ia->ifa_addr || (ia->ifa_flags & IFF_UP) == 0) {
3557 if (ia->ifa_addr->sa_family != AF_INET && ia->ifa_addr->sa_family != AF_INET6) {
3563 if (ia->ifa_addr->sa_family == AF_INET) {
3564 const struct sockaddr_in *sa_in = (
struct sockaddr_in*)ia->ifa_addr;
3572 if ((sa_in->sin_addr.s_addr & htonl(0xFF000000)) == htonl(0x7F000000)) {
3577 if ((sa_in->sin_addr.s_addr & htonl(0xFF000000)) == 0) {
3602 pj_sockaddr_set_port(&pjtmp, port);
3604 PJ_ICE_CAND_TYPE_HOST, 65535, &pjtmp, &pjtmp,
NULL,
3605 pj_sockaddr_get_len(&pjtmp));
3631 pj_sockaddr_set_port(&pjtmp, port);
3633 PJ_ICE_CAND_TYPE_HOST, 65535, &pjtmp, &pjtmp,
NULL,
3634 pj_sockaddr_get_len(&pjtmp));
3643 count < PJ_ICE_MAX_CAND) {
3644 struct sockaddr_in answer;
3648 "(%p) ICE request STUN %s %s candidate\n", instance,
3662 pj_sockaddr
ext, base;
3664 int srflx = 1, baseset = 0;
3667 pj_sockaddr_init(pj_AF_INET(), &ext, &mapped, ntohs(answer.sin_port));
3681 if (!pj_sockaddr_cmp(&candidate->
address, &ext)) {
3689 if (srflx && baseset) {
3690 pj_sockaddr_set_port(&base, port);
3692 PJ_ICE_CAND_TYPE_SRFLX, 65535, &ext, &base, &base,
3693 pj_sockaddr_get_len(&ext));
3723 rtp->txcore.tv_usec -= rtp->txcore.tv_usec % 20000;
3732 return (
unsigned int) ms;
3735 #ifdef HAVE_PJPROJECT 3751 int port,
int replace)
3753 pj_stun_config stun_config;
3754 pj_str_t ufrag, passwd;
3762 rtp->ice_local_candidates =
NULL;
3764 ast_debug_ice(2,
"(%p) ICE create%s\n", instance, replace ?
" and replace" :
"");
3776 stun_config.software_name = pj_str(
NULL);
3779 ufrag = pj_str(rtp->local_ufrag);
3780 passwd = pj_str(rtp->local_passwd);
3785 status = pj_ice_sess_create(&stun_config,
NULL, PJ_ICE_SESS_ROLE_UNKNOWN,
3786 rtp->ice_num_components, &ast_rtp_ice_sess_cb, &ufrag, &passwd,
NULL, &real_ice);
3788 if (status == PJ_SUCCESS) {
3790 real_ice->user_data = instance;
3807 if (replace && rtp->rtcp && rtp->ice_num_components > 1) {
3839 ast_log(
LOG_WARNING,
"Failed to create a new socket for RTP instance '%p'\n", instance);
3851 if (!
ast_bind(rtp->
s, &rtp->bind_address)) {
3852 ast_debug_rtp(1,
"(%p) RTP allocated port %d\n", instance, x);
3864 if (x == startplace || (
errno != EADDRINUSE &&
errno != EACCES)) {
3865 ast_log(
LOG_ERROR,
"Oh dear... we couldn't allocate a port for RTP instance '%p'\n", instance);
3872 #ifdef HAVE_PJPROJECT 3881 rtp->ice_num_components = 2;
3882 ast_debug_ice(2,
"(%p) ICE creating session %s (%d)\n", instance,
3884 if (
ice_create(instance, &rtp->bind_address, x, 0)) {
3893 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 3895 rtp->dtls.timeout_timer = -1;
3903 int saved_rtp_s = rtp->
s;
3904 #ifdef HAVE_PJPROJECT 3906 struct timespec ts = { .tv_sec = wait.tv_sec, .tv_nsec = wait.tv_usec * 1000, };
3909 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 3910 ast_rtp_dtls_stop(instance);
3920 if (rtp->rtcp && rtp->rtcp->
s > -1) {
3921 if (saved_rtp_s != rtp->rtcp->
s) {
3922 close(rtp->rtcp->
s);
3927 #ifdef HAVE_PJPROJECT 3935 if (rtp->turn_rtp) {
3936 rtp->turn_state = PJ_TURN_STATE_NULL;
3940 pj_turn_sock_destroy(rtp->turn_rtp);
3942 while (rtp->turn_state != PJ_TURN_STATE_DESTROYING) {
3945 rtp->turn_rtp =
NULL;
3949 if (rtp->turn_rtcp) {
3950 rtp->turn_state = PJ_TURN_STATE_NULL;
3954 pj_turn_sock_destroy(rtp->turn_rtcp);
3956 while (rtp->turn_state != PJ_TURN_STATE_DESTROYING) {
3959 rtp->turn_rtcp =
NULL;
3962 ast_debug_ice(2,
"(%p) ICE RTP transport deallocating\n", instance);
3967 if (rtp->ice_local_candidates) {
3968 ao2_ref(rtp->ice_local_candidates, -1);
3969 rtp->ice_local_candidates =
NULL;
3972 if (rtp->ice_active_remote_candidates) {
3973 ao2_ref(rtp->ice_active_remote_candidates, -1);
3974 rtp->ice_active_remote_candidates =
NULL;
3986 rtp->ioqueue =
NULL;
4008 rtp->expectedseqno = -1;
4026 rtp->transport_wide_cc.schedid = -1;
4031 rtp->stream_num = -1;
4045 #define SSRC_MAPPING_ELEM_CMP(elem, value) ((elem).instance == (value)) 4070 if (rtp->smoother) {
4081 ast_free(rtp->rtcp->local_addr_str);
4095 if (rtp->send_buffer) {
4100 if (rtp->recv_buffer) {
4122 rtp->dtmfmode = dtmf_mode;
4130 return rtp->dtmfmode;
4138 int hdrlen = 12, res = 0, i = 0, payload = 101;
4140 unsigned int *rtpheader = (
unsigned int*)data;
4150 if ((digit <=
'9') && (digit >=
'0')) {
4152 }
else if (digit ==
'*') {
4154 }
else if (digit ==
'#') {
4156 }
else if ((digit >=
'A') && (digit <=
'D')) {
4157 digit = digit -
'A' + 12;
4158 }
else if ((digit >=
'a') && (digit <=
'd')) {
4159 digit = digit -
'a' + 12;
4169 rtp->send_duration = 160;
4171 rtp->lastdigitts = rtp->
lastts + rtp->send_duration;
4174 rtpheader[0] = htonl((2 << 30) | (1 << 23) | (payload << 16) | (rtp->seqno));
4175 rtpheader[1] = htonl(rtp->lastdigitts);
4176 rtpheader[2] = htonl(rtp->
ssrc);
4179 for (i = 0; i < 2; i++) {
4182 rtpheader[3] = htonl((digit << 24) | (0xa << 16) | (rtp->send_duration));
4183 res =
rtp_sendto(instance, (
void *) rtpheader, hdrlen + 4, 0, &remote_address, &ice);
4190 ast_verbose(
"Sent RTP DTMF packet to %s%s (type %-2.2d, seq %-6.6d, ts %-6.6u, len %-6.6d)\n",
4192 ice ?
" (via ICE)" :
"",
4193 payload, rtp->seqno, rtp->lastdigitts, res - hdrlen);
4196 rtp->send_duration += 160;
4197 rtpheader[0] = htonl((2 << 30) | (payload << 16) | (rtp->seqno));
4201 rtp->sending_digit = 1;
4202 rtp->send_digit =
digit;
4203 rtp->send_payload = payload;
4213 int hdrlen = 12, res = 0;
4215 unsigned int *rtpheader = (
unsigned int*)data;
4226 rtpheader[0] = htonl((2 << 30) | (rtp->send_payload << 16) | (rtp->seqno));
4227 rtpheader[1] = htonl(rtp->lastdigitts);
4228 rtpheader[2] = htonl(rtp->
ssrc);
4229 rtpheader[3] = htonl((rtp->send_digit << 24) | (0xa << 16) | (rtp->send_duration));
4232 res =
rtp_sendto(instance, (
void *) rtpheader, hdrlen + 4, 0, &remote_address, &ice);
4240 ast_verbose(
"Sent RTP DTMF packet to %s%s (type %-2.2d, seq %-6.6d, ts %-6.6u, len %-6.6d)\n",
4242 ice ?
" (via ICE)" :
"",
4243 rtp->send_payload, rtp->seqno, rtp->lastdigitts, res - hdrlen);
4248 rtp->send_duration += 160;
4259 int hdrlen = 12, res = -1, i = 0;
4261 unsigned int *rtpheader = (
unsigned int*)data;
4262 unsigned int measured_samples;
4272 if ((digit <=
'9') && (digit >=
'0')) {
4274 }
else if (digit ==
'*') {
4276 }
else if (digit ==
'#') {
4278 }
else if ((digit >=
'A') && (digit <=
'D')) {
4279 digit = digit -
'A' + 12;
4280 }
else if ((digit >=
'a') && (digit <=
'd')) {
4281 digit = digit -
'a' + 12;
4290 ast_debug_rtp(2,
"(%p) RTP adjusting final end duration from %d to %u\n",
4291 instance, rtp->send_duration, measured_samples);
4292 rtp->send_duration = measured_samples;
4296 rtpheader[1] = htonl(rtp->lastdigitts);
4297 rtpheader[2] = htonl(rtp->
ssrc);
4298 rtpheader[3] = htonl((digit << 24) | (0xa << 16) | (rtp->send_duration));
4299 rtpheader[3] |= htonl((1 << 23));
4302 for (i = 0; i < 3; i++) {
4305 rtpheader[0] = htonl((2 << 30) | (rtp->send_payload << 16) | (rtp->seqno));
4307 res =
rtp_sendto(instance, (
void *) rtpheader, hdrlen + 4, 0, &remote_address, &ice);
4316 ast_verbose(
"Sent RTP DTMF packet to %s%s (type %-2.2d, seq %-6.6d, ts %-6.6u, len %-6.6d)\n",
4318 ice ?
" (via ICE)" :
"",
4319 rtp->send_payload, rtp->seqno, rtp->lastdigitts, res - hdrlen);
4330 if (rtp->smoother) {
4332 rtp->smoother =
NULL;
4335 rtp->sending_digit = 0;
4336 rtp->send_digit = 0;
4354 ast_debug_rtp(3,
"(%p) RTP setting the marker bit due to a source update\n", instance);
4372 ast_debug_rtp(3,
"(%p) RTP changing ssrc from %u to %u due to a source change\n",
4373 instance, rtp->
ssrc, ssrc);
4376 ast_debug_rtp(3,
"(%p) RTP changing ssrc for SRTP from %u to %u\n",
4377 instance, rtp->
ssrc, ssrc);
4379 if (rtcp_srtp != srtp) {
4392 static void timeval2ntp(
struct timeval tv,
unsigned int *msw,
unsigned int *lsw)
4394 unsigned int sec, usec, frac;
4395 sec = tv.tv_sec + 2208988800u;
4416 frac = ((((usec << 12) / 125) << 7) / 125) << 7;
4421 static void ntp2timeval(
unsigned int msw,
unsigned int lsw,
struct timeval *tv)
4423 tv->tv_sec = msw - 2208988800u;
4425 tv->tv_usec = ((((lsw >> 7) * 125) >> 7) * 125) >> 12;
4429 unsigned int *lost_packets,
4432 unsigned int extended_seq_no;
4433 unsigned int expected_packets;
4434 unsigned int expected_interval;
4435 unsigned int received_interval;
4440 expected_packets = extended_seq_no - rtp->seedrxseqno + 1;
4441 if (rtp->rxcount > expected_packets) {
4442 expected_packets += rtp->rxcount - expected_packets;
4444 *lost_packets = expected_packets - rtp->rxcount;
4445 expected_interval = expected_packets - rtp->rtcp->expected_prior;
4446 received_interval = rtp->rxcount - rtp->rtcp->received_prior;
4447 if (received_interval > expected_interval) {
4453 expected_interval = received_interval;
4455 lost_interval = expected_interval - received_interval;
4456 if (expected_interval == 0 || lost_interval <= 0) {
4459 *fraction_lost = (lost_interval << 8) / expected_interval;
4463 rtp->rtcp->received_prior = rtp->rxcount;
4464 rtp->rtcp->expected_prior = expected_packets;
4472 if (lost_interval <= 0) {
4473 rtp->rtcp->rxlost = 0;
4475 rtp->rtcp->rxlost = lost_interval;
4477 if (rtp->rtcp->rxlost_count == 0) {
4478 rtp->rtcp->minrxlost = rtp->rtcp->rxlost;
4480 if (lost_interval && lost_interval < rtp->rtcp->minrxlost) {
4481 rtp->rtcp->minrxlost = rtp->rtcp->rxlost;
4483 if (lost_interval > rtp->rtcp->maxrxlost) {
4484 rtp->rtcp->maxrxlost = rtp->rtcp->rxlost;
4488 &rtp->rtcp->stdev_rxlost, &rtp->rtcp->rxlost_count);
4497 unsigned int now_lsw;
4498 unsigned int now_msw;
4499 unsigned int lost_packets;
4501 struct timeval dlsr = { 0, };
4504 if (!rtp || !rtp->rtcp) {
4517 *sr = rtp->txcount > rtp->rtcp->lastsrtxcount ? 1 : 0;
4522 gettimeofday(&now,
NULL);
4534 report_block =
ast_calloc(1,
sizeof(*report_block));
4535 if (!report_block) {
4545 report_block->
lsr = rtp->rtcp->themrxlsr;
4548 timersub(&now, &rtp->rtcp->rxlsr, &dlsr);
4549 report_block->
dlsr = (((dlsr.tv_sec * 1000) + (dlsr.tv_usec / 1000)) * 65536) / 1000;
4586 if (!rtp || !rtp->rtcp) {
4602 rtp->rtcp->sr_count++;
4603 rtp->rtcp->lastsrtxcount = rtp->txcount;
4605 rtp->rtcp->rr_count++;
4609 ast_verbose(
"* Sent RTCP %s to %s%s\n", sr ?
"SR" :
"RR",
4628 ast_verbose(
" DLSR: %4.4f (sec)\n\n", (
double)(report_block->
dlsr / 65536.0));
4634 "from", rtp->rtcp->local_addr_str);
4636 rtcp_report, message_blob);
4646 uint16_t sdes_packet_len_bytes;
4647 uint16_t sdes_packet_len_rounded;
4649 if (!rtp || !rtp->rtcp) {
4661 sdes_packet_len_bytes =
4670 sdes_packet_len_rounded = (sdes_packet_len_bytes + 3) & ~0x3;
4674 rtcpheader[8] = 0x01;
4689 len += (sdes_packet_len_rounded - sdes_packet_len_bytes);
4712 if (res == 0 || res == 1) {
4713 ast_debug_rtcp(1,
"(%p) RTCP failed to generate %s report!\n", instance, sr ?
"SR" :
"RR");
4721 if (res == 0 || res == 1) {
4722 ast_debug_rtcp(1,
"(%p) RTCP failed to generate SDES!\n", instance);
4726 return packet_len + res;
4735 unsigned int fci = 0;
4736 size_t remaining_missing_seqno;
4738 if (!rtp || !rtp->rtcp) {
4751 if (!remaining_missing_seqno) {
4758 while (remaining_missing_seqno) {
4768 if (missing_seqno) {
4770 if (blp_index >= 17) {
4777 if (blp_index == 0) {
4778 fci |= (current_seqno << 16);
4780 fci |= (1 << (blp_index - 1));
4784 remaining_missing_seqno--;
4823 unsigned char *rtcpheader;
4829 if (!rtp || !rtp->rtcp || rtp->rtcp->schedid == -1) {
4839 if (res == 0 || res == 1) {
4851 res =
rtcp_sendto(instance, (
unsigned int *)rtcpheader, packet_len, 0, &remote_address, &ice);
4869 rtp->rtcp->schedid = -1;
4878 unsigned char *cp = p;
4882 datum = (time_msw << 18) & 0x00fc0000;
4883 datum |= (time_lsw >> 14) & 0x0003ffff;
4885 cp[0] = datum >> 16;
4899 #ifdef TEST_FRAMEWORK 4907 if (rtp->sending_digit) {
4911 #ifdef TEST_FRAMEWORK 4930 ast_debug_rtp(3,
"(%p) RTP audio difference is %d, ms is %u\n",
4931 instance,
abs((
int)rtp->
lastts - pred), ms);
4942 if (
abs((
int)rtp->
lastts - pred) < 7200) {
4946 ast_debug_rtp(3,
"(%p) RTP video difference is %d, ms is %u (%u), pred/ts/samples %u/%d/%d\n",
4957 if (
abs((
int)rtp->
lastts - pred) < 7200) {
4961 ast_debug_rtp(3,
"(%p) RTP other difference is %d, ms is %u, pred/ts/samples %u/%d/%d\n",
4975 if (rtp->
lastts > rtp->lastdigitts) {
4976 rtp->lastdigitts = rtp->
lastts;
4984 if (rtp->expectedseqno != -1) {
4986 int difference = frame->
seqno - rtp->expectedseqno;
4993 if (
abs(difference) > 100) {
4998 seqno += difference;
5000 if (difference >= 0) {
5002 rtp->expectedseqno = frame->
seqno + 1;
5003 rtp->seqno += difference;
5007 rtp->expectedseqno = frame->
seqno + 1;
5010 rtp->expectedseqno = -1;
5025 int abs_send_time_id;
5027 unsigned char *rtpheader;
5031 if (abs_send_time_id != -1) {
5037 packet_len = frame->
datalen + hdrlen;
5038 rtpheader = (
unsigned char *)(frame->
data.
ptr - hdrlen);
5040 put_unaligned_uint32(rtpheader, htonl((2 << 30) | (ext << 28) | (codec << 16) | (seqno) | (mark << 23)));
5047 if (abs_send_time_id != -1) {
5048 unsigned int now_msw;
5049 unsigned int now_lsw;
5055 rtpheader[16] = (abs_send_time_id << 4) | 2;
5062 if (rtp->send_buffer) {
5065 payload =
ast_malloc(
sizeof(*payload) + packet_len);
5067 payload->
size = packet_len;
5068 memcpy(payload->
buf, rtpheader, packet_len);
5075 res =
rtp_sendto(instance, (
void *)rtpheader, packet_len, 0, &remote_address, &ice);
5078 ast_debug_rtp(1,
"(%p) RTP transmission error of packet %d to %s: %s\n",
5079 instance, rtp->seqno,
5085 ast_debug(0,
"(%p) RTP NAT: Can't write RTP to private address %s, waiting for other end to send audio...\n",
5090 if (rtp->rtcp && rtp->rtcp->schedid < 0) {
5091 ast_debug_rtcp(1,
"(%p) RTCP starting transmission\n", instance);
5094 if (rtp->rtcp->schedid < 0) {
5102 ast_verbose(
"Sent RTP packet to %s%s (type %-2.2d, seq %-6.6d, ts %-6.6u, len %-6.6d)\n",
5104 ice ?
" (via ICE)" :
"",
5105 codec, rtp->seqno, rtp->
lastts, res - hdrlen);
5113 if (seqno == rtp->seqno) {
5128 for (i = 1; i < red->
num_gen+1; i++)
5135 for (i = 0; i < red->
num_gen; i++)
5136 red->
len[i] = red->
len[i+1];
5141 for (i = 0; i < red->
num_gen; i++) {
5142 len += data[i*4+3] = red->
len[i];
5162 unsigned char *rtcpheader;
5163 unsigned char bdata[1024];
5173 if (!rtp || !rtp->rtcp) {
5190 rtp->rtcp->firseq++;
5191 if(rtp->rtcp->firseq == 256) {
5192 rtp->rtcp->firseq = 0;
5200 if (res == 0 || res == 1) {
5212 res =
rtcp_sendto(instance, (
unsigned int *)rtcpheader, packet_len + fir_len, 0, rtp->bundled ? remote_address : &rtp->rtcp->them, &ice);
5225 unsigned char *rtcpheader;
5226 unsigned char bdata[1024];
5237 ast_debug_rtcp(1,
"(%p) RTCP provided feedback frame of format %d to write, but only REMB is supported\n",
5238 instance, feedback->
fmt);
5242 if (!rtp || !rtp->rtcp) {
5248 ast_debug_rtcp(1,
"(%p) RTCP provided feedback REMB report to write, but REMB support not enabled\n",
5265 if (res == 0 || res == 1) {
5275 put_unaligned_uint32(rtcpheader + packet_len + 12, htonl((
'R' << 24) | (
'E' << 16) | (
'M' << 8) | (
'B')));
5278 res =
rtcp_sendto(instance, (
unsigned int *)rtcpheader, packet_len + remb_len, 0, rtp->bundled ? remote_address : &rtp->rtcp->them, &ice);
5300 ast_debug_rtp(1,
"(%p) RTP no remote address on instance, so dropping frame\n", instance);
5317 ast_debug_rtp(1,
"(%p) RTP received frame with no data for instance, so dropping frame\n", instance);
5349 ast_debug_rtp(1,
"(%p) RTP ooh, format changed from %s to %s\n",
5353 if (rtp->smoother) {
5355 rtp->smoother =
NULL;
5370 if (!rtp->smoother) {
5380 if (rtp->smoother) {
5396 if (frame->
offset < hdrlen) {
5418 double current_time;
5424 if ((!rtp->rxcore.tv_sec && !rtp->rxcore.tv_usec) || mark) {
5425 gettimeofday(&rtp->rxcore,
NULL);
5426 rtp->drxcore = (double) rtp->rxcore.tv_sec + (
double) rtp->rxcore.tv_usec / 1000000;
5428 rtp->seedrxts = timestamp;
5430 rtp->rxcore =
ast_tvsub(rtp->rxcore, tmp);
5432 rtp->rxcore.tv_usec -= rtp->rxcore.tv_usec % 100;
5435 gettimeofday(&now,
NULL);
5440 prog = (double)((timestamp-rtp->seedrxts)/(float)(rate));
5441 dtv = (double)rtp->drxcore + (
double)(prog);
5442 current_time = (double)now.tv_sec + (
double)now.tv_usec/1000000;
5443 transit = current_time - dtv;
5444 d = transit - rtp->rxtransit;
5445 rtp->rxtransit = transit;
5449 rtp->rxjitter += (1./16.) * (d - rtp->rxjitter);
5451 if (rtp->rxjitter > rtp->rtcp->maxrxjitter)
5452 rtp->rtcp->maxrxjitter = rtp->rxjitter;
5453 if (rtp->rtcp->rxjitter_count == 1)
5454 rtp->rtcp->minrxjitter = rtp->rxjitter;
5455 if (rtp->rtcp && rtp->rxjitter < rtp->rtcp->minrxjitter)
5456 rtp->rtcp->minrxjitter = rtp->rxjitter;
5459 &rtp->rtcp->stdev_rxjitter, &rtp->rtcp->rxjitter_count);
5471 ast_debug_rtp(1,
"(%p) RTP ignore potential DTMF echo from '%s'\n",
5474 rtp->dtmfsamples = 0;
5480 rtp->dtmfsamples = 0;
5484 if (rtp->resp ==
'X') {
5490 ast_debug_rtp(1,
"(%p) RTP creating %s DTMF Frame: %d (%c), at %s\n",
5492 rtp->resp, rtp->resp,
5510 unsigned int event, event_end, samples;
5517 event = ntohl(*((
unsigned int *)(data)));
5519 event_end = ntohl(*((
unsigned int *)(data)));
5522 samples = ntohl(*((
unsigned int *)(data)));
5526 ast_verbose(
"Got RTP RFC2833 from %s (type %-2.2d, seq %-6.6u, ts %-6.6u, len %-6.6d, mark %d, event %08x, end %d, duration %-5.5u) \n",
5528 payloadtype, seqno, timestamp, len, (mark?1:0), event, ((event_end & 0x80)?1:0), samples);
5533 ast_debug(0,
"- RTP 2833 Event: %08x (len = %d)\n", event, len);
5538 }
else if (event < 11) {
5540 }
else if (event < 12) {
5542 }
else if (event < 16) {
5543 resp =
'A' + (
event - 12);
5544 }
else if (event < 17) {
5548 ast_debug_rtp(1,
"(%p) RTP ignoring RTP 2833 Event: %08x. Not a DTMF Digit.\n", instance, event);
5553 if (!rtp->last_end_timestamp.is_set || rtp->last_end_timestamp.ts != timestamp || (rtp->resp && rtp->resp != resp)) {
5555 rtp->dtmf_timeout = 0;
5558 rtp->last_end_timestamp.ts = timestamp;
5559 rtp->last_end_timestamp.is_set = 1;
5568 unsigned int new_duration = rtp->dtmf_duration;
5569 unsigned int last_duration = new_duration & 0xFFFF;
5571 if (last_duration > 64000 && samples < last_duration) {
5572 new_duration += 0xFFFF + 1;
5574 new_duration = (new_duration & ~0xFFFF) | samples;
5576 if (event_end & 0x80) {
5578 if (rtp->last_seqno != seqno && (!rtp->last_end_timestamp.is_set || timestamp > rtp->last_end_timestamp.ts)) {
5579 rtp->last_end_timestamp.ts = timestamp;
5580 rtp->last_end_timestamp.is_set = 1;
5581 rtp->dtmf_duration = new_duration;
5586 rtp->dtmf_duration = rtp->dtmf_timeout = 0;
5589 ast_debug_rtp(1,
"(%p) RTP dropping duplicate or out of order DTMF END frame (seqno: %u, ts %u, digit %c)\n",
5590 instance, seqno, timestamp, resp);
5599 if ((rtp->last_seqno > seqno && rtp->last_seqno - seqno < 50)
5600 || (rtp->last_end_timestamp.is_set
5601 && timestamp <= rtp->last_end_timestamp.ts)) {
5607 ast_debug(0,
"Dropping out of order DTMF frame (seqno %u, ts %u, digit %c)\n",
5608 seqno, timestamp, resp);
5613 if (rtp->resp && rtp->resp != resp) {
5618 rtp->dtmf_duration = rtp->dtmf_timeout = 0;
5624 rtp->dtmf_duration = new_duration;
5633 rtp->dtmf_timeout = timestamp + rtp->dtmf_duration +
dtmftimeout;
5636 rtp->last_seqno =
seqno;
5647 unsigned int event, flags, power;
5689 event = data[3] & 0x1f;
5692 ast_debug(0,
"Cisco DTMF Digit: %02x (len=%d, seq=%d, flags=%02x, power=%u, history count=%d)\n", event, len, seq, flags, power, (len - 4) / 2);
5695 }
else if (event < 11) {
5697 }
else if (event < 12) {
5699 }
else if (event < 16) {
5700 resp =
'A' + (
event - 12);
5701 }
else if (event < 17) {
5704 if ((!rtp->resp && power) || (rtp->resp && (rtp->resp != resp))) {
5709 rtp->dtmfsamples = 0;
5711 }
else if ((rtp->resp == resp) && !power) {
5715 }
else if (rtp->resp == resp) {
5719 rtp->dtmf_timeout = 0;
5732 ast_debug(0,
"- RTP 3389 Comfort noise event: Format %s (len = %d)\n",
5741 ast_log(
LOG_NOTICE,
"Comfort noise support incomplete in Asterisk (RFC 3389). Please turn off on client if possible. Client address: %s\n",
5754 memcpy(rtp->
f.
data.
ptr, data + 1, len - 1);
5771 struct timeval rtt_tv;
5774 unsigned int rtt_msw;
5775 unsigned int rtt_lsw;
5779 gettimeofday(&now,
NULL);
5782 lsr_a = ((msw & 0x0000ffff) << 16) | ((lsw & 0xffff0000) >> 16);
5783 rtt = lsr_a - lsr - dlsr;
5784 rtt_msw = (rtt & 0xffff0000) >> 16;
5785 rtt_lsw = (rtt & 0x0000ffff);
5786 rtt_tv.tv_sec = rtt_msw;
5800 rtt_tv.tv_usec = (rtt_lsw * 15625) >> 10;
5801 rtp->rtcp->rtt = (double)rtt_tv.tv_sec + ((
double)rtt_tv.tv_usec / 1000000);
5802 if (lsr_a - dlsr < lsr) {
5806 rtp->rtcp->accumulated_transit += rtp->rtcp->rtt;
5807 if (rtp->rtcp->rtt_count == 0 || rtp->rtcp->minrtt > rtp->rtcp->rtt) {
5808 rtp->rtcp->minrtt = rtp->rtcp->rtt;
5810 if (rtp->rtcp->maxrtt < rtp->rtcp->rtt) {
5811 rtp->rtcp->maxrtt = rtp->rtcp->rtt;
5815 &rtp->rtcp->stdevrtt, &rtp->rtcp->rtt_count);
5826 double reported_jitter;
5828 rtp->rtcp->reported_jitter = ia_jitter;
5829 reported_jitter = (double) rtp->rtcp->reported_jitter;
5830 if (rtp->rtcp->reported_jitter_count == 0) {
5831 rtp->rtcp->reported_minjitter = reported_jitter;
5833 if (reported_jitter < rtp->rtcp->reported_minjitter) {
5834 rtp->rtcp->reported_minjitter = reported_jitter;
5836 if (reported_jitter > rtp->rtcp->reported_maxjitter) {
5837 rtp->rtcp->reported_maxjitter = reported_jitter;
5841 &rtp->rtcp->reported_stdev_jitter, &rtp->rtcp->reported_jitter_count);
5850 double reported_lost;
5852 rtp->rtcp->reported_lost = lost_packets;
5853 reported_lost = (double)rtp->rtcp->reported_lost;
5854 if (rtp->rtcp->reported_lost_count == 0) {
5855 rtp->rtcp->reported_minlost = reported_lost;
5857 if (reported_lost < rtp->rtcp->reported_minlost) {
5858 rtp->rtcp->reported_minlost = reported_lost;
5860 if (reported_lost > rtp->rtcp->reported_maxlost) {
5861 rtp->rtcp->reported_maxlost = reported_lost;
5865 &rtp->rtcp->reported_stdev_lost, &rtp->rtcp->reported_lost_count);
5870 struct ast_rtp *rtp,
unsigned int ssrc,
int source)
5880 for (index = 0; index <
AST_VECTOR_SIZE(&rtp->ssrc_mapping); ++index) {
5884 if (mapping->
ssrc_valid && mapping_ssrc == ssrc) {
5898 struct ast_rtp *rtp,
unsigned int ssrc)
5905 struct ast_rtp *rtp,
unsigned int ssrc)
5916 str =
"Sender Report";
5919 str =
"Receiver Report";
5930 str =
"Source Description";
5964 unsigned int length)
5972 unsigned int current_word;
5976 int abs_send_time_id;
5977 unsigned int now_msw = 0;
5978 unsigned int now_lsw = 0;
5979 unsigned int packets_not_found = 0;
5981 if (!rtp->send_buffer) {
5983 "but we don't have a RTP packet storage!\n", instance);
5988 if (abs_send_time_id != -1) {
5998 for (packet_index = 3; packet_index < length; packet_index++) {
5999 current_word = ntohl(nackdata[position + packet_index]);
6000 pid = current_word >> 16;
6004 if (abs_send_time_id != -1) {
6010 res +=
rtp_sendto(instance, payload->
buf, payload->
size, 0, &remote_address, &ice);
6012 ast_debug_rtcp(1,
"(%p) RTCP received NACK request for RTP packet with seqno %d, " 6013 "but we don't have it\n", instance, pid);
6014 packets_not_found++;
6022 blp = current_word & 0xffff;
6027 unsigned int seqno = (pid + blp_index) % 65536;
6030 if (abs_send_time_id != -1) {
6033 res +=
rtp_sendto(instance, payload->
buf, payload->
size, 0, &remote_address, &ice);
6035 ast_debug_rtcp(1,
"(%p) RTCP remote end also requested RTP packet with seqno %d, " 6036 "but we don't have it\n", instance, seqno);
6037 packets_not_found++;
6045 if (packets_not_found) {
6051 ast_debug_rtcp(2,
"(%p) RTCP send buffer on RTP instance is now at maximum of %zu\n",
6061 #define RTCP_LENGTH_MASK 0xFFFF 6062 #define RTCP_PAYLOAD_TYPE_MASK 0xFF 6063 #define RTCP_REPORT_COUNT_MASK 0x1F 6064 #define RTCP_PADDING_MASK 0x01 6065 #define RTCP_VERSION_MASK 0x03 6070 #define RTCP_LENGTH_SHIFT 0 6071 #define RTCP_PAYLOAD_TYPE_SHIFT 16 6072 #define RTCP_REPORT_COUNT_SHIFT 24 6073 #define RTCP_PADDING_SHIFT 29 6074 #define RTCP_VERSION_SHIFT 30 6076 #define RTCP_VERSION 2U 6077 #define RTCP_VERSION_SHIFTED (RTCP_VERSION << RTCP_VERSION_SHIFT) 6078 #define RTCP_VERSION_MASK_SHIFTED (RTCP_VERSION_MASK << RTCP_VERSION_SHIFT) 6091 #define RTCP_VALID_MASK (RTCP_VERSION_MASK_SHIFTED | (((RTCP_PAYLOAD_TYPE_MASK & ~0x1)) << RTCP_PAYLOAD_TYPE_SHIFT)) 6092 #define RTCP_VALID_VALUE (RTCP_VERSION_SHIFTED | (RTCP_PT_SR << RTCP_PAYLOAD_TYPE_SHIFT)) 6094 #define RTCP_SR_BLOCK_WORD_LENGTH 5 6095 #define RTCP_RR_BLOCK_WORD_LENGTH 6 6096 #define RTCP_HEADER_SSRC_LENGTH 2 6097 #define RTCP_FB_REMB_BLOCK_WORD_LENGTH 4 6098 #define RTCP_FB_NACK_BLOCK_WORD_LENGTH 2 6101 const unsigned char *rtcpdata,
size_t size,
struct ast_sockaddr *addr)
6106 unsigned int *rtcpheader = (
unsigned int *)(rtcpdata);
6107 unsigned int packetwords;
6108 unsigned int position;
6109 unsigned int first_word;
6111 unsigned int ssrc_seen;
6114 #ifdef TEST_FRAMEWORK 6119 if ((*rtcpheader & 0xC0) && res_srtp && srtp && res_srtp->
unprotect(
6124 packetwords = len / 4;
6134 ast_debug_rtcp(1,
"(%p) RTCP %p -- from %s: Frame size (%u words) is too short\n",
6139 first_word = ntohl(rtcpheader[position]);
6141 ast_debug_rtcp(1,
"(%p) RTCP %p -- from %s: Failed first packet validity check\n",
6147 if (packetwords <= position) {
6150 first_word = ntohl(rtcpheader[position]);
6152 if (position != packetwords) {
6153 ast_debug_rtcp(1,
"(%p) RTCP %p -- from %s: Failed packet version or length check\n",
6177 while (position < packetwords) {
6183 unsigned int ssrc_valid;
6184 unsigned int length;
6185 unsigned int min_length;
6187 unsigned int use_packet_source = 1;
6196 first_word = ntohl(rtcpheader[i]);
6210 use_packet_source = 0;
6222 use_packet_source = 0;
6241 min_length = length;
6244 ast_debug_rtcp(1,
"(%p) RTCP %p -- from %s: %u(%s) skipping record\n",
6248 ast_verbose(
"RTCP from %s: %u(%s) skipping record\n",
6254 if (length < min_length) {
6255 ast_debug_rtcp(1,
"(%p) RTCP %p -- from %s: %u(%s) length field less than expected minimum. Min:%u Got:%u\n",
6257 min_length - 1, length - 1);
6270 rtcp_report->reception_report_count = rc;
6272 ssrc = ntohl(rtcpheader[i + 2]);
6273 rtcp_report->ssrc = ssrc;
6277 ssrc = ntohl(rtcpheader[i + 1]);
6280 ssrc = ntohl(rtcpheader[i + 2]);
6297 ast_verbose(
"Packet Subtype: %u (%s)\n", rc, subtype);
6310 if (use_packet_source) {
6315 if (child && child != transport) {
6327 rtp = transport_rtp;
6331 rtp = transport_rtp;
6344 if ((ssrc != rtp->
themssrc && use_packet_source && ssrc != 1)
6352 ast_debug_rtcp(1,
"(%p) RTCP %p -- from %s: Skipping record, received SSRC '%u' != expected '%u'\n",
6367 ast_debug(0,
"(%p) RTCP NAT: Got RTCP from other end. Now sending to address %s\n",
6376 gettimeofday(&rtp->rtcp->rxlsr,
NULL);
6377 rtp->rtcp->themrxlsr = ((ntohl(rtcpheader[i]) & 0x0000ffff) << 16) | ((ntohl(rtcpheader[i + 1]) & 0xffff0000) >> 16);
6378 rtp->rtcp->spc = ntohl(rtcpheader[i + 3]);
6379 rtp->rtcp->soc = ntohl(rtcpheader[i + 4]);
6382 rtcp_report->sender_information.packet_count = rtp->rtcp->spc;
6383 rtcp_report->sender_information.octet_count = rtp->rtcp->soc;
6385 (
unsigned int)ntohl(rtcpheader[i + 1]),
6386 &rtcp_report->sender_information.ntp_timestamp);
6387 rtcp_report->sender_information.rtp_timestamp = ntohl(rtcpheader[i + 2]);
6390 (
unsigned int)rtcp_report->sender_information.ntp_timestamp.tv_sec,
6391 (
unsigned int)rtcp_report->sender_information.ntp_timestamp.tv_usec);
6392 ast_verbose(
"RTP timestamp: %u\n", rtcp_report->sender_information.rtp_timestamp);
6394 rtcp_report->sender_information.packet_count,
6395 rtcp_report->sender_information.octet_count);
6406 report_block =
ast_calloc(1,
sizeof(*report_block));
6407 if (!report_block) {
6413 rtcp_report->report_block[0] = report_block;
6418 report_block->
ia_jitter = ntohl(rtcpheader[i + 3]);
6419 report_block->
lsr = ntohl(rtcpheader[i + 4]);
6420 report_block->
dlsr = ntohl(rtcpheader[i + 5]);
6421 if (report_block->
lsr 6425 unsigned int lsr_now, lsw, msw;
6426 gettimeofday(&now,
NULL);
6428 lsr_now = (((msw & 0xffff) << 16) | ((lsw & 0xffff0000) >> 16));
6429 ast_verbose(
"Internal RTCP NTP clock skew detected: " 6430 "lsr=%u, now=%u, dlsr=%u (%u:%03ums), " 6432 report_block->
lsr, lsr_now, report_block->
dlsr, report_block->
dlsr / 65536,
6433 (report_block->
dlsr % 65536) * 1000 / 65536,
6434 report_block->
dlsr - (lsr_now - report_block->
lsr));
6445 ast_verbose(
" Last SR(our NTP): %lu.%010lu\n",(
unsigned long)(report_block->
lsr) >> 16,((
unsigned long)(report_block->
lsr) << 16) * 4096);
6446 ast_verbose(
" DLSR: %4.4f (sec)\n",(
double)report_block->
dlsr / 65536.0);
6447 ast_verbose(
" RTT: %4.4f(sec)\n", rtp->rtcp->rtt);
6456 "to", transport_rtp->rtcp->local_addr_str,
6457 "rtt", rtp->rtcp->rtt);
6484 transport_rtp->
f.
src =
"RTP";
6486 f = &transport_rtp->
f;
6492 if (!rtp->send_buffer) {
6497 ast_verbose(
"Received generic RTCP NACK message\n");
6514 ast_verbose(
"Received an RTCP Fast Update Request\n");
6521 transport_rtp->
f.
src =
"RTP";
6522 f = &transport_rtp->
f;
6537 feedback = transport_rtp->
f.
data.
ptr;
6541 first_word = ntohl(rtcpheader[i + 2]);
6542 feedback->
remb.
br_exp = (first_word >> 18) & ((1 << 6) - 1);
6551 transport_rtp->
f.
src =
"RTP";
6552 f = &transport_rtp->
f;
6563 #ifdef TEST_FRAMEWORK 6579 rtp->rtcp->rtcp_info = 1;
6597 size_t read_area_size =
sizeof(rtcpdata) - AST_FRIENDLY_OFFSET;
6601 if ((res =
rtcp_recvfrom(instance, read_area, read_area_size,
6610 if (
errno != EAGAIN) {
6624 struct sockaddr_in addr_tmp;
6634 ast_debug_stun(2,
"(%p) STUN cannot do for non IPv4 address %s\n",
6650 struct ast_rtp_instance *instance1,
unsigned int *rtpheader,
int len,
int hdrlen)
6654 int res = 0, payload = 0, bridged_payload = 0, mark;
6659 unsigned int timestamp = ntohl(rtpheader[1]);
6662 payload = (reconstruct & 0x7f0000) >> 16;
6663 mark = (reconstruct & 0x800000) >> 23;
6667 if (!payload_type) {
6673 payload_type->asterisk_format, payload_type->format, payload_type->rtp_code);
6676 if (bridged_payload < 0) {
6682 ast_debug_rtp(1,
"(%p, %p) RTP unsupported payload type received\n", instance, instance1);
6691 if (rtp->last_end_timestamp.is_set && rtp->last_end_timestamp.ts == timestamp) {
6692 ast_debug_rtp(1,
"(%p, %p) RTP feeding packet with duplicate timestamp to core\n", instance, instance1);
6696 if (payload_type->asterisk_format) {
6697 ao2_replace(rtp->lastrxformat, payload_type->format);
6723 if (bridged->sending_digit) {
6724 ast_debug_rtp(1,
"(%p, %p) RTP Feeding packet to core until DTMF finishes\n", instance, instance1);
6730 if (payload_type->asterisk_format) {
6735 if (!bridged->asymmetric_codec
6738 ast_debug_rtp(1,
"(%p, %p) RTP asymmetric RTP codecs detected (TX: %s, RX: %s) sending frame to core\n",
6746 ao2_replace(bridged->lasttxformat, payload_type->format);
6752 ast_debug_rtp(5,
"(%p, %p) RTP remote address is null, most likely RTP has been stopped\n",
6753 instance, instance1);
6772 reconstruct &= 0xFF80FFFF;
6773 reconstruct |= (bridged_payload << 16);
6774 reconstruct |= (mark << 23);
6775 rtpheader[0] = htonl(reconstruct);
6779 bridged->
ssrc = ntohl(rtpheader[2]);
6783 res =
rtp_sendto(instance1, (
void *)rtpheader, len, 0, &remote_address, &ice);
6787 "RTP Transmission error of packet to %s: %s\n",
6793 "RTP NAT: Can't write RTP to private " 6794 "address %s, waiting for other end to " 6806 ast_verbose(
"Sent RTP P2P packet to %s%s (type %-2.2d, len %-6.6d)\n",
6808 ice ?
" (via ICE)" :
"",
6809 bridged_payload, len - hdrlen);
6831 uint16_t *status_vector_chunk,
int status)
6834 *status_vector_chunk_bits -= 2;
6840 *status_vector_chunk |= (status << (16 - 2 - (14 - *status_vector_chunk_bits)));
6843 if (*status_vector_chunk_bits) {
6849 *status_vector_chunk_bits = 14;
6855 *status_vector_chunk = (1 << 15) | (1 << 14);
6860 uint16_t *status_vector_chunk,
int *run_length_chunk_count,
int *run_length_chunk_status,
int status)
6862 if (*run_length_chunk_status != status) {
6863 while (*run_length_chunk_count > 0 && *run_length_chunk_count < 8) {
6871 status_vector_chunk, *run_length_chunk_status);
6872 *run_length_chunk_count -= 1;
6875 if (*run_length_chunk_count) {
6877 put_unaligned_uint16(rtcpheader + *packet_len, htons((0 << 15) | (*run_length_chunk_status << 13) | *run_length_chunk_count));
6882 *run_length_chunk_count = 0;
6883 *run_length_chunk_status = -1;
6885 if (*status_vector_chunk_bits == 14) {
6887 *run_length_chunk_status =
status;
6888 *run_length_chunk_count = 1;
6892 status_vector_chunk, status);
6896 *run_length_chunk_count += 1;
6904 unsigned char *rtcpheader;
6909 int status_vector_chunk_bits = 14;
6910 uint16_t status_vector_chunk = (1 << 15) | (1 << 14);
6911 int run_length_chunk_count = 0;
6912 int run_length_chunk_status = -1;
6913 int packet_len = 20;
6915 int packet_count = 0;
6916 unsigned int received_msw;
6917 unsigned int received_lsw;
6921 unsigned int large_delta_count = 0;
6922 unsigned int small_delta_count = 0;
6923 unsigned int lost_count = 0;
6925 if (!rtp || !rtp->rtcp || rtp->transport_wide_cc.schedid == -1) {
6938 rtcpheader = (
unsigned char *)bdata;
6942 previous_packet = first_packet;
6948 for (i = 0; i <
AST_VECTOR_SIZE(&rtp->transport_wide_cc.packet_statistics); ++i) {
6957 if (first_packet != statistics) {
6962 lost = statistics->
seqno - (previous_packet->
seqno + 1);
6969 &status_vector_chunk, &run_length_chunk_count, &run_length_chunk_status, 0);
6975 if (packet_len + delta_len + 20 >
sizeof(bdata)) {
6992 if (statistics->
delta < 0 || statistics->
delta > 127) {
6995 &status_vector_chunk, &run_length_chunk_count, &run_length_chunk_status, 2);
6997 large_delta_count++;
7001 &status_vector_chunk, &run_length_chunk_count, &run_length_chunk_status, 1);
7003 small_delta_count++;
7009 if (packet_len + delta_len + 20 >
sizeof(bdata)) {
7014 if (status_vector_chunk_bits != 14) {
7018 }
else if (run_length_chunk_count) {
7020 put_unaligned_uint16(rtcpheader + packet_len, htons((0 << 15) | (run_length_chunk_status << 13) | run_length_chunk_count));
7025 for (i = 0; i <
AST_VECTOR_SIZE(&rtp->transport_wide_cc.packet_statistics); ++i) {
7030 if (statistics->
delta < 0 || statistics->
delta > 127) {
7036 rtcpheader[packet_len] = statistics->
delta;
7043 if (statistics == previous_packet) {
7049 while (packet_len % 4) {
7050 rtcpheader[packet_len++] = 0;
7064 rtcpheader[19] = rtp->transport_wide_cc.feedback_count;
7069 ast_debug_rtcp(2,
"(%p) RTCP sending transport-cc feedback packet of size '%d' on '%s' with packet count of %d (small = %d, large = %d, lost = %d)\n",
7072 res =
rtcp_sendto(instance, (
unsigned int *)rtcpheader, packet_len, 0, &remote_address, &ice);
7080 rtp->transport_wide_cc.feedback_count++;
7088 unsigned char *data,
int len)
7090 uint16_t *
seqno = (uint16_t *)data;
7092 struct ast_rtp_instance *transport = rtp->bundled ? rtp->bundled : instance;
7096 if (((
int)transport_rtp->transport_wide_cc.last_seqno - (
int)ntohs(*seqno)) > 100) {
7097 transport_rtp->transport_wide_cc.cycles +=
RTP_SEQ_MOD;
7101 statistics.
seqno = transport_rtp->transport_wide_cc.cycles + ntohs(*seqno);
7107 if (
AST_VECTOR_SIZE(&transport_rtp->transport_wide_cc.packet_statistics) > 1000) {
7111 if (!
AST_VECTOR_SIZE(&transport_rtp->transport_wide_cc.packet_statistics) ||
7112 statistics.
seqno > transport_rtp->transport_wide_cc.last_extended_seqno) {
7114 if (
AST_VECTOR_APPEND(&transport_rtp->transport_wide_cc.packet_statistics, statistics)) {
7118 transport_rtp->transport_wide_cc.last_extended_seqno = statistics.
seqno;
7119 transport_rtp->transport_wide_cc.last_seqno = ntohs(*seqno);
7129 if (transport_rtp->transport_wide_cc.schedid < 0 && transport_rtp->rtcp) {
7130 ast_debug_rtcp(1,
"(%p) RTCP starting transport-cc feedback transmission on RTP instance '%p'\n", instance, transport);
7132 transport_rtp->transport_wide_cc.schedid =
ast_sched_add(rtp->sched, 1000,
7134 if (transport_rtp->transport_wide_cc.schedid < 0) {
7136 ast_log(
LOG_WARNING,
"Scheduling RTCP transport-cc feedback transmission failed on RTP instance '%p'\n",
7149 if (transport_wide_cc_id == -1) {
7155 int id = extension[pos] >> 4;
7156 int extension_len = (extension[pos] & 0xF) + 1;
7173 }
else if (
id == 15) {
7183 }
else if ((pos + extension_len) >
len) {
7191 if (
id == transport_wide_cc_id) {
7196 pos += extension_len;
7201 const struct ast_sockaddr *remote_address,
unsigned char *read_area,
int length,
int prev_seqno,
7202 unsigned int bundled)
7204 unsigned int *rtpheader = (
unsigned int*)(read_area);
7207 int res = length, hdrlen = 12, ssrc, seqno, payloadtype, padding, mark,
ext, cc;
7208 unsigned int timestamp;
7213 if ((*read_area & 0xC0) && res_srtp && srtp && res_srtp->
unprotect(
7219 if (rtp->sending_digit) {
7224 ssrc = ntohl(rtpheader[2]);
7225 seqno = ntohl(rtpheader[0]);
7226 payloadtype = (seqno & 0x7f0000) >> 16;
7227 padding = seqno & (1 << 29);
7228 mark = seqno & (1 << 23);
7229 ext = seqno & (1 << 28);
7230 cc = (seqno & 0xF000000) >> 24;
7232 timestamp = ntohl(rtpheader[1]);
7238 res -= read_area[res - 1];
7248 int extensions_size = (ntohl(rtpheader[hdrlen/4]) & 0xffff) << 2;
7249 unsigned int profile;
7250 profile = (ntohl(rtpheader[3]) & 0xffff0000) >> 16;
7252 if (profile == 0xbede) {
7256 if (profile == 0x505a) {
7257 ast_log(
LOG_DEBUG,
"Found Zfone extension in RTP stream - zrtp - not supported.\n");
7264 hdrlen += extensions_size;
7285 ast_debug(0,
"(%p) RTP forcing Marker bit, because SSRC has changed\n", instance);
7293 rtp->seedrxseqno = 0;
7295 rtp->rxoctetcount = 0;
7298 rtp->last_seqno = 0;
7299 rtp->last_end_timestamp.ts = 0;
7300 rtp->last_end_timestamp.is_set = 0;
7302 rtp->rtcp->expected_prior = 0;
7303 rtp->rtcp->received_prior = 0;
7312 rtp->rxoctetcount += (res - hdrlen);
7313 if (rtp->rxcount == 1) {
7314 rtp->seedrxseqno =
seqno;
7322 if (rtp->rtcp->schedid < 0) {
7327 if ((
int)prev_seqno - (
int)seqno > 100)
7337 struct timeval rxtime;
7358 if (!payload->asterisk_format) {
7365 process_dtmf_rfc2833(instance, read_area + hdrlen, res - hdrlen, seqno, timestamp, payloadtype, mark, &frames);
7367 f =
process_dtmf_cisco(instance, read_area + hdrlen, res - hdrlen, seqno, timestamp, payloadtype, mark);
7368 }
else if (payload->rtp_code ==
AST_RTP_CN) {
7369 f =
process_cn_rfc3389(instance, read_area + hdrlen, res - hdrlen, seqno, timestamp, payloadtype, mark);
7405 if (rtp->dtmf_timeout && rtp->dtmf_timeout < timestamp) {
7406 rtp->dtmf_timeout = 0;
7413 rtp->dtmf_timeout = rtp->dtmf_duration = 0;
7422 rtp->
f.
data.
ptr = read_area + hdrlen;
7429 && ((
int)seqno - (prev_seqno + 1) > 0)
7430 && ((
int)seqno - (prev_seqno + 1) < 10)) {
7431 unsigned char *data = rtp->
f.
data.
ptr;
7441 unsigned char *data = rtp->
f.
data.
ptr;
7442 unsigned char *header_end;
7443 int num_generations;
7446 int diff =(int)seqno - (prev_seqno+1);
7450 header_end = memchr(data, ((*data) & 0x7f), rtp->
f.
datalen);
7451 if (header_end ==
NULL) {
7456 header_length = header_end -
data;
7457 num_generations = header_length / 4;
7458 len = header_length;
7461 for (x = 0; x < num_generations; x++)
7462 len += data[x * 4 + 3];
7469 }
else if (diff > num_generations && diff < 10) {
7479 for ( x = 0; x < num_generations - diff; x++)
7480 len += data[x * 4 + 3];
7542 struct timeval interval;
7644 int res, hdrlen = 12,
version, payloadtype;
7647 unsigned int *rtpheader = (
unsigned int*)(read_area), seqno, ssrc, timestamp, prev_seqno;
7651 unsigned int bundled;
7662 if ((res =
rtp_recvfrom(instance, read_area, read_area_size, 0,
7671 if (
errno != EAGAIN) {
7693 for (i = 0; i < res; ++i) {
7694 if (read_area[i] !=
'\0') {
7703 seqno = ntohl(rtpheader[0]);
7708 struct sockaddr_in addr_tmp;
7717 ast_debug_stun(1,
"(%p) STUN cannot do for non IPv4 address %s\n",
7735 ssrc = ntohl(rtpheader[2]);
7746 if (child != instance) {
7759 switch (rtp->strict_rtp_state) {
7804 ast_verb(4,
"%p -- Strict RTP learning complete - Locking on source address %s\n",
7833 ast_verb(4,
"%p -- Strict RTP switching to RTP target address %s as source\n",
7850 rtp->rtp_source_learn.stream_type =
7852 ast_verb(4,
"%p -- Strict RTP qualifying stream type: %s\n",
7857 ast_verb(4,
"%p -- Strict RTP switching source address to %s\n",
7864 ast_debug_rtp(1,
"(%p) RTP %p -- Received packet from %s, dropping due to strict RTP protection. Will switch to it in %d packets.\n",
7873 ast_debug_rtp(1,
"(%p) RTP %p -- Received packet from %s, dropping due to strict RTP protection. Qualifying new stream.\n",
7892 ast_debug_rtp(1,
"(%p) RTP %p -- Received packet from %s, dropping due to strict RTP protection.\n",
7894 #ifdef TEST_FRAMEWORK 7896 static int strict_rtp_test_event = 1;
7897 if (strict_rtp_test_event) {
7900 strict_rtp_test_event = 0;
7921 ast_debug(0,
"(%p) RTP NAT: Got audio from other end. Now sending to address %s\n",
7927 payloadtype = (seqno & 0x7f0000) >> 16;
7929 timestamp = ntohl(rtpheader[1]);
7933 ast_debug(0,
"(%p) RTP: drop received packet from %s (type %-2.2d, seq %-6.6u, ts %-6.6u, len %-6.6d)\n",
7940 ast_verbose(
"Got RTP packet from %s (type %-2.2d, seq %-6.6u, ts %-6.6u, len %-6.6d)\n",
7942 payloadtype, seqno, timestamp, res - hdrlen);
7952 if (!rtp->recv_buffer) {
7954 frame =
ast_rtp_interpret(instance, srtp, &addr, read_area, res, prev_seqno, bundled);
7969 frame =
ast_rtp_interpret(instance, srtp, &addr, read_area, res, prev_seqno, bundled);
7976 ast_debug_rtp(2,
"(%p) RTP Packet with sequence number '%d' on instance is no longer missing\n",
7984 frame =
ast_rtp_interpret(instance, srtp, &addr, read_area, res, prev_seqno, bundled);
8019 ast_debug_rtp(2,
"(%p) RTP pulled buffered packet with sequence number '%d' to additionally return\n",
8020 instance, frame->
seqno);
8041 ast_debug_rtp(2,
"(%p) RTP source has wild gap or packet loss, sending FIR\n",
8059 ast_debug_rtp(2,
"(%p) RTP inserted just received packet with sequence number '%d' in correct order\n",
8084 ast_debug_rtp(2,
"(%p) RTP emptying queue and returning packet with sequence number '%d'\n",
8085 instance, frame->
seqno);
8102 frame =
ast_rtp_interpret(instance, srtp, &addr, read_area, res, prev_seqno, bundled);
8109 ast_debug_rtp(2,
"(%p) RTP adding just received packet with sequence number '%d' to end of dumped queue\n",
8144 ast_debug_rtp(2,
"(%p) RTP received an old packet with sequence number '%d', dropping it\n",
8149 ast_debug_rtp(2,
"(%p) RTP received a duplicate transmission of packet with sequence number '%d', dropping it\n",
8157 unsigned int missing_seqnos_added = 0;
8159 ast_debug_rtp(2,
"(%p) RTP received an out of order packet with sequence number '%d' while expecting '%d' from the future\n",
8162 payload =
ast_malloc(
sizeof(*payload) + res);
8173 payload->
size = res;
8174 memcpy(payload->
buf, rtpheader, res);
8186 if (!remove_failed) {
8187 ast_debug_rtp(2,
"(%p) RTP packet with sequence number '%d' is no longer missing\n",
8196 missing_seqno = seqno;
8197 while (remove_failed) {
8201 if (missing_seqno < 0) {
8202 missing_seqno = 65535;
8206 if (missing_seqno == prev_seqno) {
8234 ast_debug_rtp(2,
"(%p) RTP added missing sequence number '%d'\n",
8235 instance, missing_seqno);
8238 missing_seqnos_added++;
8263 rtcpheader =
ast_malloc(
sizeof(*rtcpheader) + data_size);
8265 ast_debug_rtcp(1,
"(%p) RTCP failed to allocate memory for NACK\n", instance);
8269 memset(rtcpheader, 0, data_size);
8273 if (res == 0 || res == 1) {
8282 ast_debug_rtcp(1,
"(%p) RTCP failed to construct NACK, stopping here\n", instance);
8288 res =
rtcp_sendto(instance, rtcpheader, packet_len, 0, &remote_address, &ice);
8290 ast_debug_rtcp(1,
"(%p) RTCP failed to send NACK request out\n", instance);
8292 ast_debug_rtcp(2,
"(%p) RTCP sending a NACK request to get missing packets\n", instance);
8311 if (rtp->rtcp && rtp->rtcp->type == value) {
8312 ast_debug_rtcp(1,
"(%p) RTCP ignoring duplicate property\n", instance);
8317 rtp->rtcp =
ast_calloc(1,
sizeof(*rtp->rtcp));
8322 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 8323 rtp->rtcp->dtls.timeout_timer = -1;
8325 rtp->rtcp->schedid = -1;
8328 rtp->rtcp->type =
value;
8345 ast_free(rtp->rtcp->local_addr_str);
8347 if (!rtp->rtcp->local_addr_str) {
8363 AF_INET6 : -1)) < 0) {
8364 ast_debug_rtcp(1,
"(%p) RTCP failed to create a new socket\n", instance);
8365 ast_free(rtp->rtcp->local_addr_str);
8372 if (
ast_bind(rtp->rtcp->
s, &rtp->rtcp->us)) {
8373 ast_debug_rtcp(1,
"(%p) RTCP failed to setup RTP instance\n", instance);
8374 close(rtp->rtcp->
s);
8375 ast_free(rtp->rtcp->local_addr_str);
8380 #ifdef HAVE_PJPROJECT 8385 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 8386 dtls_setup_rtcp(instance);
8399 if (rtp->rtcp->
s > -1 && rtp->rtcp->
s != rtp->
s) {
8400 close(rtp->rtcp->
s);
8402 rtp->rtcp->
s = rtp->
s;
8405 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 8406 if (rtp->rtcp->dtls.ssl && rtp->rtcp->dtls.ssl != rtp->dtls.ssl) {
8407 SSL_free(rtp->rtcp->dtls.ssl);
8409 rtp->rtcp->dtls.ssl = rtp->dtls.ssl;
8413 ast_debug_rtcp(1,
"(%p) RTCP setup on RTP instance\n", instance);
8416 if (rtp->rtcp->schedid > -1) {
8423 ast_debug_rtcp(1,
"(%p) RTCP failed to tear down RTCP\n", instance);
8428 rtp->rtcp->schedid = -1;
8430 if (rtp->transport_wide_cc.schedid > -1) {
8432 if (!
ast_sched_del(rtp->sched, rtp->transport_wide_cc.schedid)) {
8435 ast_debug_rtcp(1,
"(%p) RTCP failed to tear down transport-cc feedback\n", instance);
8440 rtp->transport_wide_cc.schedid = -1;
8442 if (rtp->rtcp->
s > -1 && rtp->rtcp->
s != rtp->
s) {
8443 close(rtp->rtcp->
s);
8445 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 8447 dtls_srtp_stop_timeout_timer(instance, rtp, 1);
8450 if (rtp->rtcp->dtls.ssl && rtp->rtcp->dtls.ssl != rtp->dtls.ssl) {
8451 SSL_free(rtp->rtcp->dtls.ssl);
8454 ast_free(rtp->rtcp->local_addr_str);
8460 rtp->asymmetric_codec =
value;
8463 if (!rtp->send_buffer) {
8467 if (rtp->send_buffer) {
8469 rtp->send_buffer =
NULL;
8474 if (!rtp->recv_buffer) {
8479 if (rtp->recv_buffer) {
8481 rtp->recv_buffer =
NULL;
8493 return rtcp ? (rtp->rtcp ? rtp->rtcp->
s : -1) : rtp->
s;
8515 ast_debug_rtcp(1,
"(%p) RTCP setting address on RTP instance\n", instance);
8526 ast_free(rtp->rtcp->local_addr_str);
8531 for (index = 0; index <
AST_VECTOR_SIZE(&rtp->ssrc_mapping); ++index) {
8538 rtp->last_seqno = 0;
8539 rtp->last_end_timestamp.ts = 0;
8540 rtp->last_end_timestamp.is_set = 0;
8547 ast_verb(4,
"%p -- Strict RTP learning after remote address set to: %s\n",
8566 if (rtp->red->t140.datalen > 0) {
8587 rtp->red->t140.data.ptr = &rtp->red->buf_data;
8589 rtp->red->t140red = rtp->red->t140;
8590 rtp->red->t140red.data.ptr = &rtp->red->t140red_data;
8592 rtp->red->ti = buffer_time;
8593 rtp->red->num_gen = generations;
8594 rtp->red->hdrlen = generations * 4 + 1;
8596 for (x = 0; x < generations; x++) {
8597 rtp->red->pt[x] = payloads[x];
8598 rtp->red->pt[x] |= 1 << 7;
8599 rtp->red->t140red_data[x*4] = rtp->red->pt[x];
8601 rtp->red->t140red_data[x*4] = rtp->red->pt[x] = payloads[x];
8611 struct rtp_red *red = rtp->red;
8619 const unsigned char *primary = red->
buf_data;
8622 if (primary[0] == 0x08 || primary[0] == 0x0a || primary[0] == 0x0d) {
8627 if (primary[0] == 0x08 || primary[0] == 0x0a || primary[0] == 0x0d) {
8649 if (rtp->smoother) {
8651 rtp->smoother =
NULL;
8743 struct sockaddr_in suggestion_tmp;
8760 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 8764 dtls_srtp_stop_timeout_timer(instance, rtp, 0);
8766 dtls_srtp_stop_timeout_timer(instance, rtp, 1);
8771 if (rtp->rtcp && rtp->rtcp->schedid > -1) {
8778 rtp->rtcp->schedid = -1;
8781 if (rtp->transport_wide_cc.schedid > -1) {
8783 if (!
ast_sched_del(rtp->sched, rtp->transport_wide_cc.schedid)) {
8787 rtp->transport_wide_cc.schedid = -1;
8818 unsigned int *rtpheader;
8820 int res, payload = 0;
8834 level = 127 - (level & 0x7f);
8839 rtpheader = (
unsigned int *)data;
8840 rtpheader[0] = htonl((2 << 30) | (payload << 16) | (rtp->seqno));
8841 rtpheader[1] = htonl(rtp->
lastts);
8842 rtpheader[2] = htonl(rtp->
ssrc);
8845 res =
rtp_sendto(instance, (
void *) rtpheader, hdrlen + 1, 0, &remote_address, &ice);
8853 ast_verbose(
"Sent Comfort Noise RTP packet to %s%s (type %-2.2d, seq %-6.6d, ts %-6.6u, len %-6.6d)\n",
8855 ice ?
" (via ICE)" :
"",
8856 AST_RTP_CN, rtp->seqno, rtp->lastdigitts, res - hdrlen);
8903 for (index = 0; index <
AST_VECTOR_SIZE(&bundled_rtp->ssrc_mapping); ++index) {
8906 if (mapping->
instance == instance) {
8923 rtp->stream_num = stream_num;
8928 switch (extension) {
8945 if (child_rtp->bundled == parent) {
8950 if (child_rtp->bundled) {
8962 ao2_ref(child_rtp->bundled, -1);
8963 child_rtp->bundled =
NULL;
8978 child_rtp->bundled =
ao2_bump(parent);
8990 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 8995 dtls_srtp_add_local_ssrc(parent_rtp, parent, 0, child_rtp->
ssrc, 0);
9011 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 9018 #ifdef HAVE_PJPROJECT 9024 ast_debug_dtls(3,
"(%p) DTLS - ast_rtp_activate rtp=%p - setup and perform DTLS'\n", instance, rtp);
9026 dtls_perform_setup(&rtp->dtls);
9027 dtls_perform_handshake(instance, &rtp->dtls, 0);
9030 dtls_perform_setup(&rtp->rtcp->dtls);
9031 dtls_perform_handshake(instance, &rtp->rtcp->dtls, 1);
9041 char *debughost =
NULL;
9042 char *debugport =
NULL;
9045 ast_cli(a->
fd,
"Lookup failed for '%s'\n", arg);
9049 ast_cli(a->
fd,
"RTP Packet Debugging Enabled for address: %s\n",
9058 char *debughost =
NULL;
9059 char *debugport =
NULL;
9062 ast_cli(a->
fd,
"Lookup failed for '%s'\n", arg);
9066 ast_cli(a->
fd,
"RTCP Packet Debugging Enabled for address: %s\n",
9076 e->
command =
"rtp set debug {on|off|ip}";
9078 "Usage: rtp set debug {on|off|ip host[:port]}\n" 9079 " Enable/Disable dumping of all RTP packets. If 'ip' is\n" 9080 " specified, limit the dumped packets to those to and from\n" 9081 " the specified 'host' with optional port.\n";
9088 if (!strncasecmp(a->
argv[e->
args-1],
"on", 2)) {
9091 ast_cli(a->
fd,
"RTP Packet Debugging Enabled\n");
9093 }
else if (!strncasecmp(a->
argv[e->
args-1],
"off", 3)) {
9095 ast_cli(a->
fd,
"RTP Packet Debugging Disabled\n");
9098 }
else if (a->
argc == e->
args +1) {
9110 e->
command =
"rtp show settings";
9112 "Usage: rtp show settings\n" 9113 " Display RTP configuration settings\n";
9123 ast_cli(a->
fd,
"\n\nGeneral Settings:\n");
9138 #ifdef HAVE_PJPROJECT 9149 e->
command =
"rtcp set debug {on|off|ip}";
9151 "Usage: rtcp set debug {on|off|ip host[:port]}\n" 9152 " Enable/Disable dumping of all RTCP packets. If 'ip' is\n" 9153 " specified, limit the dumped packets to those to and from\n" 9154 " the specified 'host' with optional port.\n";
9161 if (!strncasecmp(a->
argv[e->
args-1],
"on", 2)) {
9164 ast_cli(a->
fd,
"RTCP Packet Debugging Enabled\n");
9166 }
else if (!strncasecmp(a->
argv[e->
args-1],
"off", 3)) {
9168 ast_cli(a->
fd,
"RTCP Packet Debugging Disabled\n");
9171 }
else if (a->
argc == e->
args +1) {
9182 e->
command =
"rtcp set stats {on|off}";
9184 "Usage: rtcp set stats {on|off}\n" 9185 " Enable/Disable dumping of RTCP stats.\n";
9194 if (!strncasecmp(a->
argv[e->
args-1],
"on", 2))
9196 else if (!strncasecmp(a->
argv[e->
args-1],
"off", 3))
9210 !strcasecmp(a->
argv[index - 1],
"random");
9215 static const char *
const completions_2[] = {
"stop",
"<N>",
NULL };
9216 static const char *
const completions_3[] = {
"random",
"incoming packets",
NULL };
9217 static const char *
const completions_5[] = {
"on",
"every",
NULL };
9218 static const char *
const completions_units[] = {
"random",
"usec",
"msec",
"sec",
"min",
NULL };
9220 unsigned int use_random_num = 0;
9221 unsigned int use_random_interval = 0;
9222 unsigned int num_to_drop = 0;
9223 unsigned int interval = 0;
9224 const char *interval_s =
NULL;
9225 const char *unit_s =
NULL;
9227 const char *addr_s =
NULL;
9233 "Usage: rtp drop [stop|[<N> [random] incoming packets[ every <N> [random] {usec|msec|sec|min}][ on <ip[:port]>]]\n" 9234 " Drop RTP incoming packets.\n";
9238 use_random_interval =
use_random(a, a->
pos, 8 + use_random_num) ||
9241 switch (a->
pos - use_random_num - use_random_interval) {
9249 if (!strcasecmp(a->
argv[a->
pos - 2],
"on")) {
9255 if (!strcasecmp(a->
argv[a->
pos - 2 - use_random_interval],
"every")) {
9260 if (!strcasecmp(a->
argv[a->
pos - 3 - use_random_interval],
"every")) {
9274 use_random_interval =
use_random(a, a->
argc, 8 + use_random_num) ||
9277 if (!strcasecmp(a->
argv[2],
"stop")) {
9279 }
else if (a->
argc < 5) {
9282 ast_cli(a->
fd,
"%s is not a valid number of packets to drop\n", a->
argv[2]);
9284 }
else if (a->
argc - use_random_num == 5) {
9286 }
else if (a->
argc - use_random_num >= 7 && !strcasecmp(a->
argv[5 + use_random_num],
"on")) {
9288 addr_s = a->
argv[6 + use_random_num];
9289 if (a->
argc - use_random_num - use_random_interval == 10 &&
9290 !strcasecmp(a->
argv[7 + use_random_num],
"every")) {
9292 interval_s = a->
argv[8 + use_random_num];
9293 unit_s = a->
argv[9 + use_random_num + use_random_interval];
9295 }
else if (a->
argc - use_random_num >= 8 && !strcasecmp(a->
argv[5 + use_random_num],
"every")) {
9297 interval_s = a->
argv[6 + use_random_num];
9298 unit_s = a->
argv[7 + use_random_num + use_random_interval];
9299 if (a->
argc == 10 + use_random_num + use_random_interval &&
9300 !strcasecmp(a->
argv[8 + use_random_num + use_random_interval],
"on")) {
9302 addr_s = a->
argv[9 + use_random_num + use_random_interval];
9308 if (a->
argc - use_random_num >= 8 && !interval_s && !addr_s) {
9313 ast_cli(a->
fd,
"%s is not a valid interval number\n", interval_s);
9317 memset(&addr, 0,
sizeof(addr));
9319 ast_cli(a->
fd,
"%s is not a valid hostname[:port]\n", addr_s);
9352 #ifdef HAVE_PJPROJECT 9355 int acl_subscription_flag = 0;
9384 #ifdef HAVE_PJPROJECT 9395 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 9427 ast_log(
LOG_WARNING,
"Disabling RTP checksums is not supported on this operating system!\n");
9433 ast_log(
LOG_WARNING,
"DTMF timeout of '%d' outside range, using default of '%d' instead\n",
9441 }
else if (!strcasecmp(s,
"seqno")) {
9449 ast_log(
LOG_WARNING,
"Value for 'probation' could not be read, using default of '%d' instead\n",
9458 #ifdef HAVE_PJPROJECT 9472 struct sockaddr_in addr;
9493 unsigned int include_local_address = 0;
9504 sep = strchr(var->
value,
',');
9509 include_local_address = strcmp(sep,
"include_local_address") == 0;
9517 if (!(candidate =
ast_calloc(1,
sizeof(*candidate)))) {
9538 const char* sense =
NULL;
9540 if (strncasecmp(var->
name,
"ice_", 4) == 0) {
9541 sense = var->
name + 4;
9543 }
else if (strncasecmp(var->
name,
"stun_", 5) == 0) {
9544 sense = var->
name + 5;
9550 if (strcasecmp(sense,
"blacklist") == 0) {
9554 if (strcasecmp(sense,
"acl") && strcasecmp(sense,
"permit") && strcasecmp(sense,
"deny")) {
9563 if (acl_subscription_flag && !acl_change_sub) {
9567 }
else if (!acl_subscription_flag && acl_change_sub) {
9571 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) 9573 if ((sscanf(s,
"%d", &dtls_mtu) != 1) || dtls_mtu < 256) {
9574 ast_log(
LOG_WARNING,
"Value for 'dtls_mtu' could not be read, using default of '%d' instead\n",
9598 #ifdef HAVE_PJPROJECT 9626 #ifdef HAVE_PJPROJECT 9632 if (pj_init() != PJ_SUCCESS) {
9636 if (pjlib_util_init() != PJ_SUCCESS) {
9641 if (pjnath_init() != PJ_SUCCESS) {
9650 if (pj_timer_heap_create(
pool, 100, &
timer_heap) != PJ_SUCCESS) {
9655 if (pj_lock_create_recursive_mutex(
pool,
"rtp%p", &lock) != PJ_SUCCESS) {
9660 pj_timer_heap_set_lock(
timer_heap, lock, PJ_TRUE);
9669 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) && defined(HAVE_OPENSSL_BIO_METHOD) 9670 dtls_bio_methods = BIO_meth_new(BIO_TYPE_BIO,
"rtp write");
9671 if (!dtls_bio_methods) {
9672 #ifdef HAVE_PJPROJECT 9677 BIO_meth_set_write(dtls_bio_methods, dtls_bio_write);
9678 BIO_meth_set_ctrl(dtls_bio_methods, dtls_bio_ctrl);
9679 BIO_meth_set_create(dtls_bio_methods, dtls_bio_new);
9680 BIO_meth_set_destroy(dtls_bio_methods, dtls_bio_free);
9684 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) && defined(HAVE_OPENSSL_BIO_METHOD) 9685 BIO_meth_free(dtls_bio_methods);
9687 #ifdef HAVE_PJPROJECT 9694 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) && defined(HAVE_OPENSSL_BIO_METHOD) 9695 BIO_meth_free(dtls_bio_methods);
9697 #ifdef HAVE_PJPROJECT 9714 #if defined(HAVE_OPENSSL) && (OPENSSL_VERSION_NUMBER >= 0x10001000L) && !defined(OPENSSL_NO_SRTP) && defined(HAVE_OPENSSL_BIO_METHOD) 9715 if (dtls_bio_methods) {
9716 BIO_meth_free(dtls_bio_methods);
9720 #ifdef HAVE_PJPROJECT 9740 .requires =
"res_pjproject",
static int ast_rtp_new(struct ast_rtp_instance *instance, struct ast_sched_context *sched, struct ast_sockaddr *addr, void *data)
struct ast_sockaddr local
static struct ast_rtp_instance * rtp_find_instance_by_media_source_ssrc(struct ast_rtp_instance *instance, struct ast_rtp *rtp, unsigned int ssrc)
#define AST_VECTOR_FREE(vec)
Deallocates this vector.
struct stasis_message_type * ast_rtp_rtcp_sent_type(void)
Message type for an RTCP message sent from this Asterisk instance.
struct ast_variable * next
struct ast_rtp_instance * instance
The RTP instance this SSRC belongs to.
#define AST_THREADSTORAGE(name)
Define a thread storage variable.
double local_normdevrxploss
#define RTCP_FB_REMB_BLOCK_WORD_LENGTH
static int rtp_learning_rtp_seq_update(struct rtp_learning_info *info, uint16_t seq)
#define ast_debug_category(sublevel, ids,...)
Log for a debug category.
An object that represents data sent during a SR/RR RTCP report.
static int rtp_reload(int reload, int by_external_config)
#define DEFAULT_STRICT_RTP
#define ast_rwlock_rdlock(a)
static void statistics(void)
static void rtp_transport_wide_cc_feedback_status_vector_append(unsigned char *rtcpheader, int *packet_len, int *status_vector_chunk_bits, uint16_t *status_vector_chunk, int status)
Main Channel structure associated with a channel.
Structure used for mapping an incoming SSRC to an RTP instance.
double reported_stdev_jitter
static void ast_rtp_ice_start(struct ast_rtp_instance *instance)
#define AST_CLI_DEFINE(fn, txt,...)
#define ast_frdup(fr)
Copies a frame.
#define AST_VECTOR_ADD_SORTED(vec, elem, cmp)
Add an element into a sorted vector.
ssize_t ast_sendto(int sockfd, const void *buf, size_t len, int flags, const struct ast_sockaddr *dest_addr)
Wrapper around sendto(2) that uses ast_sockaddr.
ast_rtp_dtls_verify
DTLS verification settings.
double reported_stdev_lost
static size_t get_recv_buffer_max(struct ast_rtp_instance *instance)
int(* set_configuration)(struct ast_rtp_instance *instance, const struct ast_rtp_dtls_cfg *dtls_cfg)
#define AST_LIST_LOCK(head)
Locks a list.
struct ast_rtp_payload_type * ast_rtp_codecs_get_payload(struct ast_rtp_codecs *codecs, int payload)
Retrieve rx payload mapped information by payload type.
List of ICE host candidate mappings.
Asterisk locking-related definitions:
#define AST_RTP_STAT_STRCPY(current_stat, combined, placement, value)
#define FLAG_3389_WARNING
Asterisk main include file. File version handling, generic pbx functions.
Data buffer containing fixed number of data payloads.
#define AST_LIST_FIRST(head)
Returns the first entry contained in a list.
#define ast_rtp_engine_register(engine)
#define DEFAULT_SRTP_REPLAY_PROTECTION
static int ast_rtp_dtmf_compatible(struct ast_channel *chan0, struct ast_rtp_instance *instance0, struct ast_channel *chan1, struct ast_rtp_instance *instance1)
int ao2_container_count(struct ao2_container *c)
Returns the number of elements in a container.
#define RTCP_HEADER_SSRC_LENGTH
void ast_pjproject_caching_pool_destroy(pj_caching_pool *cp)
Destroy caching pool factory and all cached pools.
ast_suseconds_t ast_time_tv_to_usec(const struct timeval *tv)
Convert a timeval structure to microseconds.
struct ast_data_buffer * ast_data_buffer_alloc(ast_data_buffer_free_callback free_fn, size_t size)
Allocate a data buffer.
static int ast_rtcp_generate_compound_prefix(struct ast_rtp_instance *instance, unsigned char *rtcpheader, struct ast_rtp_rtcp_report *report, int *sr)
static void process_dtmf_rfc2833(struct ast_rtp_instance *instance, unsigned char *data, int len, unsigned int seqno, unsigned int timestamp, int payloadtype, int mark, struct frame_list *frames)
static int ast_rtcp_generate_nack(struct ast_rtp_instance *instance, unsigned char *rtcpheader)
void * ast_data_buffer_remove(struct ast_data_buffer *buffer, size_t pos)
Remove a data payload from the data buffer.
void * ast_threadstorage_get(struct ast_threadstorage *ts, size_t init_size)
Retrieve thread storage.
struct ast_json * ast_json_pack(char const *format,...)
Helper for creating complex JSON values.
int ast_rtp_instance_extmap_get_id(struct ast_rtp_instance *instance, enum ast_rtp_extension extension)
Retrieve the id for an RTP extension.
static struct ast_sched_context * sched
#define ast_smoother_feed(s, f)
Security Event Reporting API.
struct ast_smoother * ast_smoother_new(int bytes)
unsigned int lastovidtimestamp
static const char * rtcp_payload_type2str(unsigned int pt)
static void rtp_write_rtcp_fir(struct ast_rtp_instance *instance, struct ast_rtp *rtp, struct ast_sockaddr *remote_address)
#define AST_RWLIST_HEAD_STATIC(name, type)
Defines a structure to be used to hold a read/write list of specified type, statically initialized...
static void rtp_instance_parse_extmap_extensions(struct ast_rtp_instance *instance, struct ast_rtp *rtp, unsigned char *extension, int len)
unsigned int highest_seq_no
static pj_turn_sock_cb ast_rtp_turn_rtcp_sock_cb
static char * handle_cli_rtp_drop_incoming_packets(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static int ast_rtp_dtmf_end_with_duration(struct ast_rtp_instance *instance, char digit, unsigned int duration)
unsigned int rxjitter_count
unsigned int lastotexttimestamp
int ast_sockaddr_parse(struct ast_sockaddr *addr, const char *str, int flags)
Parse an IPv4 or IPv6 address string.
static int rtp_raw_write(struct ast_rtp_instance *instance, struct ast_frame *frame, int codec)
#define RTCP_REPORT_COUNT_SHIFT
Structure for storing RTP packets for retransmission.
double remote_normdevjitter
#define AST_VECTOR_REMOVE_CMP_UNORDERED(vec, value, cmp, cleanup)
Remove an element from a vector that matches the given comparison.
int ast_find_ourip(struct ast_sockaddr *ourip, const struct ast_sockaddr *bindaddr, int family)
Find our IP address.
#define AST_RTP_RTCP_FMT_NACK
int ast_cli_unregister_multiple(struct ast_cli_entry *e, int len)
Unregister multiple commands.
#define ast_test_flag(p, flag)
#define DEFAULT_TURN_PORT
Statistics information (used for transport-cc)
struct ast_variable * ast_variable_browse(const struct ast_config *config, const char *category_name)
static void rtp_learning_seq_init(struct rtp_learning_info *info, uint16_t seq)
struct stasis_topic * ast_security_topic(void)
A stasis_topic which publishes messages for security related issues.
#define DEFAULT_DTMF_TIMEOUT
static void ast_sockaddr_copy(struct ast_sockaddr *dst, const struct ast_sockaddr *src)
Copies the data from one ast_sockaddr to another.
static struct ast_rtp_instance * __rtp_find_instance_by_ssrc(struct ast_rtp_instance *instance, struct ast_rtp *rtp, unsigned int ssrc, int source)
static int ast_rtcp_write(const void *data)
Write a RTCP packet to the far end.
void ast_json_unref(struct ast_json *value)
Decrease refcount on value. If refcount reaches zero, value is freed.
static int ast_rtp_fd(struct ast_rtp_instance *instance, int rtcp)
static int compare_by_value(int elem, int value)
Helper function to compare an elem in a vector by value.
#define AST_RTP_RTCP_FMT_PLI
int ast_debug_category_set_sublevel(const char *name, int sublevel)
Set the debug category's sublevel.
#define MISSING_SEQNOS_ADDED_TRIGGER
#define AST_RWLIST_WRLOCK(head)
Write locks a list.
static int rtp_transport_wide_cc_feedback_produce(const void *data)
RTP learning mode tracking information.
#define AST_DEBUG_CATEGORY_STUN
static int ast_rtp_dtmf_begin(struct ast_rtp_instance *instance, char digit)
#define ast_set_flag(p, flag)
static void set_rtp_rtcp_schedid(struct ast_rtp_instance *instance, int id)
unsigned int rxlost_count
Structure which contains ioqueue thread information.
unsigned int include_local
struct ast_rtp_codecs * ast_rtp_instance_get_codecs(struct ast_rtp_instance *instance)
Get the codecs structure of an RTP instance.
descriptor for a cli entry.
Packet statistics (used for transport-cc)
#define AST_LIST_UNLOCK(head)
Attempts to unlock a list.
struct ast_rtp_engine_test * ast_rtp_instance_get_test(struct ast_rtp_instance *instance)
Obtain a pointer to the test callbacks on an RTP instance.
double reported_minjitter
double remote_stdevjitter
#define ast_socket_nonblock(domain, type, protocol)
Create a non-blocking socket.
static void rtp_instance_unlock(struct ast_rtp_instance *instance)
#define RTP_DTLS_ESTABLISHED
struct ast_srtp_policy *(* alloc)(void)
#define CONFIG_STATUS_FILEINVALID
static int rtp_allocate_transport(struct ast_rtp_instance *instance, struct ast_rtp *rtp)
static void ast2pj_rtp_ice_role(enum ast_rtp_ice_role ast_role, enum pj_ice_sess_role *pj_role)
static pj_caching_pool cachingpool
Pool factory used by pjlib to allocate memory.
int ast_sockaddr_ipv4_mapped(const struct ast_sockaddr *addr, struct ast_sockaddr *ast_mapped)
Convert an IPv4-mapped IPv6 address into an IPv4 address.
#define AST_RWLIST_UNLOCK(head)
Attempts to unlock a read/write based list.
static pj_turn_sock_cb ast_rtp_turn_rtp_sock_cb
#define RTCP_SR_BLOCK_WORD_LENGTH
#define ao2_container_alloc_list(ao2_options, container_options, sort_fn, cmp_fn)
int ast_sockaddr_to_pj_sockaddr(const struct ast_sockaddr *addr, pj_sockaddr *pjaddr)
Fill a pj_sockaddr from an ast_sockaddr.
#define SSL_CTRL_SET_ECDH_AUTO
const char * ast_codec_media_type2str(enum ast_media_type type)
Conversion function to take a media type and turn it into a string.
struct ast_config * ast_config_load2(const char *filename, const char *who_asked, struct ast_flags flags)
Load a config file.
Structure for variables, used for configurations and for channel variables.
static void rtp_learning_start(struct ast_rtp *rtp)
Start the strictrtp learning mode.
static pj_pool_t * pool
Global memory pool for configuration and timers.
#define AST_VECTOR_APPEND(vec, elem)
Append an element to a vector, growing the vector if needed.
#define RTCP_MIN_INTERVALMS
static void put_unaligned_uint16(void *p, unsigned short datum)
struct timeval ast_time_create_by_unit_str(unsigned long val, const char *unit)
Convert the given unit value, and create a timeval object from it.
static int __rtp_recvfrom(struct ast_rtp_instance *instance, void *buf, size_t size, int flags, struct ast_sockaddr *sa, int rtcp)
static void ice_wrap_dtor(void *vdoomed)
ao2 ICE wrapper object destructor.
Universally unique identifier support.
int ast_tvzero(const struct timeval t)
Returns true if the argument is 0,0.
int terminate
Termination request.
unsigned short reception_report_count
An object that represents data received in a feedback report.
#define AST_LIST_NEXT(elm, field)
Returns the next entry in the list after the given entry.
static int ioqueue_worker_thread(void *data)
Worker thread for ioqueue and timerheap.
struct ast_rtp_rtcp_report_block * report_block[0]
#define RTCP_PAYLOAD_TYPE_MASK
static void put_unaligned_uint32(void *p, unsigned int datum)
static void timeval2ntp(struct timeval tv, unsigned int *msw, unsigned int *lsw)
struct stasis_message_type * stasis_message_type(const struct stasis_message *msg)
Get the message type for a stasis_message.
static int stun_software_attribute
int stasis_subscription_set_filter(struct stasis_subscription *subscription, enum stasis_subscription_message_filter filter)
Set the message type filtering level on a subscription.
struct stasis_message_type * ast_named_acl_change_type(void)
a stasis_message_type for changes against a named ACL or the set of all named ACLs ...
static struct ast_rtp_instance * rtp_find_instance_by_packet_source_ssrc(struct ast_rtp_instance *instance, struct ast_rtp *rtp, unsigned int ssrc)
static void ast_rtp_on_turn_rtp_state(pj_turn_sock *turn_sock, pj_turn_state_t old_state, pj_turn_state_t new_state)
#define AST_SCHED_DEL_UNREF(sched, id, refcall)
schedule task to get deleted and call unref function
#define MAXIMUM_RTP_SEND_BUFFER_SIZE
unsigned int reported_jitter
static pj_ice_sess_cb ast_rtp_ice_sess_cb
#define ast_cond_init(cond, attr)
#define ast_cli_register_multiple(e, len)
Register multiple commands.
void ao2_iterator_destroy(struct ao2_iterator *iter)
Destroy a container iterator.
struct ast_srtp * ast_rtp_instance_get_srtp(struct ast_rtp_instance *instance, int rtcp)
Obtain the SRTP instance associated with an RTP instance.
static void ast_rtp_on_ice_rx_data(pj_ice_sess *ice, unsigned comp_id, unsigned transport_id, void *pkt, pj_size_t size, const pj_sockaddr_t *src_addr, unsigned src_addr_len)
struct timeval ast_tvnow(void)
Returns current timeval. Meant to replace calls to gettimeofday().
ast_rtp_extension
Known RTP extensions.
A report block within a SR/RR report.
static struct ast_frame * create_dtmf_frame(struct ast_rtp_instance *instance, enum ast_frame_type type, int compensate)
static struct ast_frame * ast_rtp_interpret(struct ast_rtp_instance *instance, struct ast_srtp *srtp, const struct ast_sockaddr *remote_address, unsigned char *read_area, int length, int prev_seqno, unsigned int bundled)
Wrapper for an ast_acl linked list.
#define SSRC_MAPPING_ELEM_CMP(elem, value)
SSRC mapping comparator for AST_VECTOR_REMOVE_CMP_UNORDERED()
#define ao2_alloc_options(data_size, destructor_fn, options)
static const char * ast_rtp_ice_get_ufrag(struct ast_rtp_instance *instance)
void ast_rtp_instance_set_last_tx(struct ast_rtp_instance *rtp, time_t time)
Set the last RTP transmission time.
int64_t ast_tvdiff_ms(struct timeval end, struct timeval start)
Computes the difference (in milliseconds) between two struct timeval instances.
void ast_verbose(const char *fmt,...)
static char * rtcp_do_debug_ip(struct ast_cli_args *a)
#define ast_strdup(str)
A wrapper for strdup()
int(* set_master_key)(struct ast_srtp_policy *policy, const unsigned char *key, size_t key_len, const unsigned char *salt, size_t salt_len)
static void rtp_deallocate_transport(struct ast_rtp_instance *instance, struct ast_rtp *rtp)
struct ast_rtp_rtcp_feedback_remb remb
static int timer_worker_thread(void *data)
Worker thread for timerheap.
void ast_frame_free(struct ast_frame *fr, int cache)
Requests a frame to be allocated.
#define TRANSPORT_TURN_RTP
int ast_sockaddr_cmp(const struct ast_sockaddr *a, const struct ast_sockaddr *b)
Compares two ast_sockaddr structures.
static struct ast_codec t140red
static void calc_mean_and_standard_deviation(double new_sample, double *mean, double *std_dev, unsigned int *count)
unsigned int rtp_timestamp
void ast_cli(int fd, const char *fmt,...)
static int ast_rtp_qos_set(struct ast_rtp_instance *instance, int tos, int cos, const char *desc)
enum ast_acl_sense ast_apply_acl_nolog(struct ast_acl_list *acl_list, const struct ast_sockaddr *addr)
Apply a set of rules to a given IP address, don't log failure.
int ast_rtp_instance_add_srtp_policy(struct ast_rtp_instance *instance, struct ast_srtp_policy *remote_policy, struct ast_srtp_policy *local_policy, int rtcp)
Add or replace the SRTP policies for the given RTP instance.
#define AST_LIST_REMOVE(head, elm, field)
Removes a specific entry from a list.
static void ast_rtp_update_source(struct ast_rtp_instance *instance)
#define ast_rwlock_unlock(a)
int(* set_suite)(struct ast_srtp_policy *policy, enum ast_srtp_suite suite)
int ast_stun_handle_packet(int s, struct sockaddr_in *src, unsigned char *data, size_t len, stun_cb_f *stun_cb, void *arg)
handle an incoming STUN message.
Structure for an ICE candidate.
void ast_free_ptr(void *ptr)
free() wrapper
static int ast_rtp_destroy(struct ast_rtp_instance *instance)
Socket address structure.
#define ast_cond_signal(cond)
Asterisk internal frame definitions.
static struct ast_str * password
int ast_bind(int sockfd, const struct ast_sockaddr *addr)
Wrapper around bind(2) that uses struct ast_sockaddr.
static void rtp_transport_wide_cc_feedback_status_append(unsigned char *rtcpheader, int *packet_len, int *status_vector_chunk_bits, uint16_t *status_vector_chunk, int *run_length_chunk_count, int *run_length_chunk_status, int status)
#define ast_verb(level,...)
int ast_sockaddr_cmp_addr(const struct ast_sockaddr *a, const struct ast_sockaddr *b)
Compares the addresses of two ast_sockaddr structures.
static void rtp_write_rtcp_psfb(struct ast_rtp_instance *instance, struct ast_rtp *rtp, struct ast_frame *frame, struct ast_sockaddr *remote_address)
unsigned int expected_prior
static void ast_rtp_stun_request(struct ast_rtp_instance *instance, struct ast_sockaddr *suggestion, const char *username)
#define RTCP_MAX_INTERVALMS
int ast_rtp_codecs_payload_code_tx(struct ast_rtp_codecs *codecs, int asterisk_format, const struct ast_format *format, int code)
Retrieve a tx mapped payload type based on whether it is an Asterisk format and the code...
struct ast_rtp_rtcp_report::@315 sender_information
static char * handle_cli_rtp_set_debug(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
unsigned int ast_rtp_codecs_get_framing(struct ast_rtp_codecs *codecs)
Get the framing used for a set of codecs.
static void ast_rtp_ice_stop(struct ast_rtp_instance *instance)
static int rtcp_recvfrom(struct ast_rtp_instance *instance, void *buf, size_t size, int flags, struct ast_sockaddr *sa)
struct stasis_message_type * ast_rtp_rtcp_received_type(void)
Message type for an RTCP message received from some external source.
struct ast_frame_subclass subclass
static struct ast_sockaddr lo6
static void pj_thread_register_check(void)
Function used to check if the calling thread is registered with pjlib. If it is not it will be regist...
pj_thread_t * thread
The thread handling the queue and timer heap.
static void acl_change_stasis_cb(void *data, struct stasis_subscription *sub, struct stasis_message *message)
const char * ast_rtp_instance_get_channel_id(struct ast_rtp_instance *instance)
Get the unique ID of the channel that owns this RTP instance.
static void ast_sockaddr_setnull(struct ast_sockaddr *addr)
Sets address addr to null.
#define ast_debug_dtls_packet_is_allowed
int args
This gets set in ast_cli_register()
static int ast_rtp_dtmf_mode_set(struct ast_rtp_instance *instance, enum ast_rtp_dtmf_mode dtmf_mode)
pthread_cond_t ast_cond_t
#define ast_strlen_zero(foo)
#define TRANSPORT_TURN_RTCP
static int rtp_red_buffer(struct ast_rtp_instance *instance, struct ast_frame *frame)
int ast_data_buffer_put(struct ast_data_buffer *buffer, size_t pos, void *payload)
Place a data payload at a position in the data buffer.
char * ast_cli_complete(const char *word, const char *const choices[], int pos)
#define AST_RED_MAX_GENERATION
int(* change_source)(struct ast_srtp *srtp, unsigned int from_ssrc, unsigned int to_ssrc)
static int ast_sockaddr_isnull(const struct ast_sockaddr *addr)
Checks if the ast_sockaddr is null. "null" in this sense essentially means uninitialized, or having a 0 length.
static int ast_rtp_extension_enable(struct ast_rtp_instance *instance, enum ast_rtp_extension extension)
static int rtp_transport_wide_cc_packet_statistics_cmp(struct rtp_transport_wide_cc_packet_statistics a, struct rtp_transport_wide_cc_packet_statistics b)
#define ast_sockaddr_port(addr)
Get the port number of a socket address.
enum ast_rtp_ice_candidate_type type
unsigned char rawdata[8192+AST_FRIENDLY_OFFSET]
void * ao2_object_get_lockaddr(void *obj)
Return the mutex lock address of an object.
void timersub(struct timeval *tvend, struct timeval *tvstart, struct timeval *tvdiff)
Configuration File Parser.
static const char * ast_rtp_ice_get_password(struct ast_rtp_instance *instance)
#define AST_RWLIST_RDLOCK(head)
Read locks a list.
static void ast_rtp_on_ice_complete(pj_ice_sess *ice, pj_status_t status)
void ast_smoother_free(struct ast_smoother *s)
static void ast_rtp_on_turn_rx_rtp_data(pj_turn_sock *turn_sock, void *pkt, unsigned pkt_len, const pj_sockaddr_t *peer_addr, unsigned addr_len)
int ast_ouraddrfor(const struct ast_sockaddr *them, struct ast_sockaddr *us)
Get our local IP address when contacting a remote host.
static int rtp_debug_test_addr(struct ast_sockaddr *addr)
#define ast_debug(level,...)
Log a DEBUG message.
Handle unaligned data access.
int ast_sockaddr_is_any(const struct ast_sockaddr *addr)
Determine if the address type is unspecified, or "any" address.
#define RTCP_LENGTH_SHIFT
struct ast_srtp_res * res_srtp
static struct sockaddr_in stunaddr
char cname[AST_UUID_STR_LEN]
static void update_lost_stats(struct ast_rtp *rtp, unsigned int lost_packets)
void(* set_ssrc)(struct ast_srtp_policy *policy, unsigned long ssrc, int inbound)
#define AST_VECTOR_INIT(vec, size)
Initialize a vector.
int ast_sockaddr_split_hostport(char *str, char **host, char **port, int flags)
Splits a string into its host and port components.
#define FLAG_NAT_INACTIVE_NOWARN
General Asterisk PBX channel definitions.
static const int STANDARD_STUN_PORT
static struct ast_rtp_engine_ice ast_rtp_ice
#define AST_VECTOR_GET_ADDR(vec, idx)
Get an address of element in a vector.
#define AST_SCHED_DEL(sched, id)
Remove a scheduler entry.
double accumulated_transit
#define AST_FRIENDLY_OFFSET
Offset into a frame's data buffer.
#define ast_sockaddr_from_sin(addr, sin)
Converts a struct sockaddr_in to a struct ast_sockaddr.
int ast_rtp_engine_unregister(struct ast_rtp_engine *engine)
Unregister an RTP engine.
void ast_rtp_instance_set_data(struct ast_rtp_instance *instance, void *data)
Set the data portion of an RTP instance.
#define AST_VECTOR_ELEM_CLEANUP_NOOP(elem)
Vector element cleanup that does nothing.
#define RAII_VAR(vartype, varname, initval, dtor)
Declare a variable that will call a destructor function when it goes out of scope.
static void ast_rtp_ice_candidate_destroy(void *obj)
Destructor for locally created ICE candidates.
static int ice_reset_session(struct ast_rtp_instance *instance)
#define ast_debug_rtp(sublevel,...)
Log debug level RTP information.
double reported_normdev_lost
int ast_stun_request(int s, struct sockaddr_in *dst, const char *username, struct sockaddr_in *answer)
Generic STUN request.
static int update_rtt_stats(struct ast_rtp *rtp, unsigned int lsr, unsigned int dlsr)
#define AST_RWLOCK_INIT_VALUE
ast_rtp_ice_role
ICE role during negotiation.
Access Control of various sorts.
static struct ao2_container * codecs
Registered codecs.
unsigned int use_random_interval
static struct ast_sockaddr rtpdebugaddr
static void rtp_add_candidates_to_ice(struct ast_rtp_instance *instance, struct ast_rtp *rtp, struct ast_sockaddr *addr, int port, int component, int transport)
static char * handle_cli_rtcp_set_stats(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static int unload_module(void)
static int ast_rtp_write(struct ast_rtp_instance *instance, struct ast_frame *frame)
#define AST_SMOOTHER_FLAG_FORCED
static size_t get_recv_buffer_count(struct ast_rtp_instance *instance)
structure to hold extensions
Asterisk internal frame definitions.
#define ao2_ref(o, delta)
#define RTCP_PAYLOAD_TYPE_SHIFT
static struct ast_sockaddr rtcpdebugaddr
#define ast_debug_rtcp(sublevel,...)
Log debug level RTCP information.
void ast_config_destroy(struct ast_config *config)
Destroys a config.
#define MAXIMUM_RTP_RECV_BUFFER_SIZE
static void ast_rtp_ice_set_authentication(struct ast_rtp_instance *instance, const char *ufrag, const char *password)
long int ast_random(void)
Conversion utility functions.
char channel_uniqueid[MAX_CHANNEL_ID]
struct timeval ast_samp2tv(unsigned int _nsamp, unsigned int _rate)
Returns a timeval corresponding to the duration of n samples at rate r. Useful to convert samples to ...
ast_rtp_ice_component_type
ICE component types.
static void ast_rtp_ice_change_components(struct ast_rtp_instance *instance, int num_components)
#define AST_RWLIST_REMOVE_CURRENT
#define ast_strdupa(s)
duplicate a string in memory from the stack
static struct ast_acl_list * stun_acl
#define AST_RTP_RTCP_RTPFB
unsigned int ast_codec_samples_count(struct ast_frame *frame)
Get the number of samples contained within a frame.
enum ast_rtp_dtls_hash hash
double local_stdevrxploss
#define ast_malloc(len)
A wrapper for malloc()
#define AST_VECTOR(name, type)
Define a vector structure.
#define AST_LIST_REMOVE_HEAD(head, field)
Removes and returns the head entry from a list.
unsigned int themssrc_valid
static int ast_rtp_dtmf_continuation(struct ast_rtp_instance *instance)
#define FLAG_NEED_MARKER_BIT
void * ast_data_buffer_get(const struct ast_data_buffer *buffer, size_t pos)
Retrieve a data payload from the data buffer.
static void drop_packets_data_update(struct timeval tv)
static struct ast_acl_list * ice_acl
AST_LIST_HEAD_NOLOCK(contactliststruct, contact)
#define DEFAULT_LEARNING_MIN_DURATION
void ast_rtp_publish_rtcp_message(struct ast_rtp_instance *rtp, struct stasis_message_type *message_type, struct ast_rtp_rtcp_report *report, struct ast_json *blob)
Publish an RTCP message to Stasis Message Bus API.
unsigned int txoctetcount
static void ast_rtp_stop(struct ast_rtp_instance *instance)
#define AST_DEBUG_CATEGORY_ICE
#define STRICT_RTP_LEARN_TIMEOUT
Strict RTP learning timeout time in milliseconds.
struct ast_sockaddr relay_address
Core PBX routines and definitions.
static void rtp_terminate_pjproject(void)
int ast_rtp_get_rate(const struct ast_format *format)
Retrieve the sample rate of a format according to RTP specifications.
double remote_normdevrxploss
struct ast_rtp_rtcp_report * ast_rtp_rtcp_report_alloc(unsigned int report_blocks)
Allocate an ao2 ref counted instance of ast_rtp_rtcp_report.
Structure that represents the optional DTLS SRTP support within an RTP engine.
static int ast_rtp_bundle(struct ast_rtp_instance *child, struct ast_rtp_instance *parent)
#define AST_RWLIST_TRAVERSE_SAFE_BEGIN
static struct ast_frame * ast_rtcp_interpret(struct ast_rtp_instance *instance, struct ast_srtp *srtp, const unsigned char *rtcpdata, size_t size, struct ast_sockaddr *addr)
static pj_status_t ast_rtp_on_ice_tx_pkt(pj_ice_sess *ice, unsigned comp_id, unsigned transport_id, const void *pkt, pj_size_t size, const pj_sockaddr_t *dst_addr, unsigned dst_addr_len)
#define CONFIG_STATUS_FILEUNCHANGED
#define stasis_subscribe(topic, callback, data)
int ast_rtp_instance_set_local_address(struct ast_rtp_instance *instance, const struct ast_sockaddr *address)
Set the address that we are expecting to receive RTP on.
#define AST_LIST_HEAD_STATIC(name, type)
Defines a structure to be used to hold a list of specified type, statically initialized.
#define RTCP_VERSION_SHIFTED
#define ast_test_suite_event_notify(s, f,...)
static int timer_terminate
Used to tell the timer thread to terminate.
void ast_pjproject_caching_pool_init(pj_caching_pool *cp, const pj_pool_factory_policy *policy, pj_size_t max_capacity)
Initialize the caching pool factory.
ast_frame_type
Frame types.
ast_rtp_dtls_setup
DTLS setup types.
#define DEFAULT_LEARNING_MIN_SEQUENTIAL
#define ast_debug_stun(sublevel,...)
Log debug level STUN information.
The AMI - Asterisk Manager Interface - is a TCP protocol created to manage Asterisk with third-party ...
static void calculate_lost_packet_statistics(struct ast_rtp *rtp, unsigned int *lost_packets, int *fraction_lost)
#define AST_LOG_CATEGORY_RTCP_PACKET
static int rtp_recvfrom(struct ast_rtp_instance *instance, void *buf, size_t size, int flags, struct ast_sockaddr *sa)
static void ast_rtp_remote_address_set(struct ast_rtp_instance *instance, struct ast_sockaddr *addr)
static int rtcp_debug_test_addr(struct ast_sockaddr *addr)
#define ast_smoother_feed_be(s, f)
static pj_thread_t * timer_thread
Thread executing the timer heap.
enum ast_rtp_dtls_setup default_setup
#define TURN_STATE_WAIT_TIME
void(* set_authentication)(struct ast_rtp_instance *instance, const char *ufrag, const char *password)
int ast_tvcmp(struct timeval _a, struct timeval _b)
Compres two struct timeval instances returning -1, 0, 1 if the first arg is smaller, equal or greater to the second.
#define AST_LIST_INSERT_TAIL(head, elm, field)
Appends a list entry to the tail of a list.
unsigned int reported_lost_count
#define RTCP_RR_BLOCK_WORD_LENGTH
int attribute_pure ast_true(const char *val)
Make sure something is true. Determine if a string containing a boolean value is "true". This function checks to see whether a string passed to it is an indication of an "true" value. It checks to see if the string is "yes", "true", "y", "t", "on" or "1".
#define DEFAULT_RTP_START
unsigned int reported_lost
static int srtp_replay_protection
unsigned int rxoctetcount
unsigned int received_prior
static void ast_rtp_ice_add_cand(struct ast_rtp_instance *instance, struct ast_rtp *rtp, unsigned comp_id, unsigned transport_id, pj_ice_cand_type type, pj_uint16_t local_pref, const pj_sockaddr_t *addr, const pj_sockaddr_t *base_addr, const pj_sockaddr_t *rel_addr, int addr_len)
enum ast_rtp_dtls_verify verify
static void host_candidate_overrides_clear(void)
Helper function which clears the ICE host candidate mapping.
#define ast_debug_rtcp_packet_is_allowed
#define AST_LOG_CATEGORY_DISABLED
#define ast_sockaddr_set_port(addr, port)
Sets the port number of a socket address.
#define ast_sockaddr_from_sockaddr(addr, sa)
Converts a struct sockaddr to a struct ast_sockaddr.
ast_rtp_dtls_connection
DTLS connection states.
static struct ast_frame * ast_rtp_read(struct ast_rtp_instance *instance, int rtcp)
int ast_set_qos(int sockfd, int tos, int cos, const char *desc)
Set type of service.
static struct stasis_subscription * acl_change_sub
struct ast_acl_list * ast_free_acl_list(struct ast_acl_list *acl)
Free a list of ACLs.
unsigned int use_random_num
static int stun_address_is_blacklisted(const struct ast_sockaddr *addr)
#define ast_rtp_instance_set_remote_address(instance, address)
Set the address of the remote endpoint that we are sending RTP to.
static int len(struct ast_channel *chan, const char *cmd, char *data, char *buf, size_t buflen)
static struct ast_frame * ast_rtcp_read(struct ast_rtp_instance *instance)
enum ast_rtp_ice_component_type id
static ast_rwlock_t ice_acl_lock
unsigned int packet_count
#define AST_PJPROJECT_INIT_LOG_LEVEL()
Get maximum log level pjproject was compiled with.
struct timeval ast_tvadd(struct timeval a, struct timeval b)
Returns the sum of two timevals a + b.
unsigned int ast_rtp_instance_get_ssrc(struct ast_rtp_instance *rtp)
Retrieve the local SSRC value that we will be using.
static enum ast_rtp_dtmf_mode ast_rtp_dtmf_mode_get(struct ast_rtp_instance *instance)
static char * ast_sockaddr_stringify(const struct ast_sockaddr *addr)
Wrapper around ast_sockaddr_stringify_fmt() with default format.
ssize_t ast_recvfrom(int sockfd, void *buf, size_t len, int flags, struct ast_sockaddr *src_addr)
Wrapper around recvfrom(2) that uses struct ast_sockaddr.
#define ast_debug_rtp_packet_is_allowed
char * ast_skip_blanks(const char *str)
Gets a pointer to the first non-whitespace character in a string.
static void rtp_instance_parse_transport_wide_cc(struct ast_rtp_instance *instance, struct ast_rtp *rtp, unsigned char *data, int len)
static const char * ast_rtp_get_cname(struct ast_rtp_instance *instance)
#define ast_strndup(str, len)
A wrapper for strndup()
#define SRTP_MASTER_KEY_LEN
#define RTCP_FB_NACK_BLOCK_WORD_LENGTH
#define ao2_iterator_next(iter)
#define ao2_alloc(data_size, destructor_fn)
static int __rtp_sendto(struct ast_rtp_instance *instance, void *buf, size_t size, int flags, struct ast_sockaddr *sa, int rtcp, int *via_ice, int use_srtp)
pj_ioqueue_t * ioqueue
Ioqueue which polls on sockets.
#define AST_RTP_RTCP_FMT_TRANSPORT_WIDE_CC
ast_rtp_dtls_hash
DTLS fingerprint hashes.
static int should_drop_packets(struct ast_sockaddr *addr)
#define RTCP_REPORT_COUNT_MASK
static int ast_rtp_rtcp_handle_nack(struct ast_rtp_instance *instance, unsigned int *nackdata, unsigned int position, unsigned int length)
static unsigned int calc_txstamp(struct ast_rtp *rtp, struct timeval *delivery)
#define AST_RTP_RTCP_FMT_FIR
#define AST_LIST_TRAVERSE(head, var, field)
Loops over (traverses) the entries in a list.
#define AST_LIST_ENTRY(type)
Declare a forward link structure inside a list entry.
#define AST_LIST_INSERT_HEAD(head, elm, field)
Inserts a list entry at the head of a list.
static int ast_rtp_get_stat(struct ast_rtp_instance *instance, struct ast_rtp_instance_stats *stats, enum ast_rtp_instance_stat stat)
static int ast_rtp_sendcng(struct ast_rtp_instance *instance, int level)
generate comfort noice (CNG)
#define ast_debug_ice(sublevel,...)
Log debug level ICE information.
static char * generate_random_string(char *buf, size_t size)
#define AST_RTP_CISCO_DTMF
static char version[AST_MAX_EXTENSION]
double reported_maxjitter
static void update_address_with_ice_candidate(pj_ice_sess *ice, enum ast_rtp_ice_component_type component, struct ast_sockaddr *cand_address)
Helper function which updates an ast_sockaddr with the candidate used for the component.
static struct ao2_container * ast_rtp_ice_get_local_candidates(struct ast_rtp_instance *instance)
const char * ast_inet_ntoa(struct in_addr ia)
thread-safe replacement for inet_ntoa().
Structure defining an RTCP session.
#define RTCP_DEFAULT_INTERVALMS
static struct ast_frame * process_dtmf_cisco(struct ast_rtp_instance *instance, unsigned char *data, int len, unsigned int seqno, unsigned int timestamp, int payloadtype, int mark)
#define ast_calloc(num, len)
A wrapper for calloc()
#define AST_VECTOR_RESET(vec, cleanup)
Reset vector.
void * ast_rtp_instance_get_data(struct ast_rtp_instance *instance)
Get the data portion of an RTP instance.
enum ast_media_type stream_type
static void destroy(struct ast_trans_pvt *pvt)
static unsigned int ast_rtp_get_ssrc(struct ast_rtp_instance *instance)
int(* unprotect)(struct ast_srtp *srtp, void *buf, int *size, int rtcp)
static struct ast_codec t140
unsigned int frame_ending
#define DEFAULT_RTP_RECV_BUFFER_SIZE
static const char * rtcp_payload_subtype2str(unsigned int pt, unsigned int subtype)
static void calc_rxstamp(struct timeval *tv, struct ast_rtp *rtp, unsigned int timestamp, int mark)
char * ast_uuid_generate_str(char *buf, size_t size)
Generate a UUID string.
int ast_parse_arg(const char *arg, enum ast_parse_flags flags, void *result,...)
The argument parsing routine.
#define AST_DEBUG_CATEGORY_DTLS
static void ast_rtp_set_remote_ssrc(struct ast_rtp_instance *instance, unsigned int ssrc)
struct stasis_subscription * stasis_unsubscribe_and_join(struct stasis_subscription *subscription)
Cancel a subscription, blocking until the last message is processed.
int ast_sched_del(struct ast_sched_context *con, int id) attribute_warn_unused_result
Deletes a scheduled event.
Module has failed to load, may be in an inconsistent state.
#define DTMF_SAMPLE_RATE_MS
static char * handle_cli_rtp_settings(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
static int ast_rtcp_generate_report(struct ast_rtp_instance *instance, unsigned char *rtcpheader, struct ast_rtp_rtcp_report *rtcp_report, int *sr)
static char * rtp_do_debug_ip(struct ast_cli_args *a)
#define ast_frisolate(fr)
Makes a frame independent of any static storage.
#define ao2_find(container, arg, flags)
unsigned int ephemeral_cert
Structure that represents the test functionality for res_rtp_asterisk unit tests. ...
static void ast_rtp_ice_start_media(pj_ice_sess *ice, pj_status_t status)
static int rtp_address_is_ice_blacklisted(const struct ast_sockaddr *address)
int ast_str_to_uint(const char *str, unsigned int *res)
Convert the given string to an unsigned integer.
#define AST_VECTOR_GET_CMP(vec, value, cmp)
Get an element from a vector that matches the given comparison.
int ast_sched_add(struct ast_sched_context *con, int when, ast_sched_cb callback, const void *data) attribute_warn_unused_result
Adds a scheduled event.
static void * cleanup(void *unused)
void ast_rtp_instance_get_local_address(struct ast_rtp_instance *instance, struct ast_sockaddr *address)
Get the local address that we are expecting RTP on.
Structure used to handle boolean flags.
#define DEFAULT_ICESUPPORT
struct ast_rtp_ioqueue_thread * next
#define AST_VECTOR_REMOVE_CMP_ORDERED(vec, value, cmp, cleanup)
Remove an element from a vector that matches the given comparison while maintaining order...
int ast_smoother_test_flag(struct ast_smoother *s, int flag)
#define ast_clear_flag(p, flag)
AST_MODULE_INFO(ASTERISK_GPL_KEY, AST_MODFLAG_GLOBAL_SYMBOLS|AST_MODFLAG_LOAD_ORDER, "HTTP Phone Provisioning",.support_level=AST_MODULE_SUPPORT_EXTENDED,.load=load_module,.unload=unload_module,.reload=reload,.load_pri=AST_MODPRI_CHANNEL_DEPEND,.requires="http",)
static int replace(struct ast_channel *chan, const char *cmd, char *data, struct ast_str **buf, ssize_t len)
struct ast_sockaddr advertised
unsigned int lastsrtxcount
static void ast_rtp_ice_add_remote_candidate(struct ast_rtp_instance *instance, const struct ast_rtp_engine_ice_candidate *candidate)
#define DEFAULT_RTP_SEND_BUFFER_SIZE
static void ast_rtp_change_source(struct ast_rtp_instance *instance)
#define ast_rwlock_wrlock(a)
struct ast_frame ast_null_frame
static int load_module(void)
static int learning_min_duration
#define AST_SMOOTHER_FLAG_BE
const char * ast_variable_retrieve(struct ast_config *config, const char *category, const char *variable)
static struct ast_cli_entry cli_rtp[]
#define ast_debug_dtls(sublevel,...)
Log debug level DTLS information.
static int bridge_p2p_rtp_write(struct ast_rtp_instance *instance, struct ast_rtp_instance *instance1, unsigned int *rtpheader, int len, int hdrlen)
unsigned int lastividtimestamp
static volatile unsigned int seq
static void ntp2timeval(unsigned int msw, unsigned int lsw, struct timeval *tv)
#define AST_RWLIST_INSERT_TAIL
static int ice_candidates_compare(struct ao2_container *left, struct ao2_container *right)
#define AST_LIST_HEAD_INIT_NOLOCK(head)
Initializes a list head structure.
void ast_smoother_set_flags(struct ast_smoother *smoother, int flags)
unsigned char buf_data[64000]
static int rtp_red_init(struct ast_rtp_instance *instance, int buffer_time, int *payloads, int generations)
static void rtp_ioqueue_thread_remove(struct ast_rtp_ioqueue_thread *ioqueue)
Removal function for ioqueue thread, determines if it should be terminated and destroyed.
char * strsep(char **str, const char *delims)
static struct ast_rtp_engine asterisk_rtp_engine
static void pj2ast_rtp_ice_role(enum pj_ice_sess_role pj_role, enum ast_rtp_ice_role *ast_role)
unsigned char len[AST_RED_MAX_GENERATION]
static int reconstruct(int sign, int dqln, int y)
#define ao2_replace(dst, src)
static int ice_create(struct ast_rtp_instance *instance, struct ast_sockaddr *addr, int port, int replace)
When we need to walk through a container, we use an ao2_iterator to keep track of the current positio...
Structure for rwlock and tracking information.
static int rtp_sendto(struct ast_rtp_instance *instance, void *buf, size_t size, int flags, struct ast_sockaddr *sa, int *ice)
Standard Command Line Interface.
struct ast_frame * ast_smoother_read(struct ast_smoother *s)
static void put_unaligned_time24(void *p, uint32_t time_msw, uint32_t time_lsw)
static int ast_rtcp_calculate_sr_rr_statistics(struct ast_rtp_instance *instance, struct ast_rtp_rtcp_report *rtcp_report, struct ast_sockaddr remote_address, int ice, int sr)
static size_t get_send_buffer_count(struct ast_rtp_instance *instance)
static pj_str_t turnpassword
#define FLAG_REQ_LOCAL_BRIDGE_BIT
void ast_copy_string(char *dst, const char *src, size_t size)
Size-limited null-terminating string copy.
void ast_append_acl(const char *sense, const char *stuff, struct ast_acl_list **path, int *error, int *named_acl_flag)
Add a rule to an ACL struct.
#define S_OR(a, b)
returns the equivalent of logic or for strings: first one if not empty, otherwise second one...
struct timeval ast_tv(ast_time_t sec, ast_suseconds_t usec)
Returns a timeval from sec, usec.
#define AST_RTP_STAT_SET(current_stat, combined, placement, value)
size_t ast_data_buffer_count(const struct ast_data_buffer *buffer)
Return the number of payloads in a data buffer.
#define RTCP_VERSION_MASK_SHIFTED
int attribute_pure ast_false(const char *val)
Make sure something is false. Determine if a string containing a boolean value is "false"...
struct ast_rtp_instance * ast_rtp_instance_get_bridged(struct ast_rtp_instance *instance)
Get the other RTP instance that an instance is bridged to.
int(* protect)(struct ast_srtp *srtp, void **buf, int *size, int rtcp)
void ast_rtp_instance_get_requested_target_address(struct ast_rtp_instance *instance, struct ast_sockaddr *address)
Get the requested target address of the remote endpoint.
int ast_rtp_engine_srtp_is_registered(void)
int ast_rtp_instance_get_prop(struct ast_rtp_instance *instance, enum ast_rtp_property property)
Get the value of an RTP instance property.
static unsigned int ast_rtcp_calc_interval(struct ast_rtp *rtp)
Structure which contains ICE host candidate mapping information.
static int learning_min_sequential
static char * handle_cli_rtcp_set_debug(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
#define AST_RTP_STAT_TERMINATOR(combined)
int ast_sockaddr_is_ipv4(const struct ast_sockaddr *addr)
Determine if the address is an IPv4 address.
pj_pool_t * pool
Pool used by the thread.
static struct ast_rtp_ioqueue_thread * rtp_ioqueue_thread_get_or_create(void)
Finder and allocator for an ioqueue thread.
static int ice_candidate_cmp(void *obj, void *arg, int flags)
int stasis_subscription_accept_message_type(struct stasis_subscription *subscription, const struct stasis_message_type *type)
Indicate to a subscription that we are interested in a message type.
struct stasis_forward * sub
static void ast_rtp_prop_set(struct ast_rtp_instance *instance, enum ast_rtp_property property, int value)
static void rtp_ioqueue_thread_destroy(struct ast_rtp_ioqueue_thread *ioqueue)
Destroyer for ioqueue thread.
Data structure associated with a single frame of data.
int ast_rtp_codecs_find_payload_code(struct ast_rtp_codecs *codecs, int payload)
Search for the tx payload type in the ast_rtp_codecs structure.
#define AST_RTP_RTCP_PSFB
enum ast_srtp_suite suite
struct ssl_ctx_st SSL_CTX
double remote_stdevrxploss
static struct ast_threadstorage pj_thread_storage
#define SRTP_MASTER_SALT_LEN
Structure that represents the optional ICE support within an RTP engine.
Abstract JSON element (object, array, string, int, ...).
static void update_jitter_stats(struct ast_rtp *rtp, unsigned int ia_jitter)
Options provided by main asterisk program.
#define TRANSPORT_SOCKET_RTCP
void(* destroy)(struct ast_srtp_policy *policy)
unsigned int ssrc
The received SSRC.
static void ast_rtp_ice_lite(struct ast_rtp_instance *instance)
int error(const char *format,...)
#define ast_frame_byteswap_be(fr)
static int create_new_socket(const char *type, int af)
struct timeval ast_tvsub(struct timeval a, struct timeval b)
Returns the difference of two timevals a - b.
int64_t ast_tvdiff_us(struct timeval end, struct timeval start)
Computes the difference (in microseconds) between two struct timeval instances.
static int rtcp_mux(struct ast_rtp *rtp, const unsigned char *packet)
void ast_rtp_instance_set_prop(struct ast_rtp_instance *instance, enum ast_rtp_property property, int value)
Set the value of an RTP instance property.
static int red_write(const void *data)
Write t140 redundacy frame.
#define ast_sockaddr_to_sin(addr, sin)
Converts a struct ast_sockaddr to a struct sockaddr_in.
union ast_frame::@263 data
ast_media_type
Types of media.
unsigned int reported_jitter_count
static int reload_module(void)
enum ast_frame_type frametype
struct ast_sockaddr address
#define AST_CLI_YESNO(x)
Return Yes or No depending on the argument.
static struct ast_frame * red_t140_to_red(struct rtp_red *red)
#define CALC_LEARNING_MIN_DURATION(count)
Calculate the min learning duration in ms.
double local_normdevjitter
struct timeval ast_time_create_by_unit(unsigned long val, enum TIME_UNIT unit)
Convert the given unit value, and create a timeval object from it.
#define AST_LOG_CATEGORY_RTP_PACKET
#define AST_LOG_CATEGORY_ENABLED
static int ast_rtcp_generate_sdes(struct ast_rtp_instance *instance, unsigned char *rtcpheader, struct ast_rtp_rtcp_report *rtcp_report)
static pj_timer_heap_t * timer_heap
Global timer heap.
struct ast_format * format
static int rtcp_sendto(struct ast_rtp_instance *instance, void *buf, size_t size, int flags, struct ast_sockaddr *sa, int *ice)
void ast_data_buffer_resize(struct ast_data_buffer *buffer, size_t size)
Resize a data buffer.
struct timeval ntp_timestamp
int ast_cli_completion_add(char *value)
Add a result to a request for completion options.
enum ast_media_type ast_rtp_codecs_get_stream_type(struct ast_rtp_codecs *codecs)
Determine the type of RTP stream media from the codecs mapped.
static int ast_rtp_dtmf_end(struct ast_rtp_instance *instance, char digit)
#define MAX_TIMESTAMP_SKEW
static void ast_rtp_set_stream_num(struct ast_rtp_instance *instance, int stream_num)
#define ASTERISK_GPL_KEY
The text the key() function should return.
#define DEBUG_ATLEAST(level)
Pluggable RTP Architecture.
static int find_by_value(int elem, int value)
Helper function to find an elem in a vector by value.
static struct rtp_drop_packets_data drop_packets_data
Asterisk module definitions.
unsigned int count
Current number of descriptors being waited on.
static snd_pcm_format_t format
unsigned int lastitexttimestamp
static struct ast_rtp_engine_test ast_rtp_test
#define ast_rtp_instance_get_remote_address(instance, address)
Get the address of the remote endpoint that we are sending RTP to.
static ast_rwlock_t stun_acl_lock
#define FLAG_NAT_INACTIVE
#define DEFAULT_STUN_SOFTWARE_ATTRIBUTE
const struct ast_channel_tech * ast_channel_tech(const struct ast_channel *chan)
static pj_str_t turnusername
struct ao2_iterator ao2_iterator_init(struct ao2_container *c, int flags) attribute_warn_unused_result
Create an iterator for a container.
#define ast_cond_timedwait(cond, mutex, time)
size_t ast_data_buffer_max(const struct ast_data_buffer *buffer)
Return the maximum number of payloads a data buffer can hold.
static void ast_rtp_on_valid_pair(pj_ice_sess *ice)
#define AST_RWLIST_TRAVERSE_SAFE_END
static void ast_rtp_ice_turn_request(struct ast_rtp_instance *instance, enum ast_rtp_ice_component_type component, enum ast_transport transport, const char *server, unsigned int port, const char *username, const char *password)
int ast_sockaddr_is_ipv6(const struct ast_sockaddr *addr)
Determine if this is an IPv6 address.
#define AST_VECTOR_SIZE(vec)
Get the number of elements in a vector.
int ast_rtp_instance_set_incoming_source_address(struct ast_rtp_instance *instance, const struct ast_sockaddr *address)
Set the incoming source address of the remote endpoint that we are sending RTP to.
static void ast_rtp_on_turn_rx_rtcp_data(pj_turn_sock *turn_sock, void *pkt, unsigned pkt_len, const pj_sockaddr_t *peer_addr, unsigned addr_len)
DTLS configuration structure.
static struct ast_frame * process_cn_rfc3389(struct ast_rtp_instance *instance, unsigned char *data, int len, unsigned int seqno, unsigned int timestamp, int payloadtype, int mark)
static void ast_rtp_on_turn_rtcp_state(pj_turn_sock *turn_sock, pj_turn_state_t old_state, pj_turn_state_t new_state)
static unsigned int use_random(struct ast_cli_args *a, int pos, unsigned int index)
void ast_data_buffer_free(struct ast_data_buffer *buffer)
Free a data buffer (and all held data payloads)
static int ast_rtp_local_bridge(struct ast_rtp_instance *instance0, struct ast_rtp_instance *instance1)
struct ast_srtp_policy_res * res_srtp_policy
#define AST_RTP_RTCP_FMT_REMB
static void rtp_unload_acl(ast_rwlock_t *lock, struct ast_acl_list **acl)
double reported_normdev_jitter
pj_timer_heap_t * timerheap
Timer heap for scheduled items.
struct ast_rtp_rtcp_report_block::@314 lost_count
#define ao2_link(container, obj)
#define TRANSPORT_SOCKET_RTP
static void ast_rtp_ice_set_role(struct ast_rtp_instance *instance, enum ast_rtp_ice_role role)