# HG changeset patch # User Ethan Blanton # Date 1240953251 0 # Node ID 51167c69228e1fac534001853e29ef7b1712dbcd # Parent c00f8076642f00e4c2088b216862d16ae1beb5de# Parent 7f552614ec8a6169e07889df9ca1e8c921605008 merge of '175f0b579cc408c333dd4a10fa92ff9b56108ed9' and '1fcba66fbd836c93985c0490b29a1cd899ae1542' diff -r c00f8076642f -r 51167c69228e ChangeLog --- a/ChangeLog Tue Apr 28 21:14:05 2009 +0000 +++ b/ChangeLog Tue Apr 28 21:14:11 2009 +0000 @@ -1,5 +1,25 @@ Pidgin and Finch: The Pimpin' Penguin IM Clients That're Good for the Soul +version 2.5.6 (??/??/2009): + libpurple: + * Improve sleep behavior by aggregation longer timeouts on second + boundaries to allow better power saving. (Arunan Balasubramaniam) + * Fix various crashes on exit. + + IRC: + * Correctly handle WHOIS for users who are joined to a large number of + channels. + * Notify the user if a /nick command fails, rather than trying + fallback nicks. + + MSN: + * Fix a race condition causing occasional Pidgin crashes. + * Fix some errors about the friendly name changing too fast caused + by MSN/Yahoo integration buddies. + + Yahoo: + * Fix a crash when sending very long messages. + version 2.5.5 (03/01/2009): libpurple: * Fix a crash when removing an account with an unknown protocol id. diff -r c00f8076642f -r 51167c69228e finch/gntblist.c --- a/finch/gntblist.c Tue Apr 28 21:14:05 2009 +0000 +++ b/finch/gntblist.c Tue Apr 28 21:14:11 2009 +0000 @@ -931,7 +931,7 @@ else if (PURPLE_BLIST_NODE_IS_GROUP(node)) return purple_group_get_name((PurpleGroup*)node); - snprintf(text, sizeof(text) - 1, "%s %s", status, name); + g_snprintf(text, sizeof(text) - 1, "%s %s", status, name); return text; } @@ -2638,7 +2638,7 @@ char menuid[128]; FinchBlistManager *manager = iter->data; GntMenuItem *item = gnt_menuitem_new(_(manager->name)); - snprintf(menuid, sizeof(menuid), "grouping-%s", manager->id); + g_snprintf(menuid, sizeof(menuid), "grouping-%s", manager->id); gnt_menuitem_set_id(GNT_MENU_ITEM(item), menuid); gnt_menu_add_item(GNT_MENU(subsub), item); g_object_set_data_full(G_OBJECT(item), "grouping-id", g_strdup(manager->id), g_free); diff -r c00f8076642f -r 51167c69228e finch/gntnotify.c --- a/finch/gntnotify.c Tue Apr 28 21:14:05 2009 +0000 +++ b/finch/gntnotify.c Tue Apr 28 21:14:11 2009 +0000 @@ -263,7 +263,7 @@ userinfo_hash(PurpleAccount *account, const char *who) { char key[256]; - snprintf(key, sizeof(key), "%s - %s", purple_account_get_username(account), purple_normalize(account, who)); + g_snprintf(key, sizeof(key), "%s - %s", purple_account_get_username(account), purple_normalize(account, who)); return g_utf8_strup(key, -1); } diff -r c00f8076642f -r 51167c69228e libpurple/conversation.c --- a/libpurple/conversation.c Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/conversation.c Tue Apr 28 21:14:11 2009 +0000 @@ -33,7 +33,7 @@ #include "signals.h" #include "util.h" -#define SEND_TYPED_TIMEOUT 5000 +#define SEND_TYPED_TIMEOUT_SECONDS 5 static GList *conversations = NULL; static GList *ims = NULL; @@ -1122,8 +1122,9 @@ { g_return_if_fail(im != NULL); - im->send_typed_timeout = purple_timeout_add(SEND_TYPED_TIMEOUT, send_typed_cb, - purple_conv_im_get_conversation(im)); + im->send_typed_timeout = purple_timeout_add_seconds(SEND_TYPED_TIMEOUT_SECONDS, + send_typed_cb, + purple_conv_im_get_conversation(im)); } void diff -r c00f8076642f -r 51167c69228e libpurple/core.c --- a/libpurple/core.c Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/core.c Tue Apr 28 21:14:11 2009 +0000 @@ -209,15 +209,10 @@ /* The SSL plugins must be uninit before they're unloaded */ purple_ssl_uninit(); - /* Unload all plugins before the UI because UI plugins might call - * UI-specific functions */ - purple_debug_info("main", "Unloading all plugins\n"); - purple_plugins_destroy_all(); - - /* Shut down the UI before all the subsystems */ - ops = purple_core_get_ui_ops(); - if (ops != NULL && ops->quit != NULL) - ops->quit(); + /* Unload all non-loader, non-prpl plugins before shutting down + * subsystems. */ + purple_debug_info("main", "Unloading normal plugins\n"); + purple_plugins_unload(PURPLE_PLUGIN_STANDARD); /* Save .xml files, remove signals, etc. */ purple_smileys_uninit(); @@ -239,7 +234,16 @@ purple_imgstore_uninit(); purple_network_uninit(); - /* Everything after this must not try to read any prefs */ + /* Everything after unloading all plugins must not fail if prpls aren't + * around */ + purple_debug_info("main", "Unloading all plugins\n"); + purple_plugins_destroy_all(); + + ops = purple_core_get_ui_ops(); + if (ops != NULL && ops->quit != NULL) + ops->quit(); + + /* Everything after prefs_uninit must not try to read any prefs */ purple_prefs_uninit(); purple_plugins_uninit(); #ifdef HAVE_DBUS @@ -247,7 +251,7 @@ #endif purple_cmds_uninit(); - /* Everything after this cannot try to write things to the confdir */ + /* Everything after util_uninit cannot try to write things to the confdir */ purple_util_uninit(); purple_signals_uninit(); diff -r c00f8076642f -r 51167c69228e libpurple/plugin.c --- a/libpurple/plugin.c Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/plugin.c Tue Apr 28 21:14:11 2009 +0000 @@ -1229,6 +1229,21 @@ } void +purple_plugins_unload(PurplePluginType type) +{ +#ifdef PURPLE_PLUGINS + GList *l; + + for (l = plugins; l; l = l->next) { + PurplePlugin *plugin = l->data; + if (plugin->info->type == type && purple_plugin_is_loaded(plugin)) + purple_plugin_unload(plugin); + } + +#endif /* PURPLE_PLUGINS */ +} + +void purple_plugins_destroy_all(void) { #ifdef PURPLE_PLUGINS diff -r c00f8076642f -r 51167c69228e libpurple/plugin.h --- a/libpurple/plugin.h Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/plugin.h Tue Apr 28 21:14:11 2009 +0000 @@ -503,6 +503,11 @@ void purple_plugins_unload_all(void); /** + * Unloads all plugins of a specific type. + */ +void purple_plugins_unload(PurplePluginType type); + +/** * Destroys all registered plugins. */ void purple_plugins_destroy_all(void); diff -r c00f8076642f -r 51167c69228e libpurple/plugins/filectl.c --- a/libpurple/plugins/filectl.c Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/plugins/filectl.c Tue Apr 28 21:14:11 2009 +0000 @@ -220,7 +220,7 @@ plugin_load(PurplePlugin *plugin) { init_file(); - check = purple_timeout_add(5000, (GSourceFunc)check_file, NULL); + check = purple_timeout_add_seconds(5, (GSourceFunc)check_file, NULL); return TRUE; } diff -r c00f8076642f -r 51167c69228e libpurple/plugins/joinpart.c --- a/libpurple/plugins/joinpart.c Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/plugins/joinpart.c Tue Apr 28 21:14:11 2009 +0000 @@ -194,7 +194,7 @@ PURPLE_CALLBACK(received_chat_msg_cb), users); /* Cleanup every 5 minutes */ - id = purple_timeout_add(1000 * 60 * 5, (GSourceFunc)clean_users_hash, users); + id = purple_timeout_add_seconds(60 * 5, (GSourceFunc)clean_users_hash, users); data = g_new(gpointer, 2); data[0] = users; diff -r c00f8076642f -r 51167c69228e libpurple/protocols/irc/irc.h --- a/libpurple/protocols/irc/irc.h Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/protocols/irc/irc.h Tue Apr 28 21:14:11 2009 +0000 @@ -72,7 +72,7 @@ char *name; char *server; char *serverinfo; - char *channels; + GString *channels; int ircop; int identified; int idle; diff -r c00f8076642f -r 51167c69228e libpurple/protocols/irc/msgs.c --- a/libpurple/protocols/irc/msgs.c Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/protocols/irc/msgs.c Tue Apr 28 21:14:11 2009 +0000 @@ -117,7 +117,7 @@ irc_blist_timeout(irc); if (!irc->timer) - irc->timer = purple_timeout_add(45000, (GSourceFunc)irc_blist_timeout, (gpointer)irc); + irc->timer = purple_timeout_add_seconds(45, (GSourceFunc)irc_blist_timeout, (gpointer)irc); } void irc_msg_default(struct irc_conn *irc, const char *name, const char *from, char **args) @@ -325,7 +325,11 @@ if (args[3]) irc->whois.signon = (time_t)atoi(args[3]); } else if (!strcmp(name, "319")) { - irc->whois.channels = g_strdup(args[2]); + if (irc->whois.channels == NULL) { + irc->whois.channels = g_string_new(args[2]); + } else { + irc->whois.channels = g_string_append(irc->whois.channels, args[2]); + } } else if (!strcmp(name, "320")) { irc->whois.identified = 1; } @@ -380,8 +384,8 @@ g_free(irc->whois.serverinfo); } if (irc->whois.channels) { - purple_notify_user_info_add_pair(user_info, _("Currently on"), irc->whois.channels); - g_free(irc->whois.channels); + purple_notify_user_info_add_pair(user_info, _("Currently on"), irc->whois.channels->str); + g_string_free(irc->whois.channels, TRUE); } if (irc->whois.idle) { gchar *timex = purple_str_seconds_to_string(irc->whois.idle); @@ -989,10 +993,25 @@ void irc_msg_nickused(struct irc_conn *irc, const char *name, const char *from, char **args) { char *newnick, *buf, *end; + PurpleConnection *gc = purple_account_get_connection(irc->account); if (!args || !args[1]) return; + if (gc && purple_connection_get_state(gc) == PURPLE_CONNECTED) { + /* We only want to do the following dance if the connection + has not been successfully completed. If it has, just + notify the user that their /nick command didn't go. */ + buf = g_strdup_printf(_("The nickname \"%s\" is already being used."), + irc->reqnick); + purple_notify_error(gc, _("Nickname in use"), + _("Nickname in use"), buf); + g_free(buf); + g_free(irc->reqnick); + irc->reqnick = NULL; + return; + } + if (strlen(args[1]) < strlen(irc->reqnick) || irc->nickused) newnick = g_strdup(args[1]); else diff -r c00f8076642f -r 51167c69228e libpurple/protocols/jabber/buddy.c --- a/libpurple/protocols/jabber/buddy.c Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/protocols/jabber/buddy.c Tue Apr 28 21:14:11 2009 +0000 @@ -1775,7 +1775,7 @@ } js->pending_buddy_info_requests = g_slist_prepend(js->pending_buddy_info_requests, jbi); - jbi->timeout_handle = purple_timeout_add(30000, jabber_buddy_get_info_timeout, jbi); + jbi->timeout_handle = purple_timeout_add_seconds(30, jabber_buddy_get_info_timeout, jbi); } void jabber_buddy_get_info(PurpleConnection *gc, const char *who) diff -r c00f8076642f -r 51167c69228e libpurple/protocols/msn/notification.c --- a/libpurple/protocols/msn/notification.c Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/protocols/msn/notification.c Tue Apr 28 21:14:11 2009 +0000 @@ -630,7 +630,7 @@ } else { purple_debug_error("msn", - "Got FQY update for unkwown user %s on network %d.\n", + "Got FQY update for unknown user %s on network %d.\n", passport, network); } } @@ -685,6 +685,9 @@ if (++adl_count % 150 == 0) { payload = xmlnode_to_str(adl_node, &payload_len); + /* ADL's are returned all-together */ + session->adl_fqy++; + msn_notification_post_adl(session->notification->cmdproc, payload, payload_len); @@ -696,6 +699,9 @@ xmlnode_set_attrib(adl_node, "l", "1"); } } else { + /* FQY's are returned one-at-a-time */ + session->adl_fqy++; + msn_add_contact_xml(session, fqy_node, user->passport, 0, user->networkid); @@ -717,6 +723,9 @@ if (adl_count == 0 || adl_count % 150 != 0) { payload = xmlnode_to_str(adl_node, &payload_len); + /* ADL's are returned all-together */ + session->adl_fqy++; + msn_notification_post_adl(session->notification->cmdproc, payload, payload_len); g_free(payload); @@ -803,7 +812,8 @@ if (!strcmp(cmd->params[1], "OK")) { /* ADL ack */ - msn_session_finish_login(session); + if (--session->adl_fqy == 0) + msn_session_finish_login(session); } else { cmdproc->last_cmd->payload_cb = adl_cmd_parse; cmd->payload_len = atoi(cmd->params[1]); diff -r c00f8076642f -r 51167c69228e libpurple/protocols/msn/session.h --- a/libpurple/protocols/msn/session.h Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/protocols/msn/session.h Tue Apr 28 21:14:11 2009 +0000 @@ -90,6 +90,7 @@ gboolean connected; gboolean logged_in; /**< A temporal flag to ignore local buddy list adds. */ + int adl_fqy; /**< A count of ADL/FQY so status is only changed once. */ gboolean destroying; /**< A flag that states if the session is being destroyed. */ gboolean http_method; diff -r c00f8076642f -r 51167c69228e libpurple/protocols/msn/soap.c --- a/libpurple/protocols/msn/soap.c Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/protocols/msn/soap.c Tue Apr 28 21:14:11 2009 +0000 @@ -667,6 +667,7 @@ conn->handled_len = 0; conn->current_request = req; + purple_input_remove(conn->event_handle); conn->event_handle = purple_input_add(conn->ssl->fd, PURPLE_INPUT_WRITE, msn_soap_write_cb, conn); if (!msn_soap_write_cb_internal(conn, conn->ssl->fd, PURPLE_INPUT_WRITE, TRUE)) { diff -r c00f8076642f -r 51167c69228e libpurple/protocols/msnp9/httpconn.c --- a/libpurple/protocols/msnp9/httpconn.c Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/protocols/msnp9/httpconn.c Tue Apr 28 21:14:11 2009 +0000 @@ -703,7 +703,7 @@ httpconn->inpa = purple_input_add(httpconn->fd, PURPLE_INPUT_READ, read_cb, data); - httpconn->timer = purple_timeout_add(2000, msn_httpconn_poll, httpconn); + httpconn->timer = purple_timeout_add_seconds(3, msn_httpconn_poll, httpconn); msn_httpconn_process_queue(httpconn); } diff -r c00f8076642f -r 51167c69228e libpurple/protocols/msnp9/slp.c --- a/libpurple/protocols/msnp9/slp.c Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/protocols/msnp9/slp.c Tue Apr 28 21:14:11 2009 +0000 @@ -33,8 +33,8 @@ #include "smiley.h" -/* ms to delay between sending buddy icon requests to the server. */ -#define BUDDY_ICON_DELAY 20000 +/* Seconds to delay between sending buddy icon requests to the server. */ +#define BUDDY_ICON_DELAY 20 static void send_ok(MsnSlpCall *slpcall, const char *branch, const char *type, const char *content); @@ -1058,8 +1058,8 @@ purple_timeout_remove(userlist->buddy_icon_request_timer); } - /* Wait BUDDY_ICON_DELAY ms before freeing our window slot and requesting the next icon. */ - userlist->buddy_icon_request_timer = purple_timeout_add(BUDDY_ICON_DELAY, + /* Wait BUDDY_ICON_DELAY_S seconds before freeing our window slot and requesting the next icon. */ + userlist->buddy_icon_request_timer = purple_timeout_add_seconds(BUDDY_ICON_DELAY, msn_release_buddy_icon_request_timeout, userlist); } diff -r c00f8076642f -r 51167c69228e libpurple/protocols/msnp9/slpcall.c --- a/libpurple/protocols/msnp9/slpcall.c Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/protocols/msnp9/slpcall.c Tue Apr 28 21:14:11 2009 +0000 @@ -68,7 +68,7 @@ msn_slplink_add_slpcall(slplink, slpcall); - slpcall->timer = purple_timeout_add(MSN_SLPCALL_TIMEOUT, msn_slp_call_timeout, slpcall); + slpcall->timer = purple_timeout_add_seconds(MSN_SLPCALL_TIMEOUT, msn_slp_call_timeout, slpcall); return slpcall; } diff -r c00f8076642f -r 51167c69228e libpurple/protocols/msnp9/slpcall.h --- a/libpurple/protocols/msnp9/slpcall.h Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/protocols/msnp9/slpcall.h Tue Apr 28 21:14:11 2009 +0000 @@ -33,7 +33,7 @@ #include "slpsession.h" /* The official client seems to timeout slp calls after 5 minutes */ -#define MSN_SLPCALL_TIMEOUT 300000 +#define MSN_SLPCALL_TIMEOUT 300 typedef enum { diff -r c00f8076642f -r 51167c69228e libpurple/protocols/msnp9/transaction.c --- a/libpurple/protocols/msnp9/transaction.c Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/protocols/msnp9/transaction.c Tue Apr 28 21:14:11 2009 +0000 @@ -211,7 +211,7 @@ purple_timeout_remove(trans->timer); } trans->timeout_cb = cb; - trans->timer = purple_timeout_add(60000, transaction_timeout, trans); + trans->timer = purple_timeout_add_seconds(60, transaction_timeout, trans); } void diff -r c00f8076642f -r 51167c69228e libpurple/protocols/myspace/myspace.c --- a/libpurple/protocols/myspace/myspace.c Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/protocols/myspace/myspace.c Tue Apr 28 21:14:11 2009 +0000 @@ -1238,7 +1238,7 @@ /* Disable due to problems with timeouts. TODO: fix. */ #ifdef MSIM_USE_KEEPALIVE - purple_timeout_add(MSIM_KEEPALIVE_INTERVAL_CHECK, + purple_timeout_add_seconds(MSIM_KEEPALIVE_INTERVAL_CHECK, (GSourceFunc)msim_check_alive, session); #endif diff -r c00f8076642f -r 51167c69228e libpurple/protocols/myspace/myspace.h --- a/libpurple/protocols/myspace/myspace.h Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/protocols/myspace/myspace.h Tue Apr 28 21:14:11 2009 +0000 @@ -114,8 +114,8 @@ #define MSIM_KEEPALIVE_INTERVAL (3 * 60) /*#define MSIM_USE_KEEPALIVE*/ -/* Time to check if alive (milliseconds) */ -#define MSIM_KEEPALIVE_INTERVAL_CHECK (30 * 1000) +/* Time to check if alive (seconds) */ +#define MSIM_KEEPALIVE_INTERVAL_CHECK 30 /* Time to check for new mail (milliseconds) */ #define MSIM_MAIL_INTERVAL_CHECK (60 * 1000) diff -r c00f8076642f -r 51167c69228e libpurple/protocols/oscar/oscar.c --- a/libpurple/protocols/oscar/oscar.c Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/protocols/oscar/oscar.c Tue Apr 28 21:14:11 2009 +0000 @@ -1266,7 +1266,7 @@ aim_ssi_reqdata(od); if (od->getblisttimer > 0) purple_timeout_remove(od->getblisttimer); - od->getblisttimer = purple_timeout_add(30000, purple_ssi_rerequestdata, od); + od->getblisttimer = purple_timeout_add_seconds(30, purple_ssi_rerequestdata, od); aim_locate_reqrights(od); aim_buddylist_reqrights(od, conn); @@ -5031,7 +5031,7 @@ _("The AIM servers were temporarily unable to send your buddy list. Your buddy list is not lost, and will probably become available in a few minutes.")); if (od->getblisttimer > 0) purple_timeout_remove(od->getblisttimer); - od->getblisttimer = purple_timeout_add(30000, purple_ssi_rerequestdata, od); + od->getblisttimer = purple_timeout_add_seconds(30, purple_ssi_rerequestdata, od); return 1; } diff -r c00f8076642f -r 51167c69228e libpurple/protocols/oscar/peer.c --- a/libpurple/protocols/oscar/peer.c Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/protocols/oscar/peer.c Tue Apr 28 21:14:11 2009 +0000 @@ -812,7 +812,7 @@ (conn->client_connect_data != NULL)) { /* Connecting... */ - conn->connect_timeout_timer = purple_timeout_add(5000, + conn->connect_timeout_timer = purple_timeout_add_seconds(5, peer_connection_tooktoolong, conn); return; } diff -r c00f8076642f -r 51167c69228e libpurple/protocols/sametime/sametime.c --- a/libpurple/protocols/sametime/sametime.c Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/protocols/sametime/sametime.c Tue Apr 28 21:14:11 2009 +0000 @@ -809,7 +809,7 @@ static void blist_schedule(struct mwPurplePluginData *pd) { if(pd->save_event) return; - pd->save_event = purple_timeout_add(BLIST_SAVE_SECONDS * 1000, + pd->save_event = purple_timeout_add_seconds(BLIST_SAVE_SECONDS, blist_save_cb, pd); } diff -r c00f8076642f -r 51167c69228e libpurple/protocols/yahoo/yahoo.c --- a/libpurple/protocols/yahoo/yahoo.c Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/protocols/yahoo/yahoo.c Tue Apr 28 21:14:11 2009 +0000 @@ -3640,7 +3640,6 @@ " bytes, %ld characters. Max is %d bytes, %d chars." " Message is '%s'.\n", lenb, lenc, YAHOO_MAX_MESSAGE_LENGTH_BYTES, YAHOO_MAX_MESSAGE_LENGTH_CHARS, msg2); - yahoo_packet_free(pkt); g_free(msg); g_free(msg2); return -E2BIG; diff -r c00f8076642f -r 51167c69228e libpurple/protocols/zephyr/zephyr.c --- a/libpurple/protocols/zephyr/zephyr.c Tue Apr 28 21:14:05 2009 +0000 +++ b/libpurple/protocols/zephyr/zephyr.c Tue Apr 28 21:14:11 2009 +0000 @@ -1857,7 +1857,7 @@ } else if (use_tzc(zephyr)) { zephyr->nottimer = purple_timeout_add(100, check_notify_tzc, gc); } - zephyr->loctimer = purple_timeout_add(20000, check_loc, gc); + zephyr->loctimer = purple_timeout_add_seconds(20, check_loc, gc); }