[svn-commits] mmichelson: trunk r394759 - in /trunk: channels/ include/asterisk/ res/ res/r...

SVN commits to the Digium repositories svn-commits at lists.digium.com
Thu Jul 18 14:25:54 CDT 2013


Author: mmichelson
Date: Thu Jul 18 14:25:51 2013
New Revision: 394759

URL: http://svnview.digium.com/svn/asterisk?view=rev&rev=394759
Log:
Add a bunch of options from sip.conf to res_sip.conf

For a complete list of the options added, see the review linked
at the bottom of this commit message.

(closes issue ASTERISK-21506)
reported by Matt Jordan

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


Added:
    trunk/res/res_sip/config_global.c
      - copied unchanged from r394758, team/mmichelson/sip_options/res/res_sip/config_global.c
    trunk/res/res_sip/config_system.c
      - copied unchanged from r394758, team/mmichelson/sip_options/res/res_sip/config_system.c
    trunk/res/res_sip/sip_global_headers.c
      - copied unchanged from r394758, team/mmichelson/sip_options/res/res_sip/sip_global_headers.c
Modified:
    trunk/channels/chan_gulp.c
    trunk/include/asterisk/res_sip.h
    trunk/res/res_sip.c
    trunk/res/res_sip.exports.in
    trunk/res/res_sip/config_transport.c
    trunk/res/res_sip/include/res_sip_private.h
    trunk/res/res_sip/sip_configuration.c
    trunk/res/res_sip_caller_id.c
    trunk/res/res_sip_mwi.c
    trunk/res/res_sip_one_touch_record_info.c
    trunk/res/res_sip_pubsub.c
    trunk/res/res_sip_refer.c
    trunk/res/res_sip_sdp_rtp.c
    trunk/res/res_sip_session.c

Modified: trunk/channels/chan_gulp.c
URL: http://svnview.digium.com/svn/asterisk/trunk/channels/chan_gulp.c?view=diff&rev=394759&r1=394758&r2=394759
==============================================================================
--- trunk/channels/chan_gulp.c (original)
+++ trunk/channels/chan_gulp.c Thu Jul 18 14:25:51 2013
@@ -56,6 +56,7 @@
 #include "asterisk/dsp.h"
 #include "asterisk/stasis_endpoints.h"
 #include "asterisk/stasis_channels.h"
+#include "asterisk/indications.h"
 
 #include "asterisk/res_sip.h"
 #include "asterisk/res_sip_session.h"
@@ -600,6 +601,18 @@
 
 	ast_channel_named_callgroups_set(chan, session->endpoint->named_callgroups);
 	ast_channel_named_pickupgroups_set(chan, session->endpoint->named_pickupgroups);
+
+	if (!ast_strlen_zero(session->endpoint->language)) {
+		ast_channel_language_set(chan, session->endpoint->language);
+	}
+
+	if (!ast_strlen_zero(session->endpoint->zone)) {
+		struct ast_tone_zone *zone = ast_get_indication_zone(session->endpoint->zone);
+		if (!zone) {
+			ast_log(LOG_ERROR, "Unknown country code '%s' for tonezone. Check indications.conf for available country codes.\n", session->endpoint->zone);
+		}
+		ast_channel_zone_set(chan, zone);
+	}
 
 	ast_endpoint_add_channel(session->endpoint->persistent, chan);
 

Modified: trunk/include/asterisk/res_sip.h
URL: http://svnview.digium.com/svn/asterisk/trunk/include/asterisk/res_sip.h?view=diff&rev=394759&r1=394758&r2=394759
==============================================================================
--- trunk/include/asterisk/res_sip.h (original)
+++ trunk/include/asterisk/res_sip.h Thu Jul 18 14:25:51 2013
@@ -115,6 +115,10 @@
 	struct ast_sockaddr external_address;
 	/*! Transport state information */
 	struct ast_sip_transport_state *state;
+	/*! QOS DSCP TOS bits */
+	unsigned int tos;
+	/*! QOS COS value */
+	unsigned int cos;
 };
 
 /*!
@@ -323,6 +327,26 @@
 		AST_STRING_FIELD(external_media_address);
 		/*! Configured voicemail boxes for this endpoint. Used for MWI */
 		AST_STRING_FIELD(mailboxes);
+		/*! Configured RTP engine for this endpoint. */
+		AST_STRING_FIELD(rtp_engine);
+		/*! Configured tone zone for this endpoint. */
+		AST_STRING_FIELD(zone);
+		/*! Configured language for this endpoint. */
+		AST_STRING_FIELD(language);
+		/*! Feature to enact when one-touch recording INFO with Record: On is received */
+		AST_STRING_FIELD(recordonfeature);
+		/*! Feature to enact when one-touch recording INFO with Record: Off is received */
+		AST_STRING_FIELD(recordofffeature);
+		/*! SDP origin username */
+		AST_STRING_FIELD(sdpowner);
+		/*! SDP session name */
+		AST_STRING_FIELD(sdpsession);
+		/*! Default username to place in From header */
+		AST_STRING_FIELD(fromuser);
+		/*! Domain to place in From header */
+		AST_STRING_FIELD(fromdomain);
+		/*! Username to use when sending MWI NOTIFYs to this endpoint */
+		AST_STRING_FIELD(mwi_from);
 	);
 	/*! Identification information for this endpoint */
 	struct ast_party_id id;
@@ -408,6 +432,20 @@
 	struct ast_endpoint *persistent;
 	/*! The number of channels at which busy device state is returned */
 	unsigned int devicestate_busy_at;
+	/*! Determines if transfers (using REFER) are allowed by this endpoint */
+	unsigned int allowtransfer;
+	/*! DSCP TOS bits for audio streams */
+	unsigned int tos_audio;
+	/*! Priority for audio streams */
+	unsigned int cos_audio;
+	/*! DSCP TOS bits for video streams */
+	unsigned int tos_video;
+	/*! Priority for video streams */
+	unsigned int cos_video;
+	/*! Indicates if endpoint is allowed to initiate subscriptions */
+	unsigned int allowsubscribe;
+	/*! The minimum allowed expiration for subscriptions from endpoint */
+	unsigned int subminexpiry;
 };
 
 /*!
@@ -1057,13 +1095,15 @@
  * \param endpoint Optional. If specified, the request will be created out-of-dialog
  * to the endpoint.
  * \param uri Optional. If specified, the request will be sent to this URI rather
+ * this value.
  * than one configured for the endpoint.
  * \param[out] tdata The newly-created request
  * \retval 0 Success
  * \retval -1 Failure
  */
 int ast_sip_create_request(const char *method, struct pjsip_dialog *dlg,
-		struct ast_sip_endpoint *endpoint, const char *uri, pjsip_tx_data **tdata);
+		struct ast_sip_endpoint *endpoint, const char *uri,
+		pjsip_tx_data **tdata);
 
 /*!
  * \brief General purpose method for sending a SIP request
@@ -1308,4 +1348,12 @@
  */
 void ast_sip_report_auth_challenge_sent(struct ast_sip_endpoint *endpoint, pjsip_rx_data *rdata, pjsip_tx_data *tdata);
 
+void ast_sip_initialize_global_headers(void);
+void ast_sip_destroy_global_headers(void);
+
+int ast_sip_add_global_request_header(const char *name, const char *value, int replace);
+int ast_sip_add_global_response_header(const char *name, const char *value, int replace);
+
+int ast_sip_initialize_sorcery_global(struct ast_sorcery *sorcery);
+
 #endif /* _RES_SIP_H */

Modified: trunk/res/res_sip.c
URL: http://svnview.digium.com/svn/asterisk/trunk/res/res_sip.c?view=diff&rev=394759&r1=394758&r2=394759
==============================================================================
--- trunk/res/res_sip.c (original)
+++ trunk/res/res_sip.c Thu Jul 18 14:25:51 2013
@@ -386,6 +386,96 @@
 						Gulp channel driver will return busy as the device state instead of in use.
 					</para></description>
 				</configOption>
+				<configOption name="tonezone">
+					<synopsis>Set which country's indications to use for channels created for this endpoint.</synopsis>
+				</configOption>
+				<configOption name="language">
+					<synopsis>Set the default language to use for channels created for this endpoint.</synopsis>
+				</configOption>
+				<configOption name="one_touch_recording" default="no">
+					<synopsis>Determines whether one-touch recording is allowed for this endpoint.</synopsis>
+					<see-also>
+						<ref type="configOption">recordonfeature</ref>
+						<ref type="configOption">recordofffeature</ref>
+					</see-also>
+				</configOption>
+				<configOption name="recordonfeature" default="automixmon">
+					<synopsis>The feature to enact when one-touch recording is turned on.</synopsis>
+					<description>
+						<para>When an INFO request for one-touch recording arrives with a Record header set to "on", this
+						feature will be enabled for the channel. The feature designated here can be any built-in
+						or dynamic feature defined in features.conf.</para>
+						<note><para>This setting has no effect if the endpoint's one_touch_recording option is disabled</para></note>
+					</description>
+					<see-also>
+						<ref type="configOption">one_touch_recording</ref>
+						<ref type="configOption">recordofffeature</ref>
+					</see-also>
+				</configOption>
+				<configOption name="recordofffeature" default="automixmon">
+					<synopsis>The feature to enact when one-touch recording is turned off.</synopsis>
+					<description>
+						<para>When an INFO request for one-touch recording arrives with a Record header set to "off", this
+						feature will be enabled for the channel. The feature designated here can be any built-in
+						or dynamic feature defined in features.conf.</para>
+						<note><para>This setting has no effect if the endpoint's one_touch_recording option is disabled</para></note>
+					</description>
+					<see-also>
+						<ref type="configOption">one_touch_recording</ref>
+						<ref type="configOption">recordonfeature</ref>
+					</see-also>
+				</configOption>
+				<configOption name="rtpengine" default="asterisk">
+					<synopsis>Name of the RTP engine to use for channels created for this endpoint</synopsis>
+				</configOption>
+				<configOption name="allowtransfer" default="yes">
+					<synopsis>Determines whether SIP REFER transfers are allowed for this endpoint</synopsis>
+				</configOption>
+				<configOption name="sdpowner" default="-">
+					<synopsis>String placed as the username portion of an SDP origin (o=) line.</synopsis>
+				</configOption>
+				<configOption name="sdpsession" default="Asterisk">
+					<synopsis>String used for the SDP session (s=) line.</synopsis>
+				</configOption>
+				<configOption name="tos_audio">
+					<synopsis>DSCP TOS bits for audio streams</synopsis>
+					<description><para>
+						See https://wiki.asterisk.org/wiki/display/AST/IP+Quality+of+Service for more information about QoS settings
+					</para></description>
+				</configOption>
+				<configOption name="tos_video">
+					<synopsis>DSCP TOS bits for video streams</synopsis>
+					<description><para>
+						See https://wiki.asterisk.org/wiki/display/AST/IP+Quality+of+Service for more information about QoS settings
+					</para></description>
+				</configOption>
+				<configOption name="cos_audio">
+					<synopsis>Priority for audio streams</synopsis>
+					<description><para>
+						See https://wiki.asterisk.org/wiki/display/AST/IP+Quality+of+Service for more information about QoS settings
+					</para></description>
+				</configOption>
+				<configOption name="cos_video">
+					<synopsis>Priority for video streams</synopsis>
+					<description><para>
+						See https://wiki.asterisk.org/wiki/display/AST/IP+Quality+of+Service for more information about QoS settings
+					</para></description>
+				</configOption>
+				<configOption name="allowsubscribe" default="no">
+					<synopsis>Determines if endpoint is allowed to initiate subscriptions with Asterisk.</synopsis>
+				</configOption>
+				<configOption name="subminexpiry" default="60">
+					<synopsis>The minimum allowed expiry time for subscriptions initiated by the endpoint.</synopsis>
+				</configOption>
+				<configOption name="fromuser">
+					<synopsis>Username to use in From header for requests to this endpoint.</synopsis>
+				</configOption>
+				<configOption name="mwifromuser">
+					<synopsis>Username to use in From header for unsolicited MWI NOTIFYs to this endpoint.</synopsis>
+				</configOption>
+				<configOption name="fromdomain">
+					<synopsis>Domain to user in From header for requests to this endpoint.</synopsis>
+				</configOption>
 			</configObject>
 			<configObject name="auth">
 				<synopsis>Authentication type</synopsis>
@@ -674,6 +764,48 @@
 					</para></description>
 				</configOption>
 			</configObject>
+			<configObject name="system">
+				<synopsis>Options that apply to the SIP stack as well as other system-wide settings</synopsis>
+				<description><para>
+					The settings in this section are global. In addition to being global, the values will
+					not be re-evaluated when a reload is performed. This is because the values must be set
+					before the SIP stack is initialized. The only way to reset these values is to either 
+					restart Asterisk, or unload res_sip.so and then load it again.
+				</para></description>
+				<configOption name="timert1" default="500">
+					<synopsis>Set transaction timer T1 value (milliseconds).</synopsis>
+					<description><para>
+						Timer T1 is the base for determining how long to wait before retransmitting
+						requests that receive no response when using an unreliable transport (e.g. UDP).
+						For more information on this timer, see RFC 3261, Section 17.1.1.1.
+					</para></description>
+				</configOption>
+				<configOption name="timerb" default="32000">
+					<synopsis>Set transaction timer B value (milliseconds).</synopsis>
+					<description><para>
+						Timer B determines the maximum amount of time to wait after sending an INVITE
+						request before terminating the transaction. It is recommended that this be set
+						to 64 * Timer T1, but it may be set higher if desired. For more information on
+						this timer, see RFC 3261, Section 17.1.1.1.
+					</para></description>
+				</configOption>
+				<configOption name="compactheaders" default="no">
+					<synopsis>Use the short forms of common SIP header names.</synopsis>
+				</configOption>
+			</configObject>
+			<configObject name="global">
+				<synopsis>Options that apply globally to all SIP communications</synopsis>
+				<description><para>
+					The settings in this section are global. Unlike options in the <literal>system</literal>
+					section, these options can be refreshed by performing a reload.
+				</para></description>
+				<configOption name="maxforwards" default="70">
+					<synopsis>Value used in Max-Forwards header for SIP requests.</synopsis>
+				</configOption>
+				<configOption name="useragent" default="Asterisk &lt;Asterisk Version&gt;">
+					<synopsis>Value used in User-Agent header for SIP requests and Server header for SIP responses.</synopsis>
+				</configOption>
+			</configObject>
 		</configFile>
 	</configInfo>
  ***/
@@ -865,7 +997,7 @@
 	return ast_pjsip_endpoint;
 }
 
-static int sip_dialog_create_from(pj_pool_t *pool, pj_str_t *from, const char *user, const pj_str_t *target, pjsip_tpselector *selector)
+static int sip_dialog_create_from(pj_pool_t *pool, pj_str_t *from, const char *user, const char *domain, const pj_str_t *target, pjsip_tpselector *selector)
 {
 	pj_str_t tmp, local_addr;
 	pjsip_uri *uri;
@@ -874,7 +1006,7 @@
 	int local_port;
 	char uuid_str[AST_UUID_STR_LEN];
 
-	if (!user) {
+	if (ast_strlen_zero(user)) {
 		RAII_VAR(struct ast_uuid *, uuid, ast_uuid_generate(), ast_free_ptr);
 		if (!uuid) {
 			return -1;
@@ -908,6 +1040,18 @@
 	/* If the host is IPv6 turn the transport into an IPv6 version */
 	if (pj_strchr(&sip_uri->host, ':') && type < PJSIP_TRANSPORT_START_OTHER) {
 		type = (pjsip_transport_type_e)(((int)type) + PJSIP_TRANSPORT_IPV6);
+	}
+
+	if (!ast_strlen_zero(domain)) {
+		from->ptr = pj_pool_alloc(pool, PJSIP_MAX_URL_SIZE);
+		from->slen = pj_ansi_snprintf(from->ptr, PJSIP_MAX_URL_SIZE,
+				"<%s:%s@%s%s%s>",
+				(pjsip_transport_get_flag_from_type(type) & PJSIP_TRANSPORT_SECURE) ? "sips" : "sip",
+				user,
+				domain,
+				(type != PJSIP_TRANSPORT_UDP && type != PJSIP_TRANSPORT_UDP6) ? ";transport=" : "",
+				(type != PJSIP_TRANSPORT_UDP && type != PJSIP_TRANSPORT_UDP6) ? pjsip_transport_get_type_name(type) : "");
+		return 0;
 	}
 
 	/* Get the local bound address for the transport that will be used when communicating with the provided URI */
@@ -1000,7 +1144,7 @@
 		return NULL;
 	}
 
-	if (sip_dialog_create_from(dlg->pool, &local_uri, NULL, &remote_uri, &selector)) {
+	if (sip_dialog_create_from(dlg->pool, &local_uri, endpoint->fromuser, endpoint->fromdomain, &remote_uri, &selector)) {
 		pjsip_dlg_terminate(dlg);
 		return NULL;
 	}
@@ -1127,7 +1271,8 @@
 		return -1;
 	}
 
-	if (sip_dialog_create_from(pool, &from, NULL, &remote_uri, &selector)) {
+	if (sip_dialog_create_from(pool, &from, endpoint ? endpoint->fromuser : NULL,
+				endpoint ? endpoint->fromdomain : NULL, &remote_uri, &selector)) {
 		ast_log(LOG_ERROR, "Unable to create From header for %.*s request to endpoint %s\n",
 				(int) pj_strlen(&method->name), pj_strbuf(&method->name), ast_sorcery_object_get_id(endpoint));
 		pjsip_endpt_release_pool(ast_sip_get_pjsip_endpoint(), pool);
@@ -1150,7 +1295,8 @@
 }
 
 int ast_sip_create_request(const char *method, struct pjsip_dialog *dlg,
-		struct ast_sip_endpoint *endpoint, const char *uri, pjsip_tx_data **tdata)
+		struct ast_sip_endpoint *endpoint, const char *uri,
+		pjsip_tx_data **tdata)
 {
 	const pjsip_method *pmethod = get_pjsip_method(method);
 
@@ -1441,6 +1587,18 @@
 	}
 
 	return *servant_id == SIP_SERVANT_ID;
+}
+
+static void remove_request_headers(pjsip_endpoint *endpt)
+{
+	const pjsip_hdr *request_headers = pjsip_endpt_get_request_headers(endpt);
+	pjsip_hdr *iter = request_headers->next;
+
+	while (iter != request_headers) {
+		pjsip_hdr *to_erase = iter;
+		iter = iter->next;
+		pj_list_erase(to_erase);
+	}
 }
 
 static int load_module(void)
@@ -1480,9 +1638,20 @@
 		ast_log(LOG_ERROR, "Failed to create PJSIP endpoint structure. Aborting load\n");
 		goto error;
 	}
+
+	/* PJSIP will automatically try to add a Max-Forwards header. Since we want to control that,
+	 * we need to stop PJSIP from doing it automatically
+	 */
+	remove_request_headers(ast_pjsip_endpoint);
+
 	memory_pool = pj_pool_create(&caching_pool.factory, "SIP", 1024, 1024, NULL);
 	if (!memory_pool) {
 		ast_log(LOG_ERROR, "Failed to create memory pool for SIP. Aborting load\n");
+		goto error;
+	}
+
+	if (ast_sip_initialize_system()) {
+		ast_log(LOG_ERROR, "Failed to initialize SIP system configuration. Aborting load\n");
 		goto error;
 	}
 
@@ -1497,6 +1666,8 @@
 		goto error;
 	}
 
+	ast_sip_initialize_global_headers();
+
 	if (ast_res_sip_initialize_configuration()) {
 		ast_log(LOG_ERROR, "Failed to initialize SIP configuration. Aborting load\n");
 		goto error;
@@ -1521,6 +1692,7 @@
 error:
 	ast_sip_destroy_distributor();
 	ast_res_sip_destroy_configuration();
+	ast_sip_destroy_global_headers();
 	if (monitor_thread) {
 		stop_monitor_thread();
 	}
@@ -1564,6 +1736,7 @@
 {
 	ast_sip_destroy_distributor();
 	ast_res_sip_destroy_configuration();
+	ast_sip_destroy_global_headers();
 	if (monitor_thread) {
 		stop_monitor_thread();
 	}

Modified: trunk/res/res_sip.exports.in
URL: http://svnview.digium.com/svn/asterisk/trunk/res/res_sip.exports.in?view=diff&rev=394759&r1=394758&r2=394759
==============================================================================
--- trunk/res/res_sip.exports.in (original)
+++ trunk/res/res_sip.exports.in Thu Jul 18 14:25:51 2013
@@ -60,6 +60,11 @@
 		LINKER_SYMBOL_PREFIXast_sip_report_auth_failed_challenge_response;
 		LINKER_SYMBOL_PREFIXast_sip_report_auth_success;
 		LINKER_SYMBOL_PREFIXast_sip_report_auth_challenge_sent;
+		LINKER_SYMBOL_PREFIXast_sip_initialize_global_headers;
+		LINKER_SYMBOL_PREFIXast_sip_destroy_global_headers;
+		LINKER_SYMBOL_PREFIXast_sip_add_global_request_header;
+		LINKER_SYMBOL_PREFIXast_sip_add_global_response_header;
+		LINKER_SYMBOL_PREFIXast_sip_initialize_sorcery_global;
 	local:
 		*;
 };

Modified: trunk/res/res_sip/config_transport.c
URL: http://svnview.digium.com/svn/asterisk/trunk/res/res_sip/config_transport.c?view=diff&rev=394759&r1=394758&r2=394759
==============================================================================
--- trunk/res/res_sip/config_transport.c (original)
+++ trunk/res/res_sip/config_transport.c Thu Jul 18 14:25:51 2013
@@ -79,6 +79,18 @@
 	return transport;
 }
 
+static void set_qos(struct ast_sip_transport *transport, pj_qos_params *qos)
+{
+	if (transport->tos) {
+		qos->flags |= PJ_QOS_PARAM_HAS_DSCP;
+		qos->dscp_val = transport->tos;
+	}
+	if (transport->cos) {
+		qos->flags |= PJ_QOS_PARAM_HAS_SO_PRIO;
+		qos->so_prio = transport->cos;
+	}
+}
+
 /*! \brief Apply handler for transports */
 static int transport_apply(const struct ast_sorcery *sorcery, void *obj)
 {
@@ -135,12 +147,23 @@
 		} else if (transport->host.addr.sa_family == pj_AF_INET6()) {
 			res = pjsip_udp_transport_start6(ast_sip_get_pjsip_endpoint(), &transport->host.ipv6, NULL, transport->async_operations, &transport->state->transport);
 		}
+
+		if (res == PJ_SUCCESS && (transport->tos || transport->cos)) {
+			pj_sock_t sock;
+			pj_qos_params qos_params;
+
+			sock = pjsip_udp_transport_get_socket(transport->state->transport);
+			pj_sock_get_qos_params(sock, &qos_params);
+			set_qos(transport, &qos_params);
+			pj_sock_set_qos_params(sock, &qos_params);
+		}
 	} else if (transport->type == AST_TRANSPORT_TCP) {
 		pjsip_tcp_transport_cfg cfg;
 
 		pjsip_tcp_transport_cfg_default(&cfg, transport->host.addr.sa_family);
 		cfg.bind_addr = transport->host;
 		cfg.async_cnt = transport->async_operations;
+		set_qos(transport, &cfg.qos_params);
 
 		res = pjsip_tcp_transport_start3(ast_sip_get_pjsip_endpoint(), &cfg, &transport->state->factory);
 	} else if (transport->type == AST_TRANSPORT_TLS) {
@@ -148,9 +171,13 @@
 		transport->tls.cert_file = pj_str((char*)transport->cert_file);
 		transport->tls.privkey_file = pj_str((char*)transport->privkey_file);
 		transport->tls.password = pj_str((char*)transport->password);
+		set_qos(transport, &transport->tls.qos_params);
 
 		res = pjsip_tls_transport_start2(ast_sip_get_pjsip_endpoint(), &transport->tls, &transport->host, NULL, transport->async_operations, &transport->state->factory);
 	} else if ((transport->type == AST_TRANSPORT_WS) || (transport->type == AST_TRANSPORT_WSS)) {
+		if (transport->cos || transport->tos) {
+			ast_log(LOG_WARNING, "TOS and COS values ignored for websocket transport\n");
+		}
 		res = PJ_SUCCESS;
 	}
 
@@ -304,6 +331,8 @@
 	ast_sorcery_object_field_register_custom(sorcery, "transport", "method", "", transport_tls_method_handler, NULL, 0, 0);
 	ast_sorcery_object_field_register_custom(sorcery, "transport", "cipher", "", transport_tls_cipher_handler, NULL, 0, 0);
 	ast_sorcery_object_field_register_custom(sorcery, "transport", "localnet", "", transport_localnet_handler, NULL, 0, 0);
-
-	return 0;
-}
+	ast_sorcery_object_field_register(sorcery, "transport", "tos", "0", OPT_UINT_T, 0, FLDSET(struct ast_sip_transport, tos));
+	ast_sorcery_object_field_register(sorcery, "transport", "cos", "0", OPT_UINT_T, 0, FLDSET(struct ast_sip_transport, cos));
+
+	return 0;
+}

Modified: trunk/res/res_sip/include/res_sip_private.h
URL: http://svnview.digium.com/svn/asterisk/trunk/res/res_sip/include/res_sip_private.h?view=diff&rev=394759&r1=394758&r2=394759
==============================================================================
--- trunk/res/res_sip/include/res_sip_private.h (original)
+++ trunk/res/res_sip/include/res_sip_private.h Thu Jul 18 14:25:51 2013
@@ -55,4 +55,20 @@
  */
 int ast_sip_initialize_outbound_authentication(void);
 
+/*!
+ * \brief Initialize system configuration
+ *
+ * \retval 0 Success
+ * \retval non-zero Failure
+ */
+int ast_sip_initialize_system(void);
+
+/*!
+ * \brief Initialize global configuration
+ *
+ * \retval 0 Success
+ * \retval non-zero Failure
+ */
+int ast_sip_initialize_global(void);
+
 #endif /* RES_SIP_PRIVATE_H_ */

Modified: trunk/res/res_sip/sip_configuration.c
URL: http://svnview.digium.com/svn/asterisk/trunk/res/res_sip/sip_configuration.c?view=diff&rev=394759&r1=394758&r2=394759
==============================================================================
--- trunk/res/res_sip/sip_configuration.c (original)
+++ trunk/res/res_sip/sip_configuration.c Thu Jul 18 14:25:51 2013
@@ -658,6 +658,24 @@
 	ast_sorcery_object_field_register_custom(sip_sorcery, "endpoint", "namedcallgroup", "", named_groups_handler, NULL, 0, 0);
 	ast_sorcery_object_field_register_custom(sip_sorcery, "endpoint", "namedpickupgroup", "", named_groups_handler, NULL, 0, 0);
 	ast_sorcery_object_field_register(sip_sorcery, "endpoint", "devicestate_busy_at", "0", OPT_UINT_T, 0, FLDSET(struct ast_sip_endpoint, devicestate_busy_at));
+	ast_sorcery_object_field_register(sip_sorcery, "endpoint", "rtpengine", "asterisk", OPT_STRINGFIELD_T, 0, STRFLDSET(struct ast_sip_endpoint, rtp_engine));
+	ast_sorcery_object_field_register(sip_sorcery, "endpoint", "tonezone", "", OPT_STRINGFIELD_T, 0, STRFLDSET(struct ast_sip_endpoint, zone));
+	ast_sorcery_object_field_register(sip_sorcery, "endpoint", "language", "", OPT_STRINGFIELD_T, 0, STRFLDSET(struct ast_sip_endpoint, language));
+	ast_sorcery_object_field_register(sip_sorcery, "endpoint", "recordonfeature", "automixmon", OPT_STRINGFIELD_T, 0, STRFLDSET(struct ast_sip_endpoint, recordonfeature));
+	ast_sorcery_object_field_register(sip_sorcery, "endpoint", "recordofffeature", "automixmon", OPT_STRINGFIELD_T, 0, STRFLDSET(struct ast_sip_endpoint, recordofffeature));
+	ast_sorcery_object_field_register(sip_sorcery, "endpoint", "allowtransfer", "yes", OPT_BOOL_T, 1, FLDSET(struct ast_sip_endpoint, allowtransfer));
+	ast_sorcery_object_field_register(sip_sorcery, "endpoint", "sdpowner", "-", OPT_STRINGFIELD_T, 0, STRFLDSET(struct ast_sip_endpoint, sdpowner));
+	ast_sorcery_object_field_register(sip_sorcery, "endpoint", "sdpsession", "Asterisk", OPT_STRINGFIELD_T, 0, STRFLDSET(struct ast_sip_endpoint, sdpsession));
+	ast_sorcery_object_field_register(sip_sorcery, "endpoint", "tos_audio", "0", OPT_UINT_T, 0, FLDSET(struct ast_sip_endpoint, tos_audio));
+	ast_sorcery_object_field_register(sip_sorcery, "endpoint", "tos_video", "0", OPT_UINT_T, 0, FLDSET(struct ast_sip_endpoint, tos_video));
+	ast_sorcery_object_field_register(sip_sorcery, "endpoint", "cos_audio", "0", OPT_UINT_T, 0, FLDSET(struct ast_sip_endpoint, cos_audio));
+	ast_sorcery_object_field_register(sip_sorcery, "endpoint", "cos_video", "0", OPT_UINT_T, 0, FLDSET(struct ast_sip_endpoint, cos_video));
+	ast_sorcery_object_field_register(sip_sorcery, "endpoint", "allowsubscribe", "no", OPT_BOOL_T, 1, FLDSET(struct ast_sip_endpoint, allowsubscribe));
+	ast_sorcery_object_field_register(sip_sorcery, "endpoint", "subminexpiry", "0", OPT_UINT_T, 0, FLDSET(struct ast_sip_endpoint, subminexpiry));
+	ast_sorcery_object_field_register(sip_sorcery, "endpoint", "subminexpirey", "0", OPT_UINT_T, 0, FLDSET(struct ast_sip_endpoint, subminexpiry));
+	ast_sorcery_object_field_register(sip_sorcery, "endpoint", "fromuser", "", OPT_STRINGFIELD_T, 0, STRFLDSET(struct ast_sip_endpoint, fromuser));
+	ast_sorcery_object_field_register(sip_sorcery, "endpoint", "fromdomain", "", OPT_STRINGFIELD_T, 0, STRFLDSET(struct ast_sip_endpoint, fromdomain));
+	ast_sorcery_object_field_register(sip_sorcery, "endpoint", "mwifromuser", "", OPT_STRINGFIELD_T, 0, STRFLDSET(struct ast_sip_endpoint, mwi_from));
 
 	if (ast_sip_initialize_sorcery_transport(sip_sorcery)) {
 		ast_log(LOG_ERROR, "Failed to register SIP transport support with sorcery\n");
@@ -691,6 +709,13 @@
 
 	if (ast_sip_initialize_sorcery_security(sip_sorcery)) {
 		ast_log(LOG_ERROR, "Failed to register SIP security support\n");
+		ast_sorcery_unref(sip_sorcery);
+		sip_sorcery = NULL;
+		return -1;
+	}
+
+	if (ast_sip_initialize_sorcery_global(sip_sorcery)) {
+		ast_log(LOG_ERROR, "Failed to register SIP Global support\n");
 		ast_sorcery_unref(sip_sorcery);
 		sip_sorcery = NULL;
 		return -1;

Modified: trunk/res/res_sip_caller_id.c
URL: http://svnview.digium.com/svn/asterisk/trunk/res/res_sip_caller_id.c?view=diff&rev=394759&r1=394758&r2=394759
==============================================================================
--- trunk/res/res_sip_caller_id.c (original)
+++ trunk/res/res_sip_caller_id.c Thu Jul 18 14:25:51 2013
@@ -398,7 +398,9 @@
 		pj_strdup2(pool, &id_name_addr->display, id->name.str);
 	}
 
-	pj_strdup2(pool, &id_uri->user, id->number.str);
+	if (id->number.valid) {
+		pj_strdup2(pool, &id_uri->user, id->number.str);
+	}
 }
 
 /*!

Modified: trunk/res/res_sip_mwi.c
URL: http://svnview.digium.com/svn/asterisk/trunk/res/res_sip_mwi.c?view=diff&rev=394759&r1=394758&r2=394759
==============================================================================
--- trunk/res/res_sip_mwi.c (original)
+++ trunk/res/res_sip_mwi.c Thu Jul 18 14:25:51 2013
@@ -281,6 +281,14 @@
 		return 0;
 	}
 
+	if (!ast_strlen_zero(endpoint->mwi_from)) {
+		pjsip_fromto_hdr *from = pjsip_msg_find_hdr(tdata->msg, PJSIP_H_FROM, NULL);
+		pjsip_name_addr *from_name_addr = (pjsip_name_addr *) from->uri;
+		pjsip_sip_uri *from_uri = pjsip_uri_get_uri(from_name_addr->uri);
+
+		pj_strdup2(tdata->pool, &from_uri->user, endpoint->mwi_from);
+	}
+
 	switch (state) {
 	case PJSIP_EVSUB_STATE_ACTIVE:
 		state_name = "active";

Modified: trunk/res/res_sip_one_touch_record_info.c
URL: http://svnview.digium.com/svn/asterisk/trunk/res/res_sip_one_touch_record_info.c?view=diff&rev=394759&r1=394758&r2=394759
==============================================================================
--- trunk/res/res_sip_one_touch_record_info.c (original)
+++ trunk/res/res_sip_one_touch_record_info.c Thu Jul 18 14:25:51 2013
@@ -51,12 +51,22 @@
 	pjsip_generic_string_hdr *record;
 	int feature_res;
 	char feature_code[AST_FEATURE_MAX_LEN];
+	const char *feature;
 	char *digit;
 
 	record = pjsip_msg_find_hdr_by_name(rdata->msg_info.msg, &rec_str, NULL);
 
 	/* If we don't have Record header, we have nothing to do */
-	if (!record || (pj_stricmp2(&record->hvalue, "on") && pj_stricmp2(&record->hvalue, "off"))) {
+	if (!record) {
+		return 0;
+	}
+
+	if (!pj_stricmp2(&record->hvalue, "on")) {
+		feature = session->endpoint->recordonfeature;
+	} else if (!pj_stricmp2(&record->hvalue, "off")) {
+		feature = session->endpoint->recordofffeature;
+	} else {
+		/* Don't send response because another module may handle this */
 		return 0;
 	}
 
@@ -66,13 +76,13 @@
 	}
 
 	/* Is this endpoint configured with One Touch Recording? */
-	if (!session->endpoint->one_touch_recording) {
+	if (!session->endpoint->one_touch_recording || ast_strlen_zero(feature)) {
 		send_response(session, 403, rdata);
 		return 0;
 	}
 
 	ast_channel_lock(session->channel);
-	feature_res = ast_get_builtin_feature(session->channel, "automixmon", feature_code, sizeof(feature_code));
+	feature_res = ast_get_feature(session->channel, feature, feature_code, sizeof(feature_code));
 	ast_channel_unlock(session->channel);
 
 	if (feature_res || ast_strlen_zero(feature_code)) {

Modified: trunk/res/res_sip_pubsub.c
URL: http://svnview.digium.com/svn/asterisk/trunk/res/res_sip_pubsub.c?view=diff&rev=394759&r1=394758&r2=394759
==============================================================================
--- trunk/res/res_sip_pubsub.c (original)
+++ trunk/res/res_sip_pubsub.c Thu Jul 18 14:25:51 2013
@@ -616,6 +616,7 @@
 	char accept[AST_SIP_MAX_ACCEPT][64];
 	pjsip_accept_hdr *accept_header;
 	pjsip_event_hdr *event_header;
+	pjsip_expires_hdr *expires_header;
 	struct ast_sip_subscription_handler *handler;
 	RAII_VAR(struct ast_sip_endpoint *, endpoint, NULL, ao2_cleanup);
 	struct ast_sip_subscription *sub;
@@ -623,6 +624,21 @@
 
 	endpoint = ast_pjsip_rdata_get_endpoint(rdata);
 	ast_assert(endpoint != NULL);
+
+	if (!endpoint->allowsubscribe) {
+		ast_log(LOG_WARNING, "Subscriptions not permitted for endpoint %s.\n", ast_sorcery_object_get_id(endpoint));
+		pjsip_endpt_respond_stateless(ast_sip_get_pjsip_endpoint(), rdata, 603, NULL, NULL, NULL);
+		return PJ_TRUE;
+	}
+
+	expires_header = pjsip_msg_find_hdr(rdata->msg_info.msg, PJSIP_H_EXPIRES, rdata->msg_info.msg->hdr.next);
+
+	if (expires_header && expires_header->ivalue < endpoint->subminexpiry) {
+		ast_log(LOG_WARNING, "Subscription expiration %d is too brief for endpoint %s. Minimum is %d\n",
+				expires_header->ivalue, ast_sorcery_object_get_id(endpoint), endpoint->subminexpiry);
+		pjsip_endpt_respond_stateless(ast_sip_get_pjsip_endpoint(), rdata, 423, NULL, NULL, NULL);
+		return PJ_TRUE;
+	}
 
 	event_header = pjsip_msg_find_hdr_by_name(rdata->msg_info.msg, &str_event_name, rdata->msg_info.msg->hdr.next);
 	if (!event_header) {

Modified: trunk/res/res_sip_refer.c
URL: http://svnview.digium.com/svn/asterisk/trunk/res/res_sip_refer.c?view=diff&rev=394759&r1=394758&r2=394759
==============================================================================
--- trunk/res/res_sip_refer.c (original)
+++ trunk/res/res_sip_refer.c Thu Jul 18 14:25:51 2013
@@ -732,6 +732,13 @@
 	pjsip_param *replaces;
 	int response;
 
+	if (!session->endpoint->allowtransfer) {
+		pjsip_dlg_respond(session->inv_session->dlg, rdata, 603, NULL, NULL, NULL);
+		ast_log(LOG_WARNING, "Endpoint %s transfer attempt blocked due to configuration\n",
+				ast_sorcery_object_get_id(session->endpoint));
+		return 0;
+	}
+
 	/* A Refer-To header is required */
 	if (!(refer_to = pjsip_msg_find_hdr_by_name(rdata->msg_info.msg, &str_refer_to, NULL))) {
 		pjsip_dlg_respond(session->inv_session->dlg, rdata, 400, NULL, NULL, NULL);

Modified: trunk/res/res_sip_sdp_rtp.c
URL: http://svnview.digium.com/svn/asterisk/trunk/res/res_sip_sdp_rtp.c?view=diff&rev=394759&r1=394758&r2=394759
==============================================================================
--- trunk/res/res_sip_sdp_rtp.c (original)
+++ trunk/res/res_sip_sdp_rtp.c Thu Jul 18 14:25:51 2013
@@ -108,7 +108,8 @@
 {
 	struct ast_rtp_engine_ice *ice;
 
-	if (!(session_media->rtp = ast_rtp_instance_new("asterisk", sched, ipv6 ? &address_ipv6 : &address_ipv4, NULL))) {
+	if (!(session_media->rtp = ast_rtp_instance_new(session->endpoint->rtp_engine, sched, ipv6 ? &address_ipv6 : &address_ipv4, NULL))) {
+		ast_log(LOG_ERROR, "Unable to create RTP instance using RTP engine '%s'\n", session->endpoint->rtp_engine);
 		return -1;
 	}
 
@@ -130,6 +131,16 @@
 		ast_rtp_instance_dtmf_mode_set(session_media->rtp, AST_RTP_DTMF_MODE_RFC2833);
 	} else if (session->endpoint->dtmf == AST_SIP_DTMF_INBAND) {
 		ast_rtp_instance_dtmf_mode_set(session_media->rtp, AST_RTP_DTMF_MODE_INBAND);
+	}
+
+	if (!strcmp(session_media->stream_type, STR_AUDIO) &&
+			(session->endpoint->tos_audio || session->endpoint->cos_video)) {
+		ast_rtp_instance_set_qos(session_media->rtp, session->endpoint->tos_audio,
+				session->endpoint->cos_audio, "SIP RTP Audio");
+	} else if (!strcmp(session_media->stream_type, STR_VIDEO) &&
+			(session->endpoint->tos_video || session->endpoint->cos_video)) {
+		ast_rtp_instance_set_qos(session_media->rtp, session->endpoint->tos_video,
+				session->endpoint->cos_video, "SIP RTP Video");
 	}
 
 	return 0;

Modified: trunk/res/res_sip_session.c
URL: http://svnview.digium.com/svn/asterisk/trunk/res/res_sip_session.c?view=diff&rev=394759&r1=394758&r2=394759
==============================================================================
--- trunk/res/res_sip_session.c (original)
+++ trunk/res/res_sip_session.c Thu Jul 18 14:25:51 2013
@@ -1684,7 +1684,6 @@
 static struct pjmedia_sdp_session *create_local_sdp(pjsip_inv_session *inv, struct ast_sip_session *session, const pjmedia_sdp_session *offer)
 {
 	RAII_VAR(struct ao2_iterator *, successful, NULL, ao2_iterator_cleanup);
-	static const pj_str_t STR_ASTERISK = { "Asterisk", 8 };
 	static const pj_str_t STR_IN = { "IN", 2 };
 	static const pj_str_t STR_IP4 = { "IP4", 3 };
 	static const pj_str_t STR_IP6 = { "IP6", 3 };
@@ -1701,11 +1700,11 @@
 		local->origin.id = offer->origin.id;
 	}
 
-	local->origin.user = STR_ASTERISK;
+	pj_strdup2(inv->pool, &local->origin.user, session->endpoint->sdpowner);
 	local->origin.net_type = STR_IN;
 	local->origin.addr_type = session->endpoint->rtp_ipv6 ? STR_IP6 : STR_IP4;
 	local->origin.addr = *pj_gethostname();
-	local->name = local->origin.user;
+	pj_strdup2(inv->pool, &local->name, session->endpoint->sdpsession);
 
 	/* Now let the handlers add streams of various types, pjmedia will automatically reorder the media streams for us */
 	successful = ao2_callback_data(session->media, OBJ_MULTIPLE, add_sdp_streams, local, session);




More information about the svn-commits mailing list