I need to connect to ipv6 server using pyopenssl .Is that even possible?For ipv4 i don't have any problem.This is what i'v tried for ipv6:
ctx = SSL.Context(SSL.SSLv23_METHOD)
ctx.set_verify(SSL.VERIFY_NONE, verify_cb)
ctx.use_privatekey_file (os.path.join(dir, 'client.pkey'))
ctx.use_certificate_file(os.path.join(dir, 'client.cert'))
ctx.load_verify_locations(os.path.join(dir, 'CA.cert'))
#Set up client
sock = SSL.Connection(ctx, socket.socket(socket.AF_INET6, socket.SOCK_STREAM))
sock.connect(('fe80::3a63:bbff:fe31:3013%ens32',443,0,0))
But i'm getting the following error:
sock.connect(('fe80::3a63:bbff:fe31:3013%ens32',443,0,0))
File "/root/Desktop/PY/ilodos2/venv/lib/python2.7/site-packages/OpenSSL/SSL.py", line 1455, in connect
return self._socket.connect(addr)
File "/usr/lib64/python2.7/socket.py", line 228, in meth
return getattr(self._sock,name)(*args)
error: [Errno 22] Invalid argument
The documentation of pyopenssl does not talk about ipv6 at all. If pyopenssl cant be used for ipv6, are there any other modules using which i can do ssl renegotiation?
The problem itself isn't really related to PyOpenSSL, when you're using scoped (link local) ipv6 addresses you neeed to pass the correct scopeid
as the fourth item of the address
tuple:
...
For AF_INET6 address family, a four-tuple (host, port, flowinfo, scopeid) is used, where flowinfo and scopeid represent the sin6_flowinfo and sin6_scope_id members in struct sockaddr_in6 in C. For socket module methods, flowinfo and scopeid can be omitted just for backward compatibility. Note, however, omission of scopeid can cause problems in manipulating scoped IPv6 addresses.
Consult ip addr
to show the correct numerical scope id, e.g. with scopeid 2 for ens32 the following should work:
sock.connect(('fe80::3a63:bbff:fe31:3013%ens32', 443, 0, 2))
Or use getaddrinfo()
to get the correct address:
ainfo = socket.getaddrinfo('fe80::3a63:bbff:fe31:3013%ens32', 443, socket.AF_INET6, socket.SOCK_STREAM)
address = ainfo[0][4]