public inbox for ipfire-scm@lists.ipfire.org
 help / color / mirror / Atom feed
* [git.ipfire.org] IPFire 2.x development tree branch, next, updated. 04f8766c8d53a68c0781fcae56be6007c75ed6f3
@ 2026-03-24 15:23 Michael Tremer
  0 siblings, 0 replies; only message in thread
From: Michael Tremer @ 2026-03-24 15:23 UTC (permalink / raw)
  To: ipfire-scm

This is an automated email from the git hooks/post-receive script. It was
generated because a ref change was pushed to the repository containing
the project "IPFire 2.x development tree".

The branch, next has been updated
       via  04f8766c8d53a68c0781fcae56be6007c75ed6f3 (commit)
       via  f77bfaf94594856932fb649b467cb0a04b93e418 (commit)
      from  a85c4ef9e04d5c5c2c6305c09c75a5fe41efba8f (commit)

Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.

- Log -----------------------------------------------------------------
commit 04f8766c8d53a68c0781fcae56be6007c75ed6f3
Author: Michael Tremer <michael.tremer@ipfire.org>
Date:   Tue Mar 24 15:22:55 2026 +0000

    core202: Ship glibc
    
    Signed-off-by: Michael Tremer <michael.tremer@ipfire.org>

commit f77bfaf94594856932fb649b467cb0a04b93e418
Author: Michael Tremer <michael.tremer@ipfire.org>
Date:   Tue Mar 24 15:19:06 2026 +0000

    glibc: Apply fix for GLIBC-SA-2026-0005
    
    gethostbyaddr and gethostbyaddr_r may incorrectly handle DNS response
    
    Calling gethostbyaddr or gethostbyaddr_r with a configured nsswitch.conf
    that specifies the library's DNS backend in the GNU C Library version
    2.34 to version 2.43 could, with a crafted response from the configured
    DNS server, result in a violation of the DNS specification that causes
    the application to treat a non-answer section of the DNS response as a
    valid answer.
    
    A defect in the getanswer_ptr function, which implements the iteration
    and extraction of the answer from the DNS response, can cause it to
    incorrectly transition from the answer section to the next section while
    still treating it as an answer to the question.  This can happen when
    the answer contains only skipped records, and the subsequent section
    contains a semantically invalid T_PTR record.  This is considered a
    security issue because it is a violation of the DNS specification that
    leads to incorrect behaviour that could result in the wrong hostname
    being returned to the caller.  At the time of publication, no known
    affected DNS server returns results that would be incorrectly
    interpreted by the library.  An attacker would either need to be network
    adjacent or have compromised the DNS server to use this defect to hide
    returned reverse DNS results from intrusion detection systems. Even
    then, the inbound connection from the attacker, or the outbound
    connection from the application, would be visible to the intrusion
    detection system.  At best, the defect can be used to obfuscate and
    delay analysis of the evolving threat.
    
    CVE-Id: CVE-2026-4437
    Public-Date: 2026-03-20
    Vulnerable-Commit: 32e5db37684ffcbc6ae34fcc6cdcf28670506baa (2.34-323)
    Vulnerable-Commit: def97e7f71a07517810f7263213d607e08ad21f1 (2.35-188)
    Vulnerable-Commit: 77f523c473878ec0051582ef15161c6982879095 (2.36-30)
    Vulnerable-Commit: e32547d661a43da63368e488b6cfa9c53b4dcf92 (2.37)
    Reported-by: Antonio Maini (0rbitingZer0) - 0rbitingZer0@proton.me
    Reported-by: Kevin Farrell
    
    Signed-off-by: Michael Tremer <michael.tremer@ipfire.org>

-----------------------------------------------------------------------

Summary of changes:
 .../125 => core/202}/filelists/aarch64/glibc       |   0
 .../180 => core/202}/filelists/riscv64/glibc       |   0
 .../100 => core/202}/filelists/x86_64/glibc        |   0
 config/rootfiles/core/202/update.sh                |   2 +-
 lfs/glibc                                          |   1 +
 src/patches/glibc-2.43-SA-2026-0005.patch          | 242 +++++++++++++++++++++
 6 files changed, 244 insertions(+), 1 deletion(-)
 copy config/rootfiles/{oldcore/125 => core/202}/filelists/aarch64/glibc (100%)
 copy config/rootfiles/{oldcore/180 => core/202}/filelists/riscv64/glibc (100%)
 copy config/rootfiles/{oldcore/100 => core/202}/filelists/x86_64/glibc (100%)
 create mode 100644 src/patches/glibc-2.43-SA-2026-0005.patch

Difference in files:
diff --git a/config/rootfiles/core/202/filelists/aarch64/glibc b/config/rootfiles/core/202/filelists/aarch64/glibc
new file mode 120000
index 000000000..d13849ff9
--- /dev/null
+++ b/config/rootfiles/core/202/filelists/aarch64/glibc
@@ -0,0 +1 @@
+../../../../common/aarch64/glibc
\ No newline at end of file
diff --git a/config/rootfiles/core/202/filelists/riscv64/glibc b/config/rootfiles/core/202/filelists/riscv64/glibc
new file mode 120000
index 000000000..36b731f7d
--- /dev/null
+++ b/config/rootfiles/core/202/filelists/riscv64/glibc
@@ -0,0 +1 @@
+../../../../common/riscv64/glibc
\ No newline at end of file
diff --git a/config/rootfiles/core/202/filelists/x86_64/glibc b/config/rootfiles/core/202/filelists/x86_64/glibc
new file mode 120000
index 000000000..111909966
--- /dev/null
+++ b/config/rootfiles/core/202/filelists/x86_64/glibc
@@ -0,0 +1 @@
+../../../../common/x86_64/glibc
\ No newline at end of file
diff --git a/config/rootfiles/core/202/update.sh b/config/rootfiles/core/202/update.sh
index 9287d0918..51eb36a58 100644
--- a/config/rootfiles/core/202/update.sh
+++ b/config/rootfiles/core/202/update.sh
@@ -63,7 +63,7 @@ extract_files
 ldconfig
 
 # Restart init
-#telinit u
+telinit u
 
 # Move variables files to the new unbound user
 chown unbound:unbound -Rv /var/lib/unbound/ /var/cache/unbound/
diff --git a/lfs/glibc b/lfs/glibc
index 3dd1cefa2..61137c38c 100644
--- a/lfs/glibc
+++ b/lfs/glibc
@@ -119,6 +119,7 @@ $(TARGET) : $(patsubst %,$(DIR_DL)/%,$(objects))
 	@rm -rf $(DIR_APP) $(DIR_SRC)/glibc-build && cd $(DIR_SRC) && tar axf $(DIR_DL)/$(DL_FILE)
 	@mkdir $(DIR_SRC)/glibc-build
 
+	cd $(DIR_APP) && patch -Np1 < $(DIR_SRC)/src/patches/glibc-2.43-SA-2026-0005.patch
 	cd $(DIR_APP) && patch -Np1 < $(DIR_SRC)/src/patches/glibc-localedef-no-archive.patch
 
 ifneq "$(TOOLCHAIN)" "1"
diff --git a/src/patches/glibc-2.43-SA-2026-0005.patch b/src/patches/glibc-2.43-SA-2026-0005.patch
new file mode 100644
index 000000000..c545a9dda
--- /dev/null
+++ b/src/patches/glibc-2.43-SA-2026-0005.patch
@@ -0,0 +1,242 @@
+From 5c6fca0c62ce5bd6e68e259f138097756cbafd4d Mon Sep 17 00:00:00 2001
+From: Carlos O'Donell <carlos@redhat.com>
+Date: Fri, 20 Mar 2026 16:43:33 -0400
+Subject: [PATCH] resolv: Count records correctly (CVE-2026-4437)
+
+The answer section boundary was previously ignored, and the code in
+getanswer_ptr would iterate past the last resource record, but not
+beyond the end of the returned data.  This could lead to subsequent data
+being interpreted as answer records, thus violating the DNS
+specification.  Such resource records could be maliciously crafted and
+hidden from other tooling, but processed by the glibc stub resolver and
+acted upon by the application.  While we trust the data returned by the
+configured recursive resolvers, we should not trust its format and
+should validate it as required.  It is a security issue to incorrectly
+process the DNS protocol.
+
+A regression test is added for response section crossing.
+
+No regressions on x86_64-linux-gnu.
+
+Reviewed-by: Collin Funk <collin.funk1@gmail.com>
+(cherry picked from commit 9f5f18aab40ec6b61fa49a007615e6077e9a979b)
+---
+ resolv/Makefile                 |   4 +
+ resolv/nss_dns/dns-host.c       |   2 +-
+ resolv/tst-resolv-dns-section.c | 162 ++++++++++++++++++++++++++++++++
+ 3 files changed, 167 insertions(+), 1 deletion(-)
+ create mode 100644 resolv/tst-resolv-dns-section.c
+
+diff --git a/resolv/Makefile b/resolv/Makefile
+index b74c8f325e..d5ef63cdbc 100644
+--- a/resolv/Makefile
++++ b/resolv/Makefile
+@@ -107,6 +107,7 @@ tests += \
+   tst-resolv-basic \
+   tst-resolv-binary \
+   tst-resolv-byaddr \
++  tst-resolv-dns-section \
+   tst-resolv-edns \
+   tst-resolv-invalid-cname \
+   tst-resolv-network \
+@@ -118,6 +119,7 @@ tests += \
+   tst-resolv-semi-failure \
+   tst-resolv-short-response \
+   tst-resolv-trailing \
++  # tests
+ 
+ # This test calls __res_context_send directly, which is not exported
+ # from libresolv.
+@@ -301,6 +303,8 @@ $(objpfx)tst-resolv-aliases: $(objpfx)libresolv.so $(shared-thread-library)
+ $(objpfx)tst-resolv-basic: $(objpfx)libresolv.so $(shared-thread-library)
+ $(objpfx)tst-resolv-binary: $(objpfx)libresolv.so $(shared-thread-library)
+ $(objpfx)tst-resolv-byaddr: $(objpfx)libresolv.so $(shared-thread-library)
++$(objpfx)tst-resolv-dns-section: $(objpfx)libresolv.so \
++  $(shared-thread-library)
+ $(objpfx)tst-resolv-edns: $(objpfx)libresolv.so $(shared-thread-library)
+ $(objpfx)tst-resolv-network: $(objpfx)libresolv.so $(shared-thread-library)
+ $(objpfx)tst-resolv-res_init: $(objpfx)libresolv.so
+diff --git a/resolv/nss_dns/dns-host.c b/resolv/nss_dns/dns-host.c
+index 6a60c87532..893137027e 100644
+--- a/resolv/nss_dns/dns-host.c
++++ b/resolv/nss_dns/dns-host.c
+@@ -820,7 +820,7 @@ getanswer_ptr (unsigned char *packet, size_t packetlen,
+   /* expected_name may be updated to point into this buffer.  */
+   unsigned char name_buffer[NS_MAXCDNAME];
+ 
+-  while (ancount > 0)
++  for (; ancount > 0; --ancount)
+     {
+       struct ns_rr_wire rr;
+       if (!__ns_rr_cursor_next (&c, &rr))
+diff --git a/resolv/tst-resolv-dns-section.c b/resolv/tst-resolv-dns-section.c
+new file mode 100644
+index 0000000000..1171baef51
+--- /dev/null
++++ b/resolv/tst-resolv-dns-section.c
+@@ -0,0 +1,162 @@
++/* Test handling of invalid section transitions (bug 34014).
++   Copyright (C) 2022-2026 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
++   <https://www.gnu.org/licenses/>.  */
++
++#include <array_length.h>
++#include <errno.h>
++#include <netdb.h>
++#include <resolv.h>
++#include <stdlib.h>
++#include <string.h>
++#include <support/check.h>
++#include <support/format_nss.h>
++#include <support/resolv_test.h>
++#include <support/support.h>
++
++/* Name of test, and the second section type.  */
++struct item {
++  const char *test;
++  int ns_section;
++};
++
++static const struct item test_items[] =
++  {
++    { "Test crossing from ns_s_an to ns_s_ar.", ns_s_ar },
++    { "Test crossing from ns_s_an to ns_s_an.", ns_s_ns },
++
++    { NULL, 0 },
++  };
++
++/* The response is designed to contain the following:
++   - An Answer section with one T_PTR record that is skipped.
++   - A second section with a semantically invalid T_PTR record.
++   The original defect is that the response parsing would cross
++   section boundaries and handle the additional section T_PTR
++   as if it were an answer.  A conforming implementation would
++   stop as soon as it reaches the end of the section.  */
++static void
++response (const struct resolv_response_context *ctx,
++          struct resolv_response_builder *b,
++          const char *qname, uint16_t qclass, uint16_t qtype)
++{
++  TEST_COMPARE (qclass, C_IN);
++
++  /* We only test PTR.  */
++  TEST_COMPARE (qtype, T_PTR);
++
++  unsigned int count;
++  char *tail = NULL;
++
++  if (strstr (qname, "in-addr.arpa") != NULL
++      && sscanf (qname, "%u.%ms", &count, &tail) == 2)
++    TEST_COMPARE_STRING (tail, "0.168.192.in-addr.arpa");
++  else if (sscanf (qname, "%x.%ms", &count, &tail) == 2)
++    {
++    TEST_COMPARE_STRING (tail, "\
++0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.8.b.d.0.1.0.0.2.ip6.arpa");
++    }
++  else
++    FAIL_EXIT1 ("invalid QNAME: %s\n", qname);
++  free (tail);
++
++  /* We have a bounded number of possible tests.  */
++  TEST_VERIFY (count >= 0);
++  TEST_VERIFY (count <= 15);
++
++  struct resolv_response_flags flags = {};
++  resolv_response_init (b, flags);
++  resolv_response_add_question (b, qname, qclass, qtype);
++  resolv_response_section (b, ns_s_an);
++
++  /* Actual answer record, but the wrong name (skipped).  */
++  resolv_response_open_record (b, "1.0.0.10.in-addr.arpa", qclass, qtype, 60);
++
++  /* Record the answer.  */
++  resolv_response_add_name (b, "test.ptr.example.net");
++  resolv_response_close_record (b);
++
++  /* Add a second section to test section boundary crossing.  */
++  resolv_response_section (b, test_items[count].ns_section);
++  /* Semantically incorrect, but hide a T_PTR entry.  */
++  resolv_response_open_record (b, qname, qclass, qtype, 60);
++  resolv_response_add_name (b, "wrong.ptr.example.net");
++  resolv_response_close_record (b);
++}
++
++
++/* Perform one check using a reverse lookup.  */
++static void
++check_reverse (int af, int count)
++{
++  TEST_VERIFY (af == AF_INET || af == AF_INET6);
++  TEST_VERIFY (count < array_length (test_items));
++
++  char addr[sizeof (struct in6_addr)] = { 0 };
++  socklen_t addrlen;
++  if (af == AF_INET)
++    {
++      addr[0] = (char) 192;
++      addr[1] = (char) 168;
++      addr[2] = (char) 0;
++      addr[3] = (char) count;
++      addrlen = 4;
++    }
++  else
++    {
++      addr[0] = 0x20;
++      addr[1] = 0x01;
++      addr[2] = 0x0d;
++      addr[3] = 0xb8;
++      addr[4] = addr[5] = addr[6] = addr[7] = 0x0;
++      addr[8] = addr[9] = addr[10] = addr[11] = 0x0;
++      addr[12] = 0x0;
++      addr[13] = 0x0;
++      addr[14] = 0x0;
++      addr[15] = count;
++      addrlen = 16;
++    }
++
++  h_errno = 0;
++  struct hostent *answer = gethostbyaddr (addr, addrlen, af);
++  TEST_VERIFY (answer == NULL);
++  TEST_VERIFY (h_errno == NO_RECOVERY);
++  if (answer != NULL)
++    printf ("error: unexpected success: %s\n",
++	    support_format_hostent (answer));
++}
++
++static int
++do_test (void)
++{
++  struct resolv_test *obj = resolv_test_start
++    ((struct resolv_redirect_config)
++     {
++       .response_callback = response
++     });
++
++  for (int i = 0; test_items[i].test != NULL; i++)
++    {
++      check_reverse (AF_INET, i);
++      check_reverse (AF_INET6, i);
++    }
++
++  resolv_test_end (obj);
++
++  return 0;
++}
++
++#include <support/test-driver.c>
+-- 
+2.43.7
+


hooks/post-receive
--
IPFire 2.x development tree


^ permalink raw reply	[flat|nested] only message in thread

only message in thread, other threads:[~2026-03-24 15:23 UTC | newest]

Thread overview: (only message) (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2026-03-24 15:23 [git.ipfire.org] IPFire 2.x development tree branch, next, updated. 04f8766c8d53a68c0781fcae56be6007c75ed6f3 Michael Tremer

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox