blob: d77863843adc57110169d9dbdb7226bc6cea9b79 [file] [log] [blame]
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +00001# Wrapper module for _ssl, providing some additional facilities
2# implemented in Python. Written by Bill Janssen.
3
Benjamin Petersondaeb9252014-08-20 14:14:50 -05004"""This module provides some more Pythonic support for SSL.
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +00005
6Object types:
7
Bill Janssen98d19da2007-09-10 21:51:02 +00008 SSLSocket -- subtype of socket.socket which does SSL over the socket
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +00009
10Exceptions:
11
Bill Janssen98d19da2007-09-10 21:51:02 +000012 SSLError -- exception raised for I/O errors
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +000013
14Functions:
15
16 cert_time_to_seconds -- convert time string used for certificate
17 notBefore and notAfter functions to integer
18 seconds past the Epoch (the time values
19 returned from time.time())
20
21 fetch_server_certificate (HOST, PORT) -- fetch the certificate provided
22 by the server running on HOST at port PORT. No
23 validation of the certificate is performed.
24
25Integer constants:
26
27SSL_ERROR_ZERO_RETURN
28SSL_ERROR_WANT_READ
29SSL_ERROR_WANT_WRITE
30SSL_ERROR_WANT_X509_LOOKUP
31SSL_ERROR_SYSCALL
32SSL_ERROR_SSL
33SSL_ERROR_WANT_CONNECT
34
35SSL_ERROR_EOF
36SSL_ERROR_INVALID_ERROR_CODE
37
38The following group define certificate requirements that one side is
39allowing/requiring from the other side:
40
41CERT_NONE - no certificates from the other side are required (or will
42 be looked at if provided)
43CERT_OPTIONAL - certificates are not required, but if provided will be
44 validated, and if validation fails, the connection will
45 also fail
46CERT_REQUIRED - certificates are required, and will be validated, and
47 if validation fails, the connection will also fail
48
49The following constants identify various SSL protocol variants:
50
51PROTOCOL_SSLv2
52PROTOCOL_SSLv3
53PROTOCOL_SSLv23
54PROTOCOL_TLSv1
Benjamin Petersondaeb9252014-08-20 14:14:50 -050055PROTOCOL_TLSv1_1
56PROTOCOL_TLSv1_2
57
58The following constants identify various SSL alert message descriptions as per
59http://www.iana.org/assignments/tls-parameters/tls-parameters.xml#tls-parameters-6
60
61ALERT_DESCRIPTION_CLOSE_NOTIFY
62ALERT_DESCRIPTION_UNEXPECTED_MESSAGE
63ALERT_DESCRIPTION_BAD_RECORD_MAC
64ALERT_DESCRIPTION_RECORD_OVERFLOW
65ALERT_DESCRIPTION_DECOMPRESSION_FAILURE
66ALERT_DESCRIPTION_HANDSHAKE_FAILURE
67ALERT_DESCRIPTION_BAD_CERTIFICATE
68ALERT_DESCRIPTION_UNSUPPORTED_CERTIFICATE
69ALERT_DESCRIPTION_CERTIFICATE_REVOKED
70ALERT_DESCRIPTION_CERTIFICATE_EXPIRED
71ALERT_DESCRIPTION_CERTIFICATE_UNKNOWN
72ALERT_DESCRIPTION_ILLEGAL_PARAMETER
73ALERT_DESCRIPTION_UNKNOWN_CA
74ALERT_DESCRIPTION_ACCESS_DENIED
75ALERT_DESCRIPTION_DECODE_ERROR
76ALERT_DESCRIPTION_DECRYPT_ERROR
77ALERT_DESCRIPTION_PROTOCOL_VERSION
78ALERT_DESCRIPTION_INSUFFICIENT_SECURITY
79ALERT_DESCRIPTION_INTERNAL_ERROR
80ALERT_DESCRIPTION_USER_CANCELLED
81ALERT_DESCRIPTION_NO_RENEGOTIATION
82ALERT_DESCRIPTION_UNSUPPORTED_EXTENSION
83ALERT_DESCRIPTION_CERTIFICATE_UNOBTAINABLE
84ALERT_DESCRIPTION_UNRECOGNIZED_NAME
85ALERT_DESCRIPTION_BAD_CERTIFICATE_STATUS_RESPONSE
86ALERT_DESCRIPTION_BAD_CERTIFICATE_HASH_VALUE
87ALERT_DESCRIPTION_UNKNOWN_PSK_IDENTITY
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +000088"""
89
Christian Heimesc5f05e42008-02-23 17:40:11 +000090import textwrap
Benjamin Petersondaeb9252014-08-20 14:14:50 -050091import re
92import sys
93import os
94from collections import namedtuple
95from contextlib import closing
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +000096
97import _ssl # if we can't import it, let the error propagate
Bill Janssen98d19da2007-09-10 21:51:02 +000098
Antoine Pitrouf9de5342010-04-05 21:35:07 +000099from _ssl import OPENSSL_VERSION_NUMBER, OPENSSL_VERSION_INFO, OPENSSL_VERSION
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500100from _ssl import _SSLContext
101from _ssl import (
102 SSLError, SSLZeroReturnError, SSLWantReadError, SSLWantWriteError,
103 SSLSyscallError, SSLEOFError,
104 )
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +0000105from _ssl import CERT_NONE, CERT_OPTIONAL, CERT_REQUIRED
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500106from _ssl import txt2obj as _txt2obj, nid2obj as _nid2obj
Victor Stinner7c906672015-01-06 13:53:37 +0100107from _ssl import RAND_status, RAND_add
108try:
109 from _ssl import RAND_egd
110except ImportError:
111 # LibreSSL does not provide RAND_egd
112 pass
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500113
114def _import_symbols(prefix):
115 for n in dir(_ssl):
116 if n.startswith(prefix):
117 globals()[n] = getattr(_ssl, n)
118
119_import_symbols('OP_')
120_import_symbols('ALERT_DESCRIPTION_')
121_import_symbols('SSL_ERROR_')
122_import_symbols('PROTOCOL_')
Benjamin Petersonb10d50e2015-03-04 23:18:57 -0500123_import_symbols('VERIFY_')
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500124
Benjamin Petersonb10bfbe2015-01-23 16:35:37 -0500125from _ssl import HAS_SNI, HAS_ECDH, HAS_NPN, HAS_ALPN
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500126
127from _ssl import _OPENSSL_API_VERSION
128
129_PROTOCOL_NAMES = {value: name for name, value in globals().items() if name.startswith('PROTOCOL_')}
130
Victor Stinnerb1241f92011-05-10 01:52:03 +0200131try:
Antoine Pitroud76088d2012-01-03 22:46:48 +0100132 _SSLv2_IF_EXISTS = PROTOCOL_SSLv2
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500133except NameError:
Antoine Pitroud76088d2012-01-03 22:46:48 +0100134 _SSLv2_IF_EXISTS = None
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +0000135
Antoine Pitroudfb299b2010-04-23 22:54:59 +0000136from socket import socket, _fileobject, _delegate_methods, error as socket_error
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500137if sys.platform == "win32":
138 from _ssl import enum_certificates, enum_crls
139
140from socket import socket, AF_INET, SOCK_STREAM, create_connection
141from socket import SOL_SOCKET, SO_TYPE
Bill Janssen296a59d2007-09-16 22:06:00 +0000142import base64 # for DER-to-PEM translation
Antoine Pitrou278d6652010-04-26 17:23:33 +0000143import errno
Bill Janssen98d19da2007-09-10 21:51:02 +0000144
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500145if _ssl.HAS_TLS_UNIQUE:
146 CHANNEL_BINDING_TYPES = ['tls-unique']
147else:
148 CHANNEL_BINDING_TYPES = []
149
Antoine Pitroud76088d2012-01-03 22:46:48 +0100150# Disable weak or insecure ciphers by default
151# (OpenSSL's default setting is 'DEFAULT:!aNULL:!eNULL')
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500152# Enable a better set of ciphers by default
153# This list has been explicitly chosen to:
154# * Prefer cipher suites that offer perfect forward secrecy (DHE/ECDHE)
155# * Prefer ECDHE over DHE for better performance
156# * Prefer any AES-GCM over any AES-CBC for better performance and security
157# * Then Use HIGH cipher suites as a fallback
158# * Then Use 3DES as fallback which is secure but slow
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500159# * Disable NULL authentication, NULL encryption, and MD5 MACs for security
160# reasons
161_DEFAULT_CIPHERS = (
162 'ECDH+AESGCM:DH+AESGCM:ECDH+AES256:DH+AES256:ECDH+AES128:DH+AES:ECDH+HIGH:'
Benjamin Petersona0dd7dc2015-02-19 17:57:08 -0500163 'DH+HIGH:ECDH+3DES:DH+3DES:RSA+AESGCM:RSA+AES:RSA+HIGH:RSA+3DES:!aNULL:'
164 '!eNULL:!MD5'
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500165)
Antoine Pitroud76088d2012-01-03 22:46:48 +0100166
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500167# Restricted and more secure ciphers for the server side
168# This list has been explicitly chosen to:
169# * Prefer cipher suites that offer perfect forward secrecy (DHE/ECDHE)
170# * Prefer ECDHE over DHE for better performance
171# * Prefer any AES-GCM over any AES-CBC for better performance and security
172# * Then Use HIGH cipher suites as a fallback
173# * Then Use 3DES as fallback which is secure but slow
174# * Disable NULL authentication, NULL encryption, MD5 MACs, DSS, and RC4 for
175# security reasons
176_RESTRICTED_SERVER_CIPHERS = (
177 'ECDH+AESGCM:DH+AESGCM:ECDH+AES256:DH+AES256:ECDH+AES128:DH+AES:ECDH+HIGH:'
178 'DH+HIGH:ECDH+3DES:DH+3DES:RSA+AESGCM:RSA+AES:RSA+HIGH:RSA+3DES:!aNULL:'
179 '!eNULL:!MD5:!DSS:!RC4'
180)
181
182
183class CertificateError(ValueError):
184 pass
185
186
187def _dnsname_match(dn, hostname, max_wildcards=1):
188 """Matching according to RFC 6125, section 6.4.3
189
190 http://tools.ietf.org/html/rfc6125#section-6.4.3
191 """
192 pats = []
193 if not dn:
194 return False
195
196 pieces = dn.split(r'.')
197 leftmost = pieces[0]
198 remainder = pieces[1:]
199
200 wildcards = leftmost.count('*')
201 if wildcards > max_wildcards:
202 # Issue #17980: avoid denials of service by refusing more
203 # than one wildcard per fragment. A survery of established
204 # policy among SSL implementations showed it to be a
205 # reasonable choice.
206 raise CertificateError(
207 "too many wildcards in certificate DNS name: " + repr(dn))
208
209 # speed up common case w/o wildcards
210 if not wildcards:
211 return dn.lower() == hostname.lower()
212
213 # RFC 6125, section 6.4.3, subitem 1.
214 # The client SHOULD NOT attempt to match a presented identifier in which
215 # the wildcard character comprises a label other than the left-most label.
216 if leftmost == '*':
217 # When '*' is a fragment by itself, it matches a non-empty dotless
218 # fragment.
219 pats.append('[^.]+')
220 elif leftmost.startswith('xn--') or hostname.startswith('xn--'):
221 # RFC 6125, section 6.4.3, subitem 3.
222 # The client SHOULD NOT attempt to match a presented identifier
223 # where the wildcard character is embedded within an A-label or
224 # U-label of an internationalized domain name.
225 pats.append(re.escape(leftmost))
226 else:
227 # Otherwise, '*' matches any dotless string, e.g. www*
228 pats.append(re.escape(leftmost).replace(r'\*', '[^.]*'))
229
230 # add the remaining fragments, ignore any wildcards
231 for frag in remainder:
232 pats.append(re.escape(frag))
233
234 pat = re.compile(r'\A' + r'\.'.join(pats) + r'\Z', re.IGNORECASE)
235 return pat.match(hostname)
236
237
238def match_hostname(cert, hostname):
239 """Verify that *cert* (in decoded format as returned by
240 SSLSocket.getpeercert()) matches the *hostname*. RFC 2818 and RFC 6125
241 rules are followed, but IP addresses are not accepted for *hostname*.
242
243 CertificateError is raised on failure. On success, the function
244 returns nothing.
245 """
246 if not cert:
247 raise ValueError("empty or no certificate, match_hostname needs a "
248 "SSL socket or SSL context with either "
249 "CERT_OPTIONAL or CERT_REQUIRED")
250 dnsnames = []
251 san = cert.get('subjectAltName', ())
252 for key, value in san:
253 if key == 'DNS':
254 if _dnsname_match(value, hostname):
255 return
256 dnsnames.append(value)
257 if not dnsnames:
258 # The subject is only checked when there is no dNSName entry
259 # in subjectAltName
260 for sub in cert.get('subject', ()):
261 for key, value in sub:
262 # XXX according to RFC 2818, the most specific Common Name
263 # must be used.
264 if key == 'commonName':
265 if _dnsname_match(value, hostname):
266 return
267 dnsnames.append(value)
268 if len(dnsnames) > 1:
269 raise CertificateError("hostname %r "
270 "doesn't match either of %s"
271 % (hostname, ', '.join(map(repr, dnsnames))))
272 elif len(dnsnames) == 1:
273 raise CertificateError("hostname %r "
274 "doesn't match %r"
275 % (hostname, dnsnames[0]))
276 else:
277 raise CertificateError("no appropriate commonName or "
278 "subjectAltName fields were found")
279
280
281DefaultVerifyPaths = namedtuple("DefaultVerifyPaths",
282 "cafile capath openssl_cafile_env openssl_cafile openssl_capath_env "
283 "openssl_capath")
284
285def get_default_verify_paths():
286 """Return paths to default cafile and capath.
287 """
288 parts = _ssl.get_default_verify_paths()
289
290 # environment vars shadow paths
291 cafile = os.environ.get(parts[0], parts[1])
292 capath = os.environ.get(parts[2], parts[3])
293
294 return DefaultVerifyPaths(cafile if os.path.isfile(cafile) else None,
295 capath if os.path.isdir(capath) else None,
296 *parts)
297
298
299class _ASN1Object(namedtuple("_ASN1Object", "nid shortname longname oid")):
300 """ASN.1 object identifier lookup
301 """
302 __slots__ = ()
303
304 def __new__(cls, oid):
305 return super(_ASN1Object, cls).__new__(cls, *_txt2obj(oid, name=False))
306
307 @classmethod
308 def fromnid(cls, nid):
309 """Create _ASN1Object from OpenSSL numeric ID
310 """
311 return super(_ASN1Object, cls).__new__(cls, *_nid2obj(nid))
312
313 @classmethod
314 def fromname(cls, name):
315 """Create _ASN1Object from short name, long name or OID
316 """
317 return super(_ASN1Object, cls).__new__(cls, *_txt2obj(name, name=True))
318
319
320class Purpose(_ASN1Object):
321 """SSLContext purpose flags with X509v3 Extended Key Usage objects
322 """
323
324Purpose.SERVER_AUTH = Purpose('1.3.6.1.5.5.7.3.1')
325Purpose.CLIENT_AUTH = Purpose('1.3.6.1.5.5.7.3.2')
326
327
328class SSLContext(_SSLContext):
329 """An SSLContext holds various SSL-related configuration options and
330 data, such as certificates and possibly a private key."""
331
332 __slots__ = ('protocol', '__weakref__')
333 _windows_cert_stores = ("CA", "ROOT")
334
335 def __new__(cls, protocol, *args, **kwargs):
336 self = _SSLContext.__new__(cls, protocol)
337 if protocol != _SSLv2_IF_EXISTS:
338 self.set_ciphers(_DEFAULT_CIPHERS)
339 return self
340
341 def __init__(self, protocol):
342 self.protocol = protocol
343
344 def wrap_socket(self, sock, server_side=False,
345 do_handshake_on_connect=True,
346 suppress_ragged_eofs=True,
347 server_hostname=None):
348 return SSLSocket(sock=sock, server_side=server_side,
349 do_handshake_on_connect=do_handshake_on_connect,
350 suppress_ragged_eofs=suppress_ragged_eofs,
351 server_hostname=server_hostname,
352 _context=self)
353
354 def set_npn_protocols(self, npn_protocols):
355 protos = bytearray()
356 for protocol in npn_protocols:
357 b = protocol.encode('ascii')
358 if len(b) == 0 or len(b) > 255:
359 raise SSLError('NPN protocols must be 1 to 255 in length')
360 protos.append(len(b))
361 protos.extend(b)
362
363 self._set_npn_protocols(protos)
364
Benjamin Petersonb10bfbe2015-01-23 16:35:37 -0500365 def set_alpn_protocols(self, alpn_protocols):
366 protos = bytearray()
367 for protocol in alpn_protocols:
368 b = protocol.encode('ascii')
369 if len(b) == 0 or len(b) > 255:
370 raise SSLError('ALPN protocols must be 1 to 255 in length')
371 protos.append(len(b))
372 protos.extend(b)
373
374 self._set_alpn_protocols(protos)
375
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500376 def _load_windows_store_certs(self, storename, purpose):
377 certs = bytearray()
378 for cert, encoding, trust in enum_certificates(storename):
379 # CA certs are never PKCS#7 encoded
380 if encoding == "x509_asn":
381 if trust is True or purpose.oid in trust:
382 certs.extend(cert)
Steve Dower9cb20742016-03-17 15:02:19 -0700383 if certs:
384 self.load_verify_locations(cadata=certs)
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500385 return certs
386
387 def load_default_certs(self, purpose=Purpose.SERVER_AUTH):
388 if not isinstance(purpose, _ASN1Object):
389 raise TypeError(purpose)
390 if sys.platform == "win32":
391 for storename in self._windows_cert_stores:
392 self._load_windows_store_certs(storename, purpose)
Benjamin Peterson0b30a2b2014-10-03 17:27:05 -0400393 self.set_default_verify_paths()
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500394
395
396def create_default_context(purpose=Purpose.SERVER_AUTH, cafile=None,
397 capath=None, cadata=None):
398 """Create a SSLContext object with default settings.
399
400 NOTE: The protocol and settings may change anytime without prior
401 deprecation. The values represent a fair balance between maximum
402 compatibility and security.
403 """
404 if not isinstance(purpose, _ASN1Object):
405 raise TypeError(purpose)
406
407 context = SSLContext(PROTOCOL_SSLv23)
408
409 # SSLv2 considered harmful.
410 context.options |= OP_NO_SSLv2
411
412 # SSLv3 has problematic security and is only required for really old
413 # clients such as IE6 on Windows XP
414 context.options |= OP_NO_SSLv3
415
416 # disable compression to prevent CRIME attacks (OpenSSL 1.0+)
417 context.options |= getattr(_ssl, "OP_NO_COMPRESSION", 0)
418
419 if purpose == Purpose.SERVER_AUTH:
420 # verify certs and host name in client mode
421 context.verify_mode = CERT_REQUIRED
422 context.check_hostname = True
423 elif purpose == Purpose.CLIENT_AUTH:
424 # Prefer the server's ciphers by default so that we get stronger
425 # encryption
426 context.options |= getattr(_ssl, "OP_CIPHER_SERVER_PREFERENCE", 0)
427
428 # Use single use keys in order to improve forward secrecy
429 context.options |= getattr(_ssl, "OP_SINGLE_DH_USE", 0)
430 context.options |= getattr(_ssl, "OP_SINGLE_ECDH_USE", 0)
431
432 # disallow ciphers with known vulnerabilities
433 context.set_ciphers(_RESTRICTED_SERVER_CIPHERS)
434
435 if cafile or capath or cadata:
436 context.load_verify_locations(cafile, capath, cadata)
437 elif context.verify_mode != CERT_NONE:
438 # no explicit cafile, capath or cadata but the verify mode is
439 # CERT_OPTIONAL or CERT_REQUIRED. Let's try to load default system
440 # root CA certificates for the given purpose. This may fail silently.
441 context.load_default_certs(purpose)
442 return context
443
Benjamin Petersone3e7d402014-11-23 21:02:02 -0600444def _create_unverified_context(protocol=PROTOCOL_SSLv23, cert_reqs=None,
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500445 check_hostname=False, purpose=Purpose.SERVER_AUTH,
446 certfile=None, keyfile=None,
447 cafile=None, capath=None, cadata=None):
448 """Create a SSLContext object for Python stdlib modules
449
450 All Python stdlib modules shall use this function to create SSLContext
451 objects in order to keep common settings in one place. The configuration
452 is less restrict than create_default_context()'s to increase backward
453 compatibility.
454 """
455 if not isinstance(purpose, _ASN1Object):
456 raise TypeError(purpose)
457
458 context = SSLContext(protocol)
459 # SSLv2 considered harmful.
460 context.options |= OP_NO_SSLv2
Antoine Pitrou95b61642014-10-17 19:28:30 +0200461 # SSLv3 has problematic security and is only required for really old
462 # clients such as IE6 on Windows XP
463 context.options |= OP_NO_SSLv3
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500464
465 if cert_reqs is not None:
466 context.verify_mode = cert_reqs
467 context.check_hostname = check_hostname
468
469 if keyfile and not certfile:
470 raise ValueError("certfile must be specified")
471 if certfile or keyfile:
472 context.load_cert_chain(certfile, keyfile)
473
474 # load CA root certs
475 if cafile or capath or cadata:
476 context.load_verify_locations(cafile, capath, cadata)
477 elif context.verify_mode != CERT_NONE:
478 # no explicit cafile, capath or cadata but the verify mode is
479 # CERT_OPTIONAL or CERT_REQUIRED. Let's try to load default system
480 # root CA certificates for the given purpose. This may fail silently.
481 context.load_default_certs(purpose)
482
483 return context
Antoine Pitroud76088d2012-01-03 22:46:48 +0100484
Benjamin Petersone3e7d402014-11-23 21:02:02 -0600485# Backwards compatibility alias, even though it's not a public name.
486_create_stdlib_context = _create_unverified_context
487
Nick Coghlandbcd4572016-03-20 22:39:15 +1000488# PEP 493: Verify HTTPS by default, but allow envvar to override that
489_https_verify_envvar = 'PYTHONHTTPSVERIFY'
490
491def _get_https_context_factory():
492 if not sys.flags.ignore_environment:
493 config_setting = os.environ.get(_https_verify_envvar)
494 if config_setting == '0':
495 return _create_unverified_context
496 return create_default_context
497
498_create_default_https_context = _get_https_context_factory()
499
500# PEP 493: "private" API to configure HTTPS defaults without monkeypatching
501def _https_verify_certificates(enable=True):
502 """Verify server HTTPS certificates by default?"""
503 global _create_default_https_context
504 if enable:
505 _create_default_https_context = create_default_context
506 else:
507 _create_default_https_context = _create_unverified_context
508
Benjamin Petersone3e7d402014-11-23 21:02:02 -0600509
Ezio Melottib01f5e62010-01-18 09:10:26 +0000510class SSLSocket(socket):
Bill Janssen426ea0a2007-08-29 22:35:05 +0000511 """This class implements a subtype of socket.socket that wraps
512 the underlying OS socket in an SSL context when necessary, and
513 provides read and write methods over that channel."""
514
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500515 def __init__(self, sock=None, keyfile=None, certfile=None,
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +0000516 server_side=False, cert_reqs=CERT_NONE,
Bill Janssen934b16d2008-06-28 22:19:33 +0000517 ssl_version=PROTOCOL_SSLv23, ca_certs=None,
518 do_handshake_on_connect=True,
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500519 family=AF_INET, type=SOCK_STREAM, proto=0, fileno=None,
520 suppress_ragged_eofs=True, npn_protocols=None, ciphers=None,
521 server_hostname=None,
522 _context=None):
523
Benjamin Peterson5f6b89b2014-11-23 11:16:48 -0600524 self._makefile_refs = 0
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500525 if _context:
526 self._context = _context
527 else:
528 if server_side and not certfile:
529 raise ValueError("certfile must be specified for server-side "
530 "operations")
531 if keyfile and not certfile:
532 raise ValueError("certfile must be specified")
533 if certfile and not keyfile:
534 keyfile = certfile
535 self._context = SSLContext(ssl_version)
536 self._context.verify_mode = cert_reqs
537 if ca_certs:
538 self._context.load_verify_locations(ca_certs)
539 if certfile:
540 self._context.load_cert_chain(certfile, keyfile)
541 if npn_protocols:
542 self._context.set_npn_protocols(npn_protocols)
543 if ciphers:
544 self._context.set_ciphers(ciphers)
545 self.keyfile = keyfile
546 self.certfile = certfile
547 self.cert_reqs = cert_reqs
548 self.ssl_version = ssl_version
549 self.ca_certs = ca_certs
550 self.ciphers = ciphers
Antoine Pitrou63cc99d2013-12-28 17:26:33 +0100551 # Can't use sock.type as other flags (such as SOCK_NONBLOCK) get
552 # mixed in.
553 if sock.getsockopt(SOL_SOCKET, SO_TYPE) != SOCK_STREAM:
554 raise NotImplementedError("only stream sockets are supported")
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +0000555 socket.__init__(self, _sock=sock._sock)
Antoine Pitroudfb299b2010-04-23 22:54:59 +0000556 # The initializer for socket overrides the methods send(), recv(), etc.
557 # in the instancce, which we don't need -- but we want to provide the
558 # methods defined in SSLSocket.
559 for attr in _delegate_methods:
560 try:
561 delattr(self, attr)
562 except AttributeError:
563 pass
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500564 if server_side and server_hostname:
565 raise ValueError("server_hostname can only be specified "
566 "in client mode")
567 if self._context.check_hostname and not server_hostname:
Benjamin Peterson31aa69e2014-11-23 20:13:31 -0600568 raise ValueError("check_hostname requires server_hostname")
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500569 self.server_side = server_side
570 self.server_hostname = server_hostname
Bill Janssen934b16d2008-06-28 22:19:33 +0000571 self.do_handshake_on_connect = do_handshake_on_connect
572 self.suppress_ragged_eofs = suppress_ragged_eofs
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500573
574 # See if we are connected
575 try:
576 self.getpeername()
577 except socket_error as e:
578 if e.errno != errno.ENOTCONN:
579 raise
580 connected = False
581 else:
582 connected = True
583
584 self._closed = False
585 self._sslobj = None
586 self._connected = connected
587 if connected:
588 # create the SSL object
589 try:
590 self._sslobj = self._context._wrap_socket(self._sock, server_side,
591 server_hostname, ssl_sock=self)
592 if do_handshake_on_connect:
593 timeout = self.gettimeout()
594 if timeout == 0.0:
595 # non-blocking
596 raise ValueError("do_handshake_on_connect should not be specified for non-blocking sockets")
597 self.do_handshake()
598
599 except (OSError, ValueError):
600 self.close()
601 raise
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +0000602
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500603 @property
604 def context(self):
605 return self._context
Bill Janssen24bccf22007-08-30 17:07:28 +0000606
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500607 @context.setter
608 def context(self, ctx):
609 self._context = ctx
610 self._sslobj.context = ctx
611
612 def dup(self):
613 raise NotImplemented("Can't dup() %s instances" %
614 self.__class__.__name__)
615
616 def _checkClosed(self, msg=None):
617 # raise an exception here if you wish to check for spurious closes
618 pass
619
620 def _check_connected(self):
621 if not self._connected:
622 # getpeername() will raise ENOTCONN if the socket is really
623 # not connected; note that we can be connected even without
624 # _connected being set, e.g. if connect() first returned
625 # EAGAIN.
626 self.getpeername()
627
Martin Panterd524b702016-03-28 00:22:09 +0000628 def read(self, len=1024, buffer=None):
Bill Janssen24bccf22007-08-30 17:07:28 +0000629 """Read up to LEN bytes and return them.
630 Return zero-length string on EOF."""
631
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500632 self._checkClosed()
633 if not self._sslobj:
634 raise ValueError("Read on closed or unwrapped SSL socket.")
Bill Janssen934b16d2008-06-28 22:19:33 +0000635 try:
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500636 if buffer is not None:
637 v = self._sslobj.read(len, buffer)
638 else:
Martin Panterd524b702016-03-28 00:22:09 +0000639 v = self._sslobj.read(len)
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500640 return v
641 except SSLError as x:
Bill Janssen934b16d2008-06-28 22:19:33 +0000642 if x.args[0] == SSL_ERROR_EOF and self.suppress_ragged_eofs:
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500643 if buffer is not None:
644 return 0
645 else:
646 return b''
Bill Janssen934b16d2008-06-28 22:19:33 +0000647 else:
648 raise
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +0000649
650 def write(self, data):
Bill Janssen24bccf22007-08-30 17:07:28 +0000651 """Write DATA to the underlying SSL channel. Returns
652 number of bytes of DATA actually transmitted."""
653
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500654 self._checkClosed()
655 if not self._sslobj:
656 raise ValueError("Write on closed or unwrapped SSL socket.")
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +0000657 return self._sslobj.write(data)
658
Bill Janssen98d19da2007-09-10 21:51:02 +0000659 def getpeercert(self, binary_form=False):
Bill Janssen24bccf22007-08-30 17:07:28 +0000660 """Returns a formatted version of the data in the
661 certificate provided by the other end of the SSL channel.
662 Return None if no certificate was provided, {} if a
663 certificate was provided, but not validated."""
664
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500665 self._checkClosed()
666 self._check_connected()
Bill Janssen98d19da2007-09-10 21:51:02 +0000667 return self._sslobj.peer_certificate(binary_form)
668
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500669 def selected_npn_protocol(self):
670 self._checkClosed()
671 if not self._sslobj or not _ssl.HAS_NPN:
672 return None
673 else:
674 return self._sslobj.selected_npn_protocol()
Bill Janssen98d19da2007-09-10 21:51:02 +0000675
Benjamin Petersonb10bfbe2015-01-23 16:35:37 -0500676 def selected_alpn_protocol(self):
677 self._checkClosed()
678 if not self._sslobj or not _ssl.HAS_ALPN:
679 return None
680 else:
681 return self._sslobj.selected_alpn_protocol()
682
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500683 def cipher(self):
684 self._checkClosed()
Bill Janssen98d19da2007-09-10 21:51:02 +0000685 if not self._sslobj:
686 return None
687 else:
688 return self._sslobj.cipher()
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +0000689
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500690 def compression(self):
691 self._checkClosed()
692 if not self._sslobj:
693 return None
694 else:
695 return self._sslobj.compression()
696
Ezio Melottib01f5e62010-01-18 09:10:26 +0000697 def send(self, data, flags=0):
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500698 self._checkClosed()
Bill Janssen426ea0a2007-08-29 22:35:05 +0000699 if self._sslobj:
700 if flags != 0:
701 raise ValueError(
702 "non-zero flags not allowed in calls to send() on %s" %
703 self.__class__)
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500704 try:
705 v = self._sslobj.write(data)
706 except SSLError as x:
707 if x.args[0] == SSL_ERROR_WANT_READ:
708 return 0
709 elif x.args[0] == SSL_ERROR_WANT_WRITE:
710 return 0
Bill Janssen934b16d2008-06-28 22:19:33 +0000711 else:
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500712 raise
713 else:
714 return v
Bill Janssen426ea0a2007-08-29 22:35:05 +0000715 else:
Antoine Pitrouf7f390a2010-09-14 14:37:18 +0000716 return self._sock.send(data, flags)
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +0000717
Antoine Pitrouf7f390a2010-09-14 14:37:18 +0000718 def sendto(self, data, flags_or_addr, addr=None):
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500719 self._checkClosed()
Bill Janssen426ea0a2007-08-29 22:35:05 +0000720 if self._sslobj:
Bill Janssen934b16d2008-06-28 22:19:33 +0000721 raise ValueError("sendto not allowed on instances of %s" %
Bill Janssen426ea0a2007-08-29 22:35:05 +0000722 self.__class__)
Antoine Pitrouf7f390a2010-09-14 14:37:18 +0000723 elif addr is None:
724 return self._sock.sendto(data, flags_or_addr)
Bill Janssen426ea0a2007-08-29 22:35:05 +0000725 else:
Antoine Pitrouf7f390a2010-09-14 14:37:18 +0000726 return self._sock.sendto(data, flags_or_addr, addr)
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +0000727
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500728
Ezio Melottib01f5e62010-01-18 09:10:26 +0000729 def sendall(self, data, flags=0):
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500730 self._checkClosed()
Bill Janssen426ea0a2007-08-29 22:35:05 +0000731 if self._sslobj:
732 if flags != 0:
733 raise ValueError(
734 "non-zero flags not allowed in calls to sendall() on %s" %
735 self.__class__)
Bill Janssen934b16d2008-06-28 22:19:33 +0000736 amount = len(data)
737 count = 0
738 while (count < amount):
739 v = self.send(data[count:])
740 count += v
741 return amount
Bill Janssen426ea0a2007-08-29 22:35:05 +0000742 else:
743 return socket.sendall(self, data, flags)
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +0000744
Ezio Melottib01f5e62010-01-18 09:10:26 +0000745 def recv(self, buflen=1024, flags=0):
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500746 self._checkClosed()
Bill Janssen426ea0a2007-08-29 22:35:05 +0000747 if self._sslobj:
748 if flags != 0:
749 raise ValueError(
Antoine Pitrou448da712010-03-21 19:33:38 +0000750 "non-zero flags not allowed in calls to recv() on %s" %
Bill Janssen426ea0a2007-08-29 22:35:05 +0000751 self.__class__)
Antoine Pitrou448da712010-03-21 19:33:38 +0000752 return self.read(buflen)
Bill Janssen426ea0a2007-08-29 22:35:05 +0000753 else:
Antoine Pitrouf7f390a2010-09-14 14:37:18 +0000754 return self._sock.recv(buflen, flags)
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +0000755
Ezio Melottib01f5e62010-01-18 09:10:26 +0000756 def recv_into(self, buffer, nbytes=None, flags=0):
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500757 self._checkClosed()
Bill Janssen61c001a2008-09-08 16:37:24 +0000758 if buffer and (nbytes is None):
759 nbytes = len(buffer)
760 elif nbytes is None:
761 nbytes = 1024
762 if self._sslobj:
763 if flags != 0:
764 raise ValueError(
765 "non-zero flags not allowed in calls to recv_into() on %s" %
766 self.__class__)
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500767 return self.read(nbytes, buffer)
Bill Janssen61c001a2008-09-08 16:37:24 +0000768 else:
Antoine Pitrouf7f390a2010-09-14 14:37:18 +0000769 return self._sock.recv_into(buffer, nbytes, flags)
Bill Janssen61c001a2008-09-08 16:37:24 +0000770
Antoine Pitrouf7f390a2010-09-14 14:37:18 +0000771 def recvfrom(self, buflen=1024, flags=0):
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500772 self._checkClosed()
Bill Janssen426ea0a2007-08-29 22:35:05 +0000773 if self._sslobj:
Bill Janssen934b16d2008-06-28 22:19:33 +0000774 raise ValueError("recvfrom not allowed on instances of %s" %
Bill Janssen426ea0a2007-08-29 22:35:05 +0000775 self.__class__)
776 else:
Antoine Pitrouf7f390a2010-09-14 14:37:18 +0000777 return self._sock.recvfrom(buflen, flags)
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +0000778
Ezio Melottib01f5e62010-01-18 09:10:26 +0000779 def recvfrom_into(self, buffer, nbytes=None, flags=0):
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500780 self._checkClosed()
Bill Janssen61c001a2008-09-08 16:37:24 +0000781 if self._sslobj:
782 raise ValueError("recvfrom_into not allowed on instances of %s" %
783 self.__class__)
784 else:
Antoine Pitrouf7f390a2010-09-14 14:37:18 +0000785 return self._sock.recvfrom_into(buffer, nbytes, flags)
Bill Janssen61c001a2008-09-08 16:37:24 +0000786
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500787
Ezio Melottib01f5e62010-01-18 09:10:26 +0000788 def pending(self):
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500789 self._checkClosed()
Bill Janssen934b16d2008-06-28 22:19:33 +0000790 if self._sslobj:
791 return self._sslobj.pending()
792 else:
793 return 0
794
Ezio Melottib01f5e62010-01-18 09:10:26 +0000795 def shutdown(self, how):
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500796 self._checkClosed()
Bill Janssen296a59d2007-09-16 22:06:00 +0000797 self._sslobj = None
Bill Janssen426ea0a2007-08-29 22:35:05 +0000798 socket.shutdown(self, how)
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +0000799
Ezio Melottib01f5e62010-01-18 09:10:26 +0000800 def close(self):
Bill Janssen934b16d2008-06-28 22:19:33 +0000801 if self._makefile_refs < 1:
802 self._sslobj = None
803 socket.close(self)
804 else:
805 self._makefile_refs -= 1
806
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500807 def unwrap(self):
808 if self._sslobj:
809 s = self._sslobj.shutdown()
810 self._sslobj = None
811 return s
812 else:
813 raise ValueError("No SSL wrapper around " + str(self))
Bill Janssen934b16d2008-06-28 22:19:33 +0000814
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500815 def _real_close(self):
816 self._sslobj = None
817 socket._real_close(self)
818
819 def do_handshake(self, block=False):
Bill Janssen934b16d2008-06-28 22:19:33 +0000820 """Perform a TLS/SSL handshake."""
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500821 self._check_connected()
822 timeout = self.gettimeout()
823 try:
824 if timeout == 0.0 and block:
825 self.settimeout(None)
826 self._sslobj.do_handshake()
827 finally:
828 self.settimeout(timeout)
Bill Janssen934b16d2008-06-28 22:19:33 +0000829
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500830 if self.context.check_hostname:
831 if not self.server_hostname:
832 raise ValueError("check_hostname needs server_hostname "
833 "argument")
834 match_hostname(self.getpeercert(), self.server_hostname)
Bill Janssen934b16d2008-06-28 22:19:33 +0000835
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500836 def _real_connect(self, addr, connect_ex):
837 if self.server_side:
838 raise ValueError("can't connect in server-side mode")
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +0000839 # Here we assume that the socket is client-side, and not
840 # connected at the time of the call. We connect it, then wrap it.
Antoine Pitroud3f6ea12011-02-26 23:35:27 +0000841 if self._connected:
Bill Janssen98d19da2007-09-10 21:51:02 +0000842 raise ValueError("attempt to connect already-connected SSLSocket!")
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500843 self._sslobj = self.context._wrap_socket(self._sock, False, self.server_hostname, ssl_sock=self)
Antoine Pitroud3f6ea12011-02-26 23:35:27 +0000844 try:
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500845 if connect_ex:
Antoine Pitrou40f12ab2012-12-28 19:03:43 +0100846 rc = socket.connect_ex(self, addr)
Antoine Pitroud3f6ea12011-02-26 23:35:27 +0000847 else:
Antoine Pitrou40f12ab2012-12-28 19:03:43 +0100848 rc = None
849 socket.connect(self, addr)
850 if not rc:
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500851 self._connected = True
Antoine Pitrou40f12ab2012-12-28 19:03:43 +0100852 if self.do_handshake_on_connect:
853 self.do_handshake()
Antoine Pitrou40f12ab2012-12-28 19:03:43 +0100854 return rc
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500855 except (OSError, ValueError):
Antoine Pitrou40f12ab2012-12-28 19:03:43 +0100856 self._sslobj = None
857 raise
Antoine Pitroud3f6ea12011-02-26 23:35:27 +0000858
859 def connect(self, addr):
860 """Connects to remote ADDR, and then wraps the connection in
861 an SSL channel."""
862 self._real_connect(addr, False)
863
864 def connect_ex(self, addr):
865 """Connects to remote ADDR, and then wraps the connection in
866 an SSL channel."""
867 return self._real_connect(addr, True)
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +0000868
869 def accept(self):
Bill Janssen24bccf22007-08-30 17:07:28 +0000870 """Accepts a new connection from a remote client, and returns
871 a tuple containing that new connection wrapped with a server-side
872 SSL channel, and the address of the remote client."""
873
Bill Janssen426ea0a2007-08-29 22:35:05 +0000874 newsock, addr = socket.accept(self)
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500875 newsock = self.context.wrap_socket(newsock,
876 do_handshake_on_connect=self.do_handshake_on_connect,
877 suppress_ragged_eofs=self.suppress_ragged_eofs,
878 server_side=True)
879 return newsock, addr
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +0000880
Bill Janssen296a59d2007-09-16 22:06:00 +0000881 def makefile(self, mode='r', bufsize=-1):
882
Bill Janssen61c001a2008-09-08 16:37:24 +0000883 """Make and return a file-like object that
884 works with the SSL connection. Just use the code
885 from the socket module."""
Bill Janssen296a59d2007-09-16 22:06:00 +0000886
Bill Janssen934b16d2008-06-28 22:19:33 +0000887 self._makefile_refs += 1
Antoine Pitroub558f172010-04-23 23:25:45 +0000888 # close=True so as to decrement the reference count when done with
889 # the file-like object.
890 return _fileobject(self, mode, bufsize, close=True)
Bill Janssen296a59d2007-09-16 22:06:00 +0000891
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500892 def get_channel_binding(self, cb_type="tls-unique"):
893 """Get channel binding data for current connection. Raise ValueError
894 if the requested `cb_type` is not supported. Return bytes of the data
895 or None if the data is not available (e.g. before the handshake).
896 """
897 if cb_type not in CHANNEL_BINDING_TYPES:
898 raise ValueError("Unsupported channel binding type")
899 if cb_type != "tls-unique":
900 raise NotImplementedError(
901 "{0} channel binding type not implemented"
902 .format(cb_type))
903 if self._sslobj is None:
904 return None
905 return self._sslobj.tls_unique_cb()
Bill Janssen296a59d2007-09-16 22:06:00 +0000906
Alex Gaynore98205d2014-09-04 13:33:22 -0700907 def version(self):
908 """
909 Return a string identifying the protocol version used by the
910 current SSL channel, or None if there is no established channel.
911 """
912 if self._sslobj is None:
913 return None
914 return self._sslobj.version()
915
Bill Janssen296a59d2007-09-16 22:06:00 +0000916
Bill Janssen98d19da2007-09-10 21:51:02 +0000917def wrap_socket(sock, keyfile=None, certfile=None,
918 server_side=False, cert_reqs=CERT_NONE,
Bill Janssen934b16d2008-06-28 22:19:33 +0000919 ssl_version=PROTOCOL_SSLv23, ca_certs=None,
920 do_handshake_on_connect=True,
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500921 suppress_ragged_eofs=True,
922 ciphers=None):
Bill Janssen98d19da2007-09-10 21:51:02 +0000923
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500924 return SSLSocket(sock=sock, keyfile=keyfile, certfile=certfile,
Bill Janssen98d19da2007-09-10 21:51:02 +0000925 server_side=server_side, cert_reqs=cert_reqs,
Bill Janssen934b16d2008-06-28 22:19:33 +0000926 ssl_version=ssl_version, ca_certs=ca_certs,
927 do_handshake_on_connect=do_handshake_on_connect,
Antoine Pitrou0a6373c2010-04-17 17:10:38 +0000928 suppress_ragged_eofs=suppress_ragged_eofs,
929 ciphers=ciphers)
Bill Janssen934b16d2008-06-28 22:19:33 +0000930
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +0000931# some utility functions
932
933def cert_time_to_seconds(cert_time):
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500934 """Return the time in seconds since the Epoch, given the timestring
935 representing the "notBefore" or "notAfter" date from a certificate
936 in ``"%b %d %H:%M:%S %Y %Z"`` strptime format (C locale).
Bill Janssen24bccf22007-08-30 17:07:28 +0000937
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500938 "notBefore" or "notAfter" dates must use UTC (RFC 5280).
Bill Janssen24bccf22007-08-30 17:07:28 +0000939
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500940 Month is one of: Jan Feb Mar Apr May Jun Jul Aug Sep Oct Nov Dec
941 UTC should be specified as GMT (see ASN1_TIME_print())
942 """
943 from time import strptime
944 from calendar import timegm
945
946 months = (
947 "Jan","Feb","Mar","Apr","May","Jun",
948 "Jul","Aug","Sep","Oct","Nov","Dec"
949 )
950 time_format = ' %d %H:%M:%S %Y GMT' # NOTE: no month, fixed GMT
951 try:
952 month_number = months.index(cert_time[:3].title()) + 1
953 except ValueError:
954 raise ValueError('time data %r does not match '
955 'format "%%b%s"' % (cert_time, time_format))
956 else:
957 # found valid month
958 tt = strptime(cert_time[3:], time_format)
959 # return an integer, the previous mktime()-based implementation
960 # returned a float (fractional seconds are always zero here).
961 return timegm((tt[0], month_number) + tt[2:6])
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +0000962
Bill Janssen296a59d2007-09-16 22:06:00 +0000963PEM_HEADER = "-----BEGIN CERTIFICATE-----"
964PEM_FOOTER = "-----END CERTIFICATE-----"
965
966def DER_cert_to_PEM_cert(der_cert_bytes):
Bill Janssen296a59d2007-09-16 22:06:00 +0000967 """Takes a certificate in binary DER format and returns the
968 PEM version of it as a string."""
969
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500970 f = base64.standard_b64encode(der_cert_bytes).decode('ascii')
971 return (PEM_HEADER + '\n' +
972 textwrap.fill(f, 64) + '\n' +
973 PEM_FOOTER + '\n')
Bill Janssen296a59d2007-09-16 22:06:00 +0000974
975def PEM_cert_to_DER_cert(pem_cert_string):
Bill Janssen296a59d2007-09-16 22:06:00 +0000976 """Takes a certificate in ASCII PEM format and returns the
977 DER-encoded version of it as a byte sequence"""
978
979 if not pem_cert_string.startswith(PEM_HEADER):
980 raise ValueError("Invalid PEM encoding; must start with %s"
981 % PEM_HEADER)
982 if not pem_cert_string.strip().endswith(PEM_FOOTER):
983 raise ValueError("Invalid PEM encoding; must end with %s"
984 % PEM_FOOTER)
985 d = pem_cert_string.strip()[len(PEM_HEADER):-len(PEM_FOOTER)]
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500986 return base64.decodestring(d.encode('ASCII', 'strict'))
Bill Janssen296a59d2007-09-16 22:06:00 +0000987
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500988def get_server_certificate(addr, ssl_version=PROTOCOL_SSLv23, ca_certs=None):
Bill Janssen296a59d2007-09-16 22:06:00 +0000989 """Retrieve the certificate from the server at the specified address,
990 and return it as a PEM-encoded string.
991 If 'ca_certs' is specified, validate the server cert against it.
992 If 'ssl_version' is specified, use it in the connection attempt."""
993
994 host, port = addr
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500995 if ca_certs is not None:
Bill Janssen296a59d2007-09-16 22:06:00 +0000996 cert_reqs = CERT_REQUIRED
997 else:
998 cert_reqs = CERT_NONE
Benjamin Petersondaeb9252014-08-20 14:14:50 -0500999 context = _create_stdlib_context(ssl_version,
1000 cert_reqs=cert_reqs,
1001 cafile=ca_certs)
1002 with closing(create_connection(addr)) as sock:
1003 with closing(context.wrap_socket(sock)) as sslsock:
1004 dercert = sslsock.getpeercert(True)
Bill Janssen296a59d2007-09-16 22:06:00 +00001005 return DER_cert_to_PEM_cert(dercert)
1006
Ezio Melottib01f5e62010-01-18 09:10:26 +00001007def get_protocol_name(protocol_code):
Victor Stinnerb1241f92011-05-10 01:52:03 +02001008 return _PROTOCOL_NAMES.get(protocol_code, '<unknown>')
Bill Janssen296a59d2007-09-16 22:06:00 +00001009
1010
Guido van Rossum4f2c3dd2007-08-25 15:08:43 +00001011# a replacement for the old socket.ssl function
1012
Ezio Melottib01f5e62010-01-18 09:10:26 +00001013def sslwrap_simple(sock, keyfile=None, certfile=None):
Bill Janssen24bccf22007-08-30 17:07:28 +00001014 """A replacement for the old socket.ssl function. Designed
1015 for compability with Python 2.5 and earlier. Will disappear in
1016 Python 3.0."""
Bill Jansseneb257ac2008-09-29 18:56:38 +00001017 if hasattr(sock, "_sock"):
1018 sock = sock._sock
1019
Benjamin Peterson2f334562014-10-01 23:53:01 -04001020 ctx = SSLContext(PROTOCOL_SSLv23)
1021 if keyfile or certfile:
1022 ctx.load_cert_chain(certfile, keyfile)
1023 ssl_sock = ctx._wrap_socket(sock, server_side=False)
Bill Jansseneb257ac2008-09-29 18:56:38 +00001024 try:
1025 sock.getpeername()
Benjamin Peterson941db4d2008-12-31 04:08:55 +00001026 except socket_error:
Bill Jansseneb257ac2008-09-29 18:56:38 +00001027 # no, no connection yet
1028 pass
1029 else:
1030 # yes, do the handshake
1031 ssl_sock.do_handshake()
1032
Bill Janssen934b16d2008-06-28 22:19:33 +00001033 return ssl_sock