我遇到代码错误:
File "/usr/local/lib/python2.7/site-packages/requests/packages/urllib3/contrib/pyopenssl.py", line 285, in ssl_wrap_socket
rd, _, _ = select.select([sock], [], [], sock.gettimeout())
ValueError: filedescriptor out of range in select()
这意味着具有select()
功能的文件描述符太多。代码是here。
也许出于可移植性的原因,代码使用select()
来过滤掉可读的描述符,
但我需要无限的文件描述符号,所以我必须用poll函数更改代码。
代码在Linux系统上运行;便携式思维将被忽略。
这是我的get rd代码。我是poll()
函数的新手;我的实施有什么问题吗?
该功能如下所示:
def ssl_wrap_socket(sock, keyfile=None, certfile=None, cert_reqs=None,
ca_certs=None, server_hostname=None,
ssl_version=None, ca_cert_dir=None):
ctx = OpenSSL.SSL.Context(_openssl_versions[ssl_version])
if certfile:
keyfile = keyfile or certfile # Match behaviour of the normal python ssl library
ctx.use_certificate_file(certfile)
if keyfile:
ctx.use_privatekey_file(keyfile)
if cert_reqs != ssl.CERT_NONE:
ctx.set_verify(_openssl_verify[cert_reqs], _verify_callback)
if ca_certs or ca_cert_dir:
try:
ctx.load_verify_locations(ca_certs, ca_cert_dir)
except OpenSSL.SSL.Error as e:
raise ssl.SSLError('bad ca_certs: %r' % ca_certs, e)
else:
ctx.set_default_verify_paths()
# Disable TLS compression to migitate CRIME attack (issue #309)
OP_NO_COMPRESSION = 0x20000
ctx.set_options(OP_NO_COMPRESSION)
# Set list of supported ciphersuites.
ctx.set_cipher_list(DEFAULT_SSL_CIPHER_LIST)
cnx = OpenSSL.SSL.Connection(ctx, sock)
cnx.set_tlsext_host_name(server_hostname)
cnx.set_connect_state()
while True:
try:
cnx.do_handshake()
except OpenSSL.SSL.WantReadError:
READ_ONLY = ( select.POLLIN | select.POLLPRI | select.POLLHUP | select.POLLERR)
poller = select.poll()
poller.register(sock, READ_ONLY)
fd_to_socket = {sock.fileno():sock,}
events = poller.poll(sock.gettimeout())
rd = []
for fd, flag in events:
s = fd_to_socket[fd]
if flag & (select.POLLIN | select.POLLPRI):
is s is sock:
rd.append(s)
if not rd:
raise timeout('poll timed out')
continue
except OpenSSL.SSL.Error as e:
raise ssl.SSLError('bad handshake: %r' % e)
break
return WrappedSocket(cnx, sock)