[asterisk-commits] oej: branch oej/codename-pineapple r46488 - in
/team/oej/codename-pineapple/c...
asterisk-commits at lists.digium.com
asterisk-commits at lists.digium.com
Mon Oct 30 12:52:21 MST 2006
Author: oej
Date: Mon Oct 30 13:52:21 2006
New Revision: 46488
URL: http://svn.digium.com/view/asterisk?rev=46488&view=rev
Log:
Merge the sipregister branch code, which is the basis for future type=service objects.
Modified:
team/oej/codename-pineapple/channels/chan_sip3.c
team/oej/codename-pineapple/channels/sip3/sip3.h
team/oej/codename-pineapple/channels/sip3/sip3_config.c
team/oej/codename-pineapple/channels/sip3/sip3_services.c
team/oej/codename-pineapple/channels/sip3/sip3funcs.h
Modified: team/oej/codename-pineapple/channels/chan_sip3.c
URL: http://svn.digium.com/view/asterisk/team/oej/codename-pineapple/channels/chan_sip3.c?rev=46488&r1=46487&r2=46488&view=diff
==============================================================================
--- team/oej/codename-pineapple/channels/chan_sip3.c (original)
+++ team/oej/codename-pineapple/channels/chan_sip3.c Mon Oct 30 13:52:21 2006
@@ -843,6 +843,10 @@
}
if (device->dnsmgr)
ast_dnsmgr_release(device->dnsmgr);
+ if (device->registry) {
+ device->registry->peer = NULL;
+ ASTOBJ_UNREF(device->registry,sip_registry_destroy);
+ }
free(device);
}
@@ -3913,6 +3917,7 @@
char tmpf[256] = "", *from;
struct sip_request *req;
char *colon;
+ int localdomain = TRUE;
req = oreq;
if (!req)
@@ -3979,16 +3984,48 @@
domain_context[0] = '\0';
if (!check_sip_domain(p->domain, domain_context, sizeof(domain_context))) {
+ localdomain = FALSE;
if (!global.allow_external_domains && (req->method == SIP_INVITE || req->method == SIP_REFER)) {
if (option_debug)
ast_log(LOG_DEBUG, "Got SIP %s to non-local domain '%s'; refusing request.\n", sip_method2txt(req->method), p->domain);
return -2;
}
}
- /* If we have a context defined, overwrite the original context */
+ /* If we have a domain context defined, overwrite the original context */
if (!ast_strlen_zero(domain_context))
ast_string_field_set(p, context, domain_context);
}
+
+ /* If the URI starts with our magic marker and has a corresponding
+ entry in the registry, then replace the URI with the extension
+ we want to use */
+ /* We don't have to check this at all if we have no registry entries... */
+ if (localdomain && req->method == SIP_INVITE) {
+ if (option_debug)
+ ast_log(LOG_DEBUG, "Checking %s for magic registry marker \n", uri);
+ /* Check if the incoming URI is a registry entry */
+ /* Need a function in ASTOBJ to check if there are objects
+ in the container at all here to avoid this check
+ when we have no registry entries */
+ if (!strncmp(uri, REG_MAGICMARKER, strlen(REG_MAGICMARKER))) {
+ int found = FALSE;
+
+ if (option_debug)
+ ast_log(LOG_DEBUG, "Checking for %s in registry\n", uri);
+ /* Traverse the registry to find something */
+ ASTOBJ_CONTAINER_TRAVERSE(®l, !found, do {
+ ASTOBJ_RDLOCK(iterator);
+ if (!strcmp(uri, iterator->contact)) {
+ found = TRUE;
+ /* Use the extension of this registry item for the incoming call */
+ uri = (char *) iterator->extension;
+ p->registry = iterator;
+ }
+ ASTOBJ_UNLOCK(iterator);
+ } while(0));
+ }
+ }
+
if (sip_debug_test_pvt(p))
ast_verbose("Looking for %s in %s (domain %s)\n", uri, p->context, p->domain);
@@ -4243,8 +4280,11 @@
if (ast_strlen_zero(of))
return AUTH_SUCCESSFUL;
- /* Find device in device list */
- device = find_device(of, NULL, 1);
+ if (p->registry && p->registry->peer) /* We already know this device from registry */
+ device = p->registry->peer;
+ else
+ /* Find device in device list */
+ device = find_device(of, NULL, 1);
if (device && !ast_apply_ha(device->ha, sin)) {
ASTOBJ_UNREF(device,sip_destroy_device);
device = NULL;
Modified: team/oej/codename-pineapple/channels/sip3/sip3.h
URL: http://svn.digium.com/view/asterisk/team/oej/codename-pineapple/channels/sip3/sip3.h?rev=46488&r1=46487&r2=46488&view=diff
==============================================================================
--- team/oej/codename-pineapple/channels/sip3/sip3.h (original)
+++ team/oej/codename-pineapple/channels/sip3/sip3.h Mon Oct 30 13:52:21 2006
@@ -44,8 +44,6 @@
#define IPTOS_MINCOST 0x02
#endif
-/* #define VOCAL_DATA_HACK */
-
#define DEFAULT_DEFAULT_EXPIRY 120
#define DEFAULT_MIN_EXPIRY 60
#define DEFAULT_MAX_EXPIRY 3600
@@ -54,6 +52,9 @@
/* These strings needs to be localized */
#define CALLERID_UNKNOWN "Unknown"
+
+/*! \brief Magic marker for registration contacts */
+#define REG_MAGICMARKER "ASTZVXW"
/* guard limit must be larger than guard secs */
/* guard min must be < 1000, and should be >= 250 */
@@ -608,6 +609,7 @@
#define SIP_PAGE2_CALL_ONHOLD_ONEDIR (1 << 23) /*!< 23: One directional hold */
#define SIP_PAGE2_CALL_ONHOLD_INACTIVE (2 << 24) /*!< 24: Inactive */
#define SIP_PAGE2_RFC2833_COMPENSATE (1 << 26)
+#define SIP_PAGE2_SERVICE (1 << 27) /*!< Whether this device is a service or not */
#define SIP_PAGE2_FLAGS_TO_COPY \
(SIP_PAGE2_ALLOWSUBSCRIBE | SIP_PAGE2_ALLOWOVERLAP | SIP_PAGE2_VIDEOSUPPORT | SIP_PAGE2_T38SUPPORT | SIP_PAGE2_RFC2833_COMPENSATE)
@@ -895,6 +897,7 @@
struct ast_ha *ha; /*!< Access control list */
struct ast_variable *chanvars; /*!< Variables to set for channel created by user */
struct sip_dialog *mwipvt; /*!< Subscription for MWI */
+ struct sip_registry *registry; /*!< If this is a service, which registration is connected to this device */
int lastmsg;
int autoframing;
};
@@ -916,6 +919,7 @@
AST_STRING_FIELD(secret); /*!< Password in clear text */
AST_STRING_FIELD(md5secret); /*!< Password in md5 */
AST_STRING_FIELD(contact); /*!< Contact extension */
+ AST_STRING_FIELD(extension); /*!< Extension for callback */
AST_STRING_FIELD(random);
);
int portno; /*!< Optional port override */
@@ -932,6 +936,7 @@
struct sockaddr_in us; /*!< Who the server thinks we are */
int noncecount; /*!< Nonce-count */
char lastmsg[256]; /*!< Last Message sent/received */
+ struct sip_peer *peer; /*!< If we have a known peer for this registry entry, use it for incoming calls */
};
/* Global settings only apply to the channel */
Modified: team/oej/codename-pineapple/channels/sip3/sip3_config.c
URL: http://svn.digium.com/view/asterisk/team/oej/codename-pineapple/channels/sip3/sip3_config.c?rev=46488&r1=46487&r2=46488&view=diff
==============================================================================
--- team/oej/codename-pineapple/channels/sip3/sip3_config.c (original)
+++ team/oej/codename-pineapple/channels/sip3/sip3_config.c Mon Oct 30 13:52:21 2006
@@ -305,7 +305,7 @@
struct ast_variable *tmpvar = NULL;
struct ast_flags peerflags[2] = {{(0)}};
struct ast_flags mask[2] = {{(0)}};
-
+ int register_lineno = 0;
if (!realtime)
/* Note we do NOT use find_peer here, to avoid realtime recursion */
@@ -517,6 +517,15 @@
peer->maxcallbitrate = atoi(v->value);
if (peer->maxcallbitrate < 0)
peer->maxcallbitrate = global.default_maxcallbitrate;
+ } else if (!strcasecmp(v->name, "register")) {
+ if (ast_true(v->value)) {
+ if (realtime)
+ ast_log(LOG_ERROR, "register=yes is not supported for realtime.\n");
+ else {
+ ast_set_flag(&peer->flags[1], SIP_PAGE2_SERVICE);
+ register_lineno = v->lineno;
+ }
+ }
} else if (!strcasecmp(v->name, "t38pt_udptl")) {
ast_set2_flag(&peer->flags[1], ast_true(v->value), SIP_PAGE2_T38SUPPORT_UDPTL);
} else if (!strcasecmp(v->name, "t38pt_rtp")) {
@@ -543,6 +552,14 @@
reg_source_db(peer);
ASTOBJ_UNMARK(peer);
ast_free_ha(oldha);
+ /* Start registration if needed */
+ if (ast_test_flag(&peer->flags[1], SIP_PAGE2_SERVICE)) {
+ sip_register(NULL, register_lineno, peer); /* XXX How do we handle this at reload?? */
+ } else if (peer->registry) {
+ /* We have a registry entry for a peer that no longer wished to be registered */
+ ASTOBJ_UNREF(peer->registry,sip_registry_destroy);
+ peer->registry = NULL;
+ }
return peer;
}
@@ -925,7 +942,7 @@
else
add_sip_domain(ast_strip(domain), SIP_DOMAIN_CONFIG, context ? ast_strip(context) : "");
} else if (!strcasecmp(v->name, "register")) {
- if (sip_register(v->value, v->lineno) == 0)
+ if (sip_register(v->value, v->lineno, NULL) == 0)
registry_count++;
} else if (!strcasecmp(v->name, "tos_sip")) {
if (ast_str2tos(v->value, &global.tos_sip))
Modified: team/oej/codename-pineapple/channels/sip3/sip3_services.c
URL: http://svn.digium.com/view/asterisk/team/oej/codename-pineapple/channels/sip3/sip3_services.c?rev=46488&r1=46487&r2=46488&view=diff
==============================================================================
--- team/oej/codename-pineapple/channels/sip3/sip3_services.c (original)
+++ team/oej/codename-pineapple/channels/sip3/sip3_services.c Mon Oct 30 13:52:21 2006
@@ -159,48 +159,65 @@
}
/*! \brief Parse register=> line in sip.conf and add to registry */
-int sip_register(char *value, int lineno)
+int sip_register(char *value, int lineno, struct sip_peer *peer)
{
struct sip_registry *reg;
- char copy[256];
- char *username=NULL, *hostname=NULL, *secret=NULL, *authuser=NULL;
- char *porta=NULL;
- char *contact=NULL;
- char *stringp=NULL;
+ char username[256] = "";
+ char randomcontact[256];
+ char *hostname = NULL, *secret = NULL, *authuser = NULL;
+ char *porta = NULL;
+ char *contact = NULL;
+ char *extension = NULL;
+ int portnum = 0;
- if (!value)
- return -1;
- ast_copy_string(copy, value, sizeof(copy));
- stringp=copy;
- username = stringp;
- hostname = strrchr(stringp, '@');
+ if (peer != NULL) { /* Build registration string from peer info */
+ /* Need to copy port number as well */
+ if (ast_strlen_zero(peer->fromuser))
+ snprintf(username, sizeof(username), "%s:%s@%s/%s",
+ peer->username, peer->secret, peer->tohost, peer->regexten);
+ else
+ snprintf(username, sizeof(username), "%s:%s:%s@%s/%s",
+ peer->username, peer->secret, peer->fromuser, peer->tohost, peer->regexten);
+ } else if (value)
+ ast_copy_string(username, value, sizeof(username));
+ else
+ username[0] = '\0';
+
+
+ /* ------ Parse registration string ----------- */
+ /* First split around the last '@' then parse the two components. */
+ hostname = strrchr(username, '@'); /* allow @ in the first part */
if (hostname)
*hostname++ = '\0';
if (ast_strlen_zero(username) || ast_strlen_zero(hostname)) {
ast_log(LOG_WARNING, "Format for registration is user[:secret[:authuser]]@host[:port][/contact] at line %d\n", lineno);
return -1;
}
- stringp = username;
- username = strsep(&stringp, ":");
- if (username) {
- secret = strsep(&stringp, ":");
- if (secret)
- authuser = strsep(&stringp, ":");
- }
- stringp = hostname;
- hostname = strsep(&stringp, "/");
- if (hostname)
- contact = strsep(&stringp, "/");
+ /* split user[:secret[:authuser]] */
+ secret = strchr(username, ':');
+ if (secret) {
+ *secret++ = '\0';
+ authuser = strchr(secret, ':');
+ if (authuser)
+ *authuser++ = '\0';
+ }
+ /* split host[:port][/contact] */
+ contact = strchr(hostname, '/');
+ if (contact)
+ *contact++ = '\0';
if (ast_strlen_zero(contact))
contact = "s";
- stringp=hostname;
- hostname = strsep(&stringp, ":");
- porta = strsep(&stringp, ":");
-
- if (porta && !atoi(porta)) {
- ast_log(LOG_WARNING, "%s is not a valid port number at line %d\n", porta, lineno);
- return -1;
- }
+ porta = strchr(hostname, ':');
+ if (porta) {
+ *porta++ = '\0';
+ portnum = atoi(porta);
+ if (portnum == 0) {
+ ast_log(LOG_WARNING, "%s is not a valid port number at line %d\n", porta, lineno);
+ return -1;
+ }
+ }
+
+ /* Allocate data */
if (!(reg = ast_calloc(1, sizeof(*reg)))) {
ast_log(LOG_ERROR, "Out of memory. Can't allocate SIP registry entry\n");
return -1;
@@ -212,9 +229,14 @@
return -1;
}
+ if (peer) {
+ reg->peer = peer;
+ peer->registry = reg;
+ // xxx?? ASTOBJ_REF(peer); /* Add reference counter to peer */
+ }
+
sipcounters.registry_objects++;
ASTOBJ_INIT(reg);
- ast_string_field_set(reg, contact, contact);
if (username)
ast_string_field_set(reg, username, username);
if (hostname)
@@ -223,6 +245,16 @@
ast_string_field_set(reg, authuser, authuser);
if (secret)
ast_string_field_set(reg, secret, secret);
+
+ if (extension)
+ ast_string_field_set(reg, extension, extension);
+ /* Build a random contact string for this registration entry */
+ generate_random_string(randomcontact, sizeof(randomcontact));
+ if (sipdebug)
+ ast_string_field_build(reg, contact, "%s-%s-%s-debug", REG_MAGICMARKER, randomcontact, extension);
+ else
+ ast_string_field_build(reg, contact, "%s-%s", REG_MAGICMARKER, randomcontact);
+
reg->expire = -1;
reg->expiry = expiry.default_expiry;
reg->timeout = -1;
@@ -255,6 +287,8 @@
ast_sched_del(sched, reg->expire);
if (reg->timeout > -1)
ast_sched_del(sched, reg->timeout);
+ if (reg->peer)
+ reg->peer->registry = NULL; /* XXX ASTOBJ_UNREF ??? */
ast_string_field_free_pools(reg);
sipcounters.registry_objects--;
free(reg);
@@ -415,6 +449,13 @@
if (!ast_strlen_zero(r->username))
ast_string_field_set(p, username, r->username);
/* Save extension in packet */
+
+ /* If we have a peer relationship, fetch som more data from taht peer.
+ */
+ if (r->peer) {
+ if (!ast_strlen_zero(r->peer->fromdomain))
+ ast_string_field_set(p, fromdomain, r->peer->fromdomain);
+ }
ast_string_field_set(p, exten, r->contact);
/*
Modified: team/oej/codename-pineapple/channels/sip3/sip3funcs.h
URL: http://svn.digium.com/view/asterisk/team/oej/codename-pineapple/channels/sip3/sip3funcs.h?rev=46488&r1=46487&r2=46488&view=diff
==============================================================================
--- team/oej/codename-pineapple/channels/sip3/sip3funcs.h (original)
+++ team/oej/codename-pineapple/channels/sip3/sip3funcs.h Mon Oct 30 13:52:21 2006
@@ -217,7 +217,7 @@
/* sip3_services.c - outbound registration for services from other servers/providers */
GNURK void sip_send_all_registers(void);
-GNURK int sip_register(char *value, int lineno);
+GNURK int sip_register(char *value, int lineno, struct sip_peer *peer);
GNURK void sip_registry_destroy(struct sip_registry *reg);
GNURK char *regstate2str(enum sipregistrystate regstate) attribute_const;
GNURK int handle_response_register(struct sip_dialog *p, int resp, char *rest, struct sip_request *req, int seqno);
More information about the asterisk-commits
mailing list