# HG changeset patch # User Marcus Lundblad # Date 1229536868 0 # Node ID 9100b9176a16cb6eae3f9b0ea59100ae7d5ad0c8 # Parent c2054d8d23fcaf784ee7ee23a9314b8438c4f3b1# Parent f03a067fcfbaa457656932f6df910c7671b8cf36 propagate from branch 'im.pidgin.pidgin' (head a03e0bee477b05d1143ef3e5607d990c1120da34) to branch 'im.pidgin.cpw.malu.xmpp.idle' (head e0c18c146f94850aa81c1e4094e7fe549d028148) diff -r c2054d8d23fc -r 9100b9176a16 libpurple/protocols/jabber/buddy.c --- a/libpurple/protocols/jabber/buddy.c Wed Dec 17 05:39:11 2008 +0000 +++ b/libpurple/protocols/jabber/buddy.c Wed Dec 17 18:01:08 2008 +0000 @@ -98,36 +98,41 @@ for(l = jb->resources; l; l = l->next) { - if(!jbr && !resource) { - jbr = l->data; - } else if(!resource) { - if(((JabberBuddyResource *)l->data)->priority > jbr->priority) - jbr = l->data; - else if(((JabberBuddyResource *)l->data)->priority == jbr->priority) { + JabberBuddyResource *tmp = (JabberBuddyResource *) l->data; + if (!jbr && !resource) { + jbr = tmp; + } else if (!resource) { + if (tmp->priority > jbr->priority) + jbr = tmp; + else if (tmp->priority == jbr->priority) { /* Determine if this resource is more available than the one we've currently chosen */ - switch(((JabberBuddyResource *)l->data)->state) { + switch(tmp->state) { case JABBER_BUDDY_STATE_ONLINE: case JABBER_BUDDY_STATE_CHAT: /* This resource is online/chatty. Prefer to one which isn't either. */ - if ((jbr->state != JABBER_BUDDY_STATE_ONLINE) && (jbr->state != JABBER_BUDDY_STATE_CHAT)) - jbr = l->data; + if (((jbr->state != JABBER_BUDDY_STATE_ONLINE) && (jbr->state != JABBER_BUDDY_STATE_CHAT)) + || (jbr->idle && !tmp->idle) + || (jbr->idle && tmp->idle && tmp->idle > jbr->idle)) + jbr = tmp; break; case JABBER_BUDDY_STATE_AWAY: case JABBER_BUDDY_STATE_DND: /* This resource is away/dnd. Prefer to one which is extended away, unavailable, or unknown. */ - if ((jbr->state == JABBER_BUDDY_STATE_XA) || (jbr->state == JABBER_BUDDY_STATE_UNAVAILABLE) || + if (((jbr->state == JABBER_BUDDY_STATE_XA) || (jbr->state == JABBER_BUDDY_STATE_UNAVAILABLE) || (jbr->state == JABBER_BUDDY_STATE_UNKNOWN) || (jbr->state == JABBER_BUDDY_STATE_ERROR)) - jbr = l->data; + || (jbr->idle && !tmp->idle) + || (jbr->idle && tmp->idle && tmp->idle > jbr->idle)) + jbr = tmp; break; case JABBER_BUDDY_STATE_XA: /* This resource is extended away. That's better than unavailable or unknown. */ if ((jbr->state == JABBER_BUDDY_STATE_UNAVAILABLE) || (jbr->state == JABBER_BUDDY_STATE_UNKNOWN) || (jbr->state == JABBER_BUDDY_STATE_ERROR)) - jbr = l->data; + jbr = tmp; break; case JABBER_BUDDY_STATE_UNAVAILABLE: /* This resource is unavailable. That's better than unknown. */ if ((jbr->state == JABBER_BUDDY_STATE_UNKNOWN) || (jbr->state == JABBER_BUDDY_STATE_ERROR)) - jbr = l->data; + jbr = tmp; break; case JABBER_BUDDY_STATE_UNKNOWN: case JABBER_BUDDY_STATE_ERROR: @@ -135,9 +140,9 @@ break; } } - } else if(((JabberBuddyResource *)l->data)->name) { - if(!strcmp(((JabberBuddyResource *)l->data)->name, resource)) { - jbr = l->data; + } else if(tmp->name) { + if(!strcmp(tmp->name, resource)) { + jbr = tmp; break; } } diff -r c2054d8d23fc -r 9100b9176a16 libpurple/protocols/jabber/buddy.h --- a/libpurple/protocols/jabber/buddy.h Wed Dec 17 05:39:11 2008 +0000 +++ b/libpurple/protocols/jabber/buddy.h Wed Dec 17 18:01:08 2008 +0000 @@ -69,6 +69,7 @@ int priority; JabberBuddyState state; char *status; + time_t idle; JabberCapabilities capabilities; char *thread_id; enum { diff -r c2054d8d23fc -r 9100b9176a16 libpurple/protocols/jabber/jabber.c --- a/libpurple/protocols/jabber/jabber.c Wed Dec 17 05:39:11 2008 +0000 +++ b/libpurple/protocols/jabber/jabber.c Wed Dec 17 18:01:08 2008 +0000 @@ -1441,8 +1441,14 @@ void jabber_idle_set(PurpleConnection *gc, int idle) { JabberStream *js = gc->proto_data; - + PurpleAccount *account = purple_connection_get_account(gc); + PurpleStatus *status = purple_account_get_active_status(account); + js->idle = idle ? time(NULL) - idle : idle; + + /* send out an updated prescence */ + purple_debug_info("jabber", "sending updated presence for idle\n"); + jabber_presence_send(account, status); } void jabber_add_feature(const char *shortname, const char *namespace, JabberFeatureEnabled cb) { diff -r c2054d8d23fc -r 9100b9176a16 libpurple/protocols/jabber/jabber.h --- a/libpurple/protocols/jabber/jabber.h Wed Dec 17 05:39:11 2008 +0000 +++ b/libpurple/protocols/jabber/jabber.h Wed Dec 17 18:01:08 2008 +0000 @@ -153,6 +153,7 @@ GList *file_transfers; time_t idle; + time_t old_idle; JabberID *user; PurpleConnection *gc; diff -r c2054d8d23fc -r 9100b9176a16 libpurple/protocols/jabber/presence.c --- a/libpurple/protocols/jabber/presence.c Wed Dec 17 05:39:11 2008 +0000 +++ b/libpurple/protocols/jabber/presence.c Wed Dec 17 18:01:08 2008 +0000 @@ -21,6 +21,7 @@ #include "internal.h" #include "account.h" +#include "cipher.h" #include "conversation.h" #include "debug.h" #include "notify.h" @@ -348,12 +349,19 @@ (( (binval = xmlnode_get_child(photo, "BINVAL")) && (text = xmlnode_get_data(binval))) || (text = xmlnode_get_data(photo)))) { - char *hash; + unsigned char hashval[20]; + char hash[41], *p; + int i; data = purple_base64_decode(text, &size); - hash = jabber_calculate_data_sha1sum(data, size); + + purple_cipher_digest_region("sha1", data, size, + sizeof(hashval), hashval, NULL); + p = hash; + for(i=0; i<20; i++, p+=2) + snprintf(p, 3, "%02x", hashval[i]); + purple_buddy_icons_set_for_user(js->gc->account, from, data, size, hash); - g_free(hash); g_free(text); } } @@ -502,19 +510,17 @@ priority = atoi(p); g_free(p); } - } else if(xmlns == NULL) { - /* The rest of the cases used to check xmlns individually. */ - continue; } else if(!strcmp(y->name, "delay") && !strcmp(xmlns, "urn:xmpp:delay")) { /* XXX: compare the time. jabber:x:delay can happen on presence packets that aren't really and truly delayed */ delayed = TRUE; - } else if(!strcmp(y->name, "c") && !strcmp(xmlns, "http://jabber.org/protocol/caps")) { + } else if(xmlns && !strcmp(y->name, "c") && !strcmp(xmlns, "http://jabber.org/protocol/caps")) { caps = y; /* store for later, when creating buddy resource */ } else if(!strcmp(y->name, "x")) { - if(!strcmp(xmlns, "jabber:x:delay")) { + const char *xmlns = xmlnode_get_namespace(y); + if(xmlns && !strcmp(xmlns, "jabber:x:delay")) { /* XXX: compare the time. jabber:x:delay can happen on presence packets that aren't really and truly delayed */ delayed = TRUE; - } else if(!strcmp(xmlns, "http://jabber.org/protocol/muc#user")) { + } else if(xmlns && !strcmp(xmlns, "http://jabber.org/protocol/muc#user")) { xmlnode *z; muc = TRUE; @@ -557,7 +563,7 @@ flags |= PURPLE_CBFLAGS_VOICE; } } - } else if(!strcmp(xmlns, "vcard-temp:x:update")) { + } else if(xmlns && !strcmp(xmlns, "vcard-temp:x:update")) { xmlnode *photo = xmlnode_get_child(y, "photo"); if(photo) { g_free(avatar_hash);