diff options
Diffstat (limited to 'res')
-rw-r--r-- | res/res_hep.c | 5 | ||||
-rw-r--r-- | res/res_hep_pjsip.c | 12 | ||||
-rw-r--r-- | res/res_pjsip.c | 6 | ||||
-rw-r--r-- | res/res_pjsip/pjsip_configuration.c | 1 | ||||
-rw-r--r-- | res/res_pjsip_messaging.c | 10 | ||||
-rw-r--r-- | res/res_pjsip_nat.c | 43 | ||||
-rw-r--r-- | res/res_pjsip_sdp_rtp.c | 5 | ||||
-rw-r--r-- | res/res_pjsip_session.c | 29 | ||||
-rw-r--r-- | res/res_pjsip_t38.c | 5 |
9 files changed, 84 insertions, 32 deletions
diff --git a/res/res_hep.c b/res/res_hep.c index 15e779012..8d4987c03 100644 --- a/res/res_hep.c +++ b/res/res_hep.c @@ -441,6 +441,9 @@ struct hepv3_capture_info *hepv3_create_capture_info(const void *payload, size_t memcpy(info->payload, payload, len); info->len = len; + /* Set a reasonable default */ + info->protocol_id = IPPROTO_UDP; + return info; } @@ -472,7 +475,7 @@ static int hep_queue_cb(void *data) /* Build HEPv3 header, capture info, and calculate the total packet size */ memcpy(hg_pkt.header.id, "\x48\x45\x50\x33", 4); - INITIALIZE_GENERIC_HEP_CHUNK_DATA(&hg_pkt.ip_proto, CHUNK_TYPE_IP_PROTOCOL_ID, 0x11); + INITIALIZE_GENERIC_HEP_CHUNK_DATA(&hg_pkt.ip_proto, CHUNK_TYPE_IP_PROTOCOL_ID, capture_info->protocol_id); INITIALIZE_GENERIC_HEP_CHUNK_DATA(&hg_pkt.src_port, CHUNK_TYPE_SRC_PORT, htons(ast_sockaddr_port(&capture_info->src_addr))); INITIALIZE_GENERIC_HEP_CHUNK_DATA(&hg_pkt.dst_port, CHUNK_TYPE_DST_PORT, htons(ast_sockaddr_port(&capture_info->dst_addr))); INITIALIZE_GENERIC_HEP_CHUNK_DATA(&hg_pkt.time_sec, CHUNK_TYPE_TIMESTAMP_SEC, htonl(capture_info->capture_time.tv_sec)); diff --git a/res/res_hep_pjsip.c b/res/res_hep_pjsip.c index 8f5baa2cb..1614b4319 100644 --- a/res/res_hep_pjsip.c +++ b/res/res_hep_pjsip.c @@ -73,6 +73,15 @@ static char *assign_uuid(const pj_str_t *call_id, const pj_str_t *local_tag, con return uuid; } +static int transport_to_protocol_id(pjsip_transport *tp) +{ + /* XXX If we ever add SCTP support, we'll need to revisit */ + if (tp->flag & PJSIP_TRANSPORT_RELIABLE) { + return IPPROTO_TCP; + } + return IPPROTO_UDP; +} + static pj_status_t logging_on_tx_msg(pjsip_tx_data *tdata) { char local_buf[256]; @@ -126,6 +135,7 @@ static pj_status_t logging_on_tx_msg(pjsip_tx_data *tdata) ast_sockaddr_parse(&capture_info->src_addr, local_buf, PARSE_PORT_REQUIRE); ast_sockaddr_parse(&capture_info->dst_addr, remote_buf, PARSE_PORT_REQUIRE); + capture_info->protocol_id = transport_to_protocol_id(tdata->tp_info.transport); capture_info->capture_time = ast_tvnow(); capture_info->capture_type = HEPV3_CAPTURE_TYPE_SIP; capture_info->uuid = uuid; @@ -185,6 +195,8 @@ static pj_bool_t logging_on_rx_msg(pjsip_rx_data *rdata) ast_sockaddr_parse(&capture_info->src_addr, remote_buf, PARSE_PORT_REQUIRE); ast_sockaddr_parse(&capture_info->dst_addr, local_buf, PARSE_PORT_REQUIRE); + + capture_info->protocol_id = transport_to_protocol_id(rdata->tp_info.transport); capture_info->capture_time.tv_sec = rdata->pkt_info.timestamp.sec; capture_info->capture_time.tv_usec = rdata->pkt_info.timestamp.msec * 1000; capture_info->capture_type = HEPV3_CAPTURE_TYPE_SIP; diff --git a/res/res_pjsip.c b/res/res_pjsip.c index 7b10f47f6..fc4985657 100644 --- a/res/res_pjsip.c +++ b/res/res_pjsip.c @@ -100,6 +100,9 @@ <configOption name="allow"> <synopsis>Media Codec(s) to allow</synopsis> </configOption> + <configOption name="allow_overlap" default="yes"> + <synopsis>Enable RFC3578 overlap dialing support.</synopsis> + </configOption> <configOption name="aors"> <synopsis>AoR(s) to be used with the endpoint</synopsis> <description><para> @@ -2122,6 +2125,9 @@ <parameter name="SubscribeContext"> <para><xi:include xpointer="xpointer(/docs/configInfo[@name='res_pjsip']/configFile[@name='pjsip.conf']/configObject[@name='endpoint']/configOption[@name='subscribe_context']/synopsis/node())"/></para> </parameter> + <parameter name="Allowoverlap"> + <para><xi:include xpointer="xpointer(/docs/configInfo[@name='res_pjsip']/configFile[@name='pjsip.conf']/configObject[@name='endpoint']/configOption[@name='allow_overlap']/synopsis/node())"/></para> + </parameter> </syntax> </managerEventInstance> </managerEvent> diff --git a/res/res_pjsip/pjsip_configuration.c b/res/res_pjsip/pjsip_configuration.c index eb8e19712..511ea41c1 100644 --- a/res/res_pjsip/pjsip_configuration.c +++ b/res/res_pjsip/pjsip_configuration.c @@ -1939,6 +1939,7 @@ int ast_res_pjsip_initialize_configuration(const struct ast_module_info *ast_mod ast_sorcery_object_field_register_custom(sip_sorcery, "endpoint", "contact_user", "", contact_user_handler, contact_user_to_str, NULL, 0, 0); ast_sorcery_object_field_register(sip_sorcery, "endpoint", "asymmetric_rtp_codec", "no", OPT_BOOL_T, 1, FLDSET(struct ast_sip_endpoint, asymmetric_rtp_codec)); ast_sorcery_object_field_register(sip_sorcery, "endpoint", "rtcp_mux", "no", OPT_BOOL_T, 1, FLDSET(struct ast_sip_endpoint, rtcp_mux)); + ast_sorcery_object_field_register(sip_sorcery, "endpoint", "allow_overlap", "yes", OPT_BOOL_T, 1, FLDSET(struct ast_sip_endpoint, allow_overlap)); if (ast_sip_initialize_sorcery_transport()) { ast_log(LOG_ERROR, "Failed to register SIP transport support with sorcery\n"); diff --git a/res/res_pjsip_messaging.c b/res/res_pjsip_messaging.c index 835a38393..8b465e007 100644 --- a/res/res_pjsip_messaging.c +++ b/res/res_pjsip_messaging.c @@ -235,7 +235,15 @@ static void update_from(pjsip_tx_data *tdata, char *from) parsed_name_addr = (pjsip_name_addr *) pjsip_parse_uri(tdata->pool, from, strlen(from), PJSIP_PARSE_URI_AS_NAMEADDR); if (parsed_name_addr) { - pjsip_sip_uri *parsed_uri = pjsip_uri_get_uri(parsed_name_addr->uri); + pjsip_sip_uri *parsed_uri; + + if (!PJSIP_URI_SCHEME_IS_SIP(parsed_name_addr->uri) + && !PJSIP_URI_SCHEME_IS_SIPS(parsed_name_addr->uri)) { + ast_log(LOG_WARNING, "From address '%s' is not a valid SIP/SIPS URI\n", from); + return; + } + + parsed_uri = pjsip_uri_get_uri(parsed_name_addr->uri); if (pj_strlen(&parsed_name_addr->display)) { pj_strdup(tdata->pool, &name_addr->display, &parsed_name_addr->display); diff --git a/res/res_pjsip_nat.c b/res/res_pjsip_nat.c index 7404ef5f0..5fcab6378 100644 --- a/res/res_pjsip_nat.c +++ b/res/res_pjsip_nat.c @@ -262,32 +262,33 @@ static pj_status_t nat_on_tx_message(pjsip_tx_data *tdata) return PJ_SUCCESS; } - if ( !transport_state->localnet || ast_sockaddr_isnull(&transport_state->external_address)) { - return PJ_SUCCESS; - } - - ast_sockaddr_parse(&addr, tdata->tp_info.dst_name, PARSE_PORT_FORBID); - ast_sockaddr_set_port(&addr, tdata->tp_info.dst_port); + if (transport_state->localnet) { + ast_sockaddr_parse(&addr, tdata->tp_info.dst_name, PARSE_PORT_FORBID); + ast_sockaddr_set_port(&addr, tdata->tp_info.dst_port); - /* See if where we are sending this request is local or not, and if not that we can get a Contact URI to modify */ - if (ast_apply_ha(transport_state->localnet, &addr) != AST_SENSE_ALLOW) { - return PJ_SUCCESS; + /* See if where we are sending this request is local or not, and if not that we can get a Contact URI to modify */ + if (ast_apply_ha(transport_state->localnet, &addr) != AST_SENSE_ALLOW) { + ast_debug(5, "Request is being sent to local address, skipping NAT manipulation\n"); + return PJ_SUCCESS; + } } - /* Update the contact header with the external address */ - if (uri || (uri = nat_get_contact_sip_uri(tdata))) { - pj_strdup2(tdata->pool, &uri->host, ast_sockaddr_stringify_host(&transport_state->external_address)); - if (transport->external_signaling_port) { - uri->port = transport->external_signaling_port; - ast_debug(4, "Re-wrote Contact URI port to %d\n", uri->port); + if (!ast_sockaddr_isnull(&transport_state->external_address)) { + /* Update the contact header with the external address */ + if (uri || (uri = nat_get_contact_sip_uri(tdata))) { + pj_strdup2(tdata->pool, &uri->host, ast_sockaddr_stringify_host(&transport_state->external_address)); + if (transport->external_signaling_port) { + uri->port = transport->external_signaling_port; + ast_debug(4, "Re-wrote Contact URI port to %d\n", uri->port); + } } - } - /* Update the via header if relevant */ - if ((tdata->msg->type == PJSIP_REQUEST_MSG) && (via || (via = pjsip_msg_find_hdr(tdata->msg, PJSIP_H_VIA, NULL)))) { - pj_strdup2(tdata->pool, &via->sent_by.host, ast_sockaddr_stringify_host(&transport_state->external_address)); - if (transport->external_signaling_port) { - via->sent_by.port = transport->external_signaling_port; + /* Update the via header if relevant */ + if ((tdata->msg->type == PJSIP_REQUEST_MSG) && (via || (via = pjsip_msg_find_hdr(tdata->msg, PJSIP_H_VIA, NULL)))) { + pj_strdup2(tdata->pool, &via->sent_by.host, ast_sockaddr_stringify_host(&transport_state->external_address)); + if (transport->external_signaling_port) { + via->sent_by.port = transport->external_signaling_port; + } } } diff --git a/res/res_pjsip_sdp_rtp.c b/res/res_pjsip_sdp_rtp.c index ecc39d87d..d44171cf8 100644 --- a/res/res_pjsip_sdp_rtp.c +++ b/res/res_pjsip_sdp_rtp.c @@ -1465,10 +1465,11 @@ static void change_outgoing_sdp_stream_media_address(pjsip_tx_data *tdata, struc ast_sockaddr_parse(&addr, host, PARSE_PORT_FORBID); /* Is the address within the SDP inside the same network? */ - if (ast_apply_ha(transport_state->localnet, &addr) == AST_SENSE_ALLOW) { + if (transport_state->localnet + && ast_apply_ha(transport_state->localnet, &addr) == AST_SENSE_ALLOW) { return; } - + ast_debug(5, "Setting media address to %s\n", transport->external_media_address); pj_strdup2(tdata->pool, &stream->conn->addr, transport->external_media_address); } diff --git a/res/res_pjsip_session.c b/res/res_pjsip_session.c index 98ee87209..53841c44a 100644 --- a/res/res_pjsip_session.c +++ b/res/res_pjsip_session.c @@ -1984,10 +1984,17 @@ static enum sip_get_destination_result get_destination(struct ast_sip_session *s return SIP_GET_DEST_EXTEN_FOUND; } - /* XXX In reality, we'll likely have further options so that partial matches - * can be indicated here, but for getting something up and running, we're going - * to return a "not exists" error here. + + /* + * Check for partial match via overlap dialling (if enabled) */ + if (session->endpoint->allow_overlap && ( + !strncmp(session->exten, pickupexten, strlen(session->exten)) || + ast_canmatch_extension(NULL, session->endpoint->context, session->exten, 1, NULL))) { + /* Overlap partial match */ + return SIP_GET_DEST_EXTEN_PARTIAL; + } + return SIP_GET_DEST_EXTEN_NOT_FOUND; } @@ -2104,8 +2111,17 @@ static int new_invite(void *data) pjsip_inv_terminate(invite->session->inv_session, 416, PJ_TRUE); } goto end; - case SIP_GET_DEST_EXTEN_NOT_FOUND: case SIP_GET_DEST_EXTEN_PARTIAL: + ast_debug(1, "Call from '%s' (%s:%s:%d) to extension '%s' - partial match\n", ast_sorcery_object_get_id(invite->session->endpoint), + invite->rdata->tp_info.transport->type_name, invite->rdata->pkt_info.src_name, invite->rdata->pkt_info.src_port, invite->session->exten); + + if (pjsip_inv_initial_answer(invite->session->inv_session, invite->rdata, 484, NULL, NULL, &tdata) == PJ_SUCCESS) { + ast_sip_session_send_response(invite->session, tdata); + } else { + pjsip_inv_terminate(invite->session->inv_session, 484, PJ_TRUE); + } + goto end; + case SIP_GET_DEST_EXTEN_NOT_FOUND: default: ast_log(LOG_NOTICE, "Call from '%s' (%s:%s:%d) to extension '%s' rejected because extension not found in context '%s'.\n", ast_sorcery_object_get_id(invite->session->endpoint), invite->rdata->tp_info.transport->type_name, invite->rdata->pkt_info.src_name, @@ -3090,7 +3106,10 @@ static void session_outgoing_nat_hook(pjsip_tx_data *tdata, struct ast_sip_trans ast_copy_pj_str(host, &sdp->conn->addr, sizeof(host)); ast_sockaddr_parse(&addr, host, PARSE_PORT_FORBID); - if (ast_apply_ha(transport_state->localnet, &addr) != AST_SENSE_ALLOW) { + if (!transport_state->localnet + || (transport_state->localnet + && ast_apply_ha(transport_state->localnet, &addr) == AST_SENSE_ALLOW)) { + ast_debug(5, "Setting external media address to %s\n", transport->external_media_address); pj_strdup2(tdata->pool, &sdp->conn->addr, transport->external_media_address); } } diff --git a/res/res_pjsip_t38.c b/res/res_pjsip_t38.c index 0787f0763..16d50cd27 100644 --- a/res/res_pjsip_t38.c +++ b/res/res_pjsip_t38.c @@ -869,10 +869,11 @@ static void change_outgoing_sdp_stream_media_address(pjsip_tx_data *tdata, struc ast_sockaddr_parse(&addr, host, PARSE_PORT_FORBID); /* Is the address within the SDP inside the same network? */ - if (ast_apply_ha(transport_state->localnet, &addr) == AST_SENSE_ALLOW) { + if (transport_state->localnet + && ast_apply_ha(transport_state->localnet, &addr) == AST_SENSE_ALLOW) { return; } - + ast_debug(5, "Setting media address to %s\n", transport->external_media_address); pj_strdup2(tdata->pool, &stream->conn->addr, transport->external_media_address); } |