[asterisk-commits] file: branch file/pimp_sip_location r381278 - in /team/file/pimp_sip_location...
SVN commits to the Asterisk project
asterisk-commits at lists.digium.com
Tue Feb 12 12:08:33 CST 2013
Author: file
Date: Tue Feb 12 12:08:30 2013
New Revision: 381278
URL: http://svnview.digium.com/svn/asterisk?view=rev&rev=381278
Log:
Add a first stab location code prototype.
Added:
team/file/pimp_sip_location/res/res_sip/location.c (with props)
Modified:
team/file/pimp_sip_location/channels/chan_gulp.c
team/file/pimp_sip_location/include/asterisk/res_sip.h
team/file/pimp_sip_location/include/asterisk/res_sip_session.h
team/file/pimp_sip_location/res/res_sip.c
team/file/pimp_sip_location/res/res_sip.exports.in
team/file/pimp_sip_location/res/res_sip/sip_configuration.c
team/file/pimp_sip_location/res/res_sip_session.c
Modified: team/file/pimp_sip_location/channels/chan_gulp.c
URL: http://svnview.digium.com/svn/asterisk/team/file/pimp_sip_location/channels/chan_gulp.c?view=diff&rev=381278&r1=381277&r2=381278
==============================================================================
--- team/file/pimp_sip_location/channels/chan_gulp.c (original)
+++ team/file/pimp_sip_location/channels/chan_gulp.c Tue Feb 12 12:08:30 2013
@@ -502,22 +502,44 @@
/*! \brief Function called by core to create a new outgoing Gulp session */
static struct ast_channel *gulp_request(const char *type, struct ast_format_cap *cap, const struct ast_channel *requestor, const char *data, int *cause)
{
- struct ast_sip_endpoint *endpoint = ast_sip_endpoint_alloc("constant");
+ char *tmp = ast_strdupa(data), *endpoint_name = NULL, *request_user = NULL;
+ struct ast_sip_endpoint *endpoint = NULL;
struct ast_sip_session *session = NULL;
-
- if (!endpoint) {
+ AST_DECLARE_APP_ARGS(args,
+ AST_APP_ARG(endpoint);
+ AST_APP_ARG(location);
+ );
+
+ if (ast_strlen_zero(data)) {
+ ast_log(LOG_ERROR, "Unable to create Gulp channel with empty destination\n");
+ *cause = AST_CAUSE_CHANNEL_UNACCEPTABLE;
return NULL;
}
- /* TODO: This needs to actually grab a proper endpoint and such */
- ast_string_field_set(endpoint, context, "default");
- ast_parse_allow_disallow(&endpoint->prefs, endpoint->codecs, "ulaw", 1);
- endpoint->min_se = 90;
- endpoint->sess_expires = 1800;
+ AST_NONSTANDARD_APP_ARGS(args, tmp, '/');
+
+ /* If a request user has been specified extract it from the endpoint name portion */
+ if ((endpoint_name = strchr(args.endpoint, '@'))) {
+ request_user = args.endpoint;
+ *endpoint_name++ = '\0';
+ } else {
+ endpoint_name = args.endpoint;
+ }
+
+ if (ast_strlen_zero(endpoint_name)) {
+ ast_log(LOG_ERROR, "Unable to create Gulp channel with empty endpoint name\n");
+ *cause = AST_CAUSE_CHANNEL_UNACCEPTABLE;
+ return NULL;
+ } else if (!(endpoint = ast_sorcery_retrieve_by_id(ast_sip_get_sorcery(), "endpoint", endpoint_name))) {
+ ast_log(LOG_ERROR, "Unable to create Gulp channel - endpoint '%s' was not found", endpoint_name);
+ *cause = AST_CAUSE_NO_ROUTE_DESTINATION;
+ return NULL;
+ }
pj_thread_register_check();
- if (!(session = ast_sip_session_create_outgoing(endpoint, data))) {
+ if (!(session = ast_sip_session_create_outgoing(endpoint, args.location, request_user))) {
+ ao2_cleanup(endpoint);
return NULL;
}
Modified: team/file/pimp_sip_location/include/asterisk/res_sip.h
URL: http://svnview.digium.com/svn/asterisk/team/file/pimp_sip_location/include/asterisk/res_sip.h?view=diff&rev=381278&r1=381277&r2=381278
==============================================================================
--- team/file/pimp_sip_location/include/asterisk/res_sip.h (original)
+++ team/file/pimp_sip_location/include/asterisk/res_sip.h Tue Feb 12 12:08:30 2013
@@ -39,6 +39,7 @@
struct pjsip_transport;
struct pjsip_tpfactory;
struct pjsip_tls_setting;
+struct pjsip_tpselector;
/*!
* \brief Opaque structure representing related SIP tasks
@@ -112,34 +113,19 @@
};
/*!
- * \brief Contact associated with an address of record
- */
-struct ast_sip_contact {
+ * \brief Location information for a SIP entity
+ */
+struct ast_sip_location {
+ /*! Sorcery object details, the id is the name of the location */
+ SORCERY_OBJECT(details);
AST_DECLARE_STRING_FIELDS(
- /* XXX This may work better as an object instead of a string */
- /*! Full URI of the contact */
+ /*! Full URI of the location */
AST_STRING_FIELD(uri);
+ /*! Optional explicit transport to use */
+ AST_STRING_FIELD(transport);
);
- /*! Absolute time that this contact expires */
+ /*! Absolute time that this location is valid until */
time_t expiration_time;
- /*! Next list item */
- AST_LIST_ENTRY(ast_sip_contact) next;
-};
-
-/*!
- * \brief A SIP address of record
- */
-struct ast_sip_aor {
- AST_DECLARE_STRING_FIELDS(
- /*! Name of the address of record */
- AST_STRING_FIELD(name);
- );
- /*! Default contact expiration if one is not provided in the contact */
- int expiration;
- /*! Domain for the AOR */
- struct ast_sip_domain *domain;
- /*! Contacts bound to this AOR */
- AST_LIST_HEAD_NOLOCK(, ast_sip_contact) contacts;
};
/*!
@@ -209,31 +195,6 @@
};
/*!
- * \brief Given an endpoint, get its IP address
- *
- * \param endpoint The endpoint whose location is desired
- * \param[out] location_buf The IP address and port of the endpoint, as a string
- * \param size The size of the location buffer
- * \return void
- *
- * XXX The usefulness of retrieving an IP address is limited. It's more
- * useful to get a hostname or FQDN so that the location can be resolved.
- */
-void ast_sip_endpoint_get_location(const struct ast_sip_endpoint *endpoint, char *location_buf, size_t size);
-
-/*!
- * \brief Given an IP address, get the SIP endpoint that is located there.
- *
- * The returned endpoint will need to have its reference count decremented with ao2_ref()
- * once the caller has finished using it.
- *
- * \param addr The IP address
- * \retval NULL Could not find an endpoint with this IP address
- * \retval non-NULL The endpoint with this IP address
- */
-struct ast_sip_endpoint *ast_sip_get_endpoint_from_location(const char *addr);
-
-/*!
* \brief Data used for creating authentication challenges.
*
* This data gets populated by an authenticator's get_authentication_credentials() callback.
@@ -448,6 +409,16 @@
int ast_sip_initialize_sorcery_transport(struct ast_sorcery *sorcery);
/*!
+ * \brief Initialize location support on a sorcery instance
+ *
+ * \param sorcery The sorcery instance
+ *
+ * \retval -1 failure
+ * \retval 0 success
+ */
+int ast_sip_initialize_sorcery_location(struct ast_sorcery *sorcery);
+
+/*!
* \brief Create a new SIP work structure
*
* A SIP work is a means of grouping together SIP tasks. For instance, one
@@ -497,6 +468,19 @@
/*! The text to go in the body */
const char *body_text;
};
+
+/*!
+ * \brief General purpose method for creating a dialog with an endpoint
+ *
+ * \param endpoint A pointer to the endpoint
+ * \param location_name Optional name of the location to target, may even be an explicit SIP URI
+ * \param request_user Optional user to place into the target URI
+ * \param selector Populated transport selector information, should be applied to dialog afterwards
+ *
+ * \retval non-NULL success
+ * \retval NULL failure
+ */
+ pjsip_dialog *ast_sip_create_dialog(const struct ast_sip_endpoint *endpoint, const char *location_name, const char *request_user, struct pjsip_tpselector *selector);
/*!
* \brief General purpose method for sending a SIP request
Modified: team/file/pimp_sip_location/include/asterisk/res_sip_session.h
URL: http://svnview.digium.com/svn/asterisk/team/file/pimp_sip_location/include/asterisk/res_sip_session.h?view=diff&rev=381278&r1=381277&r2=381278
==============================================================================
--- team/file/pimp_sip_location/include/asterisk/res_sip_session.h (original)
+++ team/file/pimp_sip_location/include/asterisk/res_sip_session.h Tue Feb 12 12:08:30 2013
@@ -150,9 +150,10 @@
* \brief Create a new outgoing SIP session
*
* \param endpoint The endpoint that this session uses for settings
- * \param uri The URI to call
- */
-struct ast_sip_session *ast_sip_session_create_outgoing(struct ast_sip_endpoint *endpoint, const char *uri);
+ * \param location Optional name of the location to call, be it named location or explicit URI
+ * \param request_user Optional request user to place in the request URI if permitted
+ */
+struct ast_sip_session *ast_sip_session_create_outgoing(struct ast_sip_endpoint *endpoint, const char *location, const char *request_user);
/*!
* \brief Register an SDP handler
Modified: team/file/pimp_sip_location/res/res_sip.c
URL: http://svnview.digium.com/svn/asterisk/team/file/pimp_sip_location/res/res_sip.c?view=diff&rev=381278&r1=381277&r2=381278
==============================================================================
--- team/file/pimp_sip_location/res/res_sip.c (original)
+++ team/file/pimp_sip_location/res/res_sip.c Tue Feb 12 12:08:30 2013
@@ -226,6 +226,134 @@
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)
+{
+ pj_str_t tmp, local_addr;
+ pjsip_uri *uri;
+ pjsip_sip_uri *sip_uri;
+ pjsip_transport_type_e type = PJSIP_TRANSPORT_UNSPECIFIED;
+ int local_port;
+
+ /* Parse the provided target URI so we can determine what transport it will end up using */
+ pj_strdup_with_null(pool, &tmp, target);
+
+ if (!(uri = pjsip_parse_uri(pool, tmp.ptr, tmp.slen, 0)) ||
+ (!PJSIP_URI_SCHEME_IS_SIP(uri) && !PJSIP_URI_SCHEME_IS_SIPS(uri))) {
+ return -1;
+ }
+
+ sip_uri = pjsip_uri_get_uri(uri);
+
+ /* Determine the transport type to use */
+ if (PJSIP_URI_SCHEME_IS_SIPS(sip_uri)) {
+ type = PJSIP_TRANSPORT_TLS;
+ } else if (!sip_uri->transport_param.slen) {
+ type = PJSIP_TRANSPORT_UDP;
+ } else {
+ type = pjsip_transport_get_type_from_name(&sip_uri->transport_param);
+ }
+
+ if (type == PJSIP_TRANSPORT_UNSPECIFIED) {
+ return -1;
+ }
+
+ /* If the host is IPv6 turn the transport into an IPv6 version */
+ if (pj_strchr(&sip_uri->host, ':')) {
+ type = (pjsip_transport_type_e)(((int)type) + PJSIP_TRANSPORT_IPV6);
+ }
+
+ /* 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 IPv6 was not specified in the host but is in the transport, set the proper type */
+ if (!pj_strchr(&sip_uri->host, ':') && pj_strchr(&local_addr, ':')) {
+ type = (pjsip_transport_type_e)(((int)type) + PJSIP_TRANSPORT_IPV6);
+ }
+
+ 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:%d%s%s>",
+ (pjsip_transport_get_flag_from_type(type) & PJSIP_TRANSPORT_SECURE) ? "sips" : "sip",
+ user,
+ (type & PJSIP_TRANSPORT_IPV6) ? "[" : "",
+ (int)local_addr.slen,
+ local_addr.ptr,
+ (type & PJSIP_TRANSPORT_IPV6) ? "]" : "",
+ local_port,
+ (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;
+}
+
+
+
+pjsip_dialog *ast_sip_create_dialog(const struct ast_sip_endpoint *endpoint, const char *location_name, const char *request_user, pjsip_tpselector *selector)
+{
+ pj_str_t local_uri = pj_str("sip:temp at localhost"), remote_uri;
+ RAII_VAR(struct ast_sip_location *, location, NULL, ao2_cleanup);
+ pjsip_dialog *dlg = NULL;
+ const char *transport_name = endpoint->transport;
+ const pj_str_t HCONTACT = { "Contact", 7 };
+
+ /* Ensure no selector is used unless explicitly required */
+ selector->type = PJSIP_TPSELECTOR_NONE;
+
+ if (!ast_strlen_zero(location_name) && (location = ast_sorcery_retrieve_by_id(ast_sip_get_sorcery(), "location", location_name))) {
+ pj_cstr(&remote_uri, location->uri);
+ if (!ast_strlen_zero(location->transport)) {
+ transport_name = location->transport;
+ }
+ } else {
+ pj_cstr(&remote_uri, location_name);
+ }
+
+ if (pjsip_dlg_create_uac(pjsip_ua_instance(), &local_uri, NULL, &remote_uri, NULL, &dlg) != PJ_SUCCESS) {
+ return NULL;
+ }
+
+ if (!ast_strlen_zero(transport_name)) {
+ RAII_VAR(struct ast_sip_transport *, transport, ast_sorcery_retrieve_by_id(ast_sip_get_sorcery(), "transport", transport_name), ao2_cleanup);
+
+ if (!transport || !transport->state) {
+ pjsip_dlg_terminate(dlg);
+ return NULL;
+ }
+
+ if (transport->type == AST_SIP_TRANSPORT_UDP) {
+ selector->type = PJSIP_TPSELECTOR_TRANSPORT;
+ selector->u.transport = transport->state->transport;
+ } else if (transport->type == AST_SIP_TRANSPORT_TCP || transport->type == AST_SIP_TRANSPORT_TLS) {
+ selector->type = PJSIP_TPSELECTOR_LISTENER;
+ selector->u.listener = transport->state->factory;
+ } else {
+ pjsip_dlg_terminate(dlg);
+ return NULL;
+ }
+ }
+
+ if (sip_dialog_create_from(dlg->pool, &local_uri, "temp", &remote_uri, selector)) {
+ pjsip_dlg_terminate(dlg);
+ return NULL;
+ }
+
+ /* Update the dialog with the new local URI, we do it afterwards so we can use the dialog pool for construction */
+ pj_strdup_with_null(dlg->pool, &dlg->local.info_str, &local_uri);
+ dlg->local.info->uri = pjsip_parse_uri(dlg->pool, dlg->local.info_str.ptr, dlg->local.info_str.slen, 0);
+ dlg->local.contact = pjsip_parse_hdr(dlg->pool, &HCONTACT, local_uri.ptr, local_uri.slen, NULL);
+
+ /* If a request user has been specified and we are permitted to change it, do so */
+ if (!ast_strlen_zero(request_user) && (PJSIP_URI_SCHEME_IS_SIP(dlg->target) || PJSIP_URI_SCHEME_IS_SIPS(dlg->target))) {
+ pjsip_sip_uri *target = pjsip_uri_get_uri(dlg->target);
+ pj_strdup2(dlg->pool, &target->user, request_user);
+ }
+
+ return dlg;
+}
+
/* PJSIP doesn't know about the INFO method, so we have to define it ourselves */
const pjsip_method pjsip_info_method = {PJSIP_OTHER_METHOD, {"INFO", 4} };
Modified: team/file/pimp_sip_location/res/res_sip.exports.in
URL: http://svnview.digium.com/svn/asterisk/team/file/pimp_sip_location/res/res_sip.exports.in?view=diff&rev=381278&r1=381277&r2=381278
==============================================================================
--- team/file/pimp_sip_location/res/res_sip.exports.in (original)
+++ team/file/pimp_sip_location/res/res_sip.exports.in Tue Feb 12 12:08:30 2013
@@ -24,8 +24,7 @@
LINKER_SYMBOL_PREFIXast_sip_endpoint_alloc;
LINKER_SYMBOL_PREFIXast_copy_pj_str;
LINKER_SYMBOL_PREFIXast_sip_get_sorcery;
- LINKER_SYMBOL_PREFIXast_sip_get_endpoint_from_location;
- LINKER_SYMBOL_PREFIXast_sip_endpoint_get_location;
+ LINKER_SYMBOL_PREFIXast_sip_create_dialog;
LINKER_SYMBOL_PREFIXpj_*;
LINKER_SYMBOL_PREFIXpjsip_*;
LINKER_SYMBOL_PREFIXpjmedia_*;
Added: team/file/pimp_sip_location/res/res_sip/location.c
URL: http://svnview.digium.com/svn/asterisk/team/file/pimp_sip_location/res/res_sip/location.c?view=auto&rev=381278
==============================================================================
--- team/file/pimp_sip_location/res/res_sip/location.c (added)
+++ team/file/pimp_sip_location/res/res_sip/location.c Tue Feb 12 12:08:30 2013
@@ -1,0 +1,69 @@
+/*
+ * Asterisk -- An open source telephony toolkit.
+ *
+ * Copyright (C) 2013, Digium, Inc.
+ *
+ * Joshua Colp <jcolp at digium.com>
+ *
+ * See http://www.asterisk.org for more information about
+ * the Asterisk project. Please do not directly contact
+ * any of the maintainers of this project for assistance;
+ * the project provides a web site, mailing lists and IRC
+ * channels for your use.
+ *
+ * This program is free software, distributed under the terms of
+ * the GNU General Public License Version 2. See the LICENSE file
+ * at the top of the source tree.
+ */
+
+#include "asterisk.h"
+#undef bzero
+#define bzero bzero
+#include "pjsip.h"
+#include "pjlib.h"
+
+#include "asterisk/res_sip.h"
+#include "asterisk/logger.h"
+#include "asterisk/astobj2.h"
+#include "asterisk/sorcery.h"
+
+/*! \brief Destructor for location */
+ static void location_destroy(void *obj)
+ {
+ struct ast_sip_location *location = obj;
+
+ ast_string_field_free_memory(location);
+ }
+
+/*! \brief Allocator for location */
+static void *location_alloc(const char *name)
+{
+ struct ast_sip_location *location = ao2_alloc(sizeof(*location), location_destroy);
+
+ if (!location) {
+ return NULL;
+ }
+
+ if (ast_string_field_init(location, 256)) {
+ ao2_cleanup(location);
+ return NULL;
+ }
+
+ return location;
+}
+
+/*! \brief Initialize sorcery with location support */
+int ast_sip_initialize_sorcery_location(struct ast_sorcery *sorcery)
+{
+ ast_sorcery_apply_default(sorcery, "location", "config", "res_sip.conf,criteria=type=location");
+
+ if (ast_sorcery_object_register(sorcery, "location", location_alloc, NULL, NULL)) {
+ return -1;
+ }
+
+ ast_sorcery_object_field_register(sorcery, "location", "type", "", OPT_NOOP_T, 0, 0);
+ ast_sorcery_object_field_register(sorcery, "location", "uri", "", OPT_STRINGFIELD_T, 0, STRFLDSET(struct ast_sip_location, uri));
+ ast_sorcery_object_field_register(sorcery, "location", "transport", "", OPT_STRINGFIELD_T, 0, STRFLDSET(struct ast_sip_location, transport));
+
+ return 0;
+}
Propchange: team/file/pimp_sip_location/res/res_sip/location.c
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: team/file/pimp_sip_location/res/res_sip/location.c
------------------------------------------------------------------------------
svn:keywords = Author Date Id Revision
Propchange: team/file/pimp_sip_location/res/res_sip/location.c
------------------------------------------------------------------------------
svn:mime-type = text/plain
Modified: team/file/pimp_sip_location/res/res_sip/sip_configuration.c
URL: http://svnview.digium.com/svn/asterisk/team/file/pimp_sip_location/res/res_sip/sip_configuration.c?view=diff&rev=381278&r1=381277&r2=381278
==============================================================================
--- team/file/pimp_sip_location/res/res_sip/sip_configuration.c (original)
+++ team/file/pimp_sip_location/res/res_sip/sip_configuration.c Tue Feb 12 12:08:30 2013
@@ -21,17 +21,6 @@
static struct ast_sorcery *sip_sorcery;
-/*!
- * \brief Structure used to map an IP address to an endpoint.
- *
- * This is useful for determining if an incoming request
- * is coming from a particular endpoint.
- */
-struct sip_location_to_endpoint {
- SORCERY_OBJECT(details);
- const char *endpoint_name;
-};
-
static char *handle_cli_show_endpoints(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
{
RAII_VAR(struct ao2_container *, endpoints, NULL, ao2_cleanup);
@@ -72,71 +61,6 @@
static struct ast_cli_entry cli_commands[] = {
AST_CLI_DEFINE(handle_cli_show_endpoints, "Show SIP Endpoints"),
};
-
-static void sip_location_to_endpoint_destroy(void *obj)
-{
- struct sip_location_to_endpoint *location_to_endpoint = obj;
- ast_free((char *)location_to_endpoint->endpoint_name);
-}
-
-static void *sip_location_to_endpoint_alloc(const char *name)
-{
- return ao2_alloc(sizeof(struct sip_location_to_endpoint), sip_location_to_endpoint_destroy);
-}
-/*!
- * \brief Structure used to map an endpoint name to its location
- *
- * Location is stored as a string so that a FQDN may be stored
- * and the location may be resolved.
- *
- * This is useful for determining the destination for an outgoing
- * request to a specific endpoint
- */
-struct sip_endpoint_to_location {
- SORCERY_OBJECT(details);
- const char *host;
-};
-
-static void sip_endpoint_to_location_destroy(void *obj)
-{
- struct sip_endpoint_to_location *endpoint_to_location = obj;
- ast_free((char *) endpoint_to_location->host);
-}
-
-static void *sip_endpoint_to_location_alloc(const char *name)
-{
- return ao2_alloc(sizeof(struct sip_endpoint_to_location), sip_endpoint_to_location_destroy);
-}
-
-static int host_handler(const struct aco_option *opt, struct ast_variable *var, void *obj)
-{
- RAII_VAR(struct sip_location_to_endpoint *, location_to_endpoint, NULL, ao2_cleanup);
- RAII_VAR(struct sip_endpoint_to_location *, endpoint_to_location, NULL, ao2_cleanup);
- const char *host = var->value;
- const char *name = ast_sorcery_object_get_id(obj);
-
- location_to_endpoint = ast_sorcery_alloc(sip_sorcery, "location_to_endpoint", host);
- if (!location_to_endpoint) {
- return -1;
- }
- endpoint_to_location = ast_sorcery_alloc(sip_sorcery, "endpoint_to_location", name);
- if (!endpoint_to_location) {
- return -1;
- }
-
- location_to_endpoint->endpoint_name = ast_strdup(name);
- endpoint_to_location->host = ast_strdup(host);
-
- if (ast_sorcery_create(sip_sorcery, location_to_endpoint)) {
- return -1;
- }
- if (ast_sorcery_create(sip_sorcery, endpoint_to_location)) {
- ast_sorcery_delete(sip_sorcery, location_to_endpoint);
- return -1;
- }
-
- return 0;
-}
static int dtmf_handler(const struct aco_option *opt, struct ast_variable *var, void *obj)
{
@@ -207,25 +131,18 @@
ast_sorcery_apply_config(sip_sorcery, "res_sip");
ast_sorcery_apply_default(sip_sorcery, "endpoint", "config", "res_sip.conf,criteria=type=endpoint");
- ast_sorcery_apply_default(sip_sorcery, "location_to_endpoint", "memory", NULL);
- ast_sorcery_apply_default(sip_sorcery, "endpoint_to_location", "memory", NULL);
-
if (ast_sorcery_object_register(sip_sorcery, "endpoint", ast_sip_endpoint_alloc, NULL, NULL)) {
ast_log(LOG_ERROR, "Failed to register SIP endpoint object with sorcery\n");
ast_sorcery_unref(sip_sorcery);
sip_sorcery = NULL;
return -1;
}
-
- ast_sorcery_object_register(sip_sorcery, "location_to_endpoint", sip_location_to_endpoint_alloc, NULL, NULL);
- ast_sorcery_object_register(sip_sorcery, "endpoint_to_location", sip_endpoint_to_location_alloc, NULL, NULL);
ast_sorcery_object_field_register(sip_sorcery, "endpoint", "type", "", OPT_NOOP_T, 0, 0);
ast_sorcery_object_field_register(sip_sorcery, "endpoint", "context", "default", OPT_STRINGFIELD_T, 0, STRFLDSET(struct ast_sip_endpoint, context));
ast_sorcery_object_field_register(sip_sorcery, "endpoint", "disallow", "", OPT_CODEC_T, 0, FLDSET(struct ast_sip_endpoint, prefs, codecs));
ast_sorcery_object_field_register(sip_sorcery, "endpoint", "allow", "", OPT_CODEC_T, 1, FLDSET(struct ast_sip_endpoint, prefs, codecs));
ast_sorcery_object_field_register(sip_sorcery, "endpoint", "qualify_frequency", 0, OPT_UINT_T, PARSE_IN_RANGE, FLDSET(struct ast_sip_endpoint, qualify_frequency), 0, 86400);
- ast_sorcery_object_field_register_custom(sip_sorcery, "endpoint", "host", "", host_handler, NULL, 0, 0);
ast_sorcery_object_field_register_custom(sip_sorcery, "endpoint", "dtmfmode", "rfc4733", dtmf_handler, NULL, 0, 0);
ast_sorcery_object_field_register(sip_sorcery, "endpoint", "transport", "", OPT_STRINGFIELD_T, 0, STRFLDSET(struct ast_sip_endpoint, transport));
ast_sorcery_object_field_register_custom(sip_sorcery, "endpoint", "100rel", "yes", prack_handler, NULL, 0, 0);
@@ -240,6 +157,13 @@
return -1;
}
+ if (ast_sip_initialize_sorcery_location(sip_sorcery)) {
+ ast_log(LOG_ERROR, "Failed to register SIP location support with sorcery\n");
+ ast_sorcery_unref(sip_sorcery);
+ sip_sorcery = NULL;
+ return -1;
+ }
+
ast_sorcery_load(sip_sorcery);
return 0;
@@ -291,30 +215,6 @@
return endpoint;
}
-void ast_sip_endpoint_get_location(const struct ast_sip_endpoint *endpoint, char *location_buf, size_t size)
-{
- struct sip_endpoint_to_location *endpoint_to_location;
- endpoint_to_location = ast_sorcery_retrieve_by_id(sip_sorcery, "endpoint_to_location", ast_sorcery_object_get_id(endpoint));
- if (!endpoint_to_location) {
- return;
- }
- ast_copy_string(location_buf, endpoint_to_location->host, size);
- ao2_ref(endpoint_to_location, -1);
-}
-
-struct ast_sip_endpoint *ast_sip_get_endpoint_from_location(const char *location)
-{
- struct sip_location_to_endpoint *location_to_endpoint;
- struct ast_sip_endpoint *endpoint;
- location_to_endpoint = ast_sorcery_retrieve_by_id(sip_sorcery, "location_to_endpoint", location);
- if (!location_to_endpoint) {
- return NULL;
- }
- endpoint = ast_sorcery_retrieve_by_id(sip_sorcery, "endpoint", location_to_endpoint->endpoint_name);
- ao2_ref(location_to_endpoint, -1);
- return endpoint;
-}
-
struct ao2_container *ast_res_sip_get_endpoints(void)
{
struct ao2_container *endpoints;
Modified: team/file/pimp_sip_location/res/res_sip_session.c
URL: http://svnview.digium.com/svn/asterisk/team/file/pimp_sip_location/res/res_sip_session.c?view=diff&rev=381278&r1=381277&r2=381278
==============================================================================
--- team/file/pimp_sip_location/res/res_sip_session.c (original)
+++ team/file/pimp_sip_location/res/res_sip_session.c Tue Feb 12 12:08:30 2013
@@ -478,113 +478,18 @@
return session;
}
-static int sip_session_create_from(pj_pool_t *pool, pj_str_t *from, const char *user, const pj_str_t *target, pjsip_tpselector *selector)
-{
- pj_str_t tmp, local_addr;
- pjsip_uri *uri;
- pjsip_sip_uri *sip_uri;
- pjsip_transport_type_e type = PJSIP_TRANSPORT_UNSPECIFIED;
- int local_port;
-
- /* Parse the provided target URI so we can determine what transport it will end up using */
- pj_strdup_with_null(pool, &tmp, target);
-
- if (!(uri = pjsip_parse_uri(pool, tmp.ptr, tmp.slen, 0)) ||
- (!PJSIP_URI_SCHEME_IS_SIP(uri) && !PJSIP_URI_SCHEME_IS_SIPS(uri))) {
- return -1;
- }
-
- sip_uri = pjsip_uri_get_uri(uri);
-
- /* Determine the transport type to use */
- if (PJSIP_URI_SCHEME_IS_SIPS(sip_uri)) {
- type = PJSIP_TRANSPORT_TLS;
- } else if (!sip_uri->transport_param.slen) {
- type = PJSIP_TRANSPORT_UDP;
- } else {
- type = pjsip_transport_get_type_from_name(&sip_uri->transport_param);
- }
-
- if (type == PJSIP_TRANSPORT_UNSPECIFIED) {
- return -1;
- }
-
- /* If the host is IPv6 turn the transport into an IPv6 version */
- if (pj_strchr(&sip_uri->host, ':')) {
- type = (pjsip_transport_type_e)(((int)type) + PJSIP_TRANSPORT_IPV6);
- }
-
- /* 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 IPv6 was not specified in the host but is in the transport, set the proper type */
- if (!pj_strchr(&sip_uri->host, ':') && pj_strchr(&local_addr, ':')) {
- type = (pjsip_transport_type_e)(((int)type) + PJSIP_TRANSPORT_IPV6);
- }
-
- 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:%d%s%s>",
- (pjsip_transport_get_flag_from_type(type) & PJSIP_TRANSPORT_SECURE) ? "sips" : "sip",
- user,
- (type & PJSIP_TRANSPORT_IPV6) ? "[" : "",
- (int)local_addr.slen,
- local_addr.ptr,
- (type & PJSIP_TRANSPORT_IPV6) ? "]" : "",
- local_port,
- (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;
-}
-
-struct ast_sip_session *ast_sip_session_create_outgoing(struct ast_sip_endpoint *endpoint, const char *uri)
-{
- pj_str_t local_uri = pj_str("sip:temp at localhost"), remote_uri = pj_str((char*)uri);
+struct ast_sip_session *ast_sip_session_create_outgoing(struct ast_sip_endpoint *endpoint, const char *location, const char *request_user)
+{
+ pjsip_tpselector selector;
pjsip_dialog *dlg = NULL;
- const pj_str_t HCONTACT = { "Contact", 7 };
pjsip_inv_session *inv_session = NULL;
struct ast_sip_session *session = NULL;
pjmedia_sdp_session *offer = NULL;
- pjsip_tpselector selector = { .type = PJSIP_TPSELECTOR_NONE, };
pjsip_timer_setting timer;
- if (pjsip_dlg_create_uac(pjsip_ua_instance(), &local_uri, NULL, &remote_uri, NULL, &dlg) != PJ_SUCCESS) {
- return NULL;
- }
-
- if (!ast_strlen_zero(endpoint->transport)) {
- RAII_VAR(struct ast_sip_transport *, transport, ast_sorcery_retrieve_by_id(ast_sip_get_sorcery(), "transport", endpoint->transport), ao2_cleanup);
-
- if (!transport || !transport->state) {
- pjsip_dlg_terminate(dlg);
- return NULL;
- }
-
- if (transport->type == AST_SIP_TRANSPORT_UDP) {
- selector.type = PJSIP_TPSELECTOR_TRANSPORT;
- selector.u.transport = transport->state->transport;
- } else if (transport->type == AST_SIP_TRANSPORT_TCP || transport->type == AST_SIP_TRANSPORT_TLS) {
- selector.type = PJSIP_TPSELECTOR_LISTENER;
- selector.u.listener = transport->state->factory;
- } else {
- pjsip_dlg_terminate(dlg);
- return NULL;
- }
- }
-
- if (sip_session_create_from(dlg->pool, &local_uri, "test", &remote_uri, &selector)) {
- pjsip_dlg_terminate(dlg);
- return NULL;
- }
-
- /* Update the dialog with the new local URI, we do it afterwards so we can use the dialog pool for construction */
- pj_strdup_with_null(dlg->pool, &dlg->local.info_str, &local_uri);
- dlg->local.info->uri = pjsip_parse_uri(dlg->pool, dlg->local.info_str.ptr, dlg->local.info_str.slen, 0);
- dlg->local.contact = pjsip_parse_hdr(dlg->pool, &HCONTACT, local_uri.ptr, local_uri.slen, NULL);
+ if (!(dlg = ast_sip_create_dialog(endpoint, location, request_user, &selector))) {
+ return NULL;
+ }
if (pjsip_inv_create_uac(dlg, NULL, endpoint->extensions, &inv_session) != PJ_SUCCESS) {
pjsip_dlg_terminate(dlg);
@@ -597,7 +502,7 @@
timer.min_se = endpoint->min_se;
timer.sess_expires = endpoint->sess_expires;
pjsip_timer_init_session(inv_session, &timer);
-
+
if (pjsip_dlg_add_usage(dlg, &session_module, NULL) != PJ_SUCCESS) {
pjsip_inv_terminate(inv_session, 500, PJ_FALSE);
return NULL;
More information about the asterisk-commits
mailing list