blob: dc4ed3999cc3bb583dd076a84377d6b40ce9ea18 [file] [log] [blame]
Abraham Martind2f0b072015-03-25 13:56:25 +00001from sys import platform
Jean-Paul Calderonec86bb7d2013-12-29 10:25:59 -05002from functools import wraps, partial
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08003from itertools import count
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08004from weakref import WeakValueDictionary
5from errno import errorcode
Jean-Paul Calderone935d2da2013-03-04 08:11:19 -08006
Jean-Paul Calderone63eab692014-01-18 10:19:56 -05007from six import text_type as _text_type
Konstantinos Koukopoulosc8b13ea2014-01-28 00:21:50 -08008from six import integer_types as integer_types
Jean-Paul Calderone63eab692014-01-18 10:19:56 -05009
Jean-Paul Calderonec86bb7d2013-12-29 10:25:59 -050010from OpenSSL._util import (
11 ffi as _ffi,
12 lib as _lib,
Jean-Paul Calderone4f0467a2014-01-11 11:58:41 -050013 exception_from_error_queue as _exception_from_error_queue,
Jean-Paul Calderone6462b072015-03-29 07:03:11 -040014 native as _native,
15 warn_text as _warn_text)
Jean-Paul Calderone935d2da2013-03-04 08:11:19 -080016
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -080017from OpenSSL.crypto import (
Jean-Paul Calderonec86bb7d2013-12-29 10:25:59 -050018 FILETYPE_PEM, _PassphraseHelper, PKey, X509Name, X509, X509Store)
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -080019
20_unspecified = object()
21
Jean-Paul Calderone8fb53182013-12-30 08:35:49 -050022try:
23 _memoryview = memoryview
24except NameError:
25 class _memoryview(object):
26 pass
27
Markus Unterwaditzer8e41d022014-04-19 12:27:11 +020028try:
29 _buffer = buffer
30except NameError:
31 class _buffer(object):
32 pass
33
Jean-Paul Calderone6037d072013-12-28 18:04:00 -050034OPENSSL_VERSION_NUMBER = _lib.OPENSSL_VERSION_NUMBER
35SSLEAY_VERSION = _lib.SSLEAY_VERSION
36SSLEAY_CFLAGS = _lib.SSLEAY_CFLAGS
37SSLEAY_PLATFORM = _lib.SSLEAY_PLATFORM
38SSLEAY_DIR = _lib.SSLEAY_DIR
39SSLEAY_BUILT_ON = _lib.SSLEAY_BUILT_ON
Jean-Paul Calderone935d2da2013-03-04 08:11:19 -080040
Jean-Paul Calderone6037d072013-12-28 18:04:00 -050041SENT_SHUTDOWN = _lib.SSL_SENT_SHUTDOWN
42RECEIVED_SHUTDOWN = _lib.SSL_RECEIVED_SHUTDOWN
Jean-Paul Calderone935d2da2013-03-04 08:11:19 -080043
44SSLv2_METHOD = 1
45SSLv3_METHOD = 2
46SSLv23_METHOD = 3
47TLSv1_METHOD = 4
Jean-Paul Calderone56bff942013-11-03 11:30:43 -050048TLSv1_1_METHOD = 5
49TLSv1_2_METHOD = 6
Jean-Paul Calderone935d2da2013-03-04 08:11:19 -080050
Jean-Paul Calderone6037d072013-12-28 18:04:00 -050051OP_NO_SSLv2 = _lib.SSL_OP_NO_SSLv2
52OP_NO_SSLv3 = _lib.SSL_OP_NO_SSLv3
53OP_NO_TLSv1 = _lib.SSL_OP_NO_TLSv1
Jean-Paul Calderonebe2bb422013-12-29 07:34:08 -050054
55OP_NO_TLSv1_1 = getattr(_lib, "SSL_OP_NO_TLSv1_1", 0)
56OP_NO_TLSv1_2 = getattr(_lib, "SSL_OP_NO_TLSv1_2", 0)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -080057
Jean-Paul Calderone0d7e8a12014-01-08 16:54:13 -050058try:
59 MODE_RELEASE_BUFFERS = _lib.SSL_MODE_RELEASE_BUFFERS
60except AttributeError:
61 pass
Jean-Paul Calderone935d2da2013-03-04 08:11:19 -080062
Jean-Paul Calderone6037d072013-12-28 18:04:00 -050063OP_SINGLE_DH_USE = _lib.SSL_OP_SINGLE_DH_USE
64OP_EPHEMERAL_RSA = _lib.SSL_OP_EPHEMERAL_RSA
65OP_MICROSOFT_SESS_ID_BUG = _lib.SSL_OP_MICROSOFT_SESS_ID_BUG
66OP_NETSCAPE_CHALLENGE_BUG = _lib.SSL_OP_NETSCAPE_CHALLENGE_BUG
67OP_NETSCAPE_REUSE_CIPHER_CHANGE_BUG = _lib.SSL_OP_NETSCAPE_REUSE_CIPHER_CHANGE_BUG
68OP_SSLREF2_REUSE_CERT_TYPE_BUG = _lib.SSL_OP_SSLREF2_REUSE_CERT_TYPE_BUG
69OP_MICROSOFT_BIG_SSLV3_BUFFER = _lib.SSL_OP_MICROSOFT_BIG_SSLV3_BUFFER
Jean-Paul Calderone0d7e8a12014-01-08 16:54:13 -050070try:
71 OP_MSIE_SSLV2_RSA_PADDING = _lib.SSL_OP_MSIE_SSLV2_RSA_PADDING
72except AttributeError:
73 pass
Jean-Paul Calderone6037d072013-12-28 18:04:00 -050074OP_SSLEAY_080_CLIENT_DH_BUG = _lib.SSL_OP_SSLEAY_080_CLIENT_DH_BUG
75OP_TLS_D5_BUG = _lib.SSL_OP_TLS_D5_BUG
76OP_TLS_BLOCK_PADDING_BUG = _lib.SSL_OP_TLS_BLOCK_PADDING_BUG
77OP_DONT_INSERT_EMPTY_FRAGMENTS = _lib.SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS
78OP_CIPHER_SERVER_PREFERENCE = _lib.SSL_OP_CIPHER_SERVER_PREFERENCE
79OP_TLS_ROLLBACK_BUG = _lib.SSL_OP_TLS_ROLLBACK_BUG
80OP_PKCS1_CHECK_1 = _lib.SSL_OP_PKCS1_CHECK_1
81OP_PKCS1_CHECK_2 = _lib.SSL_OP_PKCS1_CHECK_2
82OP_NETSCAPE_CA_DN_BUG = _lib.SSL_OP_NETSCAPE_CA_DN_BUG
83OP_NETSCAPE_DEMO_CIPHER_CHANGE_BUG= _lib.SSL_OP_NETSCAPE_DEMO_CIPHER_CHANGE_BUG
Jean-Paul Calderonec1780342014-01-08 16:59:03 -050084try:
85 OP_NO_COMPRESSION = _lib.SSL_OP_NO_COMPRESSION
86except AttributeError:
87 pass
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -080088
Jean-Paul Calderone6037d072013-12-28 18:04:00 -050089OP_NO_QUERY_MTU = _lib.SSL_OP_NO_QUERY_MTU
90OP_COOKIE_EXCHANGE = _lib.SSL_OP_COOKIE_EXCHANGE
Arturo Filastò5f8c7a82014-03-09 20:01:25 +010091try:
92 OP_NO_TICKET = _lib.SSL_OP_NO_TICKET
93except AttributeError:
94 pass
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -080095
Jean-Paul Calderone6037d072013-12-28 18:04:00 -050096OP_ALL = _lib.SSL_OP_ALL
Jean-Paul Calderone935d2da2013-03-04 08:11:19 -080097
Jean-Paul Calderone6037d072013-12-28 18:04:00 -050098VERIFY_PEER = _lib.SSL_VERIFY_PEER
99VERIFY_FAIL_IF_NO_PEER_CERT = _lib.SSL_VERIFY_FAIL_IF_NO_PEER_CERT
100VERIFY_CLIENT_ONCE = _lib.SSL_VERIFY_CLIENT_ONCE
101VERIFY_NONE = _lib.SSL_VERIFY_NONE
Jean-Paul Calderone935d2da2013-03-04 08:11:19 -0800102
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500103SESS_CACHE_OFF = _lib.SSL_SESS_CACHE_OFF
104SESS_CACHE_CLIENT = _lib.SSL_SESS_CACHE_CLIENT
105SESS_CACHE_SERVER = _lib.SSL_SESS_CACHE_SERVER
106SESS_CACHE_BOTH = _lib.SSL_SESS_CACHE_BOTH
107SESS_CACHE_NO_AUTO_CLEAR = _lib.SSL_SESS_CACHE_NO_AUTO_CLEAR
108SESS_CACHE_NO_INTERNAL_LOOKUP = _lib.SSL_SESS_CACHE_NO_INTERNAL_LOOKUP
109SESS_CACHE_NO_INTERNAL_STORE = _lib.SSL_SESS_CACHE_NO_INTERNAL_STORE
110SESS_CACHE_NO_INTERNAL = _lib.SSL_SESS_CACHE_NO_INTERNAL
Jean-Paul Calderoned39a3f62013-03-04 12:23:51 -0800111
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500112SSL_ST_CONNECT = _lib.SSL_ST_CONNECT
113SSL_ST_ACCEPT = _lib.SSL_ST_ACCEPT
114SSL_ST_MASK = _lib.SSL_ST_MASK
115SSL_ST_INIT = _lib.SSL_ST_INIT
116SSL_ST_BEFORE = _lib.SSL_ST_BEFORE
117SSL_ST_OK = _lib.SSL_ST_OK
118SSL_ST_RENEGOTIATE = _lib.SSL_ST_RENEGOTIATE
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800119
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500120SSL_CB_LOOP = _lib.SSL_CB_LOOP
121SSL_CB_EXIT = _lib.SSL_CB_EXIT
122SSL_CB_READ = _lib.SSL_CB_READ
123SSL_CB_WRITE = _lib.SSL_CB_WRITE
124SSL_CB_ALERT = _lib.SSL_CB_ALERT
125SSL_CB_READ_ALERT = _lib.SSL_CB_READ_ALERT
126SSL_CB_WRITE_ALERT = _lib.SSL_CB_WRITE_ALERT
127SSL_CB_ACCEPT_LOOP = _lib.SSL_CB_ACCEPT_LOOP
128SSL_CB_ACCEPT_EXIT = _lib.SSL_CB_ACCEPT_EXIT
129SSL_CB_CONNECT_LOOP = _lib.SSL_CB_CONNECT_LOOP
130SSL_CB_CONNECT_EXIT = _lib.SSL_CB_CONNECT_EXIT
131SSL_CB_HANDSHAKE_START = _lib.SSL_CB_HANDSHAKE_START
132SSL_CB_HANDSHAKE_DONE = _lib.SSL_CB_HANDSHAKE_DONE
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800133
Jean-Paul Calderonec86bb7d2013-12-29 10:25:59 -0500134class Error(Exception):
Jean-Paul Calderone511cde02013-12-29 10:31:13 -0500135 """
136 An error occurred in an `OpenSSL.SSL` API.
137 """
Jean-Paul Calderonec86bb7d2013-12-29 10:25:59 -0500138
139
140
141_raise_current_error = partial(_exception_from_error_queue, Error)
142
143
144class WantReadError(Error):
145 pass
146
147
148
149class WantWriteError(Error):
150 pass
151
152
153
154class WantX509LookupError(Error):
155 pass
156
157
158
159class ZeroReturnError(Error):
160 pass
161
162
163
164class SysCallError(Error):
165 pass
166
167
168
Jean-Paul Calderone7e166fe2013-03-06 20:54:38 -0800169class _VerifyHelper(object):
Jean-Paul Calderone6a8cd112014-04-02 21:09:08 -0400170 def __init__(self, callback):
Jean-Paul Calderone7e166fe2013-03-06 20:54:38 -0800171 self._problems = []
172
173 @wraps(callback)
174 def wrapper(ok, store_ctx):
175 cert = X509.__new__(X509)
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500176 cert._x509 = _lib.X509_STORE_CTX_get_current_cert(store_ctx)
177 error_number = _lib.X509_STORE_CTX_get_error(store_ctx)
178 error_depth = _lib.X509_STORE_CTX_get_error_depth(store_ctx)
Jean-Paul Calderone7e166fe2013-03-06 20:54:38 -0800179
Jean-Paul Calderone6a8cd112014-04-02 21:09:08 -0400180 index = _lib.SSL_get_ex_data_X509_STORE_CTX_idx()
181 ssl = _lib.X509_STORE_CTX_get_ex_data(store_ctx, index)
182 connection = Connection._reverse_mapping[ssl]
183
Jean-Paul Calderone7e166fe2013-03-06 20:54:38 -0800184 try:
185 result = callback(connection, cert, error_number, error_depth, ok)
186 except Exception as e:
187 self._problems.append(e)
188 return 0
189 else:
190 if result:
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500191 _lib.X509_STORE_CTX_set_error(store_ctx, _lib.X509_V_OK)
Jean-Paul Calderone7e166fe2013-03-06 20:54:38 -0800192 return 1
193 else:
194 return 0
195
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500196 self.callback = _ffi.callback(
197 "int (*)(int, X509_STORE_CTX *)", wrapper)
Jean-Paul Calderone7e166fe2013-03-06 20:54:38 -0800198
199
200 def raise_if_problem(self):
201 if self._problems:
202 try:
Jean-Paul Calderonec86bb7d2013-12-29 10:25:59 -0500203 _raise_current_error()
Jean-Paul Calderone7e166fe2013-03-06 20:54:38 -0800204 except Error:
205 pass
206 raise self._problems.pop(0)
207
208
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800209
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800210def _asFileDescriptor(obj):
211 fd = None
Konstantinos Koukopoulosc8b13ea2014-01-28 00:21:50 -0800212 if not isinstance(obj, integer_types):
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800213 meth = getattr(obj, "fileno", None)
214 if meth is not None:
215 obj = meth()
216
Konstantinos Koukopoulosc8b13ea2014-01-28 00:21:50 -0800217 if isinstance(obj, integer_types):
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800218 fd = obj
219
Konstantinos Koukopoulosc8b13ea2014-01-28 00:21:50 -0800220 if not isinstance(fd, integer_types):
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800221 raise TypeError("argument must be an int, or have a fileno() method.")
222 elif fd < 0:
223 raise ValueError(
224 "file descriptor cannot be a negative integer (%i)" % (fd,))
225
226 return fd
227
228
229
Jean-Paul Calderoned39a3f62013-03-04 12:23:51 -0800230def SSLeay_version(type):
231 """
232 Return a string describing the version of OpenSSL in use.
233
234 :param type: One of the SSLEAY_ constants defined in this module.
235 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500236 return _ffi.string(_lib.SSLeay_version(type))
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800237
238
239
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800240class Session(object):
241 pass
242
243
244
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800245class Context(object):
246 """
247 :py:obj:`OpenSSL.SSL.Context` instances define the parameters for setting up
248 new SSL connections.
249 """
250 _methods = {
Andrew Dunhamec84a0a2014-02-24 12:41:37 -0800251 SSLv2_METHOD: "SSLv2_method",
Jean-Paul Calderonebe2bb422013-12-29 07:34:08 -0500252 SSLv3_METHOD: "SSLv3_method",
253 SSLv23_METHOD: "SSLv23_method",
254 TLSv1_METHOD: "TLSv1_method",
255 TLSv1_1_METHOD: "TLSv1_1_method",
256 TLSv1_2_METHOD: "TLSv1_2_method",
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800257 }
Jean-Paul Calderonebe2bb422013-12-29 07:34:08 -0500258 _methods = dict(
259 (identifier, getattr(_lib, name))
260 for (identifier, name) in _methods.items()
261 if getattr(_lib, name, None) is not None)
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800262
Jean-Paul Calderone63157872013-03-20 16:43:38 -0700263
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800264 def __init__(self, method):
265 """
266 :param method: One of SSLv2_METHOD, SSLv3_METHOD, SSLv23_METHOD, or
267 TLSv1_METHOD.
268 """
Jean-Paul Calderonef73a3cb2014-02-09 08:49:06 -0500269 if not isinstance(method, integer_types):
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800270 raise TypeError("method must be an integer")
271
272 try:
273 method_func = self._methods[method]
274 except KeyError:
275 raise ValueError("No such protocol")
276
277 method_obj = method_func()
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500278 if method_obj == _ffi.NULL:
Jean-Paul Calderonea9f84ad2013-12-29 17:06:11 -0500279 # TODO: This is untested.
280 _raise_current_error()
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800281
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500282 context = _lib.SSL_CTX_new(method_obj)
283 if context == _ffi.NULL:
Jean-Paul Calderonea9f84ad2013-12-29 17:06:11 -0500284 # TODO: This is untested.
285 _raise_current_error()
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500286 context = _ffi.gc(context, _lib.SSL_CTX_free)
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800287
288 self._context = context
Jean-Paul Calderone173cff92013-03-06 10:29:21 -0800289 self._passphrase_helper = None
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800290 self._passphrase_callback = None
Jean-Paul Calderone173cff92013-03-06 10:29:21 -0800291 self._passphrase_userdata = None
Jean-Paul Calderone7e166fe2013-03-06 20:54:38 -0800292 self._verify_helper = None
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800293 self._verify_callback = None
294 self._info_callback = None
295 self._tlsext_servername_callback = None
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800296 self._app_data = None
297
Jean-Paul Calderone1aba4162013-03-05 18:50:00 -0800298 # SSL_CTX_set_app_data(self->ctx, self);
299 # SSL_CTX_set_mode(self->ctx, SSL_MODE_ENABLE_PARTIAL_WRITE |
300 # SSL_MODE_ACCEPT_MOVING_WRITE_BUFFER |
301 # SSL_MODE_AUTO_RETRY);
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500302 self.set_mode(_lib.SSL_MODE_ENABLE_PARTIAL_WRITE)
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800303
304
305 def load_verify_locations(self, cafile, capath=None):
306 """
307 Let SSL know where we can find trusted certificates for the certificate
308 chain
309
310 :param cafile: In which file we can find the certificates
311 :param capath: In which directory we can find the certificates
312 :return: None
313 """
Jean-Paul Calderone6462b072015-03-29 07:03:11 -0400314 cafile = _warn_text("cafile", cafile)
Abraham Martine82326c2015-02-04 10:18:10 +0000315
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800316 if cafile is None:
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500317 cafile = _ffi.NULL
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800318 elif not isinstance(cafile, bytes):
319 raise TypeError("cafile must be None or a byte string")
320
321 if capath is None:
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500322 capath = _ffi.NULL
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800323 elif not isinstance(capath, bytes):
324 raise TypeError("capath must be None or a byte string")
325
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500326 load_result = _lib.SSL_CTX_load_verify_locations(self._context, cafile, capath)
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800327 if not load_result:
Jean-Paul Calderonec86bb7d2013-12-29 10:25:59 -0500328 _raise_current_error()
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800329
330
331 def _wrap_callback(self, callback):
332 @wraps(callback)
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800333 def wrapper(size, verify, userdata):
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800334 return callback(size, verify, self._passphrase_userdata)
335 return _PassphraseHelper(
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800336 FILETYPE_PEM, wrapper, more_args=True, truncate=True)
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800337
338
339 def set_passwd_cb(self, callback, userdata=None):
340 """
341 Set the passphrase callback
342
343 :param callback: The Python callback to use
344 :param userdata: (optional) A Python object which will be given as
345 argument to the callback
346 :return: None
347 """
348 if not callable(callback):
349 raise TypeError("callback must be callable")
350
351 self._passphrase_helper = self._wrap_callback(callback)
352 self._passphrase_callback = self._passphrase_helper.callback
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500353 _lib.SSL_CTX_set_default_passwd_cb(
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800354 self._context, self._passphrase_callback)
355 self._passphrase_userdata = userdata
356
357
358 def set_default_verify_paths(self):
359 """
360 Use the platform-specific CA certificate locations
361
362 :return: None
363 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500364 set_result = _lib.SSL_CTX_set_default_verify_paths(self._context)
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800365 if not set_result:
Jean-Paul Calderonea9f84ad2013-12-29 17:06:11 -0500366 # TODO: This is untested.
Jean-Paul Calderonec86bb7d2013-12-29 10:25:59 -0500367 _raise_current_error()
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800368
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800369
370 def use_certificate_chain_file(self, certfile):
371 """
372 Load a certificate chain from a file
373
374 :param certfile: The name of the certificate chain file
375 :return: None
376 """
Jean-Paul Calderoned8607982014-01-18 10:30:55 -0500377 if isinstance(certfile, _text_type):
378 # Perhaps sys.getfilesystemencoding() could be better?
379 certfile = certfile.encode("utf-8")
380
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800381 if not isinstance(certfile, bytes):
Jean-Paul Calderoned8607982014-01-18 10:30:55 -0500382 raise TypeError("certfile must be bytes or unicode")
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800383
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500384 result = _lib.SSL_CTX_use_certificate_chain_file(self._context, certfile)
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800385 if not result:
Jean-Paul Calderonec86bb7d2013-12-29 10:25:59 -0500386 _raise_current_error()
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800387
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800388
Jean-Paul Calderone173cff92013-03-06 10:29:21 -0800389 def use_certificate_file(self, certfile, filetype=FILETYPE_PEM):
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800390 """
391 Load a certificate from a file
392
393 :param certfile: The name of the certificate file
394 :param filetype: (optional) The encoding of the file, default is PEM
395 :return: None
396 """
Jean-Paul Calderone684baf52014-01-18 10:31:19 -0500397 if isinstance(certfile, _text_type):
398 # Perhaps sys.getfilesystemencoding() could be better?
399 certfile = certfile.encode("utf-8")
Jean-Paul Calderone173cff92013-03-06 10:29:21 -0800400 if not isinstance(certfile, bytes):
Jean-Paul Calderone684baf52014-01-18 10:31:19 -0500401 raise TypeError("certfile must be bytes or unicode")
Jean-Paul Calderonef73a3cb2014-02-09 08:49:06 -0500402 if not isinstance(filetype, integer_types):
Jean-Paul Calderone173cff92013-03-06 10:29:21 -0800403 raise TypeError("filetype must be an integer")
404
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500405 use_result = _lib.SSL_CTX_use_certificate_file(self._context, certfile, filetype)
Jean-Paul Calderone173cff92013-03-06 10:29:21 -0800406 if not use_result:
Jean-Paul Calderonec86bb7d2013-12-29 10:25:59 -0500407 _raise_current_error()
Jean-Paul Calderone173cff92013-03-06 10:29:21 -0800408
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800409
410 def use_certificate(self, cert):
411 """
412 Load a certificate from a X509 object
413
414 :param cert: The X509 object
415 :return: None
416 """
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800417 if not isinstance(cert, X509):
418 raise TypeError("cert must be an X509 instance")
419
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500420 use_result = _lib.SSL_CTX_use_certificate(self._context, cert._x509)
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800421 if not use_result:
Jean-Paul Calderonec86bb7d2013-12-29 10:25:59 -0500422 _raise_current_error()
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800423
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800424
425 def add_extra_chain_cert(self, certobj):
426 """
427 Add certificate to chain
428
429 :param certobj: The X509 certificate object to add to the chain
430 :return: None
431 """
432 if not isinstance(certobj, X509):
433 raise TypeError("certobj must be an X509 instance")
434
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500435 copy = _lib.X509_dup(certobj._x509)
436 add_result = _lib.SSL_CTX_add_extra_chain_cert(self._context, copy)
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800437 if not add_result:
Jean-Paul Calderonea9f84ad2013-12-29 17:06:11 -0500438 # TODO: This is untested.
439 _lib.X509_free(copy)
440 _raise_current_error()
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800441
Jean-Paul Calderone173cff92013-03-06 10:29:21 -0800442
443 def _raise_passphrase_exception(self):
444 if self._passphrase_helper is None:
Jean-Paul Calderonec86bb7d2013-12-29 10:25:59 -0500445 _raise_current_error()
Jean-Paul Calderone173cff92013-03-06 10:29:21 -0800446 exception = self._passphrase_helper.raise_if_problem(Error)
447 if exception is not None:
448 raise exception
449
450
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800451 def use_privatekey_file(self, keyfile, filetype=_unspecified):
452 """
453 Load a private key from a file
454
455 :param keyfile: The name of the key file
456 :param filetype: (optional) The encoding of the file, default is PEM
457 :return: None
458 """
Jean-Paul Calderone87e525a2014-01-18 10:31:51 -0500459 if isinstance(keyfile, _text_type):
460 # Perhaps sys.getfilesystemencoding() could be better?
461 keyfile = keyfile.encode("utf-8")
462
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800463 if not isinstance(keyfile, bytes):
464 raise TypeError("keyfile must be a byte string")
465
466 if filetype is _unspecified:
467 filetype = FILETYPE_PEM
Jean-Paul Calderonef73a3cb2014-02-09 08:49:06 -0500468 elif not isinstance(filetype, integer_types):
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800469 raise TypeError("filetype must be an integer")
470
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500471 use_result = _lib.SSL_CTX_use_PrivateKey_file(
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800472 self._context, keyfile, filetype)
473 if not use_result:
Jean-Paul Calderone173cff92013-03-06 10:29:21 -0800474 self._raise_passphrase_exception()
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800475
476
477 def use_privatekey(self, pkey):
478 """
479 Load a private key from a PKey object
480
481 :param pkey: The PKey object
482 :return: None
483 """
484 if not isinstance(pkey, PKey):
485 raise TypeError("pkey must be a PKey instance")
486
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500487 use_result = _lib.SSL_CTX_use_PrivateKey(self._context, pkey._pkey)
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800488 if not use_result:
Jean-Paul Calderone173cff92013-03-06 10:29:21 -0800489 self._raise_passphrase_exception()
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800490
491
492 def check_privatekey(self):
493 """
494 Check that the private key and certificate match up
495
496 :return: None (raises an exception if something's wrong)
497 """
Jean-Paul Calderonea0344922014-12-11 14:02:31 -0500498 if not _lib.SSL_CTX_check_private_key(self._context):
499 _raise_current_error()
500
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800501
502 def load_client_ca(self, cafile):
503 """
504 Load the trusted certificates that will be sent to the client (basically
505 telling the client "These are the guys I trust"). Does not actually
506 imply any of the certificates are trusted; that must be configured
507 separately.
508
509 :param cafile: The name of the certificates file
510 :return: None
511 """
512
513 def set_session_id(self, buf):
514 """
515 Set the session identifier. This is needed if you want to do session
516 resumption.
517
518 :param buf: A Python object that can be safely converted to a string
519 :returns: None
520 """
521
522 def set_session_cache_mode(self, mode):
523 """
524 Enable/disable session caching and specify the mode used.
525
526 :param mode: One or more of the SESS_CACHE_* flags (combine using
527 bitwise or)
528 :returns: The previously set caching mode.
529 """
Jean-Paul Calderonebef4f4c2014-02-02 18:13:31 -0500530 if not isinstance(mode, integer_types):
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800531 raise TypeError("mode must be an integer")
532
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500533 return _lib.SSL_CTX_set_session_cache_mode(self._context, mode)
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800534
535
536 def get_session_cache_mode(self):
537 """
538 :returns: The currently used cache mode.
539 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500540 return _lib.SSL_CTX_get_session_cache_mode(self._context)
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800541
542
543 def set_verify(self, mode, callback):
544 """
545 Set the verify mode and verify callback
546
547 :param mode: The verify mode, this is either VERIFY_NONE or
548 VERIFY_PEER combined with possible other flags
549 :param callback: The Python callback to use
550 :return: None
551
552 See SSL_CTX_set_verify(3SSL) for further details.
553 """
Jean-Paul Calderonebef4f4c2014-02-02 18:13:31 -0500554 if not isinstance(mode, integer_types):
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800555 raise TypeError("mode must be an integer")
556
557 if not callable(callback):
558 raise TypeError("callback must be callable")
559
Jean-Paul Calderone6a8cd112014-04-02 21:09:08 -0400560 self._verify_helper = _VerifyHelper(callback)
Jean-Paul Calderone7e166fe2013-03-06 20:54:38 -0800561 self._verify_callback = self._verify_helper.callback
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500562 _lib.SSL_CTX_set_verify(self._context, mode, self._verify_callback)
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800563
564
565 def set_verify_depth(self, depth):
566 """
567 Set the verify depth
568
569 :param depth: An integer specifying the verify depth
570 :return: None
571 """
Jean-Paul Calderonebef4f4c2014-02-02 18:13:31 -0500572 if not isinstance(depth, integer_types):
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800573 raise TypeError("depth must be an integer")
574
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500575 _lib.SSL_CTX_set_verify_depth(self._context, depth)
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800576
577
578 def get_verify_mode(self):
579 """
580 Get the verify mode
581
582 :return: The verify mode
583 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500584 return _lib.SSL_CTX_get_verify_mode(self._context)
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800585
586
587 def get_verify_depth(self):
588 """
589 Get the verify depth
590
591 :return: The verify depth
592 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500593 return _lib.SSL_CTX_get_verify_depth(self._context)
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800594
595
596 def load_tmp_dh(self, dhfile):
597 """
598 Load parameters for Ephemeral Diffie-Hellman
599
600 :param dhfile: The file to load EDH parameters from
601 :return: None
602 """
603 if not isinstance(dhfile, bytes):
604 raise TypeError("dhfile must be a byte string")
605
Jean-Paul Calderone4f0467a2014-01-11 11:58:41 -0500606 bio = _lib.BIO_new_file(dhfile, b"r")
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500607 if bio == _ffi.NULL:
Jean-Paul Calderonec86bb7d2013-12-29 10:25:59 -0500608 _raise_current_error()
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500609 bio = _ffi.gc(bio, _lib.BIO_free)
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800610
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500611 dh = _lib.PEM_read_bio_DHparams(bio, _ffi.NULL, _ffi.NULL, _ffi.NULL)
612 dh = _ffi.gc(dh, _lib.DH_free)
613 _lib.SSL_CTX_set_tmp_dh(self._context, dh)
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800614
615
Jean-Paul Calderone3e4e3352014-04-19 09:28:28 -0400616 def set_tmp_ecdh(self, curve):
Alex Gaynor7b8d57a2014-01-17 12:08:54 -0600617 """
Andy Lutomirski76a61332014-03-12 15:02:56 -0700618 Select a curve to use for ECDHE key exchange.
Alex Gaynor7b8d57a2014-01-17 12:08:54 -0600619
Jean-Paul Calderonec09fd582014-04-18 22:00:10 -0400620 :param curve: A curve object to use as returned by either
621 :py:meth:`OpenSSL.crypto.get_elliptic_curve` or
622 :py:meth:`OpenSSL.crypto.get_elliptic_curves`.
Andy Lutomirskif05a2732014-03-13 17:22:25 -0700623
Alex Gaynor7b8d57a2014-01-17 12:08:54 -0600624 :return: None
625 """
Jean-Paul Calderonec09fd582014-04-18 22:00:10 -0400626 _lib.SSL_CTX_set_tmp_ecdh(self._context, curve._to_EC_KEY())
Alex Gaynor7b8d57a2014-01-17 12:08:54 -0600627
628
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800629 def set_cipher_list(self, cipher_list):
630 """
631 Change the cipher list
632
633 :param cipher_list: A cipher list, see ciphers(1)
634 :return: None
635 """
Jean-Paul Calderone63eab692014-01-18 10:19:56 -0500636 if isinstance(cipher_list, _text_type):
637 cipher_list = cipher_list.encode("ascii")
638
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800639 if not isinstance(cipher_list, bytes):
Jean-Paul Calderone63eab692014-01-18 10:19:56 -0500640 raise TypeError("cipher_list must be bytes or unicode")
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800641
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500642 result = _lib.SSL_CTX_set_cipher_list(self._context, cipher_list)
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800643 if not result:
Jean-Paul Calderonec86bb7d2013-12-29 10:25:59 -0500644 _raise_current_error()
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800645
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800646
647 def set_client_ca_list(self, certificate_authorities):
648 """
649 Set the list of preferred client certificate signers for this server context.
650
651 This list of certificate authorities will be sent to the client when the
652 server requests a client certificate.
653
654 :param certificate_authorities: a sequence of X509Names.
655 :return: None
656 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500657 name_stack = _lib.sk_X509_NAME_new_null()
658 if name_stack == _ffi.NULL:
Jean-Paul Calderonea9f84ad2013-12-29 17:06:11 -0500659 # TODO: This is untested.
Jean-Paul Calderonec86bb7d2013-12-29 10:25:59 -0500660 _raise_current_error()
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800661
662 try:
663 for ca_name in certificate_authorities:
664 if not isinstance(ca_name, X509Name):
665 raise TypeError(
666 "client CAs must be X509Name objects, not %s objects" % (
667 type(ca_name).__name__,))
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500668 copy = _lib.X509_NAME_dup(ca_name._name)
669 if copy == _ffi.NULL:
Jean-Paul Calderonea9f84ad2013-12-29 17:06:11 -0500670 # TODO: This is untested.
Jean-Paul Calderonec86bb7d2013-12-29 10:25:59 -0500671 _raise_current_error()
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500672 push_result = _lib.sk_X509_NAME_push(name_stack, copy)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800673 if not push_result:
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500674 _lib.X509_NAME_free(copy)
Jean-Paul Calderonec86bb7d2013-12-29 10:25:59 -0500675 _raise_current_error()
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800676 except:
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500677 _lib.sk_X509_NAME_free(name_stack)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800678 raise
679
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500680 _lib.SSL_CTX_set_client_CA_list(self._context, name_stack)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800681
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800682
683 def add_client_ca(self, certificate_authority):
684 """
685 Add the CA certificate to the list of preferred signers for this context.
686
687 The list of certificate authorities will be sent to the client when the
688 server requests a client certificate.
689
690 :param certificate_authority: certificate authority's X509 certificate.
691 :return: None
692 """
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800693 if not isinstance(certificate_authority, X509):
694 raise TypeError("certificate_authority must be an X509 instance")
695
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500696 add_result = _lib.SSL_CTX_add_client_CA(
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800697 self._context, certificate_authority._x509)
698 if not add_result:
Jean-Paul Calderonea9f84ad2013-12-29 17:06:11 -0500699 # TODO: This is untested.
Jean-Paul Calderonec86bb7d2013-12-29 10:25:59 -0500700 _raise_current_error()
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800701
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800702
703 def set_timeout(self, timeout):
704 """
705 Set session timeout
706
707 :param timeout: The timeout in seconds
708 :return: The previous session timeout
709 """
Jean-Paul Calderonebef4f4c2014-02-02 18:13:31 -0500710 if not isinstance(timeout, integer_types):
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800711 raise TypeError("timeout must be an integer")
712
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500713 return _lib.SSL_CTX_set_timeout(self._context, timeout)
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800714
715
716 def get_timeout(self):
717 """
718 Get the session timeout
719
720 :return: The session timeout
721 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500722 return _lib.SSL_CTX_get_timeout(self._context)
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800723
724
725 def set_info_callback(self, callback):
726 """
727 Set the info callback
728
729 :param callback: The Python callback to use
730 :return: None
731 """
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800732 @wraps(callback)
733 def wrapper(ssl, where, return_code):
Jean-Paul Calderonef2bbc9c2014-02-02 10:59:14 -0500734 callback(Connection._reverse_mapping[ssl], where, return_code)
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500735 self._info_callback = _ffi.callback(
736 "void (*)(const SSL *, int, int)", wrapper)
737 _lib.SSL_CTX_set_info_callback(self._context, self._info_callback)
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800738
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800739
740 def get_app_data(self):
741 """
742 Get the application data (supplied via set_app_data())
743
744 :return: The application data
745 """
746 return self._app_data
747
748
749 def set_app_data(self, data):
750 """
751 Set the application data (will be returned from get_app_data())
752
753 :param data: Any Python object
754 :return: None
755 """
756 self._app_data = data
757
758
759 def get_cert_store(self):
760 """
Jean-Paul Calderonea9f84ad2013-12-29 17:06:11 -0500761 Get the certificate store for the context.
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800762
Jean-Paul Calderonea9f84ad2013-12-29 17:06:11 -0500763 :return: A X509Store object or None if it does not have one.
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800764 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500765 store = _lib.SSL_CTX_get_cert_store(self._context)
766 if store == _ffi.NULL:
Jean-Paul Calderonea9f84ad2013-12-29 17:06:11 -0500767 # TODO: This is untested.
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800768 return None
769
770 pystore = X509Store.__new__(X509Store)
771 pystore._store = store
772 return pystore
773
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800774
775 def set_options(self, options):
776 """
777 Add options. Options set before are not cleared!
778
779 :param options: The options to add.
780 :return: The new option bitmask.
781 """
Jean-Paul Calderonebef4f4c2014-02-02 18:13:31 -0500782 if not isinstance(options, integer_types):
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800783 raise TypeError("options must be an integer")
784
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500785 return _lib.SSL_CTX_set_options(self._context, options)
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800786
787
788 def set_mode(self, mode):
789 """
790 Add modes via bitmask. Modes set before are not cleared!
791
792 :param mode: The mode to add.
793 :return: The new mode bitmask.
794 """
Jean-Paul Calderonebef4f4c2014-02-02 18:13:31 -0500795 if not isinstance(mode, integer_types):
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800796 raise TypeError("mode must be an integer")
797
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500798 return _lib.SSL_CTX_set_mode(self._context, mode)
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800799
800
801 def set_tlsext_servername_callback(self, callback):
802 """
803 Specify a callback function to be called when clients specify a server name.
804
805 :param callback: The callback function. It will be invoked with one
806 argument, the Connection instance.
807 """
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800808 @wraps(callback)
809 def wrapper(ssl, alert, arg):
810 callback(Connection._reverse_mapping[ssl])
811 return 0
812
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500813 self._tlsext_servername_callback = _ffi.callback(
814 "int (*)(const SSL *, int *, void *)", wrapper)
815 _lib.SSL_CTX_set_tlsext_servername_callback(
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800816 self._context, self._tlsext_servername_callback)
Jean-Paul Calderone8a1bea52013-03-05 07:57:57 -0800817
818ContextType = Context
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800819
820
821
822class Connection(object):
823 """
824 """
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800825 _reverse_mapping = WeakValueDictionary()
826
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800827 def __init__(self, context, socket=None):
828 """
829 Create a new Connection object, using the given OpenSSL.SSL.Context
830 instance and socket.
831
832 :param context: An SSL Context to use for this connection
833 :param socket: The socket to use for transport layer
834 """
835 if not isinstance(context, Context):
836 raise TypeError("context must be a Context instance")
837
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500838 ssl = _lib.SSL_new(context._context)
839 self._ssl = _ffi.gc(ssl, _lib.SSL_free)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800840 self._context = context
841
842 self._reverse_mapping[self._ssl] = self
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800843
844 if socket is None:
845 self._socket = None
Jean-Paul Calderone73b15c22013-03-05 18:30:39 -0800846 # Don't set up any gc for these, SSL_free will take care of them.
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500847 self._into_ssl = _lib.BIO_new(_lib.BIO_s_mem())
848 self._from_ssl = _lib.BIO_new(_lib.BIO_s_mem())
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800849
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500850 if self._into_ssl == _ffi.NULL or self._from_ssl == _ffi.NULL:
Jean-Paul Calderonea9f84ad2013-12-29 17:06:11 -0500851 # TODO: This is untested.
852 _raise_current_error()
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800853
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500854 _lib.SSL_set_bio(self._ssl, self._into_ssl, self._from_ssl)
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800855 else:
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800856 self._into_ssl = None
857 self._from_ssl = None
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800858 self._socket = socket
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500859 set_result = _lib.SSL_set_fd(self._ssl, _asFileDescriptor(self._socket))
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800860 if not set_result:
Jean-Paul Calderonea9f84ad2013-12-29 17:06:11 -0500861 # TODO: This is untested.
862 _raise_current_error()
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800863
864
865 def __getattr__(self, name):
866 """
867 Look up attributes on the wrapped socket object if they are not found on
868 the Connection object.
869 """
870 return getattr(self._socket, name)
871
872
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800873 def _raise_ssl_error(self, ssl, result):
Jean-Paul Calderone7e166fe2013-03-06 20:54:38 -0800874 if self._context._verify_helper is not None:
875 self._context._verify_helper.raise_if_problem()
876
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500877 error = _lib.SSL_get_error(ssl, result)
878 if error == _lib.SSL_ERROR_WANT_READ:
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800879 raise WantReadError()
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500880 elif error == _lib.SSL_ERROR_WANT_WRITE:
Jean-Paul Calderoned899af02013-03-19 22:10:37 -0700881 raise WantWriteError()
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500882 elif error == _lib.SSL_ERROR_ZERO_RETURN:
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800883 raise ZeroReturnError()
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500884 elif error == _lib.SSL_ERROR_WANT_X509_LOOKUP:
Jean-Paul Calderonea9f84ad2013-12-29 17:06:11 -0500885 # TODO: This is untested.
Jean-Paul Calderoned899af02013-03-19 22:10:37 -0700886 raise WantX509LookupError()
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500887 elif error == _lib.SSL_ERROR_SYSCALL:
888 if _lib.ERR_peek_error() == 0:
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800889 if result < 0:
Konstantinos Koukopoulos541150d2014-01-31 01:00:19 +0200890 if platform == "win32":
891 errno = _ffi.getwinerror()[0]
892 else:
893 errno = _ffi.errno
894 raise SysCallError(errno, errorcode[errno])
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800895 else:
Jean-Paul Calderoned899af02013-03-19 22:10:37 -0700896 raise SysCallError(-1, "Unexpected EOF")
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800897 else:
Jean-Paul Calderonea9f84ad2013-12-29 17:06:11 -0500898 # TODO: This is untested.
Jean-Paul Calderonec86bb7d2013-12-29 10:25:59 -0500899 _raise_current_error()
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500900 elif error == _lib.SSL_ERROR_NONE:
Jean-Paul Calderoned899af02013-03-19 22:10:37 -0700901 pass
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800902 else:
Jean-Paul Calderonec86bb7d2013-12-29 10:25:59 -0500903 _raise_current_error()
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800904
905
906 def get_context(self):
907 """
908 Get session context
909 """
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800910 return self._context
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800911
912
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800913 def set_context(self, context):
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800914 """
915 Switch this connection to a new session context
916
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800917 :param context: A :py:class:`Context` instance giving the new session
918 context to use.
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800919 """
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800920 if not isinstance(context, Context):
921 raise TypeError("context must be a Context instance")
922
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500923 _lib.SSL_set_SSL_CTX(self._ssl, context._context)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800924 self._context = context
925
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800926
927 def get_servername(self):
928 """
929 Retrieve the servername extension value if provided in the client hello
930 message, or None if there wasn't one.
931
932 :return: A byte string giving the server name or :py:data:`None`.
933 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500934 name = _lib.SSL_get_servername(self._ssl, _lib.TLSEXT_NAMETYPE_host_name)
935 if name == _ffi.NULL:
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800936 return None
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800937
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500938 return _ffi.string(name)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800939
940
941 def set_tlsext_host_name(self, name):
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800942 """
943 Set the value of the servername extension to send in the client hello.
944
945 :param name: A byte string giving the name.
946 """
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800947 if not isinstance(name, bytes):
948 raise TypeError("name must be a byte string")
Jean-Paul Calderone4f0467a2014-01-11 11:58:41 -0500949 elif b"\0" in name:
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800950 raise TypeError("name must not contain NUL byte")
951
952 # XXX I guess this can fail sometimes?
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500953 _lib.SSL_set_tlsext_host_name(self._ssl, name)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800954
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800955
956 def pending(self):
957 """
958 Get the number of bytes that can be safely read from the connection
959
960 :return: The number of bytes available in the receive buffer.
961 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500962 return _lib.SSL_pending(self._ssl)
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800963
964
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800965 def send(self, buf, flags=0):
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800966 """
967 Send data on the connection. NOTE: If you get one of the WantRead,
968 WantWrite or WantX509Lookup exceptions on this, you have to call the
969 method again with the SAME buffer.
970
Markus Unterwaditzer8e41d022014-04-19 12:27:11 +0200971 :param buf: The string, buffer or memoryview to send
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800972 :param flags: (optional) Included for compatibility with the socket
973 API, the value is ignored
974 :return: The number of bytes written
975 """
Abraham Martine82326c2015-02-04 10:18:10 +0000976 # Backward compatibility
Jean-Paul Calderone6462b072015-03-29 07:03:11 -0400977 buf = _warn_text("buf", buf)
Abraham Martine82326c2015-02-04 10:18:10 +0000978
Jean-Paul Calderone8fb53182013-12-30 08:35:49 -0500979 if isinstance(buf, _memoryview):
Jean-Paul Calderone1aba4162013-03-05 18:50:00 -0800980 buf = buf.tobytes()
Markus Unterwaditzer8e41d022014-04-19 12:27:11 +0200981 if isinstance(buf, _buffer):
982 buf = str(buf)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800983 if not isinstance(buf, bytes):
Markus Unterwaditzer8e41d022014-04-19 12:27:11 +0200984 raise TypeError("data must be a memoryview, buffer or byte string")
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800985
Jean-Paul Calderone6037d072013-12-28 18:04:00 -0500986 result = _lib.SSL_write(self._ssl, buf, len(buf))
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800987 self._raise_ssl_error(self._ssl, result)
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800988 return result
989 write = send
990
991
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800992 def sendall(self, buf, flags=0):
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800993 """
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -0800994 Send "all" data on the connection. This calls send() repeatedly until
995 all data is sent. If an error occurs, it's impossible to tell how much
996 data has been sent.
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800997
Markus Unterwaditzer8e41d022014-04-19 12:27:11 +0200998 :param buf: The string, buffer or memoryview to send
Jean-Paul Calderone131052e2013-03-05 11:56:19 -0800999 :param flags: (optional) Included for compatibility with the socket
1000 API, the value is ignored
1001 :return: The number of bytes written
1002 """
Jean-Paul Calderone6462b072015-03-29 07:03:11 -04001003 buf = _warn_text("buf", buf)
Abraham Martine82326c2015-02-04 10:18:10 +00001004
Jean-Paul Calderone8fb53182013-12-30 08:35:49 -05001005 if isinstance(buf, _memoryview):
Jean-Paul Calderone1aba4162013-03-05 18:50:00 -08001006 buf = buf.tobytes()
Markus Unterwaditzer8e41d022014-04-19 12:27:11 +02001007 if isinstance(buf, _buffer):
1008 buf = str(buf)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001009 if not isinstance(buf, bytes):
Markus Unterwaditzer8e41d022014-04-19 12:27:11 +02001010 raise TypeError("buf must be a memoryview, buffer or byte string")
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001011
1012 left_to_send = len(buf)
1013 total_sent = 0
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001014 data = _ffi.new("char[]", buf)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001015
1016 while left_to_send:
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001017 result = _lib.SSL_write(self._ssl, data + total_sent, left_to_send)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001018 self._raise_ssl_error(self._ssl, result)
1019 total_sent += result
1020 left_to_send -= result
1021
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001022
1023 def recv(self, bufsiz, flags=None):
1024 """
1025 Receive data on the connection. NOTE: If you get one of the WantRead,
1026 WantWrite or WantX509Lookup exceptions on this, you have to call the
1027 method again with the SAME buffer.
1028
1029 :param bufsiz: The maximum number of bytes to read
1030 :param flags: (optional) Included for compatibility with the socket
1031 API, the value is ignored
1032 :return: The string read from the Connection
1033 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001034 buf = _ffi.new("char[]", bufsiz)
1035 result = _lib.SSL_read(self._ssl, buf, bufsiz)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001036 self._raise_ssl_error(self._ssl, result)
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001037 return _ffi.buffer(buf, result)[:]
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001038 read = recv
1039
1040
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001041 def _handle_bio_errors(self, bio, result):
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001042 if _lib.BIO_should_retry(bio):
1043 if _lib.BIO_should_read(bio):
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001044 raise WantReadError()
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001045 elif _lib.BIO_should_write(bio):
Jean-Paul Calderonea9f84ad2013-12-29 17:06:11 -05001046 # TODO: This is untested.
Jean-Paul Calderoned899af02013-03-19 22:10:37 -07001047 raise WantWriteError()
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001048 elif _lib.BIO_should_io_special(bio):
Jean-Paul Calderonea9f84ad2013-12-29 17:06:11 -05001049 # TODO: This is untested. I think io_special means the socket
1050 # BIO has a not-yet connected socket.
Jean-Paul Calderoned899af02013-03-19 22:10:37 -07001051 raise ValueError("BIO_should_io_special")
1052 else:
Jean-Paul Calderonea9f84ad2013-12-29 17:06:11 -05001053 # TODO: This is untested.
Jean-Paul Calderoned899af02013-03-19 22:10:37 -07001054 raise ValueError("unknown bio failure")
1055 else:
Jean-Paul Calderonea9f84ad2013-12-29 17:06:11 -05001056 # TODO: This is untested.
Jean-Paul Calderonec86bb7d2013-12-29 10:25:59 -05001057 _raise_current_error()
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001058
1059
1060 def bio_read(self, bufsiz):
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001061 """
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001062 When using non-socket connections this function reads the "dirty" data
1063 that would have traveled away on the network.
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001064
1065 :param bufsiz: The maximum number of bytes to read
1066 :return: The string read.
1067 """
Jean-Paul Calderone97e041d2013-03-05 21:03:12 -08001068 if self._from_ssl is None:
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001069 raise TypeError("Connection sock was not None")
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001070
Jean-Paul Calderonebef4f4c2014-02-02 18:13:31 -05001071 if not isinstance(bufsiz, integer_types):
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001072 raise TypeError("bufsiz must be an integer")
1073
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001074 buf = _ffi.new("char[]", bufsiz)
1075 result = _lib.BIO_read(self._from_ssl, buf, bufsiz)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001076 if result <= 0:
1077 self._handle_bio_errors(self._from_ssl, result)
1078
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001079 return _ffi.buffer(buf, result)[:]
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001080
1081
1082 def bio_write(self, buf):
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001083 """
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001084 When using non-socket connections this function sends "dirty" data that
1085 would have traveled in on the network.
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001086
1087 :param buf: The string to put into the memory BIO.
1088 :return: The number of bytes written
1089 """
Jean-Paul Calderone6462b072015-03-29 07:03:11 -04001090 buf = _warn_text("buf", buf)
Abraham Martine82326c2015-02-04 10:18:10 +00001091
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001092 if self._into_ssl is None:
1093 raise TypeError("Connection sock was not None")
1094
1095 if not isinstance(buf, bytes):
1096 raise TypeError("buf must be a byte string")
1097
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001098 result = _lib.BIO_write(self._into_ssl, buf, len(buf))
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001099 if result <= 0:
1100 self._handle_bio_errors(self._into_ssl, result)
1101 return result
1102
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001103
1104 def renegotiate(self):
1105 """
1106 Renegotiate the session
1107
1108 :return: True if the renegotiation can be started, false otherwise
1109 """
1110
1111 def do_handshake(self):
1112 """
1113 Perform an SSL handshake (usually called after renegotiate() or one of
1114 set_*_state()). This can raise the same exceptions as send and recv.
1115
1116 :return: None.
1117 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001118 result = _lib.SSL_do_handshake(self._ssl)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001119 self._raise_ssl_error(self._ssl, result)
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001120
1121
1122 def renegotiate_pending(self):
1123 """
1124 Check if there's a renegotiation in progress, it will return false once
1125 a renegotiation is finished.
1126
1127 :return: Whether there's a renegotiation in progress
1128 """
1129
1130 def total_renegotiations(self):
1131 """
1132 Find out the total number of renegotiations.
1133
1134 :return: The number of renegotiations.
1135 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001136 return _lib.SSL_total_renegotiations(self._ssl)
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001137
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001138
1139 def connect(self, addr):
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001140 """
1141 Connect to remote host and set up client-side SSL
1142
1143 :param addr: A remote address
1144 :return: What the socket's connect method returns
1145 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001146 _lib.SSL_set_connect_state(self._ssl)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001147 return self._socket.connect(addr)
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001148
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001149
1150 def connect_ex(self, addr):
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001151 """
1152 Connect to remote host and set up client-side SSL. Note that if the socket's
1153 connect_ex method doesn't return 0, SSL won't be initialized.
1154
1155 :param addr: A remove address
1156 :return: What the socket's connect_ex method returns
1157 """
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001158 connect_ex = self._socket.connect_ex
1159 self.set_connect_state()
1160 return connect_ex(addr)
1161
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001162
1163 def accept(self):
1164 """
1165 Accept incoming connection and set up SSL on it
1166
1167 :return: A (conn,addr) pair where conn is a Connection and addr is an
1168 address
1169 """
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001170 client, addr = self._socket.accept()
1171 conn = Connection(self._context, client)
1172 conn.set_accept_state()
1173 return (conn, addr)
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001174
1175
1176 def bio_shutdown(self):
1177 """
1178 When using non-socket connections this function signals end of
1179 data on the input for this connection.
1180
1181 :return: None
1182 """
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001183 if self._from_ssl is None:
1184 raise TypeError("Connection sock was not None")
1185
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001186 _lib.BIO_set_mem_eof_return(self._into_ssl, 0)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001187
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001188
1189 def shutdown(self):
1190 """
1191 Send closure alert
1192
1193 :return: True if the shutdown completed successfully (i.e. both sides
1194 have sent closure alerts), false otherwise (i.e. you have to
1195 wait for a ZeroReturnError on a recv() method call
1196 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001197 result = _lib.SSL_shutdown(self._ssl)
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001198 if result < 0:
Paul Aurichbff1d1a2015-01-08 08:36:53 -08001199 self._raise_ssl_error(self._ssl, result)
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001200 elif result > 0:
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001201 return True
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001202 else:
1203 return False
1204
1205
1206 def get_cipher_list(self):
1207 """
1208 Get the session cipher list
1209
1210 :return: A list of cipher strings
1211 """
1212 ciphers = []
1213 for i in count():
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001214 result = _lib.SSL_get_cipher_list(self._ssl, i)
1215 if result == _ffi.NULL:
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001216 break
Jean-Paul Calderone4f0467a2014-01-11 11:58:41 -05001217 ciphers.append(_native(_ffi.string(result)))
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001218 return ciphers
1219
1220
1221 def get_client_ca_list(self):
1222 """
1223 Get CAs whose certificates are suggested for client authentication.
1224
1225 :return: If this is a server connection, a list of X509Names representing
1226 the acceptable CAs as set by :py:meth:`OpenSSL.SSL.Context.set_client_ca_list` or
1227 :py:meth:`OpenSSL.SSL.Context.add_client_ca`. If this is a client connection,
1228 the list of such X509Names sent by the server, or an empty list if that
1229 has not yet happened.
1230 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001231 ca_names = _lib.SSL_get_client_CA_list(self._ssl)
1232 if ca_names == _ffi.NULL:
Jean-Paul Calderonea9f84ad2013-12-29 17:06:11 -05001233 # TODO: This is untested.
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001234 return []
1235
1236 result = []
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001237 for i in range(_lib.sk_X509_NAME_num(ca_names)):
1238 name = _lib.sk_X509_NAME_value(ca_names, i)
1239 copy = _lib.X509_NAME_dup(name)
1240 if copy == _ffi.NULL:
Jean-Paul Calderonea9f84ad2013-12-29 17:06:11 -05001241 # TODO: This is untested.
Jean-Paul Calderonec86bb7d2013-12-29 10:25:59 -05001242 _raise_current_error()
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001243
1244 pyname = X509Name.__new__(X509Name)
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001245 pyname._name = _ffi.gc(copy, _lib.X509_NAME_free)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001246 result.append(pyname)
1247 return result
1248
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001249
1250 def makefile(self):
1251 """
1252 The makefile() method is not implemented, since there is no dup semantics
1253 for SSL connections
1254
Jean-Paul Calderone6749ec22014-04-17 16:30:21 -04001255 :raise: NotImplementedError
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001256 """
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001257 raise NotImplementedError("Cannot make file object of OpenSSL.SSL.Connection")
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001258
1259
1260 def get_app_data(self):
1261 """
1262 Get application data
1263
1264 :return: The application data
1265 """
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001266 return self._app_data
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001267
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001268
1269 def set_app_data(self, data):
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001270 """
1271 Set application data
1272
1273 :param data - The application data
1274 :return: None
1275 """
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001276 self._app_data = data
1277
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001278
1279 def get_shutdown(self):
1280 """
1281 Get shutdown state
1282
1283 :return: The shutdown state, a bitvector of SENT_SHUTDOWN, RECEIVED_SHUTDOWN.
1284 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001285 return _lib.SSL_get_shutdown(self._ssl)
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001286
1287
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001288 def set_shutdown(self, state):
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001289 """
1290 Set shutdown state
1291
1292 :param state - bitvector of SENT_SHUTDOWN, RECEIVED_SHUTDOWN.
1293 :return: None
1294 """
Jean-Paul Calderonef73a3cb2014-02-09 08:49:06 -05001295 if not isinstance(state, integer_types):
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001296 raise TypeError("state must be an integer")
1297
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001298 _lib.SSL_set_shutdown(self._ssl, state)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001299
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001300
1301 def state_string(self):
1302 """
1303 Get a verbose state description
1304
1305 :return: A string representing the state
1306 """
1307
1308 def server_random(self):
1309 """
1310 Get a copy of the server hello nonce.
1311
1312 :return: A string representing the state
1313 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001314 if self._ssl.session == _ffi.NULL:
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001315 return None
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001316 return _ffi.buffer(
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001317 self._ssl.s3.server_random,
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001318 _lib.SSL3_RANDOM_SIZE)[:]
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001319
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001320
1321 def client_random(self):
1322 """
1323 Get a copy of the client hello nonce.
1324
1325 :return: A string representing the state
1326 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001327 if self._ssl.session == _ffi.NULL:
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001328 return None
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001329 return _ffi.buffer(
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001330 self._ssl.s3.client_random,
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001331 _lib.SSL3_RANDOM_SIZE)[:]
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001332
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001333
1334 def master_key(self):
1335 """
1336 Get a copy of the master key.
1337
1338 :return: A string representing the state
1339 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001340 if self._ssl.session == _ffi.NULL:
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001341 return None
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001342 return _ffi.buffer(
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001343 self._ssl.session.master_key,
1344 self._ssl.session.master_key_length)[:]
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001345
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001346
1347 def sock_shutdown(self, *args, **kwargs):
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001348 """
1349 See shutdown(2)
1350
1351 :return: What the socket's shutdown() method returns
1352 """
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001353 return self._socket.shutdown(*args, **kwargs)
1354
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001355
1356 def get_peer_certificate(self):
1357 """
1358 Retrieve the other side's certificate (if any)
1359
1360 :return: The peer's certificate
1361 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001362 cert = _lib.SSL_get_peer_certificate(self._ssl)
1363 if cert != _ffi.NULL:
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001364 pycert = X509.__new__(X509)
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001365 pycert._x509 = _ffi.gc(cert, _lib.X509_free)
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001366 return pycert
1367 return None
1368
1369
1370 def get_peer_cert_chain(self):
1371 """
1372 Retrieve the other side's certificate (if any)
1373
1374 :return: A list of X509 instances giving the peer's certificate chain,
1375 or None if it does not have one.
1376 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001377 cert_stack = _lib.SSL_get_peer_cert_chain(self._ssl)
1378 if cert_stack == _ffi.NULL:
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001379 return None
1380
1381 result = []
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001382 for i in range(_lib.sk_X509_num(cert_stack)):
Jean-Paul Calderone73b15c22013-03-05 18:30:39 -08001383 # TODO could incref instead of dup here
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001384 cert = _lib.X509_dup(_lib.sk_X509_value(cert_stack, i))
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001385 pycert = X509.__new__(X509)
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001386 pycert._x509 = _ffi.gc(cert, _lib.X509_free)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001387 result.append(pycert)
1388 return result
1389
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001390
1391 def want_read(self):
1392 """
1393 Checks if more data has to be read from the transport layer to complete an
1394 operation.
1395
1396 :return: True iff more data has to be read
1397 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001398 return _lib.SSL_want_read(self._ssl)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001399
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001400
1401 def want_write(self):
1402 """
1403 Checks if there is data to write to the transport layer to complete an
1404 operation.
1405
1406 :return: True iff there is data to write
1407 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001408 return _lib.SSL_want_write(self._ssl)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001409
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001410
1411 def set_accept_state(self):
1412 """
1413 Set the connection to work in server mode. The handshake will be handled
1414 automatically by read/write.
1415
1416 :return: None
1417 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001418 _lib.SSL_set_accept_state(self._ssl)
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001419
1420
1421 def set_connect_state(self):
1422 """
1423 Set the connection to work in client mode. The handshake will be handled
1424 automatically by read/write.
1425
1426 :return: None
1427 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001428 _lib.SSL_set_connect_state(self._ssl)
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001429
1430
1431 def get_session(self):
1432 """
1433 Returns the Session currently used.
1434
1435 @return: An instance of :py:class:`OpenSSL.SSL.Session` or :py:obj:`None` if
1436 no session exists.
1437 """
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001438 session = _lib.SSL_get1_session(self._ssl)
1439 if session == _ffi.NULL:
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001440 return None
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001441
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001442 pysession = Session.__new__(Session)
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001443 pysession._session = _ffi.gc(session, _lib.SSL_SESSION_free)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001444 return pysession
1445
1446
1447 def set_session(self, session):
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001448 """
1449 Set the session to be used when the TLS/SSL connection is established.
1450
1451 :param session: A Session instance representing the session to use.
1452 :returns: None
1453 """
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001454 if not isinstance(session, Session):
1455 raise TypeError("session must be a Session instance")
1456
Jean-Paul Calderone6037d072013-12-28 18:04:00 -05001457 result = _lib.SSL_set_session(self._ssl, session._session)
Jean-Paul Calderonea63714c2013-03-05 17:02:26 -08001458 if not result:
Jean-Paul Calderonec86bb7d2013-12-29 10:25:59 -05001459 _raise_current_error()
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001460
Jean-Paul Calderonedbd76272014-03-29 18:09:40 -04001461
Jean-Paul Calderoneac209562014-03-30 11:26:32 -04001462 def _get_finished_message(self, function):
1463 """
1464 Helper to implement :py:meth:`get_finished` and
1465 :py:meth:`get_peer_finished`.
1466
1467 :param function: Either :py:data:`SSL_get_finished`: or
1468 :py:data:`SSL_get_peer_finished`.
1469
1470 :return: :py:data:`None` if the desired message has not yet been
1471 received, otherwise the contents of the message.
1472 :rtype: :py:class:`bytes` or :py:class:`NoneType`
1473 """
Jean-Paul Calderone01af9042014-03-30 11:40:42 -04001474 # The OpenSSL documentation says nothing about what might happen if the
1475 # count argument given is zero. Specifically, it doesn't say whether
1476 # the output buffer may be NULL in that case or not. Inspection of the
1477 # implementation reveals that it calls memcpy() unconditionally.
1478 # Section 7.1.4, paragraph 1 of the C standard suggests that
1479 # memcpy(NULL, source, 0) is not guaranteed to produce defined (let
1480 # alone desirable) behavior (though it probably does on just about
1481 # every implementation...)
1482 #
1483 # Allocate a tiny buffer to pass in (instead of just passing NULL as
1484 # one might expect) for the initial call so as to be safe against this
1485 # potentially undefined behavior.
1486 empty = _ffi.new("char[]", 0)
1487 size = function(self._ssl, empty, 0)
Jean-Paul Calderoneac209562014-03-30 11:26:32 -04001488 if size == 0:
1489 # No Finished message so far.
1490 return None
1491
1492 buf = _ffi.new("char[]", size)
1493 function(self._ssl, buf, size)
1494 return _ffi.buffer(buf, size)[:]
1495
1496
Fedor Brunner5747b932014-03-05 14:22:34 +01001497 def get_finished(self):
1498 """
Jean-Paul Calderoneac209562014-03-30 11:26:32 -04001499 Obtain the latest `handshake finished` message sent to the peer.
Fedor Brunner5747b932014-03-05 14:22:34 +01001500
Jean-Paul Calderoneac209562014-03-30 11:26:32 -04001501 :return: The contents of the message or :py:obj:`None` if the TLS
1502 handshake has not yet completed.
1503 :rtype: :py:class:`bytes` or :py:class:`NoneType`
Fedor Brunner5747b932014-03-05 14:22:34 +01001504 """
Jean-Paul Calderoneac209562014-03-30 11:26:32 -04001505 return self._get_finished_message(_lib.SSL_get_finished)
1506
Fedor Brunner5747b932014-03-05 14:22:34 +01001507
1508 def get_peer_finished(self):
1509 """
Jean-Paul Calderoneac209562014-03-30 11:26:32 -04001510 Obtain the latest `handshake finished` message received from the peer.
Fedor Brunner5747b932014-03-05 14:22:34 +01001511
Jean-Paul Calderoneac209562014-03-30 11:26:32 -04001512 :return: The contents of the message or :py:obj:`None` if the TLS
1513 handshake has not yet completed.
1514 :rtype: :py:class:`bytes` or :py:class:`NoneType`
Fedor Brunner5747b932014-03-05 14:22:34 +01001515 """
Jean-Paul Calderoneac209562014-03-30 11:26:32 -04001516 return self._get_finished_message(_lib.SSL_get_peer_finished)
Fedor Brunner5747b932014-03-05 14:22:34 +01001517
Jean-Paul Calderone7c556ef2014-03-30 10:45:00 -04001518
Fedor Brunnerd95014a2014-03-03 17:34:41 +01001519 def get_cipher_name(self):
1520 """
1521 Obtain the name of the currently used cipher.
Jean-Paul Calderone9e3ccd42014-03-29 18:13:36 -04001522
Fedor Brunnerd95014a2014-03-03 17:34:41 +01001523 :returns: The name of the currently used cipher or :py:obj:`None`
1524 if no connection has been established.
Jean-Paul Calderone7f0ded42014-03-30 10:34:17 -04001525 :rtype: :py:class:`unicode` or :py:class:`NoneType`
Fedor Brunnerd95014a2014-03-03 17:34:41 +01001526 """
1527 cipher = _lib.SSL_get_current_cipher(self._ssl)
1528 if cipher == _ffi.NULL:
1529 return None
1530 else:
Jean-Paul Calderone7f0ded42014-03-30 10:34:17 -04001531 name = _ffi.string(_lib.SSL_CIPHER_get_name(cipher))
1532 return name.decode("utf-8")
Fedor Brunnerd95014a2014-03-03 17:34:41 +01001533
Jean-Paul Calderonedbd76272014-03-29 18:09:40 -04001534
Fedor Brunnerd95014a2014-03-03 17:34:41 +01001535 def get_cipher_bits(self):
1536 """
1537 Obtain the number of secret bits of the currently used cipher.
Jean-Paul Calderone9e3ccd42014-03-29 18:13:36 -04001538
Fedor Brunnerd95014a2014-03-03 17:34:41 +01001539 :returns: The number of secret bits of the currently used cipher
1540 or :py:obj:`None` if no connection has been established.
Jean-Paul Calderone9e3ccd42014-03-29 18:13:36 -04001541 :rtype: :py:class:`int` or :py:class:`NoneType`
Fedor Brunnerd95014a2014-03-03 17:34:41 +01001542 """
1543 cipher = _lib.SSL_get_current_cipher(self._ssl)
1544 if cipher == _ffi.NULL:
1545 return None
1546 else:
1547 return _lib.SSL_CIPHER_get_bits(cipher, _ffi.NULL)
1548
Jean-Paul Calderonedbd76272014-03-29 18:09:40 -04001549
Fedor Brunnerd95014a2014-03-03 17:34:41 +01001550 def get_cipher_version(self):
1551 """
Jean-Paul Calderone9e3ccd42014-03-29 18:13:36 -04001552 Obtain the protocol version of the currently used cipher.
1553
Fedor Brunnerd95014a2014-03-03 17:34:41 +01001554 :returns: The protocol name of the currently used cipher
1555 or :py:obj:`None` if no connection has been established.
Jean-Paul Calderone7f0ded42014-03-30 10:34:17 -04001556 :rtype: :py:class:`unicode` or :py:class:`NoneType`
Fedor Brunnerd95014a2014-03-03 17:34:41 +01001557 """
1558 cipher = _lib.SSL_get_current_cipher(self._ssl)
1559 if cipher == _ffi.NULL:
1560 return None
1561 else:
Jean-Paul Calderone7f0ded42014-03-30 10:34:17 -04001562 version =_ffi.string(_lib.SSL_CIPHER_get_version(cipher))
1563 return version.decode("utf-8")
Fedor Brunnerd95014a2014-03-03 17:34:41 +01001564
1565
1566
Jean-Paul Calderone131052e2013-03-05 11:56:19 -08001567ConnectionType = Connection
Jean-Paul Calderone11ed8e82014-01-18 10:21:50 -05001568
Jean-Paul Calderonefab157b2014-01-18 11:21:38 -05001569# This is similar to the initialization calls at the end of OpenSSL/crypto.py
1570# but is exercised mostly by the Context initializer.
Jean-Paul Calderone11ed8e82014-01-18 10:21:50 -05001571_lib.SSL_library_init()