summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDaniel Veillard <veillard@src.gnome.org>2004-10-27 09:39:50 +0000
committerDaniel Veillard <veillard@src.gnome.org>2004-10-27 09:39:50 +0000
commit8e2c9792e923c95a4d353cbc0bb1146413b60168 (patch)
tree56ec6c65ae156086105bc87f73401c887f6f53fb
parent95ddcd326694de324a41a73d407d72604dd746d1 (diff)
downloadlibxml2-8e2c9792e923c95a4d353cbc0bb1146413b60168.tar.gz
second part of the security fix for xmlNanoFTPConnect() and
* nanoftp.c nanohttp.c: second part of the security fix for xmlNanoFTPConnect() and xmlNanoHTTPConnectHost(). Daniel
-rw-r--r--ChangeLog5
-rw-r--r--nanoftp.c38
-rw-r--r--nanohttp.c18
3 files changed, 46 insertions, 15 deletions
diff --git a/ChangeLog b/ChangeLog
index 0c46bd4c..b0fcf592 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,8 @@
+Wed Oct 27 11:44:35 CEST 2004 Daniel Veillard <daniel@veillard.com>
+
+ * nanoftp.c nanohttp.c: second part of the security fix for
+ xmlNanoFTPConnect() and xmlNanoHTTPConnectHost().
+
Tue Oct 26 23:57:02 CEST 2004 Daniel Veillard <daniel@veillard.com>
* nanoftp.c: applied fixes for a couple of potential security problems
diff --git a/nanoftp.c b/nanoftp.c
index 27054c6e..9933bb97 100644
--- a/nanoftp.c
+++ b/nanoftp.c
@@ -1106,22 +1106,25 @@ xmlNanoFTPConnect(void *ctx) {
if (!tmp) {
if (result)
freeaddrinfo (result);
+ __xmlIOErr(XML_FROM_FTP, 0, "getaddrinfo failed");
return (-1);
}
+ if (tmp->ai_addrlen > sizeof(ctxt->ftpAddr)) {
+ __xmlIOErr(XML_FROM_FTP, 0, "gethostbyname address mismatch");
+ return (-1);
+ }
+ if (tmp->ai_family == AF_INET6) {
+ memcpy (&ctxt->ftpAddr, tmp->ai_addr, tmp->ai_addrlen);
+ ((struct sockaddr_in6 *) &ctxt->ftpAddr)->sin6_port = htons (port);
+ ctxt->controlFd = socket (AF_INET6, SOCK_STREAM, 0);
+ }
else {
- if (tmp->ai_family == AF_INET6) {
- memcpy (&ctxt->ftpAddr, tmp->ai_addr, tmp->ai_addrlen);
- ((struct sockaddr_in6 *) &ctxt->ftpAddr)->sin6_port = htons (port);
- ctxt->controlFd = socket (AF_INET6, SOCK_STREAM, 0);
- }
- else {
- memcpy (&ctxt->ftpAddr, tmp->ai_addr, tmp->ai_addrlen);
- ((struct sockaddr_in *) &ctxt->ftpAddr)->sin_port = htons (port);
- ctxt->controlFd = socket (AF_INET, SOCK_STREAM, 0);
- }
- addrlen = tmp->ai_addrlen;
- freeaddrinfo (result);
+ memcpy (&ctxt->ftpAddr, tmp->ai_addr, tmp->ai_addrlen);
+ ((struct sockaddr_in *) &ctxt->ftpAddr)->sin_port = htons (port);
+ ctxt->controlFd = socket (AF_INET, SOCK_STREAM, 0);
}
+ addrlen = tmp->ai_addrlen;
+ freeaddrinfo (result);
}
else
#endif
@@ -1134,10 +1137,15 @@ xmlNanoFTPConnect(void *ctx) {
__xmlIOErr(XML_FROM_FTP, 0, "gethostbyname failed");
return (-1);
}
+ if (hp->h_length >
+ sizeof(((struct sockaddr_in *)&ctxt->ftpAddr)->sin_addr)) {
+ __xmlIOErr(XML_FROM_FTP, 0, "gethostbyname address mismatch");
+ return (-1);
+ }
- /*
- * Prepare the socket
- */
+ /*
+ * Prepare the socket
+ */
((struct sockaddr_in *)&ctxt->ftpAddr)->sin_family = AF_INET;
memcpy (&((struct sockaddr_in *)&ctxt->ftpAddr)->sin_addr,
hp->h_addr_list[0], hp->h_length);
diff --git a/nanohttp.c b/nanohttp.c
index 8dbd9fc0..0a726839 100644
--- a/nanohttp.c
+++ b/nanohttp.c
@@ -1072,11 +1072,21 @@ xmlNanoHTTPConnectHost(const char *host, int port)
for (res = result; res; res = res->ai_next) {
if (res->ai_family == AF_INET || res->ai_family == AF_INET6) {
if (res->ai_family == AF_INET6) {
+ if (res->ai_addrlen > sizeof(sockin6)) {
+ __xmlIOErr(XML_FROM_HTTP, 0, "address size mismatch\n");
+ freeaddrinfo (result);
+ return (-1);
+ }
memcpy (&sockin6, res->ai_addr, res->ai_addrlen);
sockin6.sin6_port = htons (port);
addr = (struct sockaddr *)&sockin6;
}
else {
+ if (res->ai_addrlen > sizeof(sockin)) {
+ __xmlIOErr(XML_FROM_HTTP, 0, "address size mismatch\n");
+ freeaddrinfo (result);
+ return (-1);
+ }
memcpy (&sockin, res->ai_addr, res->ai_addrlen);
sockin.sin_port = htons (port);
addr = (struct sockaddr *)&sockin;
@@ -1141,6 +1151,10 @@ xmlNanoHTTPConnectHost(const char *host, int port)
for (i = 0; h->h_addr_list[i]; i++) {
if (h->h_addrtype == AF_INET) {
/* A records (IPv4) */
+ if ((unsigned int) h->h_length > sizeof(ia)) {
+ __xmlIOErr(XML_FROM_HTTP, 0, "address size mismatch\n");
+ return (-1);
+ }
memcpy (&ia, h->h_addr_list[i], h->h_length);
sockin.sin_family = h->h_addrtype;
sockin.sin_addr = ia;
@@ -1149,6 +1163,10 @@ xmlNanoHTTPConnectHost(const char *host, int port)
#ifdef SUPPORT_IP6
} else if (have_ipv6 () && (h->h_addrtype == AF_INET6)) {
/* AAAA records (IPv6) */
+ if ((unsigned int) h->h_length > sizeof(ia6)) {
+ __xmlIOErr(XML_FROM_HTTP, 0, "address size mismatch\n");
+ return (-1);
+ }
memcpy (&ia6, h->h_addr_list[i], h->h_length);
sockin6.sin6_family = h->h_addrtype;
sockin6.sin6_addr = ia6;