aboutsummaryrefslogtreecommitdiff
path: root/gnu
diff options
context:
space:
mode:
authorMarius Bakke <marius@gnu.org>2020-07-26 13:37:12 +0200
committerMarius Bakke <marius@gnu.org>2020-07-26 13:37:12 +0200
commitebd1ba713cbefc9ad5dac609255e1344a328e360 (patch)
tree39a48103b244191090bd43984100935940611f7e /gnu
parentccc1d743a64fd71bee1a27f1f495978989b41126 (diff)
downloadguix-ebd1ba713cbefc9ad5dac609255e1344a328e360.tar
guix-ebd1ba713cbefc9ad5dac609255e1344a328e360.tar.gz
gnu: glibc: Remove old versions.
* gnu/packages/patches/glibc-CVE-2015-5180.patch, gnu/packages/patches/glibc-CVE-2015-7547.patch, gnu/packages/patches/glibc-CVE-2016-3075.patch, gnu/packages/patches/glibc-CVE-2016-3706.patch, gnu/packages/patches/glibc-CVE-2016-4429.patch, gnu/packages/patches/glibc-CVE-2017-1000366-pt1.patch, gnu/packages/patches/glibc-CVE-2017-1000366-pt2.patch, gnu/packages/patches/glibc-CVE-2017-1000366-pt3.patch, gnu/packages/patches/glibc-o-largefile.patch, gnu/packages/patches/glibc-vectorized-strcspn-guards.patch: Delete files. * gnu/local.mk (dist_patch_DATA): Adjust accordingly. * gnu/packages/base.scm (glibc-2.26, glibc-2.25, glibc-2.24, glibc-2.23, glibc-2.22): Remove variables.
Diffstat (limited to 'gnu')
-rw-r--r--gnu/local.mk10
-rw-r--r--gnu/packages/base.scm112
-rw-r--r--gnu/packages/patches/glibc-CVE-2015-5180.patch311
-rw-r--r--gnu/packages/patches/glibc-CVE-2015-7547.patch590
-rw-r--r--gnu/packages/patches/glibc-CVE-2016-3075.patch43
-rw-r--r--gnu/packages/patches/glibc-CVE-2016-3706.patch188
-rw-r--r--gnu/packages/patches/glibc-CVE-2016-4429.patch58
-rw-r--r--gnu/packages/patches/glibc-CVE-2017-1000366-pt1.patch36
-rw-r--r--gnu/packages/patches/glibc-CVE-2017-1000366-pt2.patch124
-rw-r--r--gnu/packages/patches/glibc-CVE-2017-1000366-pt3.patch206
-rw-r--r--gnu/packages/patches/glibc-o-largefile.patch25
-rw-r--r--gnu/packages/patches/glibc-vectorized-strcspn-guards.patch23
12 files changed, 0 insertions, 1726 deletions
diff --git a/gnu/local.mk b/gnu/local.mk
index f2a7b6b984..ef6533bd8d 100644
--- a/gnu/local.mk
+++ b/gnu/local.mk
@@ -1016,14 +1016,6 @@ dist_patch_DATA = \
%D%/packages/patches/ghostscript-no-header-uuid.patch \
%D%/packages/patches/ghostscript-no-header-creationdate.patch \
%D%/packages/patches/glib-tests-timer.patch \
- %D%/packages/patches/glibc-CVE-2015-5180.patch \
- %D%/packages/patches/glibc-CVE-2015-7547.patch \
- %D%/packages/patches/glibc-CVE-2016-3075.patch \
- %D%/packages/patches/glibc-CVE-2016-3706.patch \
- %D%/packages/patches/glibc-CVE-2016-4429.patch \
- %D%/packages/patches/glibc-CVE-2017-1000366-pt1.patch \
- %D%/packages/patches/glibc-CVE-2017-1000366-pt2.patch \
- %D%/packages/patches/glibc-CVE-2017-1000366-pt3.patch \
%D%/packages/patches/glibc-CVE-2018-11236.patch \
%D%/packages/patches/glibc-CVE-2018-11237.patch \
%D%/packages/patches/glibc-CVE-2019-7309.patch \
@@ -1045,9 +1037,7 @@ dist_patch_DATA = \
%D%/packages/patches/glibc-ldd-x86_64.patch \
%D%/packages/patches/glibc-locales.patch \
%D%/packages/patches/glibc-locales-2.28.patch \
- %D%/packages/patches/glibc-o-largefile.patch \
%D%/packages/patches/glibc-reinstate-prlimit64-fallback.patch \
- %D%/packages/patches/glibc-vectorized-strcspn-guards.patch \
%D%/packages/patches/glibc-versioned-locpath.patch \
%D%/packages/patches/glibc-2.27-git-fixes.patch \
%D%/packages/patches/glibc-2.28-git-fixes.patch \
diff --git a/gnu/packages/base.scm b/gnu/packages/base.scm
index 7116708743..6cd7ed749b 100644
--- a/gnu/packages/base.scm
+++ b/gnu/packages/base.scm
@@ -1014,118 +1014,6 @@ with the Linux kernel.")
"glibc-CVE-2018-11237.patch"))))
(properties `((lint-hidden-cve . ("CVE-2017-18269")))))) ; glibc-2.27-git-fixes
-(define-public glibc-2.26
- (package
- (inherit glibc)
- ;; This version number corresponds to the output of `git describe` and the
- ;; archive can be generated by checking out the commit ID and running:
- ;; git archive --prefix=$(git describe)/ HEAD | xz > $(git describe).tar.xz
- ;; See <https://bugs.gnu.org/29406> for why this was necessary.
- (version "2.26.105-g0890d5379c")
- (source (origin
- (inherit (package-source glibc))
- (uri (string-append "https://alpha.gnu.org/gnu/guix/mirror/"
- "glibc-" (version-major+minor version) "-"
- (caddr (string-split version #\.)) ".tar.xz"))
- (sha256
- (base32
- "1jck0c1i248sn02rvsfjykk77qncma34bjq89dyy2irwm50d7s3g"))
- (patches (search-patches "glibc-ldd-x86_64.patch"
- "glibc-versioned-locpath.patch"
- "glibc-allow-kernel-2.6.32.patch"))))))
-
-(define-public glibc-2.25
- (package
- (inherit glibc)
- (version "2.25")
- (source (origin
- (inherit (package-source glibc))
- (uri (string-append "mirror://gnu/glibc/glibc-"
- version ".tar.xz"))
- (sha256
- (base32
- "1813dzkgw6v8q8q1m4v96yfis7vjqc9pslqib6j9mrwh6fxxjyq6"))
- (patches (search-patches "glibc-ldd-x86_64.patch"
- "glibc-versioned-locpath.patch"
- "glibc-vectorized-strcspn-guards.patch"
- "glibc-CVE-2017-1000366-pt1.patch"
- "glibc-CVE-2017-1000366-pt2.patch"
- "glibc-CVE-2017-1000366-pt3.patch"))))))
-
-(define-public glibc-2.24
- (package
- (inherit glibc)
- (version "2.24")
- (source (origin
- (inherit (package-source glibc))
- (uri (string-append "mirror://gnu/glibc/glibc-"
- version ".tar.xz"))
- (sha256
- (base32
- "1lxmprg9gm73gvafxd503x70z32phwjzcy74i0adfi6ixzla7m4r"))
- (patches (search-patches "glibc-ldd-x86_64.patch"
- "glibc-versioned-locpath.patch"
- "glibc-vectorized-strcspn-guards.patch"
- "glibc-CVE-2015-5180.patch"
- "glibc-CVE-2017-1000366-pt1.patch"
- "glibc-CVE-2017-1000366-pt2.patch"
- "glibc-CVE-2017-1000366-pt3.patch"))))))
-
-(define-public glibc-2.23
- (package
- (inherit glibc)
- (version "2.23")
- (source (origin
- (inherit (package-source glibc))
- (uri (string-append "mirror://gnu/glibc/glibc-"
- version ".tar.xz"))
- (sha256
- (base32
- "1s8krs3y2n6pzav7ic59dz41alqalphv7vww4138ag30wh0fpvwl"))
- (patches (search-patches "glibc-ldd-x86_64.patch"
- "glibc-versioned-locpath.patch"
- "glibc-vectorized-strcspn-guards.patch"
- "glibc-CVE-2015-5180.patch"
- "glibc-CVE-2016-3075.patch"
- "glibc-CVE-2016-3706.patch"
- "glibc-CVE-2016-4429.patch"
- "glibc-CVE-2017-1000366-pt1.patch"
- "glibc-CVE-2017-1000366-pt2.patch"
- "glibc-CVE-2017-1000366-pt3.patch"))))))
-
-(define-public glibc-2.22
- (package
- (inherit glibc)
- (version "2.22")
- (source (origin
- (inherit (package-source glibc))
- (uri (string-append "mirror://gnu/glibc/glibc-"
- version ".tar.xz"))
- (sha256
- (base32
- "0j49682pm2nh4qbdw35bas82p1pgfnz4d2l7iwfyzvrvj0318wzb"))
- (patches (search-patches "glibc-ldd-x86_64.patch"
- "glibc-o-largefile.patch"
- "glibc-vectorized-strcspn-guards.patch"
- "glibc-CVE-2015-5180.patch"
- "glibc-CVE-2015-7547.patch"
- "glibc-CVE-2016-3075.patch"
- "glibc-CVE-2016-3706.patch"
- "glibc-CVE-2016-4429.patch"
- "glibc-CVE-2017-1000366-pt1.patch"
- "glibc-CVE-2017-1000366-pt2.patch"
- "glibc-CVE-2017-1000366-pt3.patch"))))
- (arguments
- (substitute-keyword-arguments (package-arguments glibc)
- ((#:phases phases)
- `(modify-phases ,phases
- (add-before 'configure 'fix-pwd
- (lambda _
- ;; Use `pwd' instead of `/bin/pwd' for glibc-2.22.
- (substitute* "configure"
- (("/bin/pwd") "pwd"))
- #t))))))))
-
(define-public (make-gcc-libc base-gcc libc)
"Return a GCC that targets LIBC."
(package (inherit base-gcc)
diff --git a/gnu/packages/patches/glibc-CVE-2015-5180.patch b/gnu/packages/patches/glibc-CVE-2015-5180.patch
deleted file mode 100644
index 92e3740fc1..0000000000
--- a/gnu/packages/patches/glibc-CVE-2015-5180.patch
+++ /dev/null
@@ -1,311 +0,0 @@
-From b3b37f1a5559a7620e31c8053ed1b44f798f2b6d Mon Sep 17 00:00:00 2001
-From: Florian Weimer <fweimer@redhat.com>
-Date: Sat, 31 Dec 2016 20:22:09 +0100
-Subject: [PATCH] CVE-2015-5180: resolv: Fix crash with internal QTYPE [BZ
- #18784]
-
-Also rename T_UNSPEC because an upcoming public header file
-update will use that name.
-
-(cherry picked from commit fc82b0a2dfe7dbd35671c10510a8da1043d746a5)
----
- ChangeLog | 14 ++++
- NEWS | 6 ++
- include/arpa/nameser_compat.h | 6 +-
- resolv/Makefile | 5 ++
- resolv/nss_dns/dns-host.c | 2 +-
- resolv/res_mkquery.c | 4 +
- resolv/res_query.c | 6 +-
- resolv/tst-resolv-qtypes.c | 185 ++++++++++++++++++++++++++++++++++++++++++
- 8 files changed, 221 insertions(+), 7 deletions(-)
- create mode 100644 resolv/tst-resolv-qtypes.c
-
-diff --git a/include/arpa/nameser_compat.h b/include/arpa/nameser_compat.h
-index 2e735ed..7c0deed 100644
---- a/include/arpa/nameser_compat.h
-+++ b/include/arpa/nameser_compat.h
-@@ -1,8 +1,8 @@
- #ifndef _ARPA_NAMESER_COMPAT_
- #include <resolv/arpa/nameser_compat.h>
-
--/* Picksome unused number to represent lookups of IPv4 and IPv6 (i.e.,
-- T_A and T_AAAA). */
--#define T_UNSPEC 62321
-+/* The number is outside the 16-bit RR type range and is used
-+ internally by the implementation. */
-+#define T_QUERY_A_AND_AAAA 439963904
-
- #endif
-diff --git a/resolv/Makefile b/resolv/Makefile
-index 8be41d3..a4c86b9 100644
---- a/resolv/Makefile
-+++ b/resolv/Makefile
-@@ -40,6 +40,9 @@ ifeq ($(have-thread-library),yes)
- extra-libs += libanl
- routines += gai_sigqueue
- tests += tst-res_hconf_reorder
-+
-+# This test sends millions of packets and is rather slow.
-+xtests += tst-resolv-qtypes
- endif
- extra-libs-others = $(extra-libs)
- libresolv-routines := gethnamaddr res_comp res_debug \
-@@ -117,3 +120,5 @@ tst-leaks2-ENV = MALLOC_TRACE=$(objpfx)tst-leaks2.mtrace
- $(objpfx)mtrace-tst-leaks2.out: $(objpfx)tst-leaks2.out
- $(common-objpfx)malloc/mtrace $(objpfx)tst-leaks2.mtrace > $@; \
- $(evaluate-test)
-+
-+$(objpfx)tst-resolv-qtypes: $(objpfx)libresolv.so $(shared-thread-library)
-diff --git a/resolv/nss_dns/dns-host.c b/resolv/nss_dns/dns-host.c
-index 5f9e357..d16fa4b 100644
---- a/resolv/nss_dns/dns-host.c
-+++ b/resolv/nss_dns/dns-host.c
-@@ -323,7 +323,7 @@ _nss_dns_gethostbyname4_r (const char *name, struct gaih_addrtuple **pat,
-
- int olderr = errno;
- enum nss_status status;
-- int n = __libc_res_nsearch (&_res, name, C_IN, T_UNSPEC,
-+ int n = __libc_res_nsearch (&_res, name, C_IN, T_QUERY_A_AND_AAAA,
- host_buffer.buf->buf, 2048, &host_buffer.ptr,
- &ans2p, &nans2p, &resplen2, &ans2p_malloced);
- if (n >= 0)
-diff --git a/resolv/res_mkquery.c b/resolv/res_mkquery.c
-index 12f9730..d80b531 100644
---- a/resolv/res_mkquery.c
-+++ b/resolv/res_mkquery.c
-@@ -103,6 +103,10 @@ res_nmkquery(res_state statp,
- int n;
- u_char *dnptrs[20], **dpp, **lastdnptr;
-
-+ if (class < 0 || class > 65535
-+ || type < 0 || type > 65535)
-+ return -1;
-+
- #ifdef DEBUG
- if (statp->options & RES_DEBUG)
- printf(";; res_nmkquery(%s, %s, %s, %s)\n",
-diff --git a/resolv/res_query.c b/resolv/res_query.c
-index 944d1a9..07dc6f6 100644
---- a/resolv/res_query.c
-+++ b/resolv/res_query.c
-@@ -122,7 +122,7 @@ __libc_res_nquery(res_state statp,
- int n, use_malloc = 0;
- u_int oflags = statp->_flags;
-
-- size_t bufsize = (type == T_UNSPEC ? 2 : 1) * QUERYSIZE;
-+ size_t bufsize = (type == T_QUERY_A_AND_AAAA ? 2 : 1) * QUERYSIZE;
- u_char *buf = alloca (bufsize);
- u_char *query1 = buf;
- int nquery1 = -1;
-@@ -137,7 +137,7 @@ __libc_res_nquery(res_state statp,
- printf(";; res_query(%s, %d, %d)\n", name, class, type);
- #endif
-
-- if (type == T_UNSPEC)
-+ if (type == T_QUERY_A_AND_AAAA)
- {
- n = res_nmkquery(statp, QUERY, name, class, T_A, NULL, 0, NULL,
- query1, bufsize);
-@@ -190,7 +190,7 @@ __libc_res_nquery(res_state statp,
- if (__builtin_expect (n <= 0, 0) && !use_malloc) {
- /* Retry just in case res_nmkquery failed because of too
- short buffer. Shouldn't happen. */
-- bufsize = (type == T_UNSPEC ? 2 : 1) * MAXPACKET;
-+ bufsize = (type == T_QUERY_A_AND_AAAA ? 2 : 1) * MAXPACKET;
- buf = malloc (bufsize);
- if (buf != NULL) {
- query1 = buf;
-diff --git a/resolv/tst-resolv-qtypes.c b/resolv/tst-resolv-qtypes.c
-new file mode 100644
-index 0000000..b3e60c6
---- /dev/null
-+++ b/resolv/tst-resolv-qtypes.c
-@@ -0,0 +1,185 @@
-+/* Exercise low-level query functions with different QTYPEs.
-+ Copyright (C) 2016 Free Software Foundation, Inc.
-+ This file is part of the GNU C Library.
-+
-+ The GNU C Library is free software; you can redistribute it and/or
-+ modify it under the terms of the GNU Lesser General Public
-+ License as published by the Free Software Foundation; either
-+ version 2.1 of the License, or (at your option) any later version.
-+
-+ The GNU C Library is distributed in the hope that it will be useful,
-+ but WITHOUT ANY WARRANTY; without even the implied warranty of
-+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
-+ Lesser General Public License for more details.
-+
-+ You should have received a copy of the GNU Lesser General Public
-+ License along with the GNU C Library; if not, see
-+ <http://www.gnu.org/licenses/>. */
-+
-+#include <resolv.h>
-+#include <string.h>
-+#include <support/check.h>
-+#include <support/check_nss.h>
-+#include <support/resolv_test.h>
-+#include <support/support.h>
-+#include <support/test-driver.h>
-+#include <support/xmemstream.h>
-+
-+/* If ture, the response function will send the actual response packet
-+ over TCP instead of UDP. */
-+static volatile bool force_tcp;
-+
-+/* Send back a fake resource record matching the QTYPE. */
-+static void
-+response (const struct resolv_response_context *ctx,
-+ struct resolv_response_builder *b,
-+ const char *qname, uint16_t qclass, uint16_t qtype)
-+{
-+ if (force_tcp && ctx->tcp)
-+ {
-+ resolv_response_init (b, (struct resolv_response_flags) { .tc = 1 });
-+ resolv_response_add_question (b, qname, qclass, qtype);
-+ return;
-+ }
-+
-+ resolv_response_init (b, (struct resolv_response_flags) { });
-+ resolv_response_add_question (b, qname, qclass, qtype);
-+ resolv_response_section (b, ns_s_an);
-+ resolv_response_open_record (b, qname, qclass, qtype, 0);
-+ resolv_response_add_data (b, &qtype, sizeof (qtype));
-+ resolv_response_close_record (b);
-+}
-+
-+static const const char *domain = "www.example.com";
-+
-+static int
-+wrap_res_query (int type, unsigned char *answer, int answer_length)
-+{
-+ return res_query (domain, C_IN, type, answer, answer_length);
-+}
-+
-+static int
-+wrap_res_search (int type, unsigned char *answer, int answer_length)
-+{
-+ return res_query (domain, C_IN, type, answer, answer_length);
-+}
-+
-+static int
-+wrap_res_querydomain (int type, unsigned char *answer, int answer_length)
-+{
-+ return res_querydomain ("www", "example.com", C_IN, type,
-+ answer, answer_length);
-+}
-+
-+static int
-+wrap_res_send (int type, unsigned char *answer, int answer_length)
-+{
-+ unsigned char buf[512];
-+ int ret = res_mkquery (QUERY, domain, C_IN, type,
-+ (const unsigned char *) "", 0, NULL,
-+ buf, sizeof (buf));
-+ if (type < 0 || type >= 65536)
-+ {
-+ /* res_mkquery fails for out-of-range record types. */
-+ TEST_VERIFY_EXIT (ret == -1);
-+ return -1;
-+ }
-+ TEST_VERIFY_EXIT (ret > 12); /* DNS header length. */
-+ return res_send (buf, ret, answer, answer_length);
-+}
-+
-+static int
-+wrap_res_nquery (int type, unsigned char *answer, int answer_length)
-+{
-+ return res_nquery (&_res, domain, C_IN, type, answer, answer_length);
-+}
-+
-+static int
-+wrap_res_nsearch (int type, unsigned char *answer, int answer_length)
-+{
-+ return res_nquery (&_res, domain, C_IN, type, answer, answer_length);
-+}
-+
-+static int
-+wrap_res_nquerydomain (int type, unsigned char *answer, int answer_length)
-+{
-+ return res_nquerydomain (&_res, "www", "example.com", C_IN, type,
-+ answer, answer_length);
-+}
-+
-+static int
-+wrap_res_nsend (int type, unsigned char *answer, int answer_length)
-+{
-+ unsigned char buf[512];
-+ int ret = res_nmkquery (&_res, QUERY, domain, C_IN, type,
-+ (const unsigned char *) "", 0, NULL,
-+ buf, sizeof (buf));
-+ if (type < 0 || type >= 65536)
-+ {
-+ /* res_mkquery fails for out-of-range record types. */
-+ TEST_VERIFY_EXIT (ret == -1);
-+ return -1;
-+ }
-+ TEST_VERIFY_EXIT (ret > 12); /* DNS header length. */
-+ return res_nsend (&_res, buf, ret, answer, answer_length);
-+}
-+
-+static void
-+test_function (const char *fname,
-+ int (*func) (int type,
-+ unsigned char *answer, int answer_length))
-+{
-+ unsigned char buf[512];
-+ for (int tcp = 0; tcp < 2; ++tcp)
-+ {
-+ force_tcp = tcp;
-+ for (unsigned int type = 1; type <= 65535; ++type)
-+ {
-+ if (test_verbose)
-+ printf ("info: sending QTYPE %d with %s (tcp=%d)\n",
-+ type, fname, tcp);
-+ int ret = func (type, buf, sizeof (buf));
-+ if (ret != 47)
-+ FAIL_EXIT1 ("%s tcp=%d qtype=%d return value %d",
-+ fname,tcp, type, ret);
-+ /* One question, one answer record. */
-+ TEST_VERIFY (memcmp (buf + 4, "\0\1\0\1\0\0\0\0", 8) == 0);
-+ /* Question section. */
-+ static const char qname[] = "\3www\7example\3com";
-+ size_t qname_length = sizeof (qname);
-+ TEST_VERIFY (memcmp (buf + 12, qname, qname_length) == 0);
-+ /* RDATA part of answer. */
-+ uint16_t type16 = type;
-+ TEST_VERIFY (memcmp (buf + ret - 2, &type16, sizeof (type16)) == 0);
-+ }
-+ }
-+
-+ TEST_VERIFY (func (-1, buf, sizeof (buf) == -1));
-+ TEST_VERIFY (func (65536, buf, sizeof (buf) == -1));
-+}
-+
-+static int
-+do_test (void)
-+{
-+ struct resolv_redirect_config config =
-+ {
-+ .response_callback = response,
-+ };
-+ struct resolv_test *obj = resolv_test_start (config);
-+
-+ test_function ("res_query", &wrap_res_query);
-+ test_function ("res_search", &wrap_res_search);
-+ test_function ("res_querydomain", &wrap_res_querydomain);
-+ test_function ("res_send", &wrap_res_send);
-+
-+ test_function ("res_nquery", &wrap_res_nquery);
-+ test_function ("res_nsearch", &wrap_res_nsearch);
-+ test_function ("res_nquerydomain", &wrap_res_nquerydomain);
-+ test_function ("res_nsend", &wrap_res_nsend);
-+
-+ resolv_test_end (obj);
-+ return 0;
-+}
-+
-+#define TIMEOUT 300
-+#include <support/test-driver.c>
---
-2.9.3
-
diff --git a/gnu/packages/patches/glibc-CVE-2015-7547.patch b/gnu/packages/patches/glibc-CVE-2015-7547.patch
deleted file mode 100644
index 12abeb76d4..0000000000
--- a/gnu/packages/patches/glibc-CVE-2015-7547.patch
+++ /dev/null
@@ -1,590 +0,0 @@
-From b995d95a5943785be3ab862b2d3276f3b4a22481 Mon Sep 17 00:00:00 2001
-From: Carlos O'Donell <carlos@systemhalted.org>
-Date: Tue, 16 Feb 2016 21:26:37 -0500
-Subject: [PATCH] CVE-2015-7547: getaddrinfo() stack-based buffer overflow (Bug
- 18665).
-
-* A stack-based buffer overflow was found in libresolv when invoked from
- libnss_dns, allowing specially crafted DNS responses to seize control
- of execution flow in the DNS client. The buffer overflow occurs in
- the functions send_dg (send datagram) and send_vc (send TCP) for the
- NSS module libnss_dns.so.2 when calling getaddrinfo with AF_UNSPEC
- family. The use of AF_UNSPEC triggers the low-level resolver code to
- send out two parallel queries for A and AAAA. A mismanagement of the
- buffers used for those queries could result in the response of a query
- writing beyond the alloca allocated buffer created by
- _nss_dns_gethostbyname4_r. Buffer management is simplified to remove
- the overflow. Thanks to the Google Security Team and Red Hat for
- reporting the security impact of this issue, and Robert Holiday of
- Ciena for reporting the related bug 18665. (CVE-2015-7547)
-
-See also:
-https://sourceware.org/ml/libc-alpha/2016-02/msg00416.html
-https://sourceware.org/ml/libc-alpha/2016-02/msg00418.html
-
-(cherry picked from commit e9db92d3acfe1822d56d11abcea5bfc4c41cf6ca)
----
- ChangeLog | 15 +++
- NEWS | 14 +++
- resolv/nss_dns/dns-host.c | 111 ++++++++++++++++++-
- resolv/res_query.c | 3 +
- resolv/res_send.c | 264 ++++++++++++++++++++++++++++++++++------------
- 5 files changed, 338 insertions(+), 69 deletions(-)
-
-diff --git a/resolv/nss_dns/dns-host.c b/resolv/nss_dns/dns-host.c
-index 357ac04..a0fe9a8 100644
---- a/resolv/nss_dns/dns-host.c
-+++ b/resolv/nss_dns/dns-host.c
-@@ -1031,7 +1031,10 @@ gaih_getanswer_slice (const querybuf *answer, int anslen, const char *qname,
- int h_namelen = 0;
-
- if (ancount == 0)
-- return NSS_STATUS_NOTFOUND;
-+ {
-+ *h_errnop = HOST_NOT_FOUND;
-+ return NSS_STATUS_NOTFOUND;
-+ }
-
- while (ancount-- > 0 && cp < end_of_message && had_error == 0)
- {
-@@ -1208,7 +1211,14 @@ gaih_getanswer_slice (const querybuf *answer, int anslen, const char *qname,
- /* Special case here: if the resolver sent a result but it only
- contains a CNAME while we are looking for a T_A or T_AAAA record,
- we fail with NOTFOUND instead of TRYAGAIN. */
-- return canon == NULL ? NSS_STATUS_TRYAGAIN : NSS_STATUS_NOTFOUND;
-+ if (canon != NULL)
-+ {
-+ *h_errnop = HOST_NOT_FOUND;
-+ return NSS_STATUS_NOTFOUND;
-+ }
-+
-+ *h_errnop = NETDB_INTERNAL;
-+ return NSS_STATUS_TRYAGAIN;
- }
-
-
-@@ -1222,11 +1232,101 @@ gaih_getanswer (const querybuf *answer1, int anslen1, const querybuf *answer2,
-
- enum nss_status status = NSS_STATUS_NOTFOUND;
-
-+ /* Combining the NSS status of two distinct queries requires some
-+ compromise and attention to symmetry (A or AAAA queries can be
-+ returned in any order). What follows is a breakdown of how this
-+ code is expected to work and why. We discuss only SUCCESS,
-+ TRYAGAIN, NOTFOUND and UNAVAIL, since they are the only returns
-+ that apply (though RETURN and MERGE exist). We make a distinction
-+ between TRYAGAIN (recoverable) and TRYAGAIN' (not-recoverable).
-+ A recoverable TRYAGAIN is almost always due to buffer size issues
-+ and returns ERANGE in errno and the caller is expected to retry
-+ with a larger buffer.
-+
-+ Lastly, you may be tempted to make significant changes to the
-+ conditions in this code to bring about symmetry between responses.
-+ Please don't change anything without due consideration for
-+ expected application behaviour. Some of the synthesized responses
-+ aren't very well thought out and sometimes appear to imply that
-+ IPv4 responses are always answer 1, and IPv6 responses are always
-+ answer 2, but that's not true (see the implementation of send_dg
-+ and send_vc to see response can arrive in any order, particularly
-+ for UDP). However, we expect it holds roughly enough of the time
-+ that this code works, but certainly needs to be fixed to make this
-+ a more robust implementation.
-+
-+ ----------------------------------------------
-+ | Answer 1 Status / | Synthesized | Reason |
-+ | Answer 2 Status | Status | |
-+ |--------------------------------------------|
-+ | SUCCESS/SUCCESS | SUCCESS | [1] |
-+ | SUCCESS/TRYAGAIN | TRYAGAIN | [5] |
-+ | SUCCESS/TRYAGAIN' | SUCCESS | [1] |
-+ | SUCCESS/NOTFOUND | SUCCESS | [1] |
-+ | SUCCESS/UNAVAIL | SUCCESS | [1] |
-+ | TRYAGAIN/SUCCESS | TRYAGAIN | [2] |
-+ | TRYAGAIN/TRYAGAIN | TRYAGAIN | [2] |
-+ | TRYAGAIN/TRYAGAIN' | TRYAGAIN | [2] |
-+ | TRYAGAIN/NOTFOUND | TRYAGAIN | [2] |
-+ | TRYAGAIN/UNAVAIL | TRYAGAIN | [2] |
-+ | TRYAGAIN'/SUCCESS | SUCCESS | [3] |
-+ | TRYAGAIN'/TRYAGAIN | TRYAGAIN | [3] |
-+ | TRYAGAIN'/TRYAGAIN' | TRYAGAIN' | [3] |
-+ | TRYAGAIN'/NOTFOUND | TRYAGAIN' | [3] |
-+ | TRYAGAIN'/UNAVAIL | UNAVAIL | [3] |
-+ | NOTFOUND/SUCCESS | SUCCESS | [3] |
-+ | NOTFOUND/TRYAGAIN | TRYAGAIN | [3] |
-+ | NOTFOUND/TRYAGAIN' | TRYAGAIN' | [3] |
-+ | NOTFOUND/NOTFOUND | NOTFOUND | [3] |
-+ | NOTFOUND/UNAVAIL | UNAVAIL | [3] |
-+ | UNAVAIL/SUCCESS | UNAVAIL | [4] |
-+ | UNAVAIL/TRYAGAIN | UNAVAIL | [4] |
-+ | UNAVAIL/TRYAGAIN' | UNAVAIL | [4] |
-+ | UNAVAIL/NOTFOUND | UNAVAIL | [4] |
-+ | UNAVAIL/UNAVAIL | UNAVAIL | [4] |
-+ ----------------------------------------------
-+
-+ [1] If the first response is a success we return success.
-+ This ignores the state of the second answer and in fact
-+ incorrectly sets errno and h_errno to that of the second
-+ answer. However because the response is a success we ignore
-+ *errnop and *h_errnop (though that means you touched errno on
-+ success). We are being conservative here and returning the
-+ likely IPv4 response in the first answer as a success.
-+
-+ [2] If the first response is a recoverable TRYAGAIN we return
-+ that instead of looking at the second response. The
-+ expectation here is that we have failed to get an IPv4 response
-+ and should retry both queries.
-+
-+ [3] If the first response was not a SUCCESS and the second
-+ response is not NOTFOUND (had a SUCCESS, need to TRYAGAIN,
-+ or failed entirely e.g. TRYAGAIN' and UNAVAIL) then use the
-+ result from the second response, otherwise the first responses
-+ status is used. Again we have some odd side-effects when the
-+ second response is NOTFOUND because we overwrite *errnop and
-+ *h_errnop that means that a first answer of NOTFOUND might see
-+ its *errnop and *h_errnop values altered. Whether it matters
-+ in practice that a first response NOTFOUND has the wrong
-+ *errnop and *h_errnop is undecided.
-+
-+ [4] If the first response is UNAVAIL we return that instead of
-+ looking at the second response. The expectation here is that
-+ it will have failed similarly e.g. configuration failure.
-+
-+ [5] Testing this code is complicated by the fact that truncated
-+ second response buffers might be returned as SUCCESS if the
-+ first answer is a SUCCESS. To fix this we add symmetry to
-+ TRYAGAIN with the second response. If the second response
-+ is a recoverable error we now return TRYAGIN even if the first
-+ response was SUCCESS. */
-+
- if (anslen1 > 0)
- status = gaih_getanswer_slice(answer1, anslen1, qname,
- &pat, &buffer, &buflen,
- errnop, h_errnop, ttlp,
- &first);
-+
- if ((status == NSS_STATUS_SUCCESS || status == NSS_STATUS_NOTFOUND
- || (status == NSS_STATUS_TRYAGAIN
- /* We want to look at the second answer in case of an
-@@ -1242,8 +1342,15 @@ gaih_getanswer (const querybuf *answer1, int anslen1, const querybuf *answer2,
- &pat, &buffer, &buflen,
- errnop, h_errnop, ttlp,
- &first);
-+ /* Use the second response status in some cases. */
- if (status != NSS_STATUS_SUCCESS && status2 != NSS_STATUS_NOTFOUND)
- status = status2;
-+ /* Do not return a truncated second response (unless it was
-+ unavoidable e.g. unrecoverable TRYAGAIN). */
-+ if (status == NSS_STATUS_SUCCESS
-+ && (status2 == NSS_STATUS_TRYAGAIN
-+ && *errnop == ERANGE && *h_errnop != NO_RECOVERY))
-+ status = NSS_STATUS_TRYAGAIN;
- }
-
- return status;
-diff --git a/resolv/res_query.c b/resolv/res_query.c
-index 4a9b3b3..95470a9 100644
---- a/resolv/res_query.c
-+++ b/resolv/res_query.c
-@@ -396,6 +396,7 @@ __libc_res_nsearch(res_state statp,
- {
- free (*answerp2);
- *answerp2 = NULL;
-+ *nanswerp2 = 0;
- *answerp2_malloced = 0;
- }
- }
-@@ -447,6 +448,7 @@ __libc_res_nsearch(res_state statp,
- {
- free (*answerp2);
- *answerp2 = NULL;
-+ *nanswerp2 = 0;
- *answerp2_malloced = 0;
- }
-
-@@ -521,6 +523,7 @@ __libc_res_nsearch(res_state statp,
- {
- free (*answerp2);
- *answerp2 = NULL;
-+ *nanswerp2 = 0;
- *answerp2_malloced = 0;
- }
- if (saved_herrno != -1)
-diff --git a/resolv/res_send.c b/resolv/res_send.c
-index 5e53cc2..6511bb1 100644
---- a/resolv/res_send.c
-+++ b/resolv/res_send.c
-@@ -1,3 +1,20 @@
-+/* Copyright (C) 2016 Free Software Foundation, Inc.
-+ This file is part of the GNU C Library.
-+
-+ The GNU C Library is free software; you can redistribute it and/or
-+ modify it under the terms of the GNU Lesser General Public
-+ License as published by the Free Software Foundation; either
-+ version 2.1 of the License, or (at your option) any later version.
-+
-+ The GNU C Library is distributed in the hope that it will be useful,
-+ but WITHOUT ANY WARRANTY; without even the implied warranty of
-+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
-+ Lesser General Public License for more details.
-+
-+ You should have received a copy of the GNU Lesser General Public
-+ License along with the GNU C Library; if not, see
-+ <http://www.gnu.org/licenses/>. */
-+
- /*
- * Copyright (c) 1985, 1989, 1993
- * The Regents of the University of California. All rights reserved.
-@@ -363,6 +380,8 @@ __libc_res_nsend(res_state statp, const u_char *buf, int buflen,
- #ifdef USE_HOOKS
- if (__glibc_unlikely (statp->qhook || statp->rhook)) {
- if (anssiz < MAXPACKET && ansp) {
-+ /* Always allocate MAXPACKET, callers expect
-+ this specific size. */
- u_char *buf = malloc (MAXPACKET);
- if (buf == NULL)
- return (-1);
-@@ -638,6 +657,77 @@ get_nsaddr (res_state statp, int n)
- return (struct sockaddr *) (void *) &statp->nsaddr_list[n];
- }
-
-+/* The send_vc function is responsible for sending a DNS query over TCP
-+ to the nameserver numbered NS from the res_state STATP i.e.
-+ EXT(statp).nssocks[ns]. The function supports sending both IPv4 and
-+ IPv6 queries at the same serially on the same socket.
-+
-+ Please note that for TCP there is no way to disable sending both
-+ queries, unlike UDP, which honours RES_SNGLKUP and RES_SNGLKUPREOP
-+ and sends the queries serially and waits for the result after each
-+ sent query. This implemetnation should be corrected to honour these
-+ options.
-+
-+ Please also note that for TCP we send both queries over the same
-+ socket one after another. This technically violates best practice
-+ since the server is allowed to read the first query, respond, and
-+ then close the socket (to service another client). If the server
-+ does this, then the remaining second query in the socket data buffer
-+ will cause the server to send the client an RST which will arrive
-+ asynchronously and the client's OS will likely tear down the socket
-+ receive buffer resulting in a potentially short read and lost
-+ response data. This will force the client to retry the query again,
-+ and this process may repeat until all servers and connection resets
-+ are exhausted and then the query will fail. It's not known if this
-+ happens with any frequency in real DNS server implementations. This
-+ implementation should be corrected to use two sockets by default for
-+ parallel queries.
-+
-+ The query stored in BUF of BUFLEN length is sent first followed by
-+ the query stored in BUF2 of BUFLEN2 length. Queries are sent
-+ serially on the same socket.
-+
-+ Answers to the query are stored firstly in *ANSP up to a max of
-+ *ANSSIZP bytes. If more than *ANSSIZP bytes are needed and ANSCP
-+ is non-NULL (to indicate that modifying the answer buffer is allowed)
-+ then malloc is used to allocate a new response buffer and ANSCP and
-+ ANSP will both point to the new buffer. If more than *ANSSIZP bytes
-+ are needed but ANSCP is NULL, then as much of the response as
-+ possible is read into the buffer, but the results will be truncated.
-+ When truncation happens because of a small answer buffer the DNS
-+ packets header field TC will bet set to 1, indicating a truncated
-+ message and the rest of the socket data will be read and discarded.
-+
-+ Answers to the query are stored secondly in *ANSP2 up to a max of
-+ *ANSSIZP2 bytes, with the actual response length stored in
-+ *RESPLEN2. If more than *ANSSIZP bytes are needed and ANSP2
-+ is non-NULL (required for a second query) then malloc is used to
-+ allocate a new response buffer, *ANSSIZP2 is set to the new buffer
-+ size and *ANSP2_MALLOCED is set to 1.
-+
-+ The ANSP2_MALLOCED argument will eventually be removed as the
-+ change in buffer pointer can be used to detect the buffer has
-+ changed and that the caller should use free on the new buffer.
-+
-+ Note that the answers may arrive in any order from the server and
-+ therefore the first and second answer buffers may not correspond to
-+ the first and second queries.
-+
-+ It is not supported to call this function with a non-NULL ANSP2
-+ but a NULL ANSCP. Put another way, you can call send_vc with a
-+ single unmodifiable buffer or two modifiable buffers, but no other
-+ combination is supported.
-+
-+ It is the caller's responsibility to free the malloc allocated
-+ buffers by detecting that the pointers have changed from their
-+ original values i.e. *ANSCP or *ANSP2 has changed.
-+
-+ If errors are encountered then *TERRNO is set to an appropriate
-+ errno value and a zero result is returned for a recoverable error,
-+ and a less-than zero result is returned for a non-recoverable error.
-+
-+ If no errors are encountered then *TERRNO is left unmodified and
-+ a the length of the first response in bytes is returned. */
- static int
- send_vc(res_state statp,
- const u_char *buf, int buflen, const u_char *buf2, int buflen2,
-@@ -647,11 +737,7 @@ send_vc(res_state statp,
- {
- const HEADER *hp = (HEADER *) buf;
- const HEADER *hp2 = (HEADER *) buf2;
-- u_char *ans = *ansp;
-- int orig_anssizp = *anssizp;
-- // XXX REMOVE
-- // int anssiz = *anssizp;
-- HEADER *anhp = (HEADER *) ans;
-+ HEADER *anhp = (HEADER *) *ansp;
- struct sockaddr *nsap = get_nsaddr (statp, ns);
- int truncating, connreset, n;
- /* On some architectures compiler might emit a warning indicating
-@@ -743,6 +829,8 @@ send_vc(res_state statp,
- * Receive length & response
- */
- int recvresp1 = 0;
-+ /* Skip the second response if there is no second query.
-+ To do that we mark the second response as received. */
- int recvresp2 = buf2 == NULL;
- uint16_t rlen16;
- read_len:
-@@ -779,40 +867,14 @@ send_vc(res_state statp,
- u_char **thisansp;
- int *thisresplenp;
- if ((recvresp1 | recvresp2) == 0 || buf2 == NULL) {
-+ /* We have not received any responses
-+ yet or we only have one response to
-+ receive. */
- thisanssizp = anssizp;
- thisansp = anscp ?: ansp;
- assert (anscp != NULL || ansp2 == NULL);
- thisresplenp = &resplen;
- } else {
-- if (*anssizp != MAXPACKET) {
-- /* No buffer allocated for the first
-- reply. We can try to use the rest
-- of the user-provided buffer. */
--#if __GNUC_PREREQ (4, 7)
-- DIAG_PUSH_NEEDS_COMMENT;
-- DIAG_IGNORE_NEEDS_COMMENT (5, "-Wmaybe-uninitialized");
--#endif
--#if _STRING_ARCH_unaligned
-- *anssizp2 = orig_anssizp - resplen;
-- *ansp2 = *ansp + resplen;
--#else
-- int aligned_resplen
-- = ((resplen + __alignof__ (HEADER) - 1)
-- & ~(__alignof__ (HEADER) - 1));
-- *anssizp2 = orig_anssizp - aligned_resplen;
-- *ansp2 = *ansp + aligned_resplen;
--#endif
--#if __GNUC_PREREQ (4, 7)
-- DIAG_POP_NEEDS_COMMENT;
--#endif
-- } else {
-- /* The first reply did not fit into the
-- user-provided buffer. Maybe the second
-- answer will. */
-- *anssizp2 = orig_anssizp;
-- *ansp2 = *ansp;
-- }
--
- thisanssizp = anssizp2;
- thisansp = ansp2;
- thisresplenp = resplen2;
-@@ -820,10 +882,14 @@ send_vc(res_state statp,
- anhp = (HEADER *) *thisansp;
-
- *thisresplenp = rlen;
-- if (rlen > *thisanssizp) {
-- /* Yes, we test ANSCP here. If we have two buffers
-- both will be allocatable. */
-- if (__glibc_likely (anscp != NULL)) {
-+ /* Is the answer buffer too small? */
-+ if (*thisanssizp < rlen) {
-+ /* If the current buffer is not the the static
-+ user-supplied buffer then we can reallocate
-+ it. */
-+ if (thisansp != NULL && thisansp != ansp) {
-+ /* Always allocate MAXPACKET, callers expect
-+ this specific size. */
- u_char *newp = malloc (MAXPACKET);
- if (newp == NULL) {
- *terrno = ENOMEM;
-@@ -835,6 +901,9 @@ send_vc(res_state statp,
- if (thisansp == ansp2)
- *ansp2_malloced = 1;
- anhp = (HEADER *) newp;
-+ /* A uint16_t can't be larger than MAXPACKET
-+ thus it's safe to allocate MAXPACKET but
-+ read RLEN bytes instead. */
- len = rlen;
- } else {
- Dprint(statp->options & RES_DEBUG,
-@@ -997,6 +1066,66 @@ reopen (res_state statp, int *terrno, int ns)
- return 1;
- }
-
-+/* The send_dg function is responsible for sending a DNS query over UDP
-+ to the nameserver numbered NS from the res_state STATP i.e.
-+ EXT(statp).nssocks[ns]. The function supports IPv4 and IPv6 queries
-+ along with the ability to send the query in parallel for both stacks
-+ (default) or serially (RES_SINGLKUP). It also supports serial lookup
-+ with a close and reopen of the socket used to talk to the server
-+ (RES_SNGLKUPREOP) to work around broken name servers.
-+
-+ The query stored in BUF of BUFLEN length is sent first followed by
-+ the query stored in BUF2 of BUFLEN2 length. Queries are sent
-+ in parallel (default) or serially (RES_SINGLKUP or RES_SNGLKUPREOP).
-+
-+ Answers to the query are stored firstly in *ANSP up to a max of
-+ *ANSSIZP bytes. If more than *ANSSIZP bytes are needed and ANSCP
-+ is non-NULL (to indicate that modifying the answer buffer is allowed)
-+ then malloc is used to allocate a new response buffer and ANSCP and
-+ ANSP will both point to the new buffer. If more than *ANSSIZP bytes
-+ are needed but ANSCP is NULL, then as much of the response as
-+ possible is read into the buffer, but the results will be truncated.
-+ When truncation happens because of a small answer buffer the DNS
-+ packets header field TC will bet set to 1, indicating a truncated
-+ message, while the rest of the UDP packet is discarded.
-+
-+ Answers to the query are stored secondly in *ANSP2 up to a max of
-+ *ANSSIZP2 bytes, with the actual response length stored in
-+ *RESPLEN2. If more than *ANSSIZP bytes are needed and ANSP2
-+ is non-NULL (required for a second query) then malloc is used to
-+ allocate a new response buffer, *ANSSIZP2 is set to the new buffer
-+ size and *ANSP2_MALLOCED is set to 1.
-+
-+ The ANSP2_MALLOCED argument will eventually be removed as the
-+ change in buffer pointer can be used to detect the buffer has
-+ changed and that the caller should use free on the new buffer.
-+
-+ Note that the answers may arrive in any order from the server and
-+ therefore the first and second answer buffers may not correspond to
-+ the first and second queries.
-+
-+ It is not supported to call this function with a non-NULL ANSP2
-+ but a NULL ANSCP. Put another way, you can call send_vc with a
-+ single unmodifiable buffer or two modifiable buffers, but no other
-+ combination is supported.
-+
-+ It is the caller's responsibility to free the malloc allocated
-+ buffers by detecting that the pointers have changed from their
-+ original values i.e. *ANSCP or *ANSP2 has changed.
-+
-+ If an answer is truncated because of UDP datagram DNS limits then
-+ *V_CIRCUIT is set to 1 and the return value non-zero to indicate to
-+ the caller to retry with TCP. The value *GOTSOMEWHERE is set to 1
-+ if any progress was made reading a response from the nameserver and
-+ is used by the caller to distinguish between ECONNREFUSED and
-+ ETIMEDOUT (the latter if *GOTSOMEWHERE is 1).
-+
-+ If errors are encountered then *TERRNO is set to an appropriate
-+ errno value and a zero result is returned for a recoverable error,
-+ and a less-than zero result is returned for a non-recoverable error.
-+
-+ If no errors are encountered then *TERRNO is left unmodified and
-+ a the length of the first response in bytes is returned. */
- static int
- send_dg(res_state statp,
- const u_char *buf, int buflen, const u_char *buf2, int buflen2,
-@@ -1006,8 +1135,6 @@ send_dg(res_state statp,
- {
- const HEADER *hp = (HEADER *) buf;
- const HEADER *hp2 = (HEADER *) buf2;
-- u_char *ans = *ansp;
-- int orig_anssizp = *anssizp;
- struct timespec now, timeout, finish;
- struct pollfd pfd[1];
- int ptimeout;
-@@ -1040,6 +1167,8 @@ send_dg(res_state statp,
- int need_recompute = 0;
- int nwritten = 0;
- int recvresp1 = 0;
-+ /* Skip the second response if there is no second query.
-+ To do that we mark the second response as received. */
- int recvresp2 = buf2 == NULL;
- pfd[0].fd = EXT(statp).nssocks[ns];
- pfd[0].events = POLLOUT;
-@@ -1203,55 +1332,56 @@ send_dg(res_state statp,
- int *thisresplenp;
-
- if ((recvresp1 | recvresp2) == 0 || buf2 == NULL) {
-+ /* We have not received any responses
-+ yet or we only have one response to
-+ receive. */
- thisanssizp = anssizp;
- thisansp = anscp ?: ansp;
- assert (anscp != NULL || ansp2 == NULL);
- thisresplenp = &resplen;
- } else {
-- if (*anssizp != MAXPACKET) {
-- /* No buffer allocated for the first
-- reply. We can try to use the rest
-- of the user-provided buffer. */
--#if _STRING_ARCH_unaligned
-- *anssizp2 = orig_anssizp - resplen;
-- *ansp2 = *ansp + resplen;
--#else
-- int aligned_resplen
-- = ((resplen + __alignof__ (HEADER) - 1)
-- & ~(__alignof__ (HEADER) - 1));
-- *anssizp2 = orig_anssizp - aligned_resplen;
-- *ansp2 = *ansp + aligned_resplen;
--#endif
-- } else {
-- /* The first reply did not fit into the
-- user-provided buffer. Maybe the second
-- answer will. */
-- *anssizp2 = orig_anssizp;
-- *ansp2 = *ansp;
-- }
--
- thisanssizp = anssizp2;
- thisansp = ansp2;
- thisresplenp = resplen2;
- }
-
- if (*thisanssizp < MAXPACKET
-- /* Yes, we test ANSCP here. If we have two buffers
-- both will be allocatable. */
-- && anscp
-+ /* If the current buffer is not the the static
-+ user-supplied buffer then we can reallocate
-+ it. */
-+ && (thisansp != NULL && thisansp != ansp)
- #ifdef FIONREAD
-+ /* Is the size too small? */
- && (ioctl (pfd[0].fd, FIONREAD, thisresplenp) < 0
- || *thisanssizp < *thisresplenp)
- #endif
- ) {
-+ /* Always allocate MAXPACKET, callers expect
-+ this specific size. */
- u_char *newp = malloc (MAXPACKET);
- if (newp != NULL) {
-- *anssizp = MAXPACKET;
-- *thisansp = ans = newp;
-+ *thisanssizp = MAXPACKET;
-+ *thisansp = newp;
- if (thisansp == ansp2)
- *ansp2_malloced = 1;
- }
- }
-+ /* We could end up with truncation if anscp was NULL
-+ (not allowed to change caller's buffer) and the
-+ response buffer size is too small. This isn't a
-+ reliable way to detect truncation because the ioctl
-+ may be an inaccurate report of the UDP message size.
-+ Therefore we use this only to issue debug output.
-+ To do truncation accurately with UDP we need
-+ MSG_TRUNC which is only available on Linux. We
-+ can abstract out the Linux-specific feature in the
-+ future to detect truncation. */
-+ if (__glibc_unlikely (*thisanssizp < *thisresplenp)) {
-+ Dprint(statp->options & RES_DEBUG,
-+ (stdout, ";; response may be truncated (UDP)\n")
-+ );
-+ }
-+
- HEADER *anhp = (HEADER *) *thisansp;
- socklen_t fromlen = sizeof(struct sockaddr_in6);
- assert (sizeof(from) <= fromlen);
---
-2.9.3
-
diff --git a/gnu/packages/patches/glibc-CVE-2016-3075.patch b/gnu/packages/patches/glibc-CVE-2016-3075.patch
deleted file mode 100644
index d16722806e..0000000000
--- a/gnu/packages/patches/glibc-CVE-2016-3075.patch
+++ /dev/null
@@ -1,43 +0,0 @@
-From 146b58d11fddbef15b888906e3be4f33900c416f Mon Sep 17 00:00:00 2001
-From: Florian Weimer <fweimer@redhat.com>
-Date: Tue, 29 Mar 2016 12:57:56 +0200
-Subject: [PATCH] CVE-2016-3075: Stack overflow in _nss_dns_getnetbyname_r [BZ
- #19879]
-
-The defensive copy is not needed because the name may not alias the
-output buffer.
-
-(cherry picked from commit 317b199b4aff8cfa27f2302ab404d2bb5032b9a4)
-(cherry picked from commit 883dceebc8f11921a9890211a4e202e5be17562f)
----
- ChangeLog | 7 +++++++
- NEWS | 10 ++++++++--
- resolv/nss_dns/dns-network.c | 5 +----
- 3 files changed, 16 insertions(+), 6 deletions(-)
-
-diff --git a/resolv/nss_dns/dns-network.c b/resolv/nss_dns/dns-network.c
-index 2eb2f67..8f301a7 100644
---- a/resolv/nss_dns/dns-network.c
-+++ b/resolv/nss_dns/dns-network.c
-@@ -118,17 +118,14 @@ _nss_dns_getnetbyname_r (const char *name, struct netent *result,
- } net_buffer;
- querybuf *orig_net_buffer;
- int anslen;
-- char *qbuf;
- enum nss_status status;
-
- if (__res_maybe_init (&_res, 0) == -1)
- return NSS_STATUS_UNAVAIL;
-
-- qbuf = strdupa (name);
--
- net_buffer.buf = orig_net_buffer = (querybuf *) alloca (1024);
-
-- anslen = __libc_res_nsearch (&_res, qbuf, C_IN, T_PTR, net_buffer.buf->buf,
-+ anslen = __libc_res_nsearch (&_res, name, C_IN, T_PTR, net_buffer.buf->buf,
- 1024, &net_buffer.ptr, NULL, NULL, NULL, NULL);
- if (anslen < 0)
- {
---
-2.9.3
-
diff --git a/gnu/packages/patches/glibc-CVE-2016-3706.patch b/gnu/packages/patches/glibc-CVE-2016-3706.patch
deleted file mode 100644
index 617242df24..0000000000
--- a/gnu/packages/patches/glibc-CVE-2016-3706.patch
+++ /dev/null
@@ -1,188 +0,0 @@
-From 1a8a7c12950a0026a3c406a7cb1608f96aa1460e Mon Sep 17 00:00:00 2001
-From: Florian Weimer <fweimer@redhat.com>
-Date: Fri, 29 Apr 2016 10:35:34 +0200
-Subject: [PATCH] CVE-2016-3706: getaddrinfo: stack overflow in hostent
- conversion [BZ #20010]
-
-When converting a struct hostent response to struct gaih_addrtuple, the
-gethosts macro (which is called from gaih_inet) used alloca, without
-malloc fallback for large responses. This commit changes this code to
-use calloc unconditionally.
-
-This commit also consolidated a second hostent-to-gaih_addrtuple
-conversion loop (in gaih_inet) to use the new conversion function.
-
-(cherry picked from commit 4ab2ab03d4351914ee53248dc5aef4a8c88ff8b9)
----
- ChangeLog | 10 ++++
- sysdeps/posix/getaddrinfo.c | 130 +++++++++++++++++++++++---------------------
- 2 files changed, 79 insertions(+), 61 deletions(-)
-
-diff --git a/sysdeps/posix/getaddrinfo.c b/sysdeps/posix/getaddrinfo.c
-index 1ef3f20..fed2d3b 100644
---- a/sysdeps/posix/getaddrinfo.c
-+++ b/sysdeps/posix/getaddrinfo.c
-@@ -168,9 +168,58 @@ gaih_inet_serv (const char *servicename, const struct gaih_typeproto *tp,
- return 0;
- }
-
-+/* Convert struct hostent to a list of struct gaih_addrtuple objects.
-+ h_name is not copied, and the struct hostent object must not be
-+ deallocated prematurely. *RESULT must be NULL or a pointer to an
-+ object allocated using malloc, which is freed. */
-+static bool
-+convert_hostent_to_gaih_addrtuple (const struct addrinfo *req,
-+ int family,
-+ struct hostent *h,
-+ struct gaih_addrtuple **result)
-+{
-+ free (*result);
-+ *result = NULL;
-+
-+ /* Count the number of addresses in h->h_addr_list. */
-+ size_t count = 0;
-+ for (char **p = h->h_addr_list; *p != NULL; ++p)
-+ ++count;
-+
-+ /* Report no data if no addresses are available, or if the incoming
-+ address size is larger than what we can store. */
-+ if (count == 0 || h->h_length > sizeof (((struct gaih_addrtuple) {}).addr))
-+ return true;
-+
-+ struct gaih_addrtuple *array = calloc (count, sizeof (*array));
-+ if (array == NULL)
-+ return false;
-+
-+ for (size_t i = 0; i < count; ++i)
-+ {
-+ if (family == AF_INET && req->ai_family == AF_INET6)
-+ {
-+ /* Perform address mapping. */
-+ array[i].family = AF_INET6;
-+ memcpy(array[i].addr + 3, h->h_addr_list[i], sizeof (uint32_t));
-+ array[i].addr[2] = htonl (0xffff);
-+ }
-+ else
-+ {
-+ array[i].family = family;
-+ memcpy (array[i].addr, h->h_addr_list[i], h->h_length);
-+ }
-+ array[i].next = array + i + 1;
-+ }
-+ array[0].name = h->h_name;
-+ array[count - 1].next = NULL;
-+
-+ *result = array;
-+ return true;
-+}
-+
- #define gethosts(_family, _type) \
- { \
-- int i; \
- int herrno; \
- struct hostent th; \
- struct hostent *h; \
-@@ -219,36 +268,23 @@ gaih_inet_serv (const char *servicename, const struct gaih_typeproto *tp,
- } \
- else if (h != NULL) \
- { \
-- for (i = 0; h->h_addr_list[i]; i++) \
-+ /* Make sure that addrmem can be freed. */ \
-+ if (!malloc_addrmem) \
-+ addrmem = NULL; \
-+ if (!convert_hostent_to_gaih_addrtuple (req, _family,h, &addrmem)) \
- { \
-- if (*pat == NULL) \
-- { \
-- *pat = __alloca (sizeof (struct gaih_addrtuple)); \
-- (*pat)->scopeid = 0; \
-- } \
-- uint32_t *addr = (*pat)->addr; \
-- (*pat)->next = NULL; \
-- (*pat)->name = i == 0 ? strdupa (h->h_name) : NULL; \
-- if (_family == AF_INET && req->ai_family == AF_INET6) \
-- { \
-- (*pat)->family = AF_INET6; \
-- addr[3] = *(uint32_t *) h->h_addr_list[i]; \
-- addr[2] = htonl (0xffff); \
-- addr[1] = 0; \
-- addr[0] = 0; \
-- } \
-- else \
-- { \
-- (*pat)->family = _family; \
-- memcpy (addr, h->h_addr_list[i], sizeof(_type)); \
-- } \
-- pat = &((*pat)->next); \
-+ _res.options |= old_res_options & RES_USE_INET6; \
-+ result = -EAI_SYSTEM; \
-+ goto free_and_return; \
- } \
-+ *pat = addrmem; \
-+ /* The conversion uses malloc unconditionally. */ \
-+ malloc_addrmem = true; \
- \
- if (localcanon != NULL && canon == NULL) \
- canon = strdupa (localcanon); \
- \
-- if (_family == AF_INET6 && i > 0) \
-+ if (_family == AF_INET6 && *pat != NULL) \
- got_ipv6 = true; \
- } \
- }
-@@ -612,44 +648,16 @@ gaih_inet (const char *name, const struct gaih_service *service,
- {
- if (h != NULL)
- {
-- int i;
-- /* We found data, count the number of addresses. */
-- for (i = 0; h->h_addr_list[i]; ++i)
-- ;
-- if (i > 0 && *pat != NULL)
-- --i;
--
-- if (__libc_use_alloca (alloca_used
-- + i * sizeof (struct gaih_addrtuple)))
-- addrmem = alloca_account (i * sizeof (struct gaih_addrtuple),
-- alloca_used);
-- else
-- {
-- addrmem = malloc (i
-- * sizeof (struct gaih_addrtuple));
-- if (addrmem == NULL)
-- {
-- result = -EAI_MEMORY;
-- goto free_and_return;
-- }
-- malloc_addrmem = true;
-- }
--
-- /* Now convert it into the list. */
-- struct gaih_addrtuple *addrfree = addrmem;
-- for (i = 0; h->h_addr_list[i]; ++i)
-+ /* We found data, convert it. */
-+ if (!convert_hostent_to_gaih_addrtuple
-+ (req, AF_INET, h, &addrmem))
- {
-- if (*pat == NULL)
-- {
-- *pat = addrfree++;
-- (*pat)->scopeid = 0;
-- }
-- (*pat)->next = NULL;
-- (*pat)->family = AF_INET;
-- memcpy ((*pat)->addr, h->h_addr_list[i],
-- h->h_length);
-- pat = &((*pat)->next);
-+ result = -EAI_MEMORY;
-+ goto free_and_return;
- }
-+ *pat = addrmem;
-+ /* The conversion uses malloc unconditionally. */
-+ malloc_addrmem = true;
- }
- }
- else
---
-2.9.3
-
diff --git a/gnu/packages/patches/glibc-CVE-2016-4429.patch b/gnu/packages/patches/glibc-CVE-2016-4429.patch
deleted file mode 100644
index 5eebd10543..0000000000
--- a/gnu/packages/patches/glibc-CVE-2016-4429.patch
+++ /dev/null
@@ -1,58 +0,0 @@
-From bdce95930e1d9a7d013d1ba78740243491262879 Mon Sep 17 00:00:00 2001
-From: Florian Weimer <fweimer@redhat.com>
-Date: Mon, 23 May 2016 20:18:34 +0200
-Subject: [PATCH] CVE-2016-4429: sunrpc: Do not use alloca in clntudp_call [BZ
- #20112]
-
-The call is technically in a loop, and under certain circumstances
-(which are quite difficult to reproduce in a test case), alloca
-can be invoked repeatedly during a single call to clntudp_call.
-As a result, the available stack space can be exhausted (even
-though individual alloca sizes are bounded implicitly by what
-can fit into a UDP packet, as a side effect of the earlier
-successful send operation).
-
-(cherry picked from commit bc779a1a5b3035133024b21e2f339fe4219fb11c)
----
- ChangeLog | 7 +++++++
- NEWS | 4 ++++
- sunrpc/clnt_udp.c | 10 +++++++++-
- 3 files changed, 20 insertions(+), 1 deletion(-)
-
-diff --git a/sunrpc/clnt_udp.c b/sunrpc/clnt_udp.c
-index a6cf5f1..4d9acb1 100644
---- a/sunrpc/clnt_udp.c
-+++ b/sunrpc/clnt_udp.c
-@@ -388,9 +388,15 @@ send_again:
- struct sock_extended_err *e;
- struct sockaddr_in err_addr;
- struct iovec iov;
-- char *cbuf = (char *) alloca (outlen + 256);
-+ char *cbuf = malloc (outlen + 256);
- int ret;
-
-+ if (cbuf == NULL)
-+ {
-+ cu->cu_error.re_errno = errno;
-+ return (cu->cu_error.re_status = RPC_CANTRECV);
-+ }
-+
- iov.iov_base = cbuf + 256;
- iov.iov_len = outlen;
- msg.msg_name = (void *) &err_addr;
-@@ -415,10 +421,12 @@ send_again:
- cmsg = CMSG_NXTHDR (&msg, cmsg))
- if (cmsg->cmsg_level == SOL_IP && cmsg->cmsg_type == IP_RECVERR)
- {
-+ free (cbuf);
- e = (struct sock_extended_err *) CMSG_DATA(cmsg);
- cu->cu_error.re_errno = e->ee_errno;
- return (cu->cu_error.re_status = RPC_CANTRECV);
- }
-+ free (cbuf);
- }
- #endif
- do
---
-2.9.3
-
diff --git a/gnu/packages/patches/glibc-CVE-2017-1000366-pt1.patch b/gnu/packages/patches/glibc-CVE-2017-1000366-pt1.patch
deleted file mode 100644
index 71e80968be..0000000000
--- a/gnu/packages/patches/glibc-CVE-2017-1000366-pt1.patch
+++ /dev/null
@@ -1,36 +0,0 @@
-From f6110a8fee2ca36f8e2d2abecf3cba9fa7b8ea7d Mon Sep 17 00:00:00 2001
-From: Florian Weimer <fweimer@redhat.com>
-Date: Mon, 19 Jun 2017 17:09:55 +0200
-Subject: [PATCH] CVE-2017-1000366: Ignore LD_LIBRARY_PATH for AT_SECURE=1
- programs [BZ #21624]
-
-LD_LIBRARY_PATH can only be used to reorder system search paths, which
-is not useful functionality.
-
-This makes an exploitable unbounded alloca in _dl_init_paths unreachable
-for AT_SECURE=1 programs.
-
-patch from:
-https://sourceware.org/git/?p=glibc.git;a=commit;h=f6110a8fee2ca36f8e2d2abecf3cba9fa7b8ea7d
----
- ChangeLog | 7 +++++++
- elf/rtld.c | 3 ++-
- 2 files changed, 9 insertions(+), 1 deletion(-)
-
-diff --git a/elf/rtld.c b/elf/rtld.c
-index 2446a87..2269dbe 100644
---- a/elf/rtld.c
-+++ b/elf/rtld.c
-@@ -2422,7 +2422,8 @@ process_envvars (enum mode *modep)
-
- case 12:
- /* The library search path. */
-- if (memcmp (envline, "LIBRARY_PATH", 12) == 0)
-+ if (!__libc_enable_secure
-+ && memcmp (envline, "LIBRARY_PATH", 12) == 0)
- {
- library_path = &envline[13];
- break;
---
-2.9.3
-
diff --git a/gnu/packages/patches/glibc-CVE-2017-1000366-pt2.patch b/gnu/packages/patches/glibc-CVE-2017-1000366-pt2.patch
deleted file mode 100644
index 4b859c4bfd..0000000000
--- a/gnu/packages/patches/glibc-CVE-2017-1000366-pt2.patch
+++ /dev/null
@@ -1,124 +0,0 @@
-From 6d0ba622891bed9d8394eef1935add53003b12e8 Mon Sep 17 00:00:00 2001
-From: Florian Weimer <fweimer@redhat.com>
-Date: Mon, 19 Jun 2017 22:31:04 +0200
-Subject: [PATCH] ld.so: Reject overly long LD_PRELOAD path elements
-
-patch from:
-https://sourceware.org/git/?p=glibc.git;a=patch;h=6d0ba622891bed9d8394eef1935add53003b12e8
-
----
- ChangeLog | 7 ++++++
- elf/rtld.c | 82 ++++++++++++++++++++++++++++++++++++++++++++++++++------------
- 2 files changed, 73 insertions(+), 16 deletions(-)
-
-diff --git a/elf/rtld.c b/elf/rtld.c
-index 2269dbe..86ae20c 100644
---- a/elf/rtld.c
-+++ b/elf/rtld.c
-@@ -99,6 +99,35 @@ uintptr_t __pointer_chk_guard_local
- strong_alias (__pointer_chk_guard_local, __pointer_chk_guard)
- #endif
-
-+/* Length limits for names and paths, to protect the dynamic linker,
-+ particularly when __libc_enable_secure is active. */
-+#ifdef NAME_MAX
-+# define SECURE_NAME_LIMIT NAME_MAX
-+#else
-+# define SECURE_NAME_LIMIT 255
-+#endif
-+#ifdef PATH_MAX
-+# define SECURE_PATH_LIMIT PATH_MAX
-+#else
-+# define SECURE_PATH_LIMIT 1024
-+#endif
-+
-+/* Check that AT_SECURE=0, or that the passed name does not contain
-+ directories and is not overly long. Reject empty names
-+ unconditionally. */
-+static bool
-+dso_name_valid_for_suid (const char *p)
-+{
-+ if (__glibc_unlikely (__libc_enable_secure))
-+ {
-+ /* Ignore pathnames with directories for AT_SECURE=1
-+ programs, and also skip overlong names. */
-+ size_t len = strlen (p);
-+ if (len >= SECURE_NAME_LIMIT || memchr (p, '/', len) != NULL)
-+ return false;
-+ }
-+ return *p != '\0';
-+}
-
- /* List of auditing DSOs. */
- static struct audit_list
-@@ -718,6 +747,42 @@ static const char *preloadlist attribute_relro;
- /* Nonzero if information about versions has to be printed. */
- static int version_info attribute_relro;
-
-+/* The LD_PRELOAD environment variable gives list of libraries
-+ separated by white space or colons that are loaded before the
-+ executable's dependencies and prepended to the global scope list.
-+ (If the binary is running setuid all elements containing a '/' are
-+ ignored since it is insecure.) Return the number of preloads
-+ performed. */
-+unsigned int
-+handle_ld_preload (const char *preloadlist, struct link_map *main_map)
-+{
-+ unsigned int npreloads = 0;
-+ const char *p = preloadlist;
-+ char fname[SECURE_PATH_LIMIT];
-+
-+ while (*p != '\0')
-+ {
-+ /* Split preload list at space/colon. */
-+ size_t len = strcspn (p, " :");
-+ if (len > 0 && len < sizeof (fname))
-+ {
-+ memcpy (fname, p, len);
-+ fname[len] = '\0';
-+ }
-+ else
-+ fname[0] = '\0';
-+
-+ /* Skip over the substring and the following delimiter. */
-+ p += len;
-+ if (*p != '\0')
-+ ++p;
-+
-+ if (dso_name_valid_for_suid (fname))
-+ npreloads += do_preload (fname, main_map, "LD_PRELOAD");
-+ }
-+ return npreloads;
-+}
-+
- static void
- dl_main (const ElfW(Phdr) *phdr,
- ElfW(Word) phnum,
-@@ -1464,23 +1529,8 @@ ERROR: ld.so: object '%s' cannot be loaded as audit interface: %s; ignored.\n",
-
- if (__glibc_unlikely (preloadlist != NULL))
- {
-- /* The LD_PRELOAD environment variable gives list of libraries
-- separated by white space or colons that are loaded before the
-- executable's dependencies and prepended to the global scope
-- list. If the binary is running setuid all elements
-- containing a '/' are ignored since it is insecure. */
-- char *list = strdupa (preloadlist);
-- char *p;
--
- HP_TIMING_NOW (start);
--
-- /* Prevent optimizing strsep. Speed is not important here. */
-- while ((p = (strsep) (&list, " :")) != NULL)
-- if (p[0] != '\0'
-- && (__builtin_expect (! __libc_enable_secure, 1)
-- || strchr (p, '/') == NULL))
-- npreloads += do_preload (p, main_map, "LD_PRELOAD");
--
-+ npreloads += handle_ld_preload (preloadlist, main_map);
- HP_TIMING_NOW (stop);
- HP_TIMING_DIFF (diff, start, stop);
- HP_TIMING_ACCUM_NT (load_time, diff);
---
-2.9.3
-
diff --git a/gnu/packages/patches/glibc-CVE-2017-1000366-pt3.patch b/gnu/packages/patches/glibc-CVE-2017-1000366-pt3.patch
deleted file mode 100644
index 3d8f6d2bf8..0000000000
--- a/gnu/packages/patches/glibc-CVE-2017-1000366-pt3.patch
+++ /dev/null
@@ -1,206 +0,0 @@
-From 81b82fb966ffbd94353f793ad17116c6088dedd9 Mon Sep 17 00:00:00 2001
-From: Florian Weimer <fweimer@redhat.com>
-Date: Mon, 19 Jun 2017 22:32:12 +0200
-Subject: [PATCH] ld.so: Reject overly long LD_AUDIT path elements
-
-Also only process the last LD_AUDIT entry.
-
-patch from:
-https://sourceware.org/git/?p=glibc.git;a=commit;h=81b82fb966ffbd94353f793ad17116c6088dedd9
-
----
- ChangeLog | 11 +++++++
- elf/rtld.c | 110 ++++++++++++++++++++++++++++++++++++++++++++++++++++---------
- 2 files changed, 106 insertions(+), 15 deletions(-)
-
-diff --git a/elf/rtld.c b/elf/rtld.c
-index 86ae20c..65647fb 100644
---- a/elf/rtld.c
-+++ b/elf/rtld.c
-@@ -129,13 +129,91 @@ dso_name_valid_for_suid (const char *p)
- return *p != '\0';
- }
-
--/* List of auditing DSOs. */
-+/* LD_AUDIT variable contents. Must be processed before the
-+ audit_list below. */
-+const char *audit_list_string;
-+
-+/* Cyclic list of auditing DSOs. audit_list->next is the first
-+ element. */
- static struct audit_list
- {
- const char *name;
- struct audit_list *next;
- } *audit_list;
-
-+/* Iterator for audit_list_string followed by audit_list. */
-+struct audit_list_iter
-+{
-+ /* Tail of audit_list_string still needing processing, or NULL. */
-+ const char *audit_list_tail;
-+
-+ /* The list element returned in the previous iteration. NULL before
-+ the first element. */
-+ struct audit_list *previous;
-+
-+ /* Scratch buffer for returning a name which is part of
-+ audit_list_string. */
-+ char fname[SECURE_NAME_LIMIT];
-+};
-+
-+/* Initialize an audit list iterator. */
-+static void
-+audit_list_iter_init (struct audit_list_iter *iter)
-+{
-+ iter->audit_list_tail = audit_list_string;
-+ iter->previous = NULL;
-+}
-+
-+/* Iterate through both audit_list_string and audit_list. */
-+static const char *
-+audit_list_iter_next (struct audit_list_iter *iter)
-+{
-+ if (iter->audit_list_tail != NULL)
-+ {
-+ /* First iterate over audit_list_string. */
-+ while (*iter->audit_list_tail != '\0')
-+ {
-+ /* Split audit list at colon. */
-+ size_t len = strcspn (iter->audit_list_tail, ":");
-+ if (len > 0 && len < sizeof (iter->fname))
-+ {
-+ memcpy (iter->fname, iter->audit_list_tail, len);
-+ iter->fname[len] = '\0';
-+ }
-+ else
-+ /* Do not return this name to the caller. */
-+ iter->fname[0] = '\0';
-+
-+ /* Skip over the substring and the following delimiter. */
-+ iter->audit_list_tail += len;
-+ if (*iter->audit_list_tail == ':')
-+ ++iter->audit_list_tail;
-+
-+ /* If the name is valid, return it. */
-+ if (dso_name_valid_for_suid (iter->fname))
-+ return iter->fname;
-+ /* Otherwise, wrap around and try the next name. */
-+ }
-+ /* Fall through to the procesing of audit_list. */
-+ }
-+
-+ if (iter->previous == NULL)
-+ {
-+ if (audit_list == NULL)
-+ /* No pre-parsed audit list. */
-+ return NULL;
-+ /* Start of audit list. The first list element is at
-+ audit_list->next (cyclic list). */
-+ iter->previous = audit_list->next;
-+ return iter->previous->name;
-+ }
-+ if (iter->previous == audit_list)
-+ /* Cyclic list wrap-around. */
-+ return NULL;
-+ iter->previous = iter->previous->next;
-+ return iter->previous->name;
-+}
-+
- #ifndef HAVE_INLINED_SYSCALLS
- /* Set nonzero during loading and initialization of executable and
- libraries, cleared before the executable's entry point runs. This
-@@ -1305,11 +1383,13 @@ of this helper program; chances are you did not intend to run this program.\n\
- GL(dl_rtld_map).l_tls_modid = _dl_next_tls_modid ();
-
- /* If we have auditing DSOs to load, do it now. */
-- if (__glibc_unlikely (audit_list != NULL))
-+ bool need_security_init = true;
-+ if (__glibc_unlikely (audit_list != NULL)
-+ || __glibc_unlikely (audit_list_string != NULL))
- {
-- /* Iterate over all entries in the list. The order is important. */
- struct audit_ifaces *last_audit = NULL;
-- struct audit_list *al = audit_list->next;
-+ struct audit_list_iter al_iter;
-+ audit_list_iter_init (&al_iter);
-
- /* Since we start using the auditing DSOs right away we need to
- initialize the data structures now. */
-@@ -1320,9 +1400,14 @@ of this helper program; chances are you did not intend to run this program.\n\
- use different values (especially the pointer guard) and will
- fail later on. */
- security_init ();
-+ need_security_init = false;
-
-- do
-+ while (true)
- {
-+ const char *name = audit_list_iter_next (&al_iter);
-+ if (name == NULL)
-+ break;
-+
- int tls_idx = GL(dl_tls_max_dtv_idx);
-
- /* Now it is time to determine the layout of the static TLS
-@@ -1331,7 +1416,7 @@ of this helper program; chances are you did not intend to run this program.\n\
- no DF_STATIC_TLS bit is set. The reason is that we know
- glibc will use the static model. */
- struct dlmopen_args dlmargs;
-- dlmargs.fname = al->name;
-+ dlmargs.fname = name;
- dlmargs.map = NULL;
-
- const char *objname;
-@@ -1344,7 +1429,7 @@ of this helper program; chances are you did not intend to run this program.\n\
- not_loaded:
- _dl_error_printf ("\
- ERROR: ld.so: object '%s' cannot be loaded as audit interface: %s; ignored.\n",
-- al->name, err_str);
-+ name, err_str);
- if (malloced)
- free ((char *) err_str);
- }
-@@ -1448,10 +1533,7 @@ ERROR: ld.so: object '%s' cannot be loaded as audit interface: %s; ignored.\n",
- goto not_loaded;
- }
- }
--
-- al = al->next;
- }
-- while (al != audit_list->next);
-
- /* If we have any auditing modules, announce that we already
- have two objects loaded. */
-@@ -1715,7 +1797,7 @@ ERROR: ld.so: object '%s' cannot be loaded as audit interface: %s; ignored.\n",
- if (tcbp == NULL)
- tcbp = init_tls ();
-
-- if (__glibc_likely (audit_list == NULL))
-+ if (__glibc_likely (need_security_init))
- /* Initialize security features. But only if we have not done it
- earlier. */
- security_init ();
-@@ -2346,9 +2428,7 @@ process_dl_audit (char *str)
- char *p;
-
- while ((p = (strsep) (&str, ":")) != NULL)
-- if (p[0] != '\0'
-- && (__builtin_expect (! __libc_enable_secure, 1)
-- || strchr (p, '/') == NULL))
-+ if (dso_name_valid_for_suid (p))
- {
- /* This is using the local malloc, not the system malloc. The
- memory can never be freed. */
-@@ -2412,7 +2492,7 @@ process_envvars (enum mode *modep)
- break;
- }
- if (memcmp (envline, "AUDIT", 5) == 0)
-- process_dl_audit (&envline[6]);
-+ audit_list_string = &envline[6];
- break;
-
- case 7:
---
-2.9.3
-
diff --git a/gnu/packages/patches/glibc-o-largefile.patch b/gnu/packages/patches/glibc-o-largefile.patch
deleted file mode 100644
index 2b0ae8c8bb..0000000000
--- a/gnu/packages/patches/glibc-o-largefile.patch
+++ /dev/null
@@ -1,25 +0,0 @@
-This fixes <https://sourceware.org/bugzilla/show_bug.cgi?id=18781>
-whereby, on 32-bit platforms, libc 2.22 would fail to pass O_LARGEFILE
-to 'openat'. This was caught by 'tests/sparse03.at' in the tar
-test suite.
-
-commit eb32b0d40308166c4d8f6330cc2958cb1e545075
-Author: Andreas Schwab <schwab@suse.de>
-Date: Mon Aug 10 14:12:47 2015 +0200
-
- Readd O_LARGEFILE flag for openat64 (bug 18781)
-
---- a/sysdeps/unix/sysv/linux/openat.c
-+++ b/sysdeps/unix/sysv/linux/openat.c
-@@ -68,6 +68,11 @@ __OPENAT (int fd, const char *file, int oflag, ...)
- va_end (arg);
- }
-
-+ /* We have to add the O_LARGEFILE flag for openat64. */
-+#ifdef MORE_OFLAGS
-+ oflag |= MORE_OFLAGS;
-+#endif
-+
- return SYSCALL_CANCEL (openat, fd, file, oflag, mode);
- }
- libc_hidden_def (__OPENAT)
diff --git a/gnu/packages/patches/glibc-vectorized-strcspn-guards.patch b/gnu/packages/patches/glibc-vectorized-strcspn-guards.patch
deleted file mode 100644
index 3d6c7749d4..0000000000
--- a/gnu/packages/patches/glibc-vectorized-strcspn-guards.patch
+++ /dev/null
@@ -1,23 +0,0 @@
-Copied from Debian.
-
-2017-06-14 Florian Weimer <fweimer@redhat.com>
-
- * sysdeps/i386/i686/multiarch/strcspn-c.c: Add IS_IN (libc) guard.
- * sysdeps/i386/i686/multiarch/varshift.c: Likewise.
-
---- a/sysdeps/i386/i686/multiarch/strcspn-c.c
-+++ b/sysdeps/i386/i686/multiarch/strcspn-c.c
-@@ -1,2 +1,4 @@
--#define __strcspn_sse2 __strcspn_ia32
--#include <sysdeps/x86_64/multiarch/strcspn-c.c>
-+#if IS_IN (libc)
-+# define __strcspn_sse2 __strcspn_ia32
-+# include <sysdeps/x86_64/multiarch/strcspn-c.c>
-+#endif
---- a/sysdeps/i386/i686/multiarch/varshift.c
-+++ b/sysdeps/i386/i686/multiarch/varshift.c
-@@ -1 +1,3 @@
--#include <sysdeps/x86_64/multiarch/varshift.c>
-+#if IS_IN (libc)
-+# include <sysdeps/x86_64/multiarch/varshift.c>
-+#endif