changeset 31053:943fce8ef142

Fix for CVE-2010-3711. Properly validate the return value from purple_base64_decode() (the CVE issue) and purple_base16_decode() (just a bug). Coincidentally, this should also fix #12614. committer: John Bailey <rekkanoryo@rekkanoryo.org>
author Daniel Atallah <daniel.atallah@gmail.com>
date Sun, 17 Oct 2010 03:55:04 +0000
parents 0050a61df60c
children 27cc079535d2
files libpurple/ntlm.c libpurple/plugins/perl/common/Util.xs libpurple/protocols/jabber/auth_digest_md5.c libpurple/protocols/msn/slp.c libpurple/protocols/myspace/message.c libpurple/protocols/oscar/clientlogin.c libpurple/protocols/qq/im.c libpurple/protocols/yahoo/libymsg.c
diffstat 8 files changed, 29 insertions(+), 18 deletions(-) [+]
line wrap: on
line diff
--- a/libpurple/ntlm.c	Sun Oct 17 03:40:26 2010 +0000
+++ b/libpurple/ntlm.c	Sun Oct 17 03:55:04 2010 +0000
@@ -152,9 +152,14 @@
 	static guint8 nonce[8];
 
 	tmsg = (struct type2_message*)purple_base64_decode(type2, &retlen);
-	memcpy(nonce, tmsg->nonce, 8);
-	if (flags != NULL)
-		*flags = GUINT16_FROM_LE(tmsg->flags);
+	if (tmsg != NULL && retlen >= (sizeof(struct type2_message) - 1)) {
+		memcpy(nonce, tmsg->nonce, 8);
+		if (flags != NULL)
+			*flags = GUINT16_FROM_LE(tmsg->flags);
+	} else {
+		purple_debug_error("ntlm", "Unable to parse type2 message - returning empty nonce.\n");
+		memset(nonce, 0, 8);
+	}
 	g_free(tmsg);
 
 	return nonce;
--- a/libpurple/plugins/perl/common/Util.xs	Sun Oct 17 03:40:26 2010 +0000
+++ b/libpurple/plugins/perl/common/Util.xs	Sun Oct 17 03:55:04 2010 +0000
@@ -238,7 +238,7 @@
 	guchar *ret;
 	CODE:
 		ret = purple_base16_decode(str, &len);
-		if(len) {
+		if(ret && len > 0) {
 			RETVAL = newSVpv((gchar *)ret, len);
 		} else {
 			g_free(ret);
@@ -256,7 +256,7 @@
 	guchar *ret;
 	CODE:
 		ret = purple_base64_decode(str, &len);
-		if(len) {
+		if(ret && len > 0) {
 			RETVAL = newSVpv((gchar *)ret, len);
 		} else {
 			g_free(ret);
--- a/libpurple/protocols/jabber/auth_digest_md5.c	Sun Oct 17 03:40:26 2010 +0000
+++ b/libpurple/protocols/jabber/auth_digest_md5.c	Sun Oct 17 03:55:04 2010 +0000
@@ -182,7 +182,9 @@
 
 	dec_in = (char *)purple_base64_decode(enc_in, NULL);
 	purple_debug_misc("jabber", "decoded challenge (%"
-			G_GSIZE_FORMAT "): %s\n", strlen(dec_in), dec_in);
+			G_GSIZE_FORMAT "): %s\n",
+			dec_in != NULL ? strlen(dec_in) : 0,
+			dec_in != NULL  ? dec_in : "(null)");
 
 	parts = parse_challenge(dec_in);
 
--- a/libpurple/protocols/msn/slp.c	Sun Oct 17 03:40:26 2010 +0000
+++ b/libpurple/protocols/msn/slp.c	Sun Oct 17 03:55:04 2010 +0000
@@ -554,7 +554,7 @@
 							 slpcall->slplink->remote_user);
 
 		header = (MsnFileContext *)purple_base64_decode(context, &bin_len);
-		if (bin_len >= sizeof(MsnFileContext) - 1 &&
+		if (header != NULL && bin_len >= sizeof(MsnFileContext) - 1 &&
 			(header->version == 2 ||
 			 (header->version == 3 && header->length == sizeof(MsnFileContext) + 63))) {
 			file_size = GUINT64_FROM_LE(header->file_size);
--- a/libpurple/protocols/myspace/message.c	Sun Oct 17 03:40:26 2010 +0000
+++ b/libpurple/protocols/myspace/message.c	Sun Oct 17 03:55:04 2010 +0000
@@ -1363,7 +1363,7 @@
 			 *
 			 */
 			*binary_data = (gchar *)purple_base64_decode((const gchar *)elem->data, binary_length);
-			return TRUE;
+			return ((*binary_data) != NULL);
 
 		case MSIM_TYPE_BINARY:
 			gs = (GString *)elem->data;
--- a/libpurple/protocols/oscar/clientlogin.c	Sun Oct 17 03:40:26 2010 +0000
+++ b/libpurple/protocols/oscar/clientlogin.c	Sun Oct 17 03:55:04 2010 +0000
@@ -272,7 +272,7 @@
 	char *tls_certname = NULL;
 	unsigned short port;
 	guint8 *cookiedata;
-	gsize cookiedata_len;
+	gsize cookiedata_len = 0;
 
 	od = user_data;
 	gc = od->gc;
--- a/libpurple/protocols/qq/im.c	Sun Oct 17 03:40:26 2010 +0000
+++ b/libpurple/protocols/qq/im.c	Sun Oct 17 03:55:04 2010 +0000
@@ -547,7 +547,6 @@
 	const gchar *start, *end, *last;
 	GData *attribs;
 	gchar *tmp;
-	unsigned char *rgb;
 
 	g_return_val_if_fail(msg != NULL, NULL);
 
@@ -570,8 +569,11 @@
 
 		tmp = g_datalist_get_data(&attribs, "color");
 		if (tmp && strlen(tmp) > 1) {
-			rgb = purple_base16_decode(tmp + 1, NULL);
-			g_memmove(fmt->rgb, rgb, 3);
+			unsigned char *rgb;
+			gsize rgb_len;
+			rgb = purple_base16_decode(tmp + 1, &rgb_len);
+			if (rgb != NULL && rgb_len >= 3)
+				g_memmove(fmt->rgb, rgb, 3);
 			g_free(rgb);
 		}
 
--- a/libpurple/protocols/yahoo/libymsg.c	Sun Oct 17 03:40:26 2010 +0000
+++ b/libpurple/protocols/yahoo/libymsg.c	Sun Oct 17 03:55:04 2010 +0000
@@ -317,7 +317,7 @@
 
 			if (pair->value) {
 				decoded = purple_base64_decode(pair->value, &len);
-				if (len) {
+				if (decoded && len > 0) {
 					tmp = purple_str_binary_to_ascii(decoded, len);
 					purple_debug_info("yahoo", "Got key 197, value = %s\n", tmp);
 					g_free(tmp);
@@ -2863,15 +2863,17 @@
 	if (base64) {
 		guint32 ip;
 		YahooFriend *f;
-		char *host_ip;
+		char *host_ip, *tmp;
 		struct yahoo_p2p_data *p2p_data;
 
 		decoded = purple_base64_decode(base64, &len);
-		if (len) {
-			char *tmp = purple_str_binary_to_ascii(decoded, len);
-			purple_debug_info("yahoo", "Got P2P service packet (from server): who = %s, ip = %s\n", who, tmp);
-			g_free(tmp);
+		if (decoded == NULL) {
+			purple_debug_info("yahoo","p2p: Unable to decode base64 IP (%s) \n", base64);
+			return;
 		}
+		tmp = purple_str_binary_to_ascii(decoded, len);
+		purple_debug_info("yahoo", "Got P2P service packet (from server): who = %s, ip = %s\n", who, tmp);
+		g_free(tmp);
 
 		ip = strtol((gchar *)decoded, NULL, 10);
 		g_free(decoded);