From 706c863253ecc04684ad7e07064a50ff41a5959e Mon Sep 17 00:00:00 2001 From: CentOS Sources Date: Jul 08 2019 13:50:29 +0000 Subject: import python27-python-2.7.16-6.el7 --- diff --git a/SOURCES/00320-CVE-2019-9636-and-CVE-2019-10160.patch b/SOURCES/00320-CVE-2019-9636-and-CVE-2019-10160.patch new file mode 100644 index 0000000..670f3e4 --- /dev/null +++ b/SOURCES/00320-CVE-2019-9636-and-CVE-2019-10160.patch @@ -0,0 +1,152 @@ +diff --git a/Doc/library/urlparse.rst b/Doc/library/urlparse.rst +index 22249da..0989c88 100644 +--- a/Doc/library/urlparse.rst ++++ b/Doc/library/urlparse.rst +@@ -119,12 +119,22 @@ The :mod:`urlparse` module defines the following functions: + See section :ref:`urlparse-result-object` for more information on the result + object. + ++ Characters in the :attr:`netloc` attribute that decompose under NFKC ++ normalization (as used by the IDNA encoding) into any of ``/``, ``?``, ++ ``#``, ``@``, or ``:`` will raise a :exc:`ValueError`. If the URL is ++ decomposed before parsing, or is not a Unicode string, no error will be ++ raised. ++ + .. versionchanged:: 2.5 + Added attributes to return value. + + .. versionchanged:: 2.7 + Added IPv6 URL parsing capabilities. + ++ .. versionchanged:: 2.7.17 ++ Characters that affect netloc parsing under NFKC normalization will ++ now raise :exc:`ValueError`. ++ + + .. function:: parse_qs(qs[, keep_blank_values[, strict_parsing[, max_num_fields]]]) + +@@ -232,11 +242,21 @@ The :mod:`urlparse` module defines the following functions: + See section :ref:`urlparse-result-object` for more information on the result + object. + ++ Characters in the :attr:`netloc` attribute that decompose under NFKC ++ normalization (as used by the IDNA encoding) into any of ``/``, ``?``, ++ ``#``, ``@``, or ``:`` will raise a :exc:`ValueError`. If the URL is ++ decomposed before parsing, or is not a Unicode string, no error will be ++ raised. ++ + .. versionadded:: 2.2 + + .. versionchanged:: 2.5 + Added attributes to return value. + ++ .. versionchanged:: 2.7.17 ++ Characters that affect netloc parsing under NFKC normalization will ++ now raise :exc:`ValueError`. ++ + + .. function:: urlunsplit(parts) + +diff --git a/Lib/test/test_urlparse.py b/Lib/test/test_urlparse.py +index 4e1ded7..86c4a05 100644 +--- a/Lib/test/test_urlparse.py ++++ b/Lib/test/test_urlparse.py +@@ -1,4 +1,6 @@ + from test import test_support ++import sys ++import unicodedata + import unittest + import urlparse + +@@ -624,6 +626,45 @@ class UrlParseTestCase(unittest.TestCase): + self.assertEqual(urlparse.urlparse("http://www.python.org:80"), + ('http','www.python.org:80','','','','')) + ++ def test_urlsplit_normalization(self): ++ # Certain characters should never occur in the netloc, ++ # including under normalization. ++ # Ensure that ALL of them are detected and cause an error ++ illegal_chars = u'/:#?@' ++ hex_chars = {'{:04X}'.format(ord(c)) for c in illegal_chars} ++ denorm_chars = [ ++ c for c in map(unichr, range(128, sys.maxunicode)) ++ if (hex_chars & set(unicodedata.decomposition(c).split())) ++ and c not in illegal_chars ++ ] ++ # Sanity check that we found at least one such character ++ self.assertIn(u'\u2100', denorm_chars) ++ self.assertIn(u'\uFF03', denorm_chars) ++ ++ # bpo-36742: Verify port separators are ignored when they ++ # existed prior to decomposition ++ urlparse.urlsplit(u'http://\u30d5\u309a:80') ++ with self.assertRaises(ValueError): ++ urlparse.urlsplit(u'http://\u30d5\u309a\ufe1380') ++ ++ for scheme in [u"http", u"https", u"ftp"]: ++ for netloc in [u"netloc{}false.netloc", u"n{}user@netloc"]: ++ for c in denorm_chars: ++ url = u"{}://{}/path".format(scheme, netloc.format(c)) ++ if test_support.verbose: ++ print "Checking %r" % url ++ with self.assertRaises(ValueError): ++ urlparse.urlsplit(url) ++ ++ # check error message: invalid netloc must be formated with repr() ++ # to get an ASCII error message ++ with self.assertRaises(ValueError) as cm: ++ urlparse.urlsplit(u'http://example.com\uFF03@bing.com') ++ self.assertEqual(str(cm.exception), ++ "netloc u'example.com\\uff03@bing.com' contains invalid characters " ++ "under NFKC normalization") ++ self.assertIsInstance(cm.exception.args[0], str) ++ + def test_main(): + test_support.run_unittest(UrlParseTestCase) + +diff --git a/Lib/urlparse.py b/Lib/urlparse.py +index f7c2b03..798b467 100644 +--- a/Lib/urlparse.py ++++ b/Lib/urlparse.py +@@ -165,6 +165,25 @@ def _splitnetloc(url, start=0): + delim = min(delim, wdelim) # use earliest delim position + return url[start:delim], url[delim:] # return (domain, rest) + ++def _checknetloc(netloc): ++ if not netloc or not isinstance(netloc, unicode): ++ return ++ # looking for characters like \u2100 that expand to 'a/c' ++ # IDNA uses NFKC equivalence, so normalize for this check ++ import unicodedata ++ n = netloc.replace(u'@', u'') # ignore characters already included ++ n = n.replace(u':', u'') # but not the surrounding text ++ n = n.replace(u'#', u'') ++ n = n.replace(u'?', u'') ++ netloc2 = unicodedata.normalize('NFKC', n) ++ if n == netloc2: ++ return ++ for c in '/?#@:': ++ if c in netloc2: ++ raise ValueError("netloc %r contains invalid characters " ++ "under NFKC normalization" ++ % netloc) ++ + def urlsplit(url, scheme='', allow_fragments=True): + """Parse a URL into 5 components: + :///?# +@@ -193,6 +212,7 @@ def urlsplit(url, scheme='', allow_fragments=True): + url, fragment = url.split('#', 1) + if '?' in url: + url, query = url.split('?', 1) ++ _checknetloc(netloc) + v = SplitResult(scheme, netloc, url, query, fragment) + _parse_cache[key] = v + return v +@@ -216,6 +236,7 @@ def urlsplit(url, scheme='', allow_fragments=True): + url, fragment = url.split('#', 1) + if '?' in url: + url, query = url.split('?', 1) ++ _checknetloc(netloc) + v = SplitResult(scheme, netloc, url, query, fragment) + _parse_cache[key] = v + return v diff --git a/SOURCES/00320-CVE-2019-9636.patch b/SOURCES/00320-CVE-2019-9636.patch deleted file mode 100644 index adb977f..0000000 --- a/SOURCES/00320-CVE-2019-9636.patch +++ /dev/null @@ -1,141 +0,0 @@ -diff --git a/Doc/library/urlparse.rst b/Doc/library/urlparse.rst -index 22249da..0989c88 100644 ---- a/Doc/library/urlparse.rst -+++ b/Doc/library/urlparse.rst -@@ -119,12 +119,22 @@ The :mod:`urlparse` module defines the following functions: - See section :ref:`urlparse-result-object` for more information on the result - object. - -+ Characters in the :attr:`netloc` attribute that decompose under NFKC -+ normalization (as used by the IDNA encoding) into any of ``/``, ``?``, -+ ``#``, ``@``, or ``:`` will raise a :exc:`ValueError`. If the URL is -+ decomposed before parsing, or is not a Unicode string, no error will be -+ raised. -+ - .. versionchanged:: 2.5 - Added attributes to return value. - - .. versionchanged:: 2.7 - Added IPv6 URL parsing capabilities. - -+ .. versionchanged:: 2.7.17 -+ Characters that affect netloc parsing under NFKC normalization will -+ now raise :exc:`ValueError`. -+ - - .. function:: parse_qs(qs[, keep_blank_values[, strict_parsing[, max_num_fields]]]) - -@@ -232,11 +242,21 @@ The :mod:`urlparse` module defines the following functions: - See section :ref:`urlparse-result-object` for more information on the result - object. - -+ Characters in the :attr:`netloc` attribute that decompose under NFKC -+ normalization (as used by the IDNA encoding) into any of ``/``, ``?``, -+ ``#``, ``@``, or ``:`` will raise a :exc:`ValueError`. If the URL is -+ decomposed before parsing, or is not a Unicode string, no error will be -+ raised. -+ - .. versionadded:: 2.2 - - .. versionchanged:: 2.5 - Added attributes to return value. - -+ .. versionchanged:: 2.7.17 -+ Characters that affect netloc parsing under NFKC normalization will -+ now raise :exc:`ValueError`. -+ - - .. function:: urlunsplit(parts) - -diff --git a/Lib/test/test_urlparse.py b/Lib/test/test_urlparse.py -index 4e1ded7..6fd1071 100644 ---- a/Lib/test/test_urlparse.py -+++ b/Lib/test/test_urlparse.py -@@ -1,4 +1,6 @@ - from test import test_support -+import sys -+import unicodedata - import unittest - import urlparse - -@@ -624,6 +626,35 @@ class UrlParseTestCase(unittest.TestCase): - self.assertEqual(urlparse.urlparse("http://www.python.org:80"), - ('http','www.python.org:80','','','','')) - -+ def test_urlsplit_normalization(self): -+ # Certain characters should never occur in the netloc, -+ # including under normalization. -+ # Ensure that ALL of them are detected and cause an error -+ illegal_chars = u'/:#?@' -+ hex_chars = {'{:04X}'.format(ord(c)) for c in illegal_chars} -+ denorm_chars = [ -+ c for c in map(unichr, range(128, sys.maxunicode)) -+ if (hex_chars & set(unicodedata.decomposition(c).split())) -+ and c not in illegal_chars -+ ] -+ # Sanity check that we found at least one such character -+ self.assertIn(u'\u2100', denorm_chars) -+ self.assertIn(u'\uFF03', denorm_chars) -+ -+ # bpo-36742: Verify port separators are ignored when they -+ # existed prior to decomposition -+ urlparse.urlsplit(u'http://\u30d5\u309a:80') -+ with self.assertRaises(ValueError): -+ urlparse.urlsplit(u'http://\u30d5\u309a\ufe1380') -+ -+ for scheme in [u"http", u"https", u"ftp"]: -+ for c in denorm_chars: -+ url = u"{}://netloc{}false.netloc/path".format(scheme, c) -+ if test_support.verbose: -+ print "Checking %r" % url -+ with self.assertRaises(ValueError): -+ urlparse.urlsplit(url) -+ - def test_main(): - test_support.run_unittest(UrlParseTestCase) - -diff --git a/Lib/urlparse.py b/Lib/urlparse.py -index f7c2b03..f08e0fe 100644 ---- a/Lib/urlparse.py -+++ b/Lib/urlparse.py -@@ -165,6 +165,24 @@ def _splitnetloc(url, start=0): - delim = min(delim, wdelim) # use earliest delim position - return url[start:delim], url[delim:] # return (domain, rest) - -+def _checknetloc(netloc): -+ if not netloc or not isinstance(netloc, unicode): -+ return -+ # looking for characters like \u2100 that expand to 'a/c' -+ # IDNA uses NFKC equivalence, so normalize for this check -+ import unicodedata -+ n = netloc.rpartition('@')[2] # ignore anything to the left of '@' -+ n = n.replace(':', '') # ignore characters already included -+ n = n.replace('#', '') # but not the surrounding text -+ n = n.replace('?', '') -+ netloc2 = unicodedata.normalize('NFKC', n) -+ if n == netloc2: -+ return -+ for c in '/?#@:': -+ if c in netloc2: -+ raise ValueError("netloc '" + netloc + "' contains invalid " + -+ "characters under NFKC normalization") -+ - def urlsplit(url, scheme='', allow_fragments=True): - """Parse a URL into 5 components: - :///?# -@@ -193,6 +211,7 @@ def urlsplit(url, scheme='', allow_fragments=True): - url, fragment = url.split('#', 1) - if '?' in url: - url, query = url.split('?', 1) -+ _checknetloc(netloc) - v = SplitResult(scheme, netloc, url, query, fragment) - _parse_cache[key] = v - return v -@@ -216,6 +235,7 @@ def urlsplit(url, scheme='', allow_fragments=True): - url, fragment = url.split('#', 1) - if '?' in url: - url, query = url.split('?', 1) -+ _checknetloc(netloc) - v = SplitResult(scheme, netloc, url, query, fragment) - _parse_cache[key] = v - return v diff --git a/SOURCES/00324-disallow-control-chars-in-http-urls.patch b/SOURCES/00324-disallow-control-chars-in-http-urls.patch index 426900a..7d52fa6 100644 --- a/SOURCES/00324-disallow-control-chars-in-http-urls.patch +++ b/SOURCES/00324-disallow-control-chars-in-http-urls.patch @@ -33,25 +33,13 @@ index 60a8fb4..1b41c34 100644 self._output(hdr) diff --git a/Lib/test/test_urllib.py b/Lib/test/test_urllib.py -index 1ce9201..bdc6e78 100644 +index 1ce9201..d7778d4 100644 --- a/Lib/test/test_urllib.py +++ b/Lib/test/test_urllib.py -@@ -9,6 +9,10 @@ import os - import sys - import mimetools - import tempfile -+try: -+ import ssl -+except ImportError: -+ ssl = None - - from test import test_support - from base64 import b64encode -@@ -257,6 +261,33 @@ class urlopen_HttpTests(unittest.TestCase, FakeHTTPMixin): +@@ -257,6 +257,31 @@ class urlopen_HttpTests(unittest.TestCase, FakeHTTPMixin): finally: self.unfakehttp() -+ @unittest.skipUnless(ssl, "ssl module required") + def test_url_with_control_char_rejected(self): + for char_no in range(0, 0x21) + range(0x7f, 0x100): + char = chr(char_no) @@ -64,7 +52,6 @@ index 1ce9201..bdc6e78 100644 + finally: + self.unfakehttp() + -+ @unittest.skipUnless(ssl, "ssl module required") + def test_url_with_newline_header_injection_rejected(self): + self.fakehttp(b"HTTP/1.1 200 OK\r\n\r\nHello.") + host = "localhost:7777?a=1 HTTP/1.1\r\nX-injected: header\r\nTEST: 123" @@ -82,16 +69,9 @@ index 1ce9201..bdc6e78 100644 # urlopen() should raise IOError for many error codes. self.fakehttp('''HTTP/1.1 401 Authentication Required diff --git a/Lib/test/test_urllib2.py b/Lib/test/test_urllib2.py -index 6d24d5d..d13f86f 100644 +index 6d24d5d..9531818 100644 --- a/Lib/test/test_urllib2.py +++ b/Lib/test/test_urllib2.py -@@ -1,5 +1,5 @@ - import unittest --from test import test_support -+from test import support - from test import test_urllib - - import os @@ -15,6 +15,9 @@ try: except ImportError: ssl = None @@ -102,24 +82,6 @@ index 6d24d5d..d13f86f 100644 # XXX # Request # CacheFTPHandler (hard to write) -@@ -683,7 +686,7 @@ class HandlerTests(unittest.TestCase): - h = urllib2.FileHandler() - o = h.parent = MockOpener() - -- TESTFN = test_support.TESTFN -+ TESTFN = support.TESTFN - urlpath = sanepathname2url(os.path.abspath(TESTFN)) - towrite = "hello, world\n" - urls = [ -@@ -1154,7 +1157,7 @@ class HandlerTests(unittest.TestCase): - opener.add_handler(auth_handler) - opener.add_handler(http_handler) - msg = "Basic Auth Realm was unquoted" -- with test_support.check_warnings((msg, UserWarning)): -+ with support.check_warnings((msg, UserWarning)): - self._test_basic_auth(opener, auth_handler, "Authorization", - realm, http_handler, password_manager, - "http://acme.example.com/protected", @@ -1262,7 +1265,7 @@ class HandlerTests(unittest.TestCase): self.assertEqual(len(http_handler.requests), 1) self.assertFalse(http_handler.requests[0].has_header(auth_header)) @@ -163,7 +125,7 @@ index 6d24d5d..d13f86f 100644 + host = "localhost:7777?a=1 HTTP/1.1\r\nX-injected: header\r\nTEST: 123" + schemeless_url = "//" + host + ":8080/test/?test=a" + try: -+ # We explicitly test urllib.request.urlopen() instead of the top ++ # We explicitly test urllib2.urlopen() instead of the top + # level 'def urlopen()' function defined in this... (quite ugly) + # test suite. They use different url opening codepaths. Plain + # urlopen uses FancyURLOpener which goes via a codepath that @@ -182,24 +144,6 @@ index 6d24d5d..d13f86f 100644 class RequestTests(unittest.TestCase): -@@ -1412,14 +1461,14 @@ class RequestTests(unittest.TestCase): - - def test_main(verbose=None): - from test import test_urllib2 -- test_support.run_doctest(test_urllib2, verbose) -- test_support.run_doctest(urllib2, verbose) -+ support.run_doctest(test_urllib2, verbose) -+ support.run_doctest(urllib2, verbose) - tests = (TrivialTests, - OpenerDirectorTests, - HandlerTests, - MiscTests, - RequestTests) -- test_support.run_unittest(*tests) -+ support.run_unittest(*tests) - - if __name__ == "__main__": - test_main(verbose=True) diff --git a/Lib/test/test_xmlrpc.py b/Lib/test/test_xmlrpc.py index 36b3be6..90ccb30 100644 --- a/Lib/test/test_xmlrpc.py diff --git a/SOURCES/00325-CVE-2019-9948.patch b/SOURCES/00325-CVE-2019-9948.patch new file mode 100644 index 0000000..890bf71 --- /dev/null +++ b/SOURCES/00325-CVE-2019-9948.patch @@ -0,0 +1,37 @@ +diff --git a/Lib/test/test_urllib.py b/Lib/test/test_urllib.py +index d2da0f8..7813b9f 100644 +--- a/Lib/test/test_urllib.py ++++ b/Lib/test/test_urllib.py +@@ -872,6 +872,17 @@ class URLopener_Tests(unittest.TestCase): + "spam://c:|windows%/:=&?~#+!$,;'@()*[]|/path/"), + "//c:|windows%/:=&?~#+!$,;'@()*[]|/path/") + ++ def test_local_file_open(self): ++ # bpo-35907, CVE-2019-9948: urllib must reject local_file:// scheme ++ class DummyURLopener(urllib.URLopener): ++ def open_local_file(self, url): ++ return url ++ for url in ('local_file://example', 'local-file://example'): ++ self.assertRaises(IOError, urllib.urlopen, url) ++ self.assertRaises(IOError, urllib.URLopener().open, url) ++ self.assertRaises(IOError, urllib.URLopener().retrieve, url) ++ self.assertRaises(IOError, DummyURLopener().open, url) ++ self.assertRaises(IOError, DummyURLopener().retrieve, url) + + # Just commented them out. + # Can't really tell why keep failing in windows and sparc. +diff --git a/Lib/urllib.py b/Lib/urllib.py +index 2201e3e..71e3637 100644 +--- a/Lib/urllib.py ++++ b/Lib/urllib.py +@@ -198,7 +198,9 @@ class URLopener: + name = 'open_' + urltype + self.type = urltype + name = name.replace('-', '_') +- if not hasattr(self, name): ++ ++ # bpo-35907: disallow the file reading with the type not allowed ++ if not hasattr(self, name) or name == 'open_local_file': + if proxy: + return self.open_unknown_proxy(proxy, fullurl, data) + else: diff --git a/SPECS/python.spec b/SPECS/python.spec index 555bdb1..f52f4b0 100644 --- a/SPECS/python.spec +++ b/SPECS/python.spec @@ -122,7 +122,7 @@ Summary: An interpreted, interactive, object-oriented programming language Name: %{?scl_prefix}%{python} # Remember to also rebase python-docs when changing this: Version: 2.7.16 -Release: 4%{?dist} +Release: 6%{?dist} License: Python Group: Development/Languages %{?scl:Requires: %{scl}-runtime} @@ -741,19 +741,27 @@ Patch198: 00198-add-rewheel-module.patch Patch224: 00224-PEP-493-Re-add-file-based-configuration-of-HTTPS-ver.patch # 00320 # -# Security fix for CVE-2019-9636: Information Disclosure due to urlsplit improper NFKC normalization +# Security fix for CVE-2019-9636 and CVE-2019-10160: Information Disclosure due to urlsplit improper NFKC normalization # FIXED UPSTREAM: https://bugs.python.org/issue36216 and https://bugs.python.org/issue36742 # Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1689326 -Patch320: 00320-CVE-2019-9636.patch +# and https://bugzilla.redhat.com/show_bug.cgi?id=1718924 +Patch320: 00320-CVE-2019-9636-and-CVE-2019-10160.patch # 00324 # # Disallow control chars in http URLs # Security fix for CVE-2019-9740 and CVE-2019-9947 # Fixed upstream: https://bugs.python.org/issue30458 -# Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1709403 -# and https://bugzilla.redhat.com/show_bug.cgi?id=1709407 +# Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1703534 +# and https://bugzilla.redhat.com/show_bug.cgi?id=1704372 Patch324: 00324-disallow-control-chars-in-http-urls.patch +# 00325 # +# Unnecessary URL scheme exists to allow local_file:// reading file in urllib +# Security fix for CVE-2019-9948 +# Fixed upstream: https://bugs.python.org/issue35907 +# Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1709404 +Patch325: 00325-CVE-2019-9948.patch + # (New patches go here ^^^) # # When adding new patches to "python" and "python3" in Fedora 17 onwards, @@ -1093,6 +1101,7 @@ mv Modules/cryptmodule.c Modules/_cryptmodule.c %patch224 -p1 %patch320 -p1 %patch324 -p1 +%patch325 -p1 # This shouldn't be necesarry, but is right now (2.2a3) find -name "*~" |xargs rm -f @@ -1967,6 +1976,14 @@ rm -fr %{buildroot} # ====================================================== %changelog +* Tue Jun 11 2019 Charalampos Stratakis - 2.7.16-6 +- Security fix for CVE-2019-10160 +Resolves: rhbz#1718924 + +* Tue May 28 2019 Charalampos Stratakis - 2.7.16-5 +- Security fix for CVE-2019-9948 +Resolves: rhbz#1709404 + * Mon May 20 2019 Victor Stinner - 2.7.16-4 - Fix regression in the crypt module introduced in update to Python 2.7.16 (fix the name of the _crypt module init function). @@ -1974,19 +1991,19 @@ rm -fr %{buildroot} * Wed May 15 2019 Charalampos Stratakis - 2.7.16-3 - Disallow control chars in http URLs - Fixes CVE-2019-9740 and CVE-2019-9947 -Resolves: rhbz#1709403 and rhbz#1709407 +Resolves: rhbz#1703534 and rhbz#1704372 * Mon May 13 2019 Charalampos Stratakis - 2.7.16-2 - Updated fix for CVE-2019-9636 -Resolves: rhbz#1709329 +Resolves: rhbz#1706798 * Thu Apr 25 2019 Charalampos Stratakis - 2.7.16-1 - Update to 2.7.16 -Resolves: rhbz#1709388, rhbz#1709381, rhbz#1709360 +Resolves: rhbz#1563451, rhbz#1563487, rhbz#1636839 * Tue Mar 26 2019 Charalampos Stratakis - 2.7.13-6 - Security fix for CVE-2019-9636 -Resolves: rhbz#1689325 +Resolves: rhbz#1689326 * Wed May 23 2018 Charalampos Stratakis - 2.7.13-5 - Enable tests and rewheel