From: Siddhesh Poyarekar Date: Fri, 25 Oct 2013 04:52:12 +0000 (+0530) Subject: Fix stack overflow due to large AF_INET6 requests X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=6f4b109567445b1ed70300bb0cb1752cb9998ec9;p=thirdparty%2Fglibc.git Fix stack overflow due to large AF_INET6 requests Resolves #16072 (CVE-2013-4458). This patch fixes another stack overflow in getaddrinfo when it is called with AF_INET6. The AF_UNSPEC case was fixed as CVE-2013-1914, but the AF_INET6 case went undetected back then. --- diff --git a/ChangeLog b/ChangeLog index b970fe10017..0afcd3f0495 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,5 +1,6 @@ -2013-10-10 Joseph Myers +2013-10-25 Siddhesh Poyarekar +<<<<<<< HEAD * sysdeps/ieee754/ldbl-128ibm/e_acosl.c (__ieee754_acosl): Check for NaNs before doing comparisons on argument. * sysdeps/ieee754/ldbl-128ibm/e_asinl.c (__ieee754_asinl): @@ -490,8 +491,12 @@ * sysdeps/unix/sysv/linux/tst-fanotify.c: New test. * sysdeps/unix/sysv/linux/Makefile (tests): Add tst-fanotify. +======= + [BZ #16072] + * sysdeps/posix/getaddrinfo.c (gethosts): Allocate tmpbuf on + heap for large requests. +>>>>>>> 6f95434... Fix stack overflow due to large AF_INET6 requests ->>>>>>> ffa3cd7... Fix lgammaf spurious underflow (bug 15427). 2013-09-02 Joseph Myers [BZ #14155] diff --git a/NEWS b/NEWS index b25af8ee04a..c70f333cc49 100644 --- a/NEWS +++ b/NEWS @@ -10,11 +10,14 @@ Version 2.18.1 * The following bugs are resolved with this release: 14155, 14699, 15532, 15427, 15522, 15797, 15892, 15895, 15909, 15996, - 16150. + 16072, 16150. * CVE-2013-4237 The readdir_r function could write more than NAME_MAX bytes to the d_name member of struct dirent, or omit the terminating NUL character. (Bugzilla #14699). + +* CVE-2013-4458 Stack overflow in getaddrinfo with large number of results + for AF_INET6 has been fixed (Bugzilla #16072). Version 2.18 diff --git a/sysdeps/posix/getaddrinfo.c b/sysdeps/posix/getaddrinfo.c index 7bb3ded9af0..2e972551336 100644 --- a/sysdeps/posix/getaddrinfo.c +++ b/sysdeps/posix/getaddrinfo.c @@ -197,7 +197,22 @@ gaih_inet_serv (const char *servicename, const struct gaih_typeproto *tp, &rc, &herrno, NULL, &localcanon)); \ if (rc != ERANGE || herrno != NETDB_INTERNAL) \ break; \ - tmpbuf = extend_alloca (tmpbuf, tmpbuflen, 2 * tmpbuflen); \ + if (!malloc_tmpbuf && __libc_use_alloca (alloca_used + 2 * tmpbuflen)) \ + tmpbuf = extend_alloca_account (tmpbuf, tmpbuflen, 2 * tmpbuflen, \ + alloca_used); \ + else \ + { \ + char *newp = realloc (malloc_tmpbuf ? tmpbuf : NULL, \ + 2 * tmpbuflen); \ + if (newp == NULL) \ + { \ + result = -EAI_MEMORY; \ + goto free_and_return; \ + } \ + tmpbuf = newp; \ + malloc_tmpbuf = true; \ + tmpbuflen = 2 * tmpbuflen; \ + } \ } \ if (status == NSS_STATUS_SUCCESS && rc == 0) \ h = &th; \ @@ -209,7 +224,8 @@ gaih_inet_serv (const char *servicename, const struct gaih_typeproto *tp, { \ __set_h_errno (herrno); \ _res.options |= old_res_options & RES_USE_INET6; \ - return -EAI_SYSTEM; \ + result = -EAI_SYSTEM; \ + goto free_and_return; \ } \ if (herrno == TRY_AGAIN) \ no_data = EAI_AGAIN; \