From 3cabc58417cb5d69a018aec9c818fec63db18336 Mon Sep 17 00:00:00 2001 From: Armin Kuster Date: Thu, 14 Jan 2021 11:51:17 -0800 Subject: glibc: Security fix for CVE-2020-29573 Source: glibc.org MR: 107580 Type: Security Fix Disposition: Backport from https://sourceware.org/git/?p=glibc.git;a=commit;h=681900d29683722b1cb0a8e565a0585846ec5a61 ChangeID: 7bc5edb2e1947ac0774a453000a1568bbe3bb7d2 Description: Fixedup to match 2.31 context. ldbl2mpn.c is in i386 for this version Signed-off-by: Armin Kuster Signed-off-by: Steve Sakoman --- meta/recipes-core/glibc/glibc/CVE-2020-29573.patch | 128 +++++++++++++++++++++ meta/recipes-core/glibc/glibc_2.31.bb | 1 + 2 files changed, 129 insertions(+) create mode 100644 meta/recipes-core/glibc/glibc/CVE-2020-29573.patch diff --git a/meta/recipes-core/glibc/glibc/CVE-2020-29573.patch b/meta/recipes-core/glibc/glibc/CVE-2020-29573.patch new file mode 100644 index 0000000000..1e75f2d29d --- /dev/null +++ b/meta/recipes-core/glibc/glibc/CVE-2020-29573.patch @@ -0,0 +1,128 @@ +From 681900d29683722b1cb0a8e565a0585846ec5a61 Mon Sep 17 00:00:00 2001 +From: Florian Weimer +Date: Tue, 22 Sep 2020 19:07:48 +0200 +Subject: [PATCH] x86: Harden printf against non-normal long double values (bug + 26649) + +The behavior of isnan/__builtin_isnan on bit patterns that do not +correspond to something that the CPU would produce from valid inputs +is currently under-defined in the toolchain. (The GCC built-in and +glibc disagree.) + +The isnan check in PRINTF_FP_FETCH in stdio-common/printf_fp.c +assumes the GCC behavior that returns true for non-normal numbers +which are not specified as NaN. (The glibc implementation returns +false for such numbers.) + +At present, passing non-normal numbers to __mpn_extract_long_double +causes this function to produce irregularly shaped multi-precision +integers, triggering undefined behavior in __printf_fp_l. + +With GCC 10 and glibc 2.32, this behavior is not visible because +__builtin_isnan is used, which avoids calling +__mpn_extract_long_double in this case. This commit updates the +implementation of __mpn_extract_long_double so that regularly shaped +multi-precision integers are produced in this case, avoiding +undefined behavior in __printf_fp_l. + +Upstream-Status: Backport [git://sourceware.org/git/glibc.git] +CVE: CVE-2020-29573 +Signed-off-By: Armin Kuster + +--- + sysdeps/x86/Makefile | 4 ++ + sysdeps/x86/ldbl2mpn.c | 8 ++++ + sysdeps/x86/tst-ldbl-nonnormal-printf.c | 52 +++++++++++++++++++++++++ + 3 files changed, 64 insertions(+) + create mode 100644 sysdeps/x86/tst-ldbl-nonnormal-printf.c + +Index: git/sysdeps/x86/Makefile +=================================================================== +--- git.orig/sysdeps/x86/Makefile ++++ git/sysdeps/x86/Makefile +@@ -9,6 +9,10 @@ tests += tst-get-cpu-features tst-get-cp + tests-static += tst-get-cpu-features-static + endif + ++ifeq ($(subdir),math) ++tests += tst-ldbl-nonnormal-printf ++endif # $(subdir) == math ++ + ifeq ($(subdir),setjmp) + gen-as-const-headers += jmp_buf-ssp.sym + sysdep_routines += __longjmp_cancel +Index: git/sysdeps/x86/tst-ldbl-nonnormal-printf.c +=================================================================== +--- /dev/null ++++ git/sysdeps/x86/tst-ldbl-nonnormal-printf.c +@@ -0,0 +1,52 @@ ++/* Test printf with x86-specific non-normal long double value. ++ Copyright (C) 2020 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 ++ . */ ++ ++#include ++#include ++#include ++ ++/* Fill the stack with non-zero values. This makes a crash in ++ snprintf more likely. */ ++static void __attribute__ ((noinline, noclone)) ++fill_stack (void) ++{ ++ char buffer[65536]; ++ memset (buffer, 0xc0, sizeof (buffer)); ++ asm ("" ::: "memory"); ++} ++ ++static int ++do_test (void) ++{ ++ fill_stack (); ++ ++ long double value; ++ memcpy (&value, "\x00\x04\x00\x00\x00\x00\x00\x00\x00\x04", 10); ++ ++ char buf[30]; ++ int ret = snprintf (buf, sizeof (buf), "%Lg", value); ++ TEST_COMPARE (ret, strlen (buf)); ++ if (strcmp (buf, "nan") != 0) ++ /* If snprintf does not recognize the non-normal number as a NaN, ++ it has added the missing explicit MSB. */ ++ TEST_COMPARE_STRING (buf, "3.02201e-4624"); ++ return 0; ++} ++ ++#include +Index: git/sysdeps/i386/ldbl2mpn.c +=================================================================== +--- git.orig/sysdeps/i386/ldbl2mpn.c ++++ git/sysdeps/i386/ldbl2mpn.c +@@ -115,6 +115,12 @@ __mpn_extract_long_double (mp_ptr res_pt + && res_ptr[N - 1] == 0) + /* Pseudo zero. */ + *expt = 0; +- ++ else ++ /* The sign bit is explicit, but add it in case it is missing in ++ the input. Otherwise, callers will not be able to produce the ++ expected multi-precision integer layout by shifting the sign ++ bit into the MSB. */ ++ res_ptr[N - 1] |= (mp_limb_t) 1 << (LDBL_MANT_DIG - 1 ++ - ((N - 1) * BITS_PER_MP_LIMB)); + return N; + } diff --git a/meta/recipes-core/glibc/glibc_2.31.bb b/meta/recipes-core/glibc/glibc_2.31.bb index 3a0d60abf8..067d4de64a 100644 --- a/meta/recipes-core/glibc/glibc_2.31.bb +++ b/meta/recipes-core/glibc/glibc_2.31.bb @@ -42,6 +42,7 @@ SRC_URI = "${GLIBC_GIT_URI};branch=${SRCBRANCH};name=glibc \ file://0028-inject-file-assembly-directives.patch \ file://0029-locale-prevent-maybe-uninitialized-errors-with-Os-BZ.patch \ file://CVE-2020-29562.patch \ + file://CVE-2020-29573.patch \ " S = "${WORKDIR}/git" B = "${WORKDIR}/build-${TARGET_SYS}" -- cgit 1.2.3-korg