--- /Users/jcovert/Desktop/Gtalk/res_jabber.c.1.6.1.head.c 2009-10-13 13:01:22.000000000 -0400
+++ /Users/jcovert/Desktop/Gtalk/res_jabber.c.1.6.1.gtalk-web.c 2009-10-13 18:15:57.000000000 -0400
@@ -59,18 +59,139 @@
#include "asterisk/astdb.h"
#include "asterisk/manager.h"
+/*** DOCUMENTATION
+
+
+ Send a Jabber Message
+
+
+
+ Client or transport Asterisk uses to connect to Jabber.
+
+
+ XMPP/Jabber JID (Name) of recipient.
+
+
+ Message to be sent to the buddy.
+
+
+
+ Allows user to send a message to a receipent via XMPP.
+
+
+
+
+ Retrieve the status of a jabber list member
+
+
+
+ Client or transport Asterisk users to connect to Jabber.
+
+
+ XMPP/Jabber JID (Name) of recipient.
+
+
+ Variable to store the status of requested user.
+
+
+
+ This application is deprecated. Please use the JABBER_STATUS() function instead.
+ Retrieves the numeric status associated with the specified buddy JID.
+ The return value in the Variablewill be one of the following.
+
+
+ Online.
+
+
+ Chatty.
+
+
+ Away.
+
+
+ Extended Away.
+
+
+ Do Not Disturb.
+
+
+ Offline.
+
+
+ Not In Roster.
+
+
+
+
+
+
+ Retrieve the status of a jabber list member
+
+
+
+ XMPP/Jabber ID (Name) of sender.
+
+
+ XMPP/Jabber JID (Name) of recipient.
+
+
+ Client or transport Asterisk users to connect to Jabber.
+
+
+
+ Retrieves the numeric status associated with the specified buddy JID.
+ The return value will be one of the following.
+
+
+ Online.
+
+
+ Chatty.
+
+
+ Away.
+
+
+ Extended Away.
+
+
+ Do Not Disturb.
+
+
+ Offline.
+
+
+ Not In Roster.
+
+
+
+
+
+
+ Sends a message to a Jabber Client.
+
+
+
+
+ Client or transport Asterisk uses to connect to JABBER.
+
+
+ XMPP/Jabber JID (Name) of recipient.
+
+
+ Message to be sent to the buddy.
+
+
+
+ Sends a message to a Jabber Client.
+
+
+ ***/
+
/*! \todo This should really be renamed to xmpp.conf. For backwards compatibility, we
need to read both files */
#define JABBER_CONFIG "jabber.conf"
-#ifndef FALSE
-#define FALSE 0
-#endif
-
-#ifndef TRUE
-#define TRUE 1
-#endif
-
/*-- Forward declarations */
static void aji_buddy_destroy(struct aji_buddy *obj);
static void aji_client_destroy(struct aji_client *obj);
@@ -96,7 +217,6 @@
static int aji_initialize(struct aji_client *client);
static int aji_client_connect(void *data, ikspak *pak);
static void aji_set_presence(struct aji_client *client, char *to, char *from, int level, char *desc);
-static char *aji_do_debug_deprecated(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a);
static char *aji_do_set_debug(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a);
static char *aji_do_reload(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a);
static char *aji_show_clients(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a);
@@ -123,9 +243,8 @@
static int aji_register_transport2(void *data, ikspak *pak);
*/
-static struct ast_cli_entry cli_aji_do_debug_deprecated = AST_CLI_DEFINE(aji_do_debug_deprecated, "Enable/disable jabber debugging");
static struct ast_cli_entry aji_cli[] = {
- AST_CLI_DEFINE(aji_do_set_debug, "Enable/Disable Jabber debug", .deprecate_cmd = &cli_aji_do_debug_deprecated),
+ AST_CLI_DEFINE(aji_do_set_debug, "Enable/Disable Jabber debug"),
AST_CLI_DEFINE(aji_do_reload, "Reload Jabber configuration"),
AST_CLI_DEFINE(aji_show_clients, "Show state of clients and components"),
AST_CLI_DEFINE(aji_show_buddies, "Show buddy lists of our clients"),
@@ -155,8 +274,8 @@
" If not in roster variable will be set to 7\n\n"
"Note: This application is deprecated. Please use the JABBER_STATUS() function instead.\n";
-struct aji_client_container clients;
-struct aji_capabilities *capabilities = NULL;
+static struct aji_client_container clients;
+static struct aji_capabilities *capabilities = NULL;
/*! \brief Global flags, initialized to default values */
static struct ast_flags globalflags = { AJI_AUTOPRUNE | AJI_AUTOREGISTER };
@@ -212,7 +331,7 @@
* \param pak struct The XML stanza we're processing
* \return a pointer to the added or found aji_version structure
*/
-static struct aji_version *aji_find_version(char *node, char *version, ikspak *pak)
+static struct aji_version *aji_find_version(char *node, char *version, char *ext, ikspak *pak)
{
struct aji_capabilities *list = NULL;
struct aji_version *res = NULL;
@@ -227,8 +346,9 @@
if(!strcasecmp(list->node, node)) {
res = list->versions;
while(res) {
- if(!strcasecmp(res->version, version))
+ if(!strcasecmp(res->version, version)) {
return res;
+ }
res = res->next;
}
/* Specified version not found. Let's add it to
@@ -242,6 +362,7 @@
res->jingle = 0;
res->parent = list;
ast_copy_string(res->version, version, sizeof(res->version));
+ ast_copy_string(res->ext, ext ? ext : "none", sizeof(res->ext));
res->next = list->versions;
list->versions = res;
return res;
@@ -264,6 +385,7 @@
}
ast_copy_string(list->node, node, sizeof(list->node));
ast_copy_string(res->version, version, sizeof(res->version));
+ ast_copy_string(res->ext, ext ? ext : "none", sizeof(res->ext));
res->jingle = 0;
res->parent = list;
res->next = NULL;
@@ -301,8 +423,16 @@
*/
static int gtalk_yuck(iks *node)
{
- if (iks_find_with_attrib(node, "c", "node", "http://www.google.com/xmpp/client/caps"))
+ if (iks_find_with_attrib(node, "c", "node", "http://www.google.com/xmpp/client/caps")) {
+ ast_debug(1, "Found resource with Googletalk voice capabilities\n");
+ return 1;
+ } else if (iks_find_with_attrib(node, "caps:c", "ext", "pmuc-v1 sms-v1 camera-v1 video-v1 voice-v1")) {
+ ast_debug(1, "Found resource with Gmail voice/video chat capabilities\n");
+ return 1;
+ } else if (iks_find_with_attrib(node, "caps:c", "ext", "pmuc-v1 sms-v1 video-v1 voice-v1")) {
+ ast_debug(1, "Found resource with Gmail voice/video chat capabilities (no camera)\n");
return 1;
+ }
return 0;
}
@@ -364,7 +494,7 @@
ast_log(LOG_WARNING, "JabberStatus is deprecated. Please use the JABBER_STATUS dialplan function in the future.\n");
if (!data) {
- ast_log(LOG_ERROR, "Usage: JabberStatus(,[/],\n");
+ ast_log(LOG_ERROR, "Usage: JabberStatus(,[/],\n");
return 0;
}
s = ast_strdupa(data);
@@ -880,6 +1010,21 @@
}
pak = iks_packet(node);
+ /* work around iksemel's impossibility to recognize node names
+ * containing a semicolon. Set the namespace of the corresponding
+ * node accordingly. */
+ if (iks_has_children(node) && strchr(iks_name(iks_child(node)), ':')) {
+ char *node_ns = NULL;
+ char attr[AJI_MAX_ATTRLEN];
+ char *node_name = iks_name(iks_child(node));
+ char *aux = strchr(node_name, ':') + 1;
+ snprintf(attr, strlen("xmlns:") + aux - node_name, "xmlns:%s", node_name);
+ node_ns = iks_find_attrib(iks_child(node), attr);
+ if (node_ns) {
+ pak->ns = node_ns;
+ pak->query = iks_child(node);
+ }
+ }
if (!client->component) { /*client */
switch (type) {
@@ -1527,7 +1672,8 @@
struct aji_buddy *buddy;
struct aji_resource *tmp = NULL, *last = NULL, *found = NULL;
char *ver, *node, *descrip, *type;
-
+ char *ext = NULL;
+
if(client->state != AJI_CONNECTED)
aji_create_buddy(pak->from->partial, client);
@@ -1663,19 +1809,23 @@
node = iks_find_attrib(iks_find(pak->x, "c"), "node");
ver = iks_find_attrib(iks_find(pak->x, "c"), "ver");
+ ext = iks_find_attrib(iks_find(pak->x, "c"), "ext");
/* handle gmail client's special caps:c tag */
- if (!node && !ver) {
+ if (!node && !ver && !ext) {
node = iks_find_attrib(iks_find(pak->x, "caps:c"), "node");
ver = iks_find_attrib(iks_find(pak->x, "caps:c"), "ver");
+ ext = iks_find_attrib(iks_find(pak->x, "caps:c"), "ext");
}
/* retrieve capabilites of the new resource */
if(status !=6 && found && !found->cap) {
- found->cap = aji_find_version(node, ver, pak);
- if(gtalk_yuck(pak->x)) /* gtalk should do discover */
+ found->cap = aji_find_version(node, ver, ext, pak);
+ if(gtalk_yuck(pak->x)) {/* gtalk should do discover */
found->cap->jingle = 1;
- if(found->cap->jingle && option_debug > 4) {
+ }
+
+ if(found->cap->jingle) {
ast_debug(1,"Special case for google till they support discover.\n");
}
else {
@@ -2081,7 +2231,7 @@
ASTOBJ_RDLOCK(iterator);
/* For an aji_buddy, both AUTOPRUNE and AUTOREGISTER will never
* be called at the same time */
- if (ast_test_flag(&iterator->flags, AJI_AUTOPRUNE)) {
+ if (ast_test_flag(&iterator->flags, AJI_AUTOPRUNE)) { /* If autoprune is set on jabber.conf */
res = ast_aji_send(client, iks_make_s10n(IKS_TYPE_UNSUBSCRIBE, iterator->name,
"GoodBye. Your status is no longer needed by Asterisk the Open Source PBX"
" so I am no longer subscribing to your presence.\n"));
@@ -2331,7 +2481,7 @@
iks *presence = iks_make_pres(level, desc);
iks *cnode = iks_new("c");
iks *priority = iks_new("priority");
- char priorityS[10];
+ char priorityS[AJI_MAX_ATTRLEN];
if (presence && cnode && client && priority) {
if(to)
@@ -2343,7 +2493,9 @@
iks_insert_node(presence, priority);
iks_insert_attrib(cnode, "node", "http://www.asterisk.org/xmpp/client/caps");
iks_insert_attrib(cnode, "ver", "asterisk-xmpp");
- iks_insert_attrib(cnode, "ext", "voice-v1");
+ if (ast_module_check("chan_gtalk.so") || ast_module_check("chan_gtalk")) {
+ iks_insert_attrib(cnode, "ext", "camera-v1 video-v1 voice-v1");
+ }
iks_insert_attrib(cnode, "xmlns", "http://jabber.org/protocol/caps");
iks_insert_node(presence, cnode);
res = ast_aji_send(client, presence);
@@ -2396,46 +2548,6 @@
}
/*!
- * \brief Turn on/off console debugging (deprecated, use aji_do_set_debug).
- * \return CLI_SUCCESS.
- */
-static char *aji_do_debug_deprecated(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
-{
-
- switch (cmd) {
- case CLI_INIT:
- e->command = "jabber debug [off]";
- e->usage =
- "Usage: jabber debug [off]\n"
- " Enables/disables dumping of Jabber packets for debugging purposes.\n";
- return NULL;
- case CLI_GENERATE:
- return NULL;
- }
-
- if (a->argc == 2) {
- ASTOBJ_CONTAINER_TRAVERSE(&clients, 1, {
- ASTOBJ_RDLOCK(iterator);
- iterator->debug = 1;
- ASTOBJ_UNLOCK(iterator);
- });
- ast_cli(a->fd, "Jabber Debugging Enabled.\n");
- return CLI_SUCCESS;
- } else if (a->argc == 3) {
- if (!strncasecmp(a->argv[2], "off", 3)) {
- ASTOBJ_CONTAINER_TRAVERSE(&clients, 1, {
- ASTOBJ_RDLOCK(iterator);
- iterator->debug = 0;
- ASTOBJ_UNLOCK(iterator);
- });
- ast_cli(a->fd, "Jabber Debugging Disabled.\n");
- return CLI_SUCCESS;
- }
- }
- return CLI_SHOWUSAGE; /* defaults to invalid */
-}
-
-/*!
* \brief Reload jabber module.
* \return CLI_SUCCESS.
*/
@@ -2774,14 +2886,6 @@
} else {
iks_filter_add_rule(client->f, aji_client_info_handler, client, IKS_RULE_NS, "http://jabber.org/protocol/disco#info", IKS_RULE_DONE);
}
- if (!strchr(client->user, '/') && !client->component) { /*client */
- resource = NULL;
- if (asprintf(&resource, "%s/asterisk", client->user) >= 0) {
- client->jid = iks_id_new(client->stack, resource);
- ast_free(resource);
- }
- } else
- client->jid = iks_id_new(client->stack, client->user);
iks_set_log_hook(client->p, aji_log_hook);
ASTOBJ_UNLOCK(client);
ASTOBJ_CONTAINER_LINK(&clients,client);
@@ -3028,7 +3132,7 @@
static int unload_module(void)
{
- ast_cli_unregister_multiple(aji_cli, sizeof(aji_cli) / sizeof(struct ast_cli_entry));
+ ast_cli_unregister_multiple(aji_cli, ARRAY_LEN(aji_cli));
ast_unregister_application(app_ajisend);
ast_unregister_application(app_ajistatus);
ast_manager_unregister("JabberSend");