# HG changeset patch # User Pascal Bellard # Date 1422526825 -3600 # Node ID 1c7b5ef9b071b364617d96732339210ffb79ddd9 # Parent 16e488e884db5f74fe5c425514d58db591dd2ccc glibc: CVE-2015-0235 fix diff -r 16e488e884db -r 1c7b5ef9b071 glibc/receipt --- a/glibc/receipt Tue Dec 30 13:40:55 2014 +0100 +++ b/glibc/receipt Thu Jan 29 11:20:25 2015 +0100 @@ -22,6 +22,8 @@ # Fix a bug that prevents Glibc from building with GCC-4.5.2: patch -Np1 -i $stuff/glibc-2.13-gcc_fix-1.patch + + patch -Np1 -i $stuff/glibc-2.13-CVE-2015-0235.patch # Build in a separate directory. mkdir ../glibc-build && cd ../glibc-build @@ -78,6 +80,8 @@ # Fix a bug that prevents Glibc from building with GCC-4.5.2: patch -Np1 -i $stuff/glibc-2.13-gcc_fix-1.patch + patch -Np1 -i $stuff/glibc-2.13-CVE-2015-0235.patch + # Fix a stack imbalance that occurs under some conditions: sed -i '195,213 s/PRIVATE_FUTEX/FUTEX_CLOCK_REALTIME/' \ nptl/sysdeps/unix/sysv/linux/x86_64/pthread_rwlock_timedrdlock.S \ diff -r 16e488e884db -r 1c7b5ef9b071 glibc/stuff/glibc-2.13-CVE-2015-0235.patch --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/glibc/stuff/glibc-2.13-CVE-2015-0235.patch Thu Jan 29 11:20:25 2015 +0100 @@ -0,0 +1,137 @@ +CVE-2015-0235 GHOST +From https://sourceware.org/git/?p=glibc.git;a=commit;h=d5dd6189d506068ed11c8bfa1e1e9bffde04decd +--- glibc-2.13/nss/digits_dots.c ++++ glibc-2.13/nss/digits_dots.c +@@ -47,7 +47,10 @@ + { + if (h_errnop) + *h_errnop = NETDB_INTERNAL; +- *result = NULL; ++ if (buffer_size == NULL) ++ *status = NSS_STATUS_TRYAGAIN; ++ else ++ *result = NULL; + return -1; + } + +@@ -84,14 +87,16 @@ + } + + size_needed = (sizeof (*host_addr) +- + sizeof (*h_addr_ptrs) + strlen (name) + 1); ++ sizeof (*h_addr_ptrs) ++ + sizeof (*h_allias_ptr) + strlen (name) + 1); + + if (buffer_size == NULL) + { + if (buflen < size_needed) + { ++ *status = NSS_STATUS_TRYAGAIN; + if (h_errnop != NULL) +- *h_errnop = TRY_AGAIN; ++ *h_errnop = NETDB_INTERNAL; + __set_errno (ERANGE); + goto done; + } +@@ -110,7 +115,7 @@ + *buffer_size = 0; + __set_errno (save); + if (h_errnop != NULL) +- *h_errnop = TRY_AGAIN; ++ *h_errnop = NETDB_INTERNAL; + *result = NULL; + goto done; + } +@@ -150,7 +155,9 @@ + if (! ok) + { + *h_errnop = HOST_NOT_FOUND; +- if (buffer_size) ++ if (buffer_size == NULL) ++ *status = NSS_STATUS_NOTFOUND: ++ else + *result = NULL; + goto done; + } +@@ -202,15 +209,6 @@ + + if ((isxdigit (name[0]) && strchr (name, ':') != NULL) || name[0] == ':') + { +- const char *cp; +- char *hostname; +- typedef unsigned char host_addr_t[16]; +- host_addr_t *host_addr; +- typedef char *host_addr_list_t[2]; +- host_addr_list_t *h_addr_ptrs; +- size_t size_needed; +- int addr_size; +- + switch (af) + { + default: +@@ -226,7 +224,10 @@ + /* This is not possible. We cannot represent an IPv6 address + in an `struct in_addr' variable. */ + *h_errnop = HOST_NOT_FOUND; +- *result = NULL; ++ if (buffer_size == NULL) ++ *status = NSS_STATUS_NOTFOUND; ++ else ++ *result = NULL; + goto done; + + case AF_INET6: +@@ -234,42 +235,6 @@ + break; + } + +- size_needed = (sizeof (*host_addr) +- + sizeof (*h_addr_ptrs) + strlen (name) + 1); +- +- if (buffer_size == NULL && buflen < size_needed) +- { +- if (h_errnop != NULL) +- *h_errnop = TRY_AGAIN; +- __set_errno (ERANGE); +- goto done; +- } +- else if (buffer_size != NULL && *buffer_size < size_needed) +- { +- char *new_buf; +- *buffer_size = size_needed; +- new_buf = realloc (*buffer, *buffer_size); +- +- if (new_buf == NULL) +- { +- save = errno; +- free (*buffer); +- __set_errno (save); +- *buffer = NULL; +- *buffer_size = 0; +- *result = NULL; +- goto done; +- } +- *buffer = new_buf; +- } +- +- memset (*buffer, '\0', size_needed); +- +- host_addr = (host_addr_t *) *buffer; +- h_addr_ptrs = (host_addr_list_t *) +- ((char *) host_addr + sizeof (*host_addr)); +- hostname = (char *) h_addr_ptrs + sizeof (*h_addr_ptrs); +- + for (cp = name;; ++cp) + { + if (!*cp) +@@ -282,7 +247,9 @@ + if (inet_pton (AF_INET6, name, host_addr) <= 0) + { + *h_errnop = HOST_NOT_FOUND; +- if (buffer_size) ++ if (buffer_size == NULL) ++ *status = NSS_STATUS_NOTFOUND: ++ else + *result = NULL; + goto done; + }