[asterisk-commits] file: branch 12 r403256 - in /branches/12: include/asterisk/ res/ res/res_pjsip/

SVN commits to the Asterisk project asterisk-commits at lists.digium.com
Sun Dec 1 13:56:42 CST 2013


Author: file
Date: Sun Dec  1 13:56:38 2013
New Revision: 403256

URL: http://svnview.digium.com/svn/asterisk?view=rev&rev=403256
Log:
res_pjsip_transport_websocket: Fix security events and simplify implementation.

Transport type determination for security events has been simplified to use
the type present on the message itself instead of searching through configured
transports to find the transport used.

The actual WebSocket transport has also been simplified. It now leverages the
existing PJSIP transport manager for finding the active WebSocket transport
for outgoing messages. This removes the need for res_pjsip_transport_websocket
to store a mapping itself.

(closes issue ASTERISK-22897)
Reported by: Max E. Reyes Vera J.

Review: https://reviewboard.asterisk.org/r/3036/ 

Modified:
    branches/12/include/asterisk/res_pjsip.h
    branches/12/res/res_pjsip.c
    branches/12/res/res_pjsip/location.c
    branches/12/res/res_pjsip/pjsip_options.c
    branches/12/res/res_pjsip/security_events.c
    branches/12/res/res_pjsip_transport_websocket.c

Modified: branches/12/include/asterisk/res_pjsip.h
URL: http://svnview.digium.com/svn/asterisk/branches/12/include/asterisk/res_pjsip.h?view=diff&rev=403256&r1=403255&r2=403256
==============================================================================
--- branches/12/include/asterisk/res_pjsip.h (original)
+++ branches/12/include/asterisk/res_pjsip.h Sun Dec  1 13:56:38 2013
@@ -177,17 +177,6 @@
 	struct timeval rtt_start;
 	/*! The round trip time in microseconds */
 	int64_t rtt;
-};
-
-/*!
- * \brief A transport to be used for messages to a contact
- */
-struct ast_sip_contact_transport {
-	AST_DECLARE_STRING_FIELDS(
-		/*! Full URI of the contact */
-		AST_STRING_FIELD(uri);
-	);
-	pjsip_transport *transport;
 };
 
 /*!
@@ -890,37 +879,6 @@
 struct ast_sip_contact *ast_sip_location_retrieve_contact(const char *contact_name);
 
 /*!
- * \brief Add a transport for a contact to use
- */
-
-void ast_sip_location_add_contact_transport(struct ast_sip_contact_transport *ct);
-
-/*!
- * \brief Delete a transport for a contact that went away
- */
-void ast_sip_location_delete_contact_transport(struct ast_sip_contact_transport *ct);
-
-/*!
- * \brief Retrieve a contact_transport, by URI
- *
- * \param contact_uri URI of the contact
- *
- * \retval NULL if not found
- * \retval non-NULL if found
- */
-struct ast_sip_contact_transport *ast_sip_location_retrieve_contact_transport_by_uri(const char *contact_uri);
-
-/*!
- * \brief Retrieve a contact_transport, by transport
- *
- * \param transport transport the contact uses
- *
- * \retval NULL if not found
- * \retval non-NULL if found
- */
-struct ast_sip_contact_transport *ast_sip_location_retrieve_contact_transport_by_transport(pjsip_transport *transport);
-
-/*!
  * \brief Add a new contact to an AOR
  *
  * \param aor Pointer to the AOR

Modified: branches/12/res/res_pjsip.c
URL: http://svnview.digium.com/svn/asterisk/branches/12/res/res_pjsip.c?view=diff&rev=403256&r1=403255&r2=403256
==============================================================================
--- branches/12/res/res_pjsip.c (original)
+++ branches/12/res/res_pjsip.c Sun Dec  1 13:56:38 2013
@@ -1369,7 +1369,10 @@
 	/* Get the local bound address for the transport that will be used when communicating with the provided URI */
 	if (pjsip_tpmgr_find_local_addr(pjsip_endpt_get_tpmgr(ast_sip_get_pjsip_endpoint()), pool, type, selector,
 							      &local_addr, &local_port) != PJ_SUCCESS) {
-		return -1;
+
+		/* If no local address can be retrieved using the transport manager use the host one */
+		pj_strdup(pool, &local_addr, pj_gethostname());
+		local_port = pjsip_transport_get_default_port_for_type(PJSIP_TRANSPORT_UDP);
 	}
 
 	/* If IPv6 was specified in the transport, set the proper type */
@@ -1423,22 +1426,6 @@
 	return 0;
 }
 
-static int sip_get_tpselector_from_uri(const char *uri, pjsip_tpselector *selector)
-{
-	RAII_VAR(struct ast_sip_contact_transport *, contact_transport, NULL, ao2_cleanup);
-
-	contact_transport = ast_sip_location_retrieve_contact_transport_by_uri(uri);
-
-	if (!contact_transport) {
-		return -1;
-	}
-
-	selector->type = PJSIP_TPSELECTOR_TRANSPORT;
-	selector->u.transport = contact_transport->transport;
-
-	return 0;
-}
-
 pjsip_dialog *ast_sip_create_dialog_uac(const struct ast_sip_endpoint *endpoint, const char *uri, const char *request_user)
 {
 	char enclosed_uri[PJSIP_MAX_URL_SIZE];
@@ -1457,7 +1444,7 @@
 		return NULL;
 	}
 
-	if (sip_get_tpselector_from_uri(uri, &selector) && sip_get_tpselector_from_endpoint(endpoint, &selector)) {
+	if (sip_get_tpselector_from_endpoint(endpoint, &selector)) {
 		pjsip_dlg_terminate(dlg);
 		return NULL;
 	}
@@ -2104,8 +2091,6 @@
 
 	ast_res_pjsip_init_options_handling(0);
 
-	ast_res_pjsip_init_contact_transports();
-
 	ast_module_ref(ast_module_info->self);
 
 	return AST_MODULE_LOAD_SUCCESS;

Modified: branches/12/res/res_pjsip/location.c
URL: http://svnview.digium.com/svn/asterisk/branches/12/res/res_pjsip/location.c?view=diff&rev=403256&r1=403255&r2=403256
==============================================================================
--- branches/12/res/res_pjsip/location.c (original)
+++ branches/12/res/res_pjsip/location.c Sun Dec  1 13:56:38 2013
@@ -26,9 +26,6 @@
 #include "asterisk/sorcery.h"
 #include "include/res_pjsip_private.h"
 
-#define CONTACT_TRANSPORTS_BUCKETS 7
-static struct ao2_container *contact_transports;
-
 /*! \brief Destructor for AOR */
 static void aor_destroy(void *obj)
 {
@@ -72,48 +69,6 @@
 	}
 
 	return contact;
-}
-
-/*! \brief Callback function for finding a contact_transport by URI */
-static int contact_transport_find_by_uri(void *obj, void *arg, int flags)
-{
-	struct ast_sip_contact_transport *ct = obj;
-	const char *contact_uri = arg;
-
-	return (!strcmp(ct->uri, contact_uri)) ? CMP_MATCH | CMP_STOP : 0;
-}
-
-/*! \brief Callback function for finding a contact_transport by transport */
-static int contact_transport_find_by_transport(void *obj, void *arg, int flags)
-{
-	struct ast_sip_contact_transport *ct = obj;
-	pjsip_transport *transport = arg;
-
-	return (ct->transport == transport) ? CMP_MATCH | CMP_STOP : 0;
-}
-
-void ast_sip_location_add_contact_transport(struct ast_sip_contact_transport *ct)
-{
-	ao2_link(contact_transports, ct);
-
-	return;
-}
-
-void ast_sip_location_delete_contact_transport(struct ast_sip_contact_transport *ct)
-{
-	ao2_unlink(contact_transports, ct);
-
-	return;
-}
-
-struct ast_sip_contact_transport *ast_sip_location_retrieve_contact_transport_by_uri(const char *contact_uri)
-{
-	return ao2_callback(contact_transports, 0, contact_transport_find_by_uri, (void *)contact_uri);
-}
-
-struct ast_sip_contact_transport *ast_sip_location_retrieve_contact_transport_by_transport(pjsip_transport *transport)
-{
-	return ao2_callback(contact_transports, 0, contact_transport_find_by_transport, transport);
 }
 
 struct ast_sip_aor *ast_sip_location_retrieve_aor(const char *aor_name)
@@ -449,16 +404,3 @@
 	return 0;
 }
 
-int ast_res_pjsip_init_contact_transports(void)
-{
-	if (contact_transports) {
-		ao2_t_ref(contact_transports, -1, "Remove old contact transports");
-	}
-
-	contact_transports = ao2_t_container_alloc_options(AO2_ALLOC_OPT_LOCK_RWLOCK, CONTACT_TRANSPORTS_BUCKETS, NULL, NULL, "Create container for contact transports");
-	if (!contact_transports) {
-		return -1;
-	}
-
-	return 0;
-}

Modified: branches/12/res/res_pjsip/pjsip_options.c
URL: http://svnview.digium.com/svn/asterisk/branches/12/res/res_pjsip/pjsip_options.c?view=diff&rev=403256&r1=403255&r2=403256
==============================================================================
--- branches/12/res/res_pjsip/pjsip_options.c (original)
+++ branches/12/res/res_pjsip/pjsip_options.c Sun Dec  1 13:56:38 2013
@@ -263,10 +263,9 @@
 	ao2_ref(contact, +1);
 	if (pjsip_endpt_send_request(ast_sip_get_pjsip_endpoint(),
 				     tdata, -1, contact, qualify_contact_cb) != PJ_SUCCESS) {
-		pjsip_tx_data_dec_ref(tdata);
+		/* The callback will be called so we don't need to drop the contact ref*/
 		ast_log(LOG_ERROR, "Unable to send request to qualify contact %s\n",
 			contact->uri);
-		ao2_ref(contact, -1);
 		return -1;
 	}
 

Modified: branches/12/res/res_pjsip/security_events.c
URL: http://svnview.digium.com/svn/asterisk/branches/12/res/res_pjsip/security_events.c?view=diff&rev=403256&r1=403255&r2=403256
==============================================================================
--- branches/12/res/res_pjsip/security_events.c (original)
+++ branches/12/res/res_pjsip/security_events.c Sun Dec  1 13:56:38 2013
@@ -33,35 +33,24 @@
 #include "asterisk/res_pjsip.h"
 #include "asterisk/security_events.h"
 
-static int find_transport_in_use(void *obj, void *arg, int flags)
-{
-	struct ast_sip_transport *transport = obj;
-	pjsip_rx_data *rdata = arg;
-
-	if ((transport->state->transport == rdata->tp_info.transport) ||
-		(transport->state->factory && !pj_strcmp(&transport->state->factory->addr_name.host, &rdata->tp_info.transport->local_name.host) &&
-			transport->state->factory->addr_name.port == rdata->tp_info.transport->local_name.port)) {
-		return CMP_MATCH | CMP_STOP;
+static enum ast_transport security_event_get_transport(pjsip_rx_data *rdata)
+{
+	if (rdata->tp_info.transport->key.type == PJSIP_TRANSPORT_UDP ||
+		rdata->tp_info.transport->key.type == PJSIP_TRANSPORT_UDP6) {
+		return AST_TRANSPORT_UDP;
+	} else if (rdata->tp_info.transport->key.type == PJSIP_TRANSPORT_TCP ||
+		rdata->tp_info.transport->key.type == PJSIP_TRANSPORT_TCP6) {
+		return AST_TRANSPORT_TCP;
+	} else if (rdata->tp_info.transport->key.type == PJSIP_TRANSPORT_TLS ||
+		rdata->tp_info.transport->key.type == PJSIP_TRANSPORT_TLS6) {
+		return AST_TRANSPORT_TLS;
+	} else if (!strcmp(rdata->tp_info.transport->type_name, "WS")) {
+		return AST_TRANSPORT_WS;
+	} else if (!strcmp(rdata->tp_info.transport->type_name, "WSS")) {
+		return AST_TRANSPORT_WSS;
+	} else {
+		return 0;
 	}
-
-	return 0;
-}
-
-static enum ast_transport security_event_get_transport(pjsip_rx_data *rdata)
-{
-	RAII_VAR(struct ao2_container *, transports, NULL, ao2_cleanup);
-	RAII_VAR(struct ast_sip_transport *, transport, NULL, ao2_cleanup);
-
-	/* It should be impossible for these to fail as the transport has to exist for the message to exist */
-	transports = ast_sorcery_retrieve_by_fields(ast_sip_get_sorcery(), "transport", AST_RETRIEVE_FLAG_MULTIPLE | AST_RETRIEVE_FLAG_ALL, NULL);
-
-	ast_assert(transports != NULL);
-
-	transport = ao2_callback(transports, 0, find_transport_in_use, rdata);
-
-	ast_assert(transport != NULL);
-
-	return transport->type;
 }
 
 static void security_event_populate(pjsip_rx_data *rdata, char *call_id, size_t call_id_size, struct ast_sockaddr *local, struct ast_sockaddr *remote)

Modified: branches/12/res/res_pjsip_transport_websocket.c
URL: http://svnview.digium.com/svn/asterisk/branches/12/res/res_pjsip_transport_websocket.c?view=diff&rev=403256&r1=403255&r2=403256
==============================================================================
--- branches/12/res/res_pjsip_transport_websocket.c (original)
+++ branches/12/res/res_pjsip_transport_websocket.c Sun Dec  1 13:56:38 2013
@@ -95,12 +95,7 @@
 
 static int transport_shutdown(void *data)
 {
-	RAII_VAR(struct ast_sip_contact_transport *, ct, NULL, ao2_cleanup);
 	pjsip_transport *transport = data;
-
-	if ((ct = ast_sip_location_retrieve_contact_transport_by_transport(transport))) {
-		ast_sip_location_delete_contact_transport(ct);
-	}
 
 	pjsip_transport_shutdown(transport);
 	return 0;
@@ -220,6 +215,7 @@
 	struct ast_taskprocessor *serializer = NULL;
 	struct transport_create_data create_data;
 	struct ws_transport *transport = NULL;
+	struct transport_read_data read_data;
 
 	if (ast_websocket_set_nonblock(session)) {
 		ast_websocket_unref(session);
@@ -240,9 +236,9 @@
 	}
 
 	transport = create_data.transport;
+	read_data.transport = transport;
 
 	while (ast_wait_for_input(ast_websocket_fd(session), -1) > 0) {
-		struct transport_read_data read_data;
 		enum ast_websocket_opcode opcode;
 		int fragmented;
 
@@ -251,9 +247,7 @@
 		}
 
 		if (opcode == AST_WEBSOCKET_OPCODE_TEXT || opcode == AST_WEBSOCKET_OPCODE_BINARY) {
-			read_data.transport = transport;
-
-			ast_sip_push_task(serializer, transport_read, &read_data);
+			ast_sip_push_task_synchronous(serializer, transport_read, &read_data);
 		} else if (opcode == AST_WEBSOCKET_OPCODE_CLOSE) {
 			break;
 		}
@@ -266,72 +260,11 @@
 }
 
 /*!
- * \brief Session supplement handler for avoiding DNS lookup on bogus address.
- */
-static void websocket_outgoing_request(struct ast_sip_session *session, struct pjsip_tx_data *tdata)
-{
-	char contact_uri[PJSIP_MAX_URL_SIZE] = { 0, };
-	RAII_VAR(struct ast_sip_contact_transport *, ct, NULL, ao2_cleanup);
-	pjsip_tpselector selector = { .type = PJSIP_TPSELECTOR_TRANSPORT, };
-
-	const pjsip_sip_uri *request_uri = pjsip_uri_get_uri(tdata->msg->line.req.uri);
-
-	if (pj_stricmp2(&request_uri->transport_param, "WS") && pj_stricmp2(&request_uri->transport_param, "WSS")) {
-		return;
-	}
-
-	pjsip_uri_print(PJSIP_URI_IN_REQ_URI, request_uri, contact_uri, sizeof(contact_uri));
-
-	if (!(ct = ast_sip_location_retrieve_contact_transport_by_uri(contact_uri))) {
-		return;
-	}
-
-	selector.u.transport = ct->transport;
-
-	pjsip_tx_data_set_transport(tdata, &selector);
-
-	tdata->dest_info.addr.count = 1;
-	tdata->dest_info.addr.entry[0].type = ct->transport->key.type;
-	tdata->dest_info.addr.entry[0].addr = ct->transport->key.rem_addr;
-	tdata->dest_info.addr.entry[0].addr_len = ct->transport->addr_len;
-}
-
-static struct ast_sip_session_supplement websocket_supplement = {
-	.outgoing_request = websocket_outgoing_request,
-};
-
-/*!
- * \brief Destructor for ast_sip_contact_transport
- */
-static void contact_transport_destroy(void *obj)
-{
-	struct ast_sip_contact_transport *ct = obj;
-
-	ast_string_field_free_memory(ct);
-}
-
-static void *contact_transport_alloc(void)
-{
-	struct ast_sip_contact_transport *ct = ao2_alloc(sizeof(*ct), contact_transport_destroy);
-
-	if (!ct) {
-		return NULL;
-	}
-
-	if (ast_string_field_init(ct, 256)) {
-		ao2_cleanup(ct);
-		return NULL;
-	}
-
-	return ct;
-}
-
-/*!
  * \brief Store the transport a message came in on, so it can be used for outbound messages to that contact.
  */
 static pj_bool_t websocket_on_rx_msg(pjsip_rx_data *rdata)
 {
-	pjsip_contact_hdr *contact_hdr = NULL;
+	pjsip_contact_hdr *contact;
 
 	long type = rdata->tp_info.transport->key.type;
 
@@ -339,23 +272,15 @@
 		return PJ_FALSE;
 	}
 
-	if ((contact_hdr = pjsip_msg_find_hdr(rdata->msg_info.msg, PJSIP_H_CONTACT, NULL))) {
-		RAII_VAR(struct ast_sip_contact_transport *, ct, NULL, ao2_cleanup);
-		char contact_uri[PJSIP_MAX_URL_SIZE];
-
-		pjsip_uri_print(PJSIP_URI_IN_CONTACT_HDR, pjsip_uri_get_uri(contact_hdr->uri), contact_uri, sizeof(contact_uri));
-
-		if (!(ct = ast_sip_location_retrieve_contact_transport_by_uri(contact_uri))) {
-			if (!(ct = contact_transport_alloc())) {
-				return PJ_FALSE;
-			}
-
-			ast_string_field_set(ct, uri, contact_uri);
-			ct->transport = rdata->tp_info.transport;
-
-			ast_sip_location_add_contact_transport(ct);
-		}
-	}
+	if ((contact = pjsip_msg_find_hdr(rdata->msg_info.msg, PJSIP_H_CONTACT, NULL)) &&
+		(PJSIP_URI_SCHEME_IS_SIP(contact->uri) || PJSIP_URI_SCHEME_IS_SIPS(contact->uri))) {
+		pjsip_sip_uri *uri = pjsip_uri_get_uri(contact->uri);
+
+		pj_cstr(&uri->host, rdata->pkt_info.src_name);
+		uri->port = rdata->pkt_info.src_port;
+	}
+
+	rdata->msg_info.via->rport_param = 0;
 
 	return PJ_FALSE;
 }
@@ -376,8 +301,6 @@
 		return AST_MODULE_LOAD_DECLINE;
 	}
 
-	ast_sip_session_register_supplement(&websocket_supplement);
-
 	if (ast_websocket_add_protocol("sip", websocket_cb)) {
 		ast_sip_unregister_service(&websocket_module);
 		return AST_MODULE_LOAD_DECLINE;
@@ -389,7 +312,6 @@
 static int unload_module(void)
 {
 	ast_sip_unregister_service(&websocket_module);
-	ast_sip_session_unregister_supplement(&websocket_supplement);
 	ast_websocket_remove_protocol("sip", websocket_cb);
 
 	return 0;




More information about the asterisk-commits mailing list