# HG changeset patch # User Mikael Berthe # Date 1128201425 -7200 # Node ID a926523d2392c3a36059cf9ce1c09542b05948b2 # Parent 644b8bf9ca4dec5d1eb8f2432013ab448eb702c6 Use UTF8 to handle resources and room nicknames diff -r 644b8bf9ca4d -r a926523d2392 mcabber/src/commands.c --- a/mcabber/src/commands.c Sat Oct 01 18:53:14 2005 +0200 +++ b/mcabber/src/commands.c Sat Oct 01 23:17:05 2005 +0200 @@ -930,7 +930,7 @@ gchar *buffer; for (arg += 5; *arg && *arg == ' '; arg++) ; - buffer = g_locale_to_utf8(arg, -1, NULL, NULL, NULL); + buffer = to_utf8(arg); if (!buffer) { scr_LogPrint(LPRINT_NORMAL, "Conversion error in XML string"); return; @@ -956,8 +956,7 @@ bud = BUDDATA(current_buddy); if (!strncasecmp(arg, "join", 4)) { - GSList *roster_usr; - char *roomname, *nick, *roomid; + char *roomname, *nick; arg += 4; if (*arg++ != ' ') { @@ -988,29 +987,15 @@ g_free(roomname); return; } - // room syntax: "room@server/nick" - roomid = g_strdup_printf("%s/%s", roomname, nick); - if (check_jid_syntax(roomid)) { - scr_LogPrint(LPRINT_NORMAL, "<%s> is not a valid Jabber room", roomid); - g_free(roomname); - g_free(roomid); - return; - } - mc_strtolower(roomid); - jb_room_join(roomid); - - // We need to save the nickname for future use - roster_usr = roster_add_user(roomname, NULL, NULL, ROSTER_TYPE_ROOM); - if (roster_usr) - buddy_setnickname(roster_usr->data, nick); + mc_strtolower(roomname); + jb_room_join(roomname, nick); g_free(roomname); - g_free(roomid); buddylist_build(); update_roster = TRUE; } else if (!strncasecmp(arg, "leave", 5)) { - char *roomid; + gchar *roomid, *utf8_nickname; arg += 5; for (; *arg && *arg == ' '; arg++) ; @@ -1018,9 +1003,10 @@ scr_LogPrint(LPRINT_NORMAL, "This isn't a chatroom"); return; } - roomid = g_strdup_printf("%s/%s", buddy_getjid(bud), - buddy_getnickname(bud)); + utf8_nickname = to_utf8(buddy_getnickname(bud)); + roomid = g_strdup_printf("%s/%s", buddy_getjid(bud), utf8_nickname); jb_setstatus(offline, roomid, arg); + g_free(utf8_nickname); g_free(roomid); buddy_setnickname(bud, NULL); buddy_del_all_resources(bud); diff -r 644b8bf9ca4d -r a926523d2392 mcabber/src/jabglue.c --- a/mcabber/src/jabglue.c Sat Oct 01 18:53:14 2005 +0200 +++ b/mcabber/src/jabglue.c Sat Oct 01 23:17:05 2005 +0200 @@ -36,9 +36,6 @@ #define JABBER_AGENT_GROUP "Jabber Agents" -#define to_utf8(s) ((s) ? g_locale_to_utf8((s), -1, NULL,NULL,NULL) : NULL) -#define from_utf8(s) ((s) ? g_locale_from_utf8((s), -1, NULL,NULL,NULL) : NULL) - jconn jc; static time_t LastPingTime; static unsigned int KeepaliveDelay; @@ -126,6 +123,7 @@ jconn jb_connect(const char *jid, const char *server, unsigned int port, int ssl, const char *pass) { + char *utf8_jid; if (!port) { if (ssl) port = JABBERSSLPORT; @@ -135,8 +133,12 @@ jb_disconnect(); + utf8_jid = to_utf8(jid); + if (!utf8_jid) return jc; + s_id = 1; - jc = jab_new((char*)jid, (char*)pass, (char*)server, port, ssl); + jc = jab_new(utf8_jid, (char*)pass, (char*)server, port, ssl); + g_free(utf8_jid); /* These 3 functions can deal with a NULL jc, no worry... */ jab_logger(jc, logger); @@ -470,23 +472,40 @@ } // Join a MUC room -// room syntax: "room@server/nick" -void jb_room_join(const char *room) +void jb_room_join(const char *room, const char *nickname) { xmlnode x, y; + gchar *roomid, *utf8_nickname; + GSList *roster_usr; - if (!online) return; - if (!room) return; + if (!online || !room || !nickname) return; + utf8_nickname = to_utf8(nickname); + roomid = g_strdup_printf("%s/%s", room, utf8_nickname); + g_free(utf8_nickname); + if (check_jid_syntax(roomid)) { + scr_LogPrint(LPRINT_NORMAL, "<%s/%s> is not a valid Jabber room", room, + nickname); + g_free(roomid); + return; + } + + // We need to save the nickname for future use + roster_usr = roster_add_user(room, NULL, NULL, ROSTER_TYPE_ROOM); + if (roster_usr) + buddy_setnickname(roster_usr->data, nickname); + + // Send the XML request x = jutil_presnew(JPACKET__UNKNOWN, 0, 0); xmlnode_put_attrib(x, "from", jid_full(jc->user)); - xmlnode_put_attrib(x, "to", room); + xmlnode_put_attrib(x, "to", roomid); y = xmlnode_insert_tag(x, "x"); xmlnode_put_attrib(y, "xmlns", "http://jabber.org/protocol/muc"); jab_send(jc, x); xmlnode_free(x); jb_reset_keepalive(); + g_free(roomid); } // Unlock a MUC room @@ -777,11 +796,36 @@ enum imstatus ust; char bpprio; - jb_reset_keepalive(); // reset keepalive delay + jb_reset_keepalive(); // reset keepalive timeout jpacket_reset(packet); - p = xmlnode_get_attrib(packet->x, "from"); if (p) from = p; p = xmlnode_get_attrib(packet->x, "type"); if (p) type = p; + p = xmlnode_get_attrib(packet->x, "from"); + if (p) { // Convert from UTF8 + // We need to be careful because from_utf8() can fail on some chars + // Thus we only convert the resource part + from = g_new0(char, strlen(p)+1); + strcpy(from, p); + r = strchr(from, '/'); + m = strchr(p, '/'); + if (m++) { + s = from_utf8(m); + if (s) { + // The length should be enough because from_utf should only + // reduce the string length + strcpy(r+1, s); + g_free(s); + } else { + *(r+1) = 0; + scr_LogPrint(LPRINT_LOGNORM, "Decoding of message sender has failed"); + } + } + } + + if (!from && packet->type != JPACKET_IQ) { + scr_LogPrint(LPRINT_LOGNORM, "Error in packet (could be UTF8-related)"); + return; + } switch (packet->type) { case JPACKET_MESSAGE: @@ -1053,10 +1097,15 @@ p = xmlnode_get_attrib(y, "code"); if (p && !strcmp(p, "303")) { gchar *mbuf; - mbuf = g_strdup_printf("%s is now known as %s", rname, mbnewnick); + gchar *newname_noutf8 = from_utf8(mbnewnick); + mbuf = g_strdup_printf("%s is now known as %s", rname, + (newname_noutf8 ? newname_noutf8 : "(?)")); scr_WriteIncomingMessage(r, mbuf, 0, HBB_PREFIX_INFO); g_free(mbuf); - buddy_resource_setname(room_elt->data, rname, mbnewnick); + if (newname_noutf8) { + buddy_resource_setname(room_elt->data, rname, newname_noutf8); + g_free(newname_noutf8); + } } } @@ -1128,5 +1177,6 @@ default: break; } + g_free(from); } diff -r 644b8bf9ca4d -r a926523d2392 mcabber/src/jabglue.h --- a/mcabber/src/jabglue.h Sat Oct 01 18:53:14 2005 +0200 +++ b/mcabber/src/jabglue.h Sat Oct 01 23:17:05 2005 +0200 @@ -53,7 +53,7 @@ inline void jb_reset_keepalive(); void jb_set_keepalive_delay(unsigned int delay); inline void jb_set_priority(unsigned int priority); -void jb_room_join(const char *room); +void jb_room_join(const char *room, const char *nickname); void jb_room_unlock(const char *room); #endif /* __JABGLUE_H__ */ diff -r 644b8bf9ca4d -r a926523d2392 mcabber/src/roster.c --- a/mcabber/src/roster.c Sat Oct 01 18:53:14 2005 +0200 +++ b/mcabber/src/roster.c Sat Oct 01 23:17:05 2005 +0200 @@ -754,7 +754,7 @@ return roster_usr->name; } -void buddy_setnickname(gpointer rosterdata, char *newname) +void buddy_setnickname(gpointer rosterdata, const char *newname) { roster *roster_usr = rosterdata; diff -r 644b8bf9ca4d -r a926523d2392 mcabber/src/roster.h --- a/mcabber/src/roster.h Sat Oct 01 18:53:14 2005 +0200 +++ b/mcabber/src/roster.h Sat Oct 01 23:17:05 2005 +0200 @@ -69,7 +69,7 @@ const char *buddy_getjid(gpointer rosterdata); void buddy_setname(gpointer rosterdata, char *newname); const char *buddy_getname(gpointer rosterdata); -void buddy_setnickname(gpointer rosterdata, char *newname); +void buddy_setnickname(gpointer rosterdata, const char *newname); const char *buddy_getnickname(gpointer rosterdata); guint buddy_gettype(gpointer rosterdata); void buddy_setgroup(gpointer rosterdata, char *newgroupname); diff -r 644b8bf9ca4d -r a926523d2392 mcabber/src/utils.h --- a/mcabber/src/utils.h Sat Oct 01 18:53:14 2005 +0200 +++ b/mcabber/src/utils.h Sat Oct 01 23:17:05 2005 +0200 @@ -1,6 +1,9 @@ #ifndef __UTILS_H__ #define __UTILS_H__ 1 +#define to_utf8(s) ((s) ? g_locale_to_utf8((s), -1, NULL,NULL,NULL) : NULL) +#define from_utf8(s) ((s) ? g_locale_from_utf8((s), -1, NULL,NULL,NULL) : NULL) + void ut_InitDebug(unsigned int level, const char *file); void ut_WriteLog(unsigned int flag, const char *data);