Author: tomaz
Date: Thu Aug  2 00:39:09 2012
New Revision: 1368323

URL: http://svn.apache.org/viewvc?rev=1368323&view=rev
Log:
Fix hostname validation in the SSL verification code (CVE-2012-3446). Reported 
by researchers
from the University of Texas at Austin (Martin Georgiev, Suman Jana and Vitaly 
Shmatikov). 
For more info, see http://libcloud.apache.org/security.html.

Modified:
    libcloud/branches/0.11.x/CHANGES
    libcloud/branches/0.11.x/libcloud/__init__.py
    libcloud/branches/0.11.x/libcloud/httplib_ssl.py
    libcloud/branches/0.11.x/libcloud/test/test_httplib_ssl.py

Modified: libcloud/branches/0.11.x/CHANGES
URL: 
http://svn.apache.org/viewvc/libcloud/branches/0.11.x/CHANGES?rev=1368323&r1=1368322&r2=1368323&view=diff
==============================================================================
--- libcloud/branches/0.11.x/CHANGES (original)
+++ libcloud/branches/0.11.x/CHANGES Thu Aug  2 00:39:09 2012
@@ -1,5 +1,14 @@
                                    -*- coding: utf-8 -*-
 
+Changes with Apache Libcloud 0.11.1:
+
+  *) General
+
+    - Fix hostname validation in the SSL verification code (CVE-2012-3446).
+
+      Reported by researchers from the University of Texas at Austin (Martin
+      Georgiev, Suman Jana and Vitaly Shmatikov).
+
 Changes with Apache Libcloud 0.11.0:
 
   *) Compute
@@ -139,7 +148,7 @@ Changes with Apache Libcloud 0.11.0:
       CloudFiles driver.
       [Tomaz Muraus]
 
-    - Fix a bug with content_type and and encoding of object and path names in 
+    - Fix a bug with content_type and and encoding of object and path names in
       the Atmos driver.
       [Russell Keith-Magee]
 
@@ -234,7 +243,7 @@ Changes with Apache Libcloud 0.10.1:
 
     - Add ex_rescue and ex_unrescue method to OpenStack 1.1 driver. ;
       LIBCLOUD-193
-      [Shawn Smith] 
+      [Shawn Smith]
 
     - Include 'password' in the node extra dictionary when calling deploy_node
       if the password auth is used.
@@ -419,7 +428,7 @@ Changes with Apache Libcloud 0.8.0:
      - Enable ex_delete_image method in the OpenStack 1.1 driver.
        [Shawn Smith]
 
-     - Return NodeImage instance in OpenStack 1.1 driver ex_save_image method 
+     - Return NodeImage instance in OpenStack 1.1 driver ex_save_image method
        ; LIBCLOUD-138
        [Shawn Smith]
 

Modified: libcloud/branches/0.11.x/libcloud/__init__.py
URL: 
http://svn.apache.org/viewvc/libcloud/branches/0.11.x/libcloud/__init__.py?rev=1368323&r1=1368322&r2=1368323&view=diff
==============================================================================
--- libcloud/branches/0.11.x/libcloud/__init__.py (original)
+++ libcloud/branches/0.11.x/libcloud/__init__.py Thu Aug  2 00:39:09 2012
@@ -20,7 +20,7 @@ libcloud provides a unified interface to
 """
 
 __all__ = ['__version__', 'enable_debug']
-__version__ = '0.11.0'
+__version__ = '0.11.1'
 
 try:
     import paramiko

Modified: libcloud/branches/0.11.x/libcloud/httplib_ssl.py
URL: 
http://svn.apache.org/viewvc/libcloud/branches/0.11.x/libcloud/httplib_ssl.py?rev=1368323&r1=1368322&r2=1368323&view=diff
==============================================================================
--- libcloud/branches/0.11.x/libcloud/httplib_ssl.py (original)
+++ libcloud/branches/0.11.x/libcloud/httplib_ssl.py Thu Aug  2 00:39:09 2012
@@ -122,13 +122,8 @@ class LibcloudHTTPSConnection(httplib.HT
         # replace * with alphanumeric and dash
         # replace . with literal .
         valid_patterns = [
-            re.compile(
-                pattern.replace(
-                    r".", r"\."
-                ).replace(
-                    r"*", r"[0-9A-Za-z]+"
-                )
-            )
+            re.compile('^' + pattern.replace(r".", r"\.") \
+                                    .replace(r"*", r"[0-9A-Za-z]+") + '$')
             for pattern in (set(common_name) | set(alt_names))]
 
         return any(

Modified: libcloud/branches/0.11.x/libcloud/test/test_httplib_ssl.py
URL: 
http://svn.apache.org/viewvc/libcloud/branches/0.11.x/libcloud/test/test_httplib_ssl.py?rev=1368323&r1=1368322&r2=1368323&view=diff
==============================================================================
--- libcloud/branches/0.11.x/libcloud/test/test_httplib_ssl.py (original)
+++ libcloud/branches/0.11.x/libcloud/test/test_httplib_ssl.py Thu Aug  2 
00:39:09 2012
@@ -45,16 +45,49 @@ class TestHttpLibSSLTests(unittest.TestC
          'subjectAltName': ((('DNS', 'foo.alt.name')),
                            (('DNS', 'foo.alt.name.1')))}
 
+        cert3 = {'notAfter': 'Feb 16 16:54:50 2013 GMT',
+         'subject': ((('countryName', 'US'),),
+                     (('stateOrProvinceName', 'Delaware'),),
+                     (('localityName', 'Wilmington'),),
+                     (('organizationName', 'Python Software Foundation'),),
+                     (('organizationalUnitName', 'SSL'),),
+                     (('commonName', 'python.org'),))}
+
         self.assertFalse(self.httplib_object._verify_hostname(
                          hostname='invalid', cert=cert1))
+        self.assertFalse(self.httplib_object._verify_hostname(
+                         hostname='machine.python.org', cert=cert1))
+        self.assertFalse(self.httplib_object._verify_hostname(
+                         hostname='foomachine.python.org', cert=cert1))
+        self.assertFalse(self.httplib_object._verify_hostname(
+                        hostname='somesomemachine.python.org', cert=cert1))
+        self.assertFalse(self.httplib_object._verify_hostname(
+                        hostname='somemachine.python.orga', cert=cert1))
+        self.assertFalse(self.httplib_object._verify_hostname(
+                        hostname='somemachine.python.org.org', cert=cert1))
         self.assertTrue(self.httplib_object._verify_hostname(
                         hostname='somemachine.python.org', cert=cert1))
 
         self.assertFalse(self.httplib_object._verify_hostname(
                          hostname='invalid', cert=cert2))
+        self.assertFalse(self.httplib_object._verify_hostname(
+                        hostname='afoo.alt.name.1', cert=cert2))
+        self.assertFalse(self.httplib_object._verify_hostname(
+                        hostname='a.foo.alt.name.1', cert=cert2))
+        self.assertFalse(self.httplib_object._verify_hostname(
+                        hostname='foo.alt.name.1.2', cert=cert2))
+        self.assertFalse(self.httplib_object._verify_hostname(
+                        hostname='afoo.alt.name.1.2', cert=cert2))
         self.assertTrue(self.httplib_object._verify_hostname(
                         hostname='foo.alt.name.1', cert=cert2))
 
+        self.assertTrue(self.httplib_object._verify_hostname(
+                        hostname='python.org', cert=cert3))
+        self.assertFalse(self.httplib_object._verify_hostname(
+                        hostname='opython.org', cert=cert3))
+        self.assertFalse(self.httplib_object._verify_hostname(
+                        hostname='ython.org', cert=cert3))
+
     def test_get_subject_alt_names(self):
         cert1 = {'notAfter': 'Feb 16 16:54:50 2013 GMT',
          'subject': ((('countryName', 'US'),),


Reply via email to