GNU bug report logs - #46856
[PATCH] gnu: Python 2: Fix CVE-2021-3177.

Previous Next

Package: guix-patches;

Reported by: Leo Famulari <leo <at> famulari.name>

Date: Mon, 1 Mar 2021 19:59:02 UTC

Severity: normal

Tags: patch

Done: Leo Famulari <leo <at> famulari.name>

Bug is archived. No further changes may be made.

To add a comment to this bug, you must first unarchive it, by sending
a message to control AT debbugs.gnu.org, with unarchive 46856 in the body.
You can then email your comments to 46856 AT debbugs.gnu.org in the normal way.

Toggle the display of automated, internal messages from the tracker.

View this report as an mbox folder, status mbox, maintainer mbox


Report forwarded to guix-patches <at> gnu.org:
bug#46856; Package guix-patches. (Mon, 01 Mar 2021 19:59:02 GMT) Full text and rfc822 format available.

Acknowledgement sent to Leo Famulari <leo <at> famulari.name>:
New bug report received and forwarded. Copy sent to guix-patches <at> gnu.org. (Mon, 01 Mar 2021 19:59:02 GMT) Full text and rfc822 format available.

Message #5 received at submit <at> debbugs.gnu.org (full text, mbox):

From: Leo Famulari <leo <at> famulari.name>
To: guix-patches <at> gnu.org
Subject: [PATCH] gnu: Python 2: Fix CVE-2021-3177.
Date: Mon,  1 Mar 2021 14:58:22 -0500
* gnu/packages/patches/python-2.7-CVE-2021-3177.patch: New file.
* gnu/local.mk (dist_patch_DATA): Add it.
* gnu/packages/python.scm (python-2.7)[replacement]: New field.
(python-2.7/fixed): New variable.
---
 gnu/local.mk                                  |   1 +
 .../patches/python-2.7-CVE-2021-3177.patch    | 157 ++++++++++++++++++
 gnu/packages/python.scm                       |   9 +
 3 files changed, 167 insertions(+)
 create mode 100644 gnu/packages/patches/python-2.7-CVE-2021-3177.patch

diff --git a/gnu/local.mk b/gnu/local.mk
index 0954158d4c..0f8fb20e83 100644
--- a/gnu/local.mk
+++ b/gnu/local.mk
@@ -1518,6 +1518,7 @@ dist_patch_DATA =						\
   %D%/packages/patches/python-2.7-search-paths.patch		\
   %D%/packages/patches/python-2.7-site-prefixes.patch		\
   %D%/packages/patches/python-2.7-source-date-epoch.patch	\
+  %D%/packages/patches/python-2.7-CVE-2021-3177.patch		\
   %D%/packages/patches/python-3-arm-alignment.patch		\
   %D%/packages/patches/python-3-deterministic-build-info.patch	\
   %D%/packages/patches/python-3-search-paths.patch		\
diff --git a/gnu/packages/patches/python-2.7-CVE-2021-3177.patch b/gnu/packages/patches/python-2.7-CVE-2021-3177.patch
new file mode 100644
index 0000000000..9f2032ad4a
--- /dev/null
+++ b/gnu/packages/patches/python-2.7-CVE-2021-3177.patch
@@ -0,0 +1,157 @@
+Fix CVE-2021-3177 for Python 2.7:
+
+https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2021-3177
+
+Patch copied from Debian:
+
+https://salsa.debian.org/cpython-team/python2/-/blob/e54f3303884f1362f3311ec36f070b40603dd76e/debian/patches/CVE-2021-3177.diff
+
+bpo-42938: Replace snprintf with Python unicode formatting in ctypes param reprs.
+--- a/Lib/ctypes/test/test_parameters.py
++++ b/Lib/ctypes/test/test_parameters.py
+@@ -206,6 +206,49 @@ class SimpleTypesTestCase(unittest.TestC
+         with self.assertRaises(ZeroDivisionError):
+             WorseStruct().__setstate__({}, b'foo')
+ 
++    def test_parameter_repr(self):
++        from ctypes import (
++            c_bool,
++            c_char,
++            c_wchar,
++            c_byte,
++            c_ubyte,
++            c_short,
++            c_ushort,
++            c_int,
++            c_uint,
++            c_long,
++            c_ulong,
++            c_longlong,
++            c_ulonglong,
++            c_float,
++            c_double,
++            c_longdouble,
++            c_char_p,
++            c_wchar_p,
++            c_void_p,
++        )
++        self.assertRegexpMatches(repr(c_bool.from_param(True)), r"^<cparam '\?' at 0x[A-Fa-f0-9]+>$")
++        self.assertEqual(repr(c_char.from_param('a')), "<cparam 'c' (a)>")
++        self.assertRegexpMatches(repr(c_wchar.from_param('a')), r"^<cparam 'u' at 0x[A-Fa-f0-9]+>$")
++        self.assertEqual(repr(c_byte.from_param(98)), "<cparam 'b' (98)>")
++        self.assertEqual(repr(c_ubyte.from_param(98)), "<cparam 'B' (98)>")
++        self.assertEqual(repr(c_short.from_param(511)), "<cparam 'h' (511)>")
++        self.assertEqual(repr(c_ushort.from_param(511)), "<cparam 'H' (511)>")
++        self.assertRegexpMatches(repr(c_int.from_param(20000)), r"^<cparam '[li]' \(20000\)>$")
++        self.assertRegexpMatches(repr(c_uint.from_param(20000)), r"^<cparam '[LI]' \(20000\)>$")
++        self.assertRegexpMatches(repr(c_long.from_param(20000)), r"^<cparam '[li]' \(20000\)>$")
++        self.assertRegexpMatches(repr(c_ulong.from_param(20000)), r"^<cparam '[LI]' \(20000\)>$")
++        self.assertRegexpMatches(repr(c_longlong.from_param(20000)), r"^<cparam '[liq]' \(20000\)>$")
++        self.assertRegexpMatches(repr(c_ulonglong.from_param(20000)), r"^<cparam '[LIQ]' \(20000\)>$")
++        self.assertEqual(repr(c_float.from_param(1.5)), "<cparam 'f' (1.5)>")
++        self.assertEqual(repr(c_double.from_param(1.5)), "<cparam 'd' (1.5)>")
++        self.assertEqual(repr(c_double.from_param(1e300)), "<cparam 'd' (1e+300)>")
++        self.assertRegexpMatches(repr(c_longdouble.from_param(1.5)), r"^<cparam ('d' \(1.5\)|'g' at 0x[A-Fa-f0-9]+)>$")
++        self.assertRegexpMatches(repr(c_char_p.from_param(b'hihi')), "^<cparam 'z' \(0x[A-Fa-f0-9]+\)>$")
++        self.assertRegexpMatches(repr(c_wchar_p.from_param('hihi')), "^<cparam 'Z' \(0x[A-Fa-f0-9]+\)>$")
++        self.assertRegexpMatches(repr(c_void_p.from_param(0x12)), r"^<cparam 'P' \(0x0*12\)>$")
++
+ ################################################################
+ 
+ if __name__ == '__main__':
+--- a/Modules/_ctypes/callproc.c
++++ b/Modules/_ctypes/callproc.c
+@@ -460,50 +460,53 @@ PyCArg_dealloc(PyCArgObject *self)
+ static PyObject *
+ PyCArg_repr(PyCArgObject *self)
+ {
+-    char buffer[256];
+     switch(self->tag) {
+     case 'b':
+     case 'B':
+-        sprintf(buffer, "<cparam '%c' (%d)>",
++        return PyString_FromFormat("<cparam '%c' (%d)>",
+             self->tag, self->value.b);
+-        break;
+     case 'h':
+     case 'H':
+-        sprintf(buffer, "<cparam '%c' (%d)>",
++        return PyString_FromFormat("<cparam '%c' (%d)>",
+             self->tag, self->value.h);
+-        break;
+     case 'i':
+     case 'I':
+-        sprintf(buffer, "<cparam '%c' (%d)>",
++        return PyString_FromFormat("<cparam '%c' (%d)>",
+             self->tag, self->value.i);
+-        break;
+     case 'l':
+     case 'L':
+-        sprintf(buffer, "<cparam '%c' (%ld)>",
++        return PyString_FromFormat("<cparam '%c' (%ld)>",
+             self->tag, self->value.l);
+-        break;
+ 
+ #ifdef HAVE_LONG_LONG
+     case 'q':
+     case 'Q':
+-        sprintf(buffer,
+-            "<cparam '%c' (%" PY_FORMAT_LONG_LONG "d)>",
++        return PyString_FromFormat("<cparam '%c' (%" PY_FORMAT_LONG_LONG "d)>",
+             self->tag, self->value.q);
+-        break;
+ #endif
+     case 'd':
+-        sprintf(buffer, "<cparam '%c' (%f)>",
+-            self->tag, self->value.d);
+-        break;
+-    case 'f':
+-        sprintf(buffer, "<cparam '%c' (%f)>",
+-            self->tag, self->value.f);
+-        break;
++    case 'f': {
++        PyObject *f = PyFloat_FromDouble((self->tag == 'f') ? self->value.f : self->value.d);
++        if (f == NULL) {
++            return NULL;
++        }
++        PyObject *r = PyObject_Repr(f);
++        Py_DECREF(f);
++        if (r == NULL) {
++            return NULL;
++        }
++        char *value = PyString_AsString(r);
++        if (value == NULL) {
++            return NULL;
++        }
++        PyObject *result = PyString_FromFormat("<cparam '%c' (%s)>", self->tag, value);
++        Py_DECREF(r);
++        return result;
++    }
+ 
+     case 'c':
+-        sprintf(buffer, "<cparam '%c' (%c)>",
++        return PyString_FromFormat("<cparam '%c' (%c)>",
+             self->tag, self->value.c);
+-        break;
+ 
+ /* Hm, are these 'z' and 'Z' codes useful at all?
+    Shouldn't they be replaced by the functionality of c_string
+@@ -512,16 +515,13 @@ PyCArg_repr(PyCArgObject *self)
+     case 'z':
+     case 'Z':
+     case 'P':
+-        sprintf(buffer, "<cparam '%c' (%p)>",
++        return PyString_FromFormat("<cparam '%c' (%p)>",
+             self->tag, self->value.p);
+-        break;
+ 
+     default:
+-        sprintf(buffer, "<cparam '%c' at %p>",
++        return PyString_FromFormat("<cparam '%c' at %p>",
+             self->tag, self);
+-        break;
+     }
+-    return PyString_FromString(buffer);
+ }
+ 
+ static PyMemberDef PyCArgType_members[] = {
diff --git a/gnu/packages/python.scm b/gnu/packages/python.scm
index 9d97050c66..e05c91b3d0 100644
--- a/gnu/packages/python.scm
+++ b/gnu/packages/python.scm
@@ -107,6 +107,7 @@
 (define-public python-2.7
   (package
     (name "python2")
+    (replacement python-2.7/fixed)
     (version "2.7.17")
     (source
      (origin
@@ -350,6 +351,14 @@ data types.")
     (properties '((cpe-name . "python")))
     (license license:psfl)))
 
+(define python-2.7/fixed
+  (package
+    (inherit python-2.7)
+    (source (origin
+              (inherit (package-source python-2.7))
+              (patches (append (search-patches "python-2.7-CVE-2021-3177.patch")
+                               (origin-patches (package-source python-2.7))))))))
+
 ;; Current 2.x version.
 (define-public python-2 python-2.7)
 
-- 
2.30.1





Reply sent to Leo Famulari <leo <at> famulari.name>:
You have taken responsibility. (Tue, 02 Mar 2021 21:59:02 GMT) Full text and rfc822 format available.

Notification sent to Leo Famulari <leo <at> famulari.name>:
bug acknowledged by developer. (Tue, 02 Mar 2021 21:59:02 GMT) Full text and rfc822 format available.

Message #10 received at 46856-done <at> debbugs.gnu.org (full text, mbox):

From: Leo Famulari <leo <at> famulari.name>
To: 46856-done <at> debbugs.gnu.org
Subject: Re: [PATCH] gnu: Python 2: Fix CVE-2021-3177.
Date: Tue, 2 Mar 2021 16:58:00 -0500
Pushed as 3905580180d8f8ed1eec07baa307b4bff0d726d6




bug archived. Request was from Debbugs Internal Request <help-debbugs <at> gnu.org> to internal_control <at> debbugs.gnu.org. (Wed, 31 Mar 2021 11:24:05 GMT) Full text and rfc822 format available.

This bug report was last modified 3 years and 27 days ago.

Previous Next


GNU bug tracking system
Copyright (C) 1999 Darren O. Benham, 1997,2003 nCipher Corporation Ltd, 1994-97 Ian Jackson.