⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 oscar.c

📁 oscar message protocol stack
💻 C
📖 第 1 页 / 共 5 页
字号:
		else			gaim_debug_warning("oscar", "String is not valid UTF-8.\n");	}	return ret;}/* * We try decoding using two different character sets.  The charset * specified in the IM determines the order in which we attempt to * decode.  We do this because there are lots of broken ICQ clients * that don't correctly send non-ASCII messages.  And if Gaim isn't * able to deal with that crap, then people complain like banshees. * charsetstr1 is always set to what the correct encoding should be. */static gchar *gaim_plugin_oscar_decode_im_part(GaimAccount *account, const char *sourcesn, fu16_t charset, fu16_t charsubset, fu8_t *data, fu16_t datalen){	gchar *ret = NULL;	const gchar *charsetstr1, *charsetstr2;	gaim_debug_info("oscar", "Parsing IM part, charset=0x%04hx, charsubset=0x%04hx, datalen=%hd\n", charset, charsubset, datalen);	if ((datalen == 0) || (data == NULL))		return NULL;	if (charset == AIM_CHARSET_UNICODE) {		charsetstr1 = "UCS-2BE";		charsetstr2 = "UTF-8";	} else if (charset == AIM_CHARSET_CUSTOM) {		if ((sourcesn != NULL) && isdigit(sourcesn[0]))			charsetstr1 = gaim_account_get_string(account, "encoding", OSCAR_DEFAULT_CUSTOM_ENCODING);		else			charsetstr1 = "ISO-8859-1";		charsetstr2 = "UTF-8";	} else if (charset == AIM_CHARSET_ASCII) {		/* Should just be "ASCII" */		charsetstr1 = "ASCII";		charsetstr2 = gaim_account_get_string(account, "encoding", OSCAR_DEFAULT_CUSTOM_ENCODING);	} else if (charset == 0x000d) {		/* Mobile AIM client on a Nokia 3100 and an LG VX6000 */		charsetstr1 = "ISO-8859-1";		charsetstr2 = gaim_account_get_string(account, "encoding", OSCAR_DEFAULT_CUSTOM_ENCODING);	} else {		/* Unknown, hope for valid UTF-8... */		charsetstr1 = "UTF-8";		charsetstr2 = gaim_account_get_string(account, "encoding", OSCAR_DEFAULT_CUSTOM_ENCODING);	}	ret = gaim_plugin_oscar_convert_to_utf8(data, datalen, charsetstr1, FALSE);	if (ret == NULL)		ret = gaim_plugin_oscar_convert_to_utf8(data, datalen, charsetstr2, TRUE);	if (ret == NULL)		ret = g_strdup(_("(There was an error receiving this message.  The buddy you are speaking to most likely has a buggy client.)"));	return ret;}static voidgaim_plugin_oscar_convert_to_best_encoding(GaimConnection *gc, const char *destsn, const gchar *from,										   gchar **msg, gsize *msglen,										   fu16_t *charset, fu16_t *charsubset){	OscarData *od = gc->proto_data;	GaimAccount *account = gaim_connection_get_account(gc);	GError *err = NULL;	aim_userinfo_t *userinfo = NULL;	const gchar *charsetstr;	/* Attempt to send as ASCII */	if (oscar_charset_check(from) == AIM_CHARSET_ASCII) {		*msg = g_convert(from, strlen(from), "ASCII", "UTF-8", NULL, msglen, NULL);		*charset = AIM_CHARSET_ASCII;		*charsubset = 0x0000;		return;	}	/*	 * If we're sending to an ICQ user, and they are advertising the	 * Unicode capability, then attempt to send as UCS-2BE.	 */	if ((destsn != NULL) && isdigit(destsn[0]))		userinfo = aim_locate_finduserinfo(od->sess, destsn);	if ((userinfo != NULL) && (userinfo->capabilities & AIM_CAPS_ICQUTF8)) {		*msg = g_convert(from, strlen(from), "UCS-2BE", "UTF-8", NULL, msglen, NULL);		if (*msg != NULL) {			*charset = AIM_CHARSET_UNICODE;			*charsubset = 0x0000;			return;		}	}	/*	 * If this is AIM then attempt to send as ISO-8859-1.  If this is	 * ICQ then attempt to send as the user specified character encoding.	 */	charsetstr = "ISO-8859-1";	if ((destsn != NULL) && isdigit(destsn[0]))		charsetstr = gaim_account_get_string(account, "encoding", OSCAR_DEFAULT_CUSTOM_ENCODING);	*msg = g_convert(from, strlen(from), charsetstr, "UTF-8", NULL, msglen, NULL);	if (*msg != NULL) {		*charset = AIM_CHARSET_CUSTOM;		*charsubset = 0x0000;		return;	}	/*	 * Nothing else worked, so send as UCS-2BE.	 */	*msg = g_convert(from, strlen(from), "UCS-2BE", "UTF-8", NULL, msglen, &err);	if (*msg != NULL) {		*charset = AIM_CHARSET_UNICODE;		*charsubset = 0x0000;		return;	}	gaim_debug_error("oscar", "Error converting a Unicode message: %s\n", err->message);	g_error_free(err);	gaim_debug_error("oscar", "This should NEVER happen!  Sending UTF-8 text flagged as ASCII.\n");	*msg = g_strdup(from);	*msglen = strlen(*msg);	*charset = AIM_CHARSET_ASCII;	*charsubset = 0x0000;	return;}gchar *oscar_caps_to_string(guint caps){	GString *str;	gchar *tmp;	guint bit = 1;	str = g_string_new("");	if (!caps) {		return NULL;	} else while (bit <= AIM_CAPS_LAST) {		if (bit & caps) {			switch (bit) {			case AIM_CAPS_BUDDYICON:				tmp = _("Buddy Icon");				break;			case AIM_CAPS_TALK:				tmp = _("Voice");				break;			case AIM_CAPS_DIRECTIM:				tmp = _("AIM Direct IM");				break;			case AIM_CAPS_CHAT:				tmp = _("Chat");				break;			case AIM_CAPS_GETFILE:				tmp = _("Get File");				break;			case AIM_CAPS_SENDFILE:				tmp = _("Send File");				break;			case AIM_CAPS_GAMES:			case AIM_CAPS_GAMES2:				tmp = _("Games");				break;			case AIM_CAPS_ADDINS:				tmp = _("Add-Ins");				break;			case AIM_CAPS_SENDBUDDYLIST:				tmp = _("Send Buddy List");				break;			case AIM_CAPS_ICQ_DIRECT:				tmp = _("ICQ Direct Connect");				break;			case AIM_CAPS_APINFO:				tmp = _("AP User");				break;			case AIM_CAPS_ICQRTF:				tmp = _("ICQ RTF");				break;			case AIM_CAPS_EMPTY:				tmp = _("Nihilist");				break;			case AIM_CAPS_ICQSERVERRELAY:				tmp = _("ICQ Server Relay");				break;			case AIM_CAPS_ICQUTF8OLD:				tmp = _("Old ICQ UTF8");				break;			case AIM_CAPS_TRILLIANCRYPT:				tmp = _("Trillian Encryption");				break;			case AIM_CAPS_ICQUTF8:				tmp = _("ICQ UTF8");				break;			case AIM_CAPS_HIPTOP:				tmp = _("Hiptop");				break;			case AIM_CAPS_SECUREIM:				tmp = _("Security Enabled");				break;			case AIM_CAPS_VIDEO:				tmp = _("Video Chat");				break;			/* Not actually sure about this one... WinAIM doesn't show anything */			case AIM_CAPS_ICHATAV:				tmp = _("iChat AV");				break;			case AIM_CAPS_LIVEVIDEO:				tmp = _("Live Video");				break;			case AIM_CAPS_CAMERA:				tmp = _("Camera");				break;			default:				tmp = NULL;				break;			}			if (tmp)				g_string_append_printf(str, "%s%s", (*(str->str) == '\0' ? "" : ", "), tmp);		}		bit <<= 1;	}	return g_string_free(str, FALSE);}static char *oscar_icqstatus(int state) {	/* Make a cute little string that shows the status of the dude or dudet */	if (state & AIM_ICQ_STATE_CHAT)		return g_strdup_printf(_("Free For Chat"));	else if (state & AIM_ICQ_STATE_DND)		return g_strdup_printf(_("Do Not Disturb"));	else if (state & AIM_ICQ_STATE_OUT)		return g_strdup_printf(_("Not Available"));	else if (state & AIM_ICQ_STATE_BUSY)		return g_strdup_printf(_("Occupied"));	else if (state & AIM_ICQ_STATE_AWAY)		return g_strdup_printf(_("Away"));	else if (state & AIM_ICQ_STATE_WEBAWARE)		return g_strdup_printf(_("Web Aware"));	else if (state & AIM_ICQ_STATE_INVISIBLE)		return g_strdup_printf(_("Invisible"));	else		return g_strdup_printf(_("Online"));}static void oscar_string_append(GString *str, char *newline, char *name, char *value){	gchar *utf8;	if (value && value[0] && (utf8 = gaim_utf8_try_convert(value))) {		g_string_append_printf(str, "%s<b>%s:</b> %s", newline, name, utf8);		g_free(utf8);	}}static void oscar_string_append_info(GaimConnection *gc, GString *str, char *newline, GaimBuddy *b, aim_userinfo_t *userinfo){	OscarData *od = gc->proto_data;	GaimAccount *account = gaim_connection_get_account(gc);	GaimGroup *g = NULL;	struct buddyinfo *bi = NULL;	char *tmp;	if ((str == NULL) || (str == NULL) || (newline == NULL) || ((b == NULL) && (userinfo == NULL)))		return;	if (userinfo == NULL)		userinfo = aim_locate_finduserinfo(od->sess, b->name);	if (b == NULL)		b = gaim_find_buddy(gc->account, userinfo->sn);	if (b != NULL)		g = gaim_find_buddys_group(b);	if (userinfo != NULL)		bi = g_hash_table_lookup(od->buddyinfo, gaim_normalize(account, userinfo->sn));	if (b != NULL) {		if (GAIM_BUDDY_IS_ONLINE(b)) {			if (isdigit(b->name[0])) {				tmp = oscar_icqstatus((b->uc & 0xffff0000) >> 16);				oscar_string_append(str, newline, _("Status"), tmp);				g_free(tmp);			}		} else {			tmp = aim_ssi_itemlist_findparentname(od->sess->ssi.local, b->name);			if (aim_ssi_waitingforauth(od->sess->ssi.local, tmp, b->name))				oscar_string_append(str, newline, _("Status"), _("Not Authorized"));			else				oscar_string_append(str, newline, _("Status"), _("Offline"));		}	}	if ((bi != NULL) && (bi->ipaddr != 0)) {		tmp =  g_strdup_printf("%hhu.%hhu.%hhu.%hhu",						(bi->ipaddr & 0xff000000) >> 24,						(bi->ipaddr & 0x00ff0000) >> 16,						(bi->ipaddr & 0x0000ff00) >> 8,						(bi->ipaddr & 0x000000ff));		oscar_string_append(str, newline, _("IP Address"), tmp);		g_free(tmp);	}	if ((userinfo != NULL) && (userinfo->capabilities != 0)) {		tmp = oscar_caps_to_string(userinfo->capabilities);		oscar_string_append(str, newline, _("Capabilities"), tmp);		g_free(tmp);	}	if ((b != NULL) && (b->name != NULL) && (g != NULL) && (g->name != NULL)) {		tmp = aim_ssi_getcomment(od->sess->ssi.local, g->name, b->name);		if (tmp != NULL) {			char *tmp2 = g_markup_escape_text(tmp, strlen(tmp));			g_free(tmp);			oscar_string_append(str, newline, _("Buddy Comment"), tmp2);			g_free(tmp2);		}	}	if ((bi != NULL) && (bi->availmsg != NULL) && !(b->uc & UC_UNAVAILABLE)) {		tmp = g_markup_escape_text(bi->availmsg, strlen(bi->availmsg));		oscar_string_append(str, newline, _("Available"), tmp);		g_free(tmp);	}}static char *extract_name(const char *name) {	char *tmp, *x;	int i, j;	if (!name)		return NULL;		x = strchr(name, '-');	if (!x) return NULL;	x = strchr(++x, '-');	if (!x) return NULL;	tmp = g_strdup(++x);	for (i = 0, j = 0; x[i]; i++) {		char hex[3];		if (x[i] != '%') {			tmp[j++] = x[i];			continue;		}		strncpy(hex, x + ++i, 2); hex[2] = 0;		i++;		tmp[j++] = strtol(hex, NULL, 16);	}	tmp[j] = 0;	return tmp;}static struct chat_connection *find_oscar_chat(GaimConnection *gc, int id) {	GSList *g = ((OscarData *)gc->proto_data)->oscar_chats;	struct chat_connection *c = NULL;	while (g) {		c = (struct chat_connection *)g->data;		if (c->id == id)			break;		g = g->next;		c = NULL;	}	return c;}static struct chat_connection *find_oscar_chat_by_conn(GaimConnection *gc,							aim_conn_t *conn) {	GSList *g = ((OscarData *)gc->proto_data)->oscar_chats;	struct chat_connection *c = NULL;	while (g) {		c = (struct chat_connection *)g->data;		if (c->conn == conn)			break;		g = g->next;		c = NULL;	}	return c;}static struct chat_connection *find_oscar_chat_by_conv(GaimConnection *gc,							GaimConversation *conv) {	GSList *g = ((OscarData *)gc->proto_data)->oscar_chats;	struct chat_connection *c = NULL;	while (g) {		c = (struct chat_connection *)g->data;		if (c->conv == conv)			break;		g = g->next;		c = NULL;	}	return c;}/***************************************************************************** * Begin scary direct im stuff *****************************************************************************/static struct oscar_direct_im *oscar_direct_im_find(OscarData *od, const char *who) {	GSList *d = od->direct_ims;	struct oscar_direct_im *m = NULL;	while (d) {		m = (struct oscar_direct_im *)d->data;		if (!aim_sncmp(who, m->name))			return m;		d = d->next;	}	return NULL;}static void oscar_direct_im_destroy(OscarData *od, struct oscar_direct_im *dim){	gaim_debug_info("oscar",			   "destroying Direct IM for %s.\n", dim->name);	od->direct_ims = g_slist_remove(od->direct_ims, dim);	if (dim->gpc_pend) {		dim->killme = TRUE;		return;	}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -