From 2b603fd7e1335a07143a5542c698cf2c26628d3b Mon Sep 17 00:00:00 2001 From: Zhenchao Li Date: Tue, 27 Jul 2010 21:29:12 +0800 Subject: [PATCH] add some code to allow testing using some pre-existing certificates. TODO: manually handle handshake states to allow non-blocking I/O --- src/common/jingle_ft.py | 5 +++-- src/common/jingle_xtls.py | 12 +++++++++++- src/common/socks5.py | 13 +++++++++++++ 3 files changed, 27 insertions(+), 3 deletions(-) diff --git a/src/common/jingle_ft.py b/src/common/jingle_ft.py index 9e3ec53a2..d340ddbf9 100644 --- a/src/common/jingle_ft.py +++ b/src/common/jingle_ft.py @@ -199,7 +199,7 @@ class JingleFileTransfer(JingleContent): port = gajim.config.get('file_transfers_port') listener = gajim.socks5queue.start_listener(port, sha_str, - self._store_socks5_sid, self.file_props['sid']) + self._store_socks5_sid, self.file_props['sid'], fingerprint = 'server') if not listener: return @@ -209,7 +209,8 @@ class JingleFileTransfer(JingleContent): if not gajim.socks5queue.get_file_props(self.session.connection.name, self.file_props['sid']): gajim.socks5queue.add_file_props(self.session.connection.name, self.file_props) gajim.socks5queue.connect_to_hosts(self.session.connection.name, self.file_props['sid'], - self.send_candidate_used, self._on_connect_error) + self.send_candidate_used, self._on_connect_error, + fingerprint = 'client') elif not self.weinitiate and self.state == STATE_ACCEPTED: # transport-info iq-result self.state = STATE_TRANSPORT_INFO elif self.weinitiate and self.state == STATE_INITIALIZED: # proxy activated diff --git a/src/common/jingle_xtls.py b/src/common/jingle_xtls.py index cc5ea3945..10a63bc4a 100644 --- a/src/common/jingle_xtls.py +++ b/src/common/jingle_xtls.py @@ -16,6 +16,8 @@ ## along with Gajim. If not, see . ## +import os + import logging log = logging.getLogger('gajim.c.jingle_xtls') @@ -36,8 +38,16 @@ def get_context(fingerprint, verify_cb=None): """ constructs and returns the context objects """ - ctx = SSL.Context(TLSv1_METHOD) + ctx = SSL.Context(SSL.TLSv1_METHOD) ctx.set_verify(SSL.VERIFY_PEER|SSL.VERIFY_FAIL_IF_NO_PEER_CERT, verify_cb or default_callback) # TODO: set private key, set certificate, set verification path + if fingerprint == 'server': # for testing purposes only + ctx.use_privatekey_file (os.path.expanduser('~/certs/server.pkey')) + ctx.use_certificate_file(os.path.expanduser('~/certs/server.cert')) + ctx.load_verify_locations(os.path.expanduser('~/certs/CA.cert')) + elif fingerprint == 'client': + ctx.use_privatekey_file (os.path.expanduser('~/certs/client.pkey')) + ctx.use_certificate_file(os.path.expanduser('~/certs/client.cert')) + ctx.load_verify_locations(os.path.expanduser('~/certs/CA.cert')) return ctx diff --git a/src/common/socks5.py b/src/common/socks5.py index 364f0eadc..09489bde0 100644 --- a/src/common/socks5.py +++ b/src/common/socks5.py @@ -36,6 +36,11 @@ from errno import EINPROGRESS from errno import EAFNOSUPPORT from xmpp.idlequeue import IdleObject +import jingle_xtls + +if jingle_xtls.PYOPENSSL_PRESENT: + import OpenSSL + import logging log = logging.getLogger('gajim.c.socks5') @@ -867,12 +872,16 @@ class Socks5Listener(IdleObject): self.started = False self._sock = None self.fd = -1 + self.fingerprint = fingerprint def bind(self): for ai in self.ais: # try the different possibilities (ipv6, ipv4, etc.) try: self._serv = socket.socket(*ai[:3]) + if not self.fingerprint is None: + self._serv = OpenSSL.SSL.Connection( + jingle_xtls.get_context('server'), self._serv) except socket.error, e: if e.args[0] == EAFNOSUPPORT: self.ai = None @@ -949,6 +958,7 @@ class Socks5Receiver(Socks5, IdleObject): self.streamhost = streamhost self.queue = None self.file_props = file_props + self.fingerprint = fingerprint self.connect_timeout = 0 self.connected = False self.pauses = 0 @@ -992,6 +1002,9 @@ class Socks5Receiver(Socks5, IdleObject): for ai in self.ais: try: self._sock = socket.socket(*ai[:3]) + if not self.fingerprint is None: + self._sock = OpenSSL.SSL.Connection( + jingle_xtls.get_context('client'), self._sock) # this will not block the GUI self._sock.setblocking(False) self._server = ai[4]