transit: use bidirectional connections
This commit is contained in:
parent
01dbec820b
commit
99e08c2e37
|
@ -8,11 +8,11 @@ APPID = "lothar.com/wormhole/file-xfer"
|
||||||
|
|
||||||
# we're receiving
|
# we're receiving
|
||||||
transit_receiver = TransitReceiver()
|
transit_receiver = TransitReceiver()
|
||||||
direct_hints = transit_receiver.get_direct_hints()
|
|
||||||
|
|
||||||
mydata = json.dumps({
|
mydata = json.dumps({
|
||||||
"transit": {
|
"transit": {
|
||||||
"direct_connection_hints": direct_hints,
|
"direct_connection_hints": transit_receiver.get_direct_hints(),
|
||||||
|
"relay_connection_hints": transit_receiver.get_relay_hints(),
|
||||||
},
|
},
|
||||||
}).encode("utf-8")
|
}).encode("utf-8")
|
||||||
r = Receiver(APPID, mydata)
|
r = Receiver(APPID, mydata)
|
||||||
|
@ -31,8 +31,8 @@ encrypted_filesize = filesize + SecretBox.NONCE_SIZE+16
|
||||||
tdata = data["transit"]
|
tdata = data["transit"]
|
||||||
transit_key = r.derive_key(APPID+"/transit-key")
|
transit_key = r.derive_key(APPID+"/transit-key")
|
||||||
transit_receiver.set_transit_key(transit_key)
|
transit_receiver.set_transit_key(transit_key)
|
||||||
transit_receiver.add_sender_direct_hints(tdata["direct_connection_hints"])
|
transit_receiver.add_their_direct_hints(tdata["direct_connection_hints"])
|
||||||
transit_receiver.add_sender_relay_hints(tdata["relay_connection_hints"])
|
transit_receiver.add_their_relay_hints(tdata["relay_connection_hints"])
|
||||||
skt = transit_receiver.establish_connection()
|
skt = transit_receiver.establish_connection()
|
||||||
print("Receiving %d bytes.." % filesize)
|
print("Receiving %d bytes.." % filesize)
|
||||||
encrypted = b""
|
encrypted = b""
|
||||||
|
|
|
@ -10,8 +10,6 @@ APPID = "lothar.com/wormhole/file-xfer"
|
||||||
filename = sys.argv[1]
|
filename = sys.argv[1]
|
||||||
assert os.path.isfile(filename)
|
assert os.path.isfile(filename)
|
||||||
transit_sender = TransitSender()
|
transit_sender = TransitSender()
|
||||||
direct_hints = transit_sender.get_direct_hints()
|
|
||||||
relay_hints = transit_sender.get_relay_hints()
|
|
||||||
|
|
||||||
filesize = os.stat(filename).st_size
|
filesize = os.stat(filename).st_size
|
||||||
data = json.dumps({
|
data = json.dumps({
|
||||||
|
@ -20,8 +18,8 @@ data = json.dumps({
|
||||||
"filesize": filesize,
|
"filesize": filesize,
|
||||||
},
|
},
|
||||||
"transit": {
|
"transit": {
|
||||||
"direct_connection_hints": direct_hints,
|
"direct_connection_hints": transit_sender.get_direct_hints(),
|
||||||
"relay_connection_hints": relay_hints,
|
"relay_connection_hints": transit_sender.get_relay_hints(),
|
||||||
},
|
},
|
||||||
}).encode("utf-8")
|
}).encode("utf-8")
|
||||||
|
|
||||||
|
@ -44,7 +42,8 @@ encrypted = box.encrypt(plaintext, nonce)
|
||||||
tdata = them_d["transit"]
|
tdata = them_d["transit"]
|
||||||
transit_key = i.derive_key(APPID+"/transit-key")
|
transit_key = i.derive_key(APPID+"/transit-key")
|
||||||
transit_sender.set_transit_key(transit_key)
|
transit_sender.set_transit_key(transit_key)
|
||||||
transit_sender.add_receiver_hints(tdata["direct_connection_hints"])
|
transit_sender.add_their_direct_hints(tdata["direct_connection_hints"])
|
||||||
|
transit_sender.add_their_relay_hints(tdata["relay_connection_hints"])
|
||||||
skt = transit_sender.establish_connection()
|
skt = transit_sender.establish_connection()
|
||||||
|
|
||||||
print("Sending %d bytes.." % filesize)
|
print("Sending %d bytes.." % filesize)
|
||||||
|
|
|
@ -153,13 +153,28 @@ class TransitSender:
|
||||||
self._negotiation_check_lock = threading.Lock()
|
self._negotiation_check_lock = threading.Lock()
|
||||||
self._have_transit_key = threading.Condition()
|
self._have_transit_key = threading.Condition()
|
||||||
self._transit_key = None
|
self._transit_key = None
|
||||||
|
self._start_server()
|
||||||
|
|
||||||
|
def _start_server(self):
|
||||||
|
server = MyTCPServer(("",9999), None)
|
||||||
|
_, port = server.server_address
|
||||||
|
self.my_direct_hints = ["%s,%d" % (addr, port)
|
||||||
|
for addr in ipaddrs.find_addresses()]
|
||||||
|
server.owner = self
|
||||||
|
server_thread = threading.Thread(target=server.serve_forever)
|
||||||
|
server_thread.daemon = True
|
||||||
|
server_thread.start()
|
||||||
|
self.listener = server
|
||||||
|
|
||||||
def get_direct_hints(self):
|
def get_direct_hints(self):
|
||||||
return []
|
return self.my_direct_hints
|
||||||
def get_relay_hints(self):
|
def get_relay_hints(self):
|
||||||
return []
|
return []
|
||||||
def add_receiver_hints(self, hints):
|
|
||||||
self.receiver_hints = hints
|
def add_their_direct_hints(self, hints):
|
||||||
|
self._their_direct_hints = hints
|
||||||
|
def add_their_relay_hints(self, hints):
|
||||||
|
self._their_relay_hints = hints # ignored
|
||||||
|
|
||||||
def set_transit_key(self, key):
|
def set_transit_key(self, key):
|
||||||
# This _have_transit_key condition/lock protects us against the race
|
# This _have_transit_key condition/lock protects us against the race
|
||||||
|
@ -168,24 +183,26 @@ class TransitSender:
|
||||||
# (and thus the key).
|
# (and thus the key).
|
||||||
self._have_transit_key.acquire()
|
self._have_transit_key.acquire()
|
||||||
self._transit_key = key
|
self._transit_key = key
|
||||||
#self.handler_send_handshake = build_receiver_handshake(key)
|
self.handler_send_handshake = build_sender_handshake(key) # no "go"
|
||||||
#self.handler_expected_handshake = build_sender_handshake(key) + "go\n"
|
self.handler_expected_handshake = build_receiver_handshake(key)
|
||||||
self._have_transit_key.notify_all()
|
self._have_transit_key.notify_all()
|
||||||
self._have_transit_key.release()
|
self._have_transit_key.release()
|
||||||
|
|
||||||
def establish_connection(self):
|
def _start_outbound(self):
|
||||||
sender_handshake = build_sender_handshake(self._transit_key)
|
sender_handshake = build_sender_handshake(self._transit_key)
|
||||||
receiver_handshake = build_receiver_handshake(self._transit_key)
|
receiver_handshake = build_receiver_handshake(self._transit_key)
|
||||||
self.listener = None
|
|
||||||
self.connectors = []
|
self.connectors = []
|
||||||
self.winning_skt = None
|
for hint in self._their_direct_hints:
|
||||||
for hint in self.receiver_hints:
|
|
||||||
t = threading.Thread(target=connector,
|
t = threading.Thread(target=connector,
|
||||||
args=(self, hint,
|
args=(self, hint,
|
||||||
sender_handshake, receiver_handshake))
|
sender_handshake, receiver_handshake))
|
||||||
t.daemon = True
|
t.daemon = True
|
||||||
t.start()
|
t.start()
|
||||||
|
|
||||||
|
def establish_connection(self):
|
||||||
|
self.winning_skt = None
|
||||||
|
self._start_outbound()
|
||||||
|
|
||||||
# we sit here until one of our inbound or outbound sockets succeeds
|
# we sit here until one of our inbound or outbound sockets succeeds
|
||||||
flag = self.winning.wait(TIMEOUT)
|
flag = self.winning.wait(TIMEOUT)
|
||||||
|
|
||||||
|
@ -225,7 +242,10 @@ class TransitReceiver:
|
||||||
self._negotiation_check_lock = threading.Lock()
|
self._negotiation_check_lock = threading.Lock()
|
||||||
self._have_transit_key = threading.Condition()
|
self._have_transit_key = threading.Condition()
|
||||||
self._transit_key = None
|
self._transit_key = None
|
||||||
server = MyTCPServer(("",9999), None)
|
self._start_server()
|
||||||
|
|
||||||
|
def _start_server(self):
|
||||||
|
server = MyTCPServer(("",9998), None)
|
||||||
_, port = server.server_address
|
_, port = server.server_address
|
||||||
self.my_direct_hints = ["%s,%d" % (addr, port)
|
self.my_direct_hints = ["%s,%d" % (addr, port)
|
||||||
for addr in ipaddrs.find_addresses()]
|
for addr in ipaddrs.find_addresses()]
|
||||||
|
@ -237,6 +257,13 @@ class TransitReceiver:
|
||||||
|
|
||||||
def get_direct_hints(self):
|
def get_direct_hints(self):
|
||||||
return self.my_direct_hints
|
return self.my_direct_hints
|
||||||
|
def get_relay_hints(self):
|
||||||
|
return []
|
||||||
|
|
||||||
|
def add_their_direct_hints(self, hints):
|
||||||
|
self._their_direct_hints = hints
|
||||||
|
def add_their_relay_hints(self, hints):
|
||||||
|
self._their_relay_hints = hints # ignored
|
||||||
|
|
||||||
def set_transit_key(self, key):
|
def set_transit_key(self, key):
|
||||||
# This _have_transit_key condition/lock protects us against the race
|
# This _have_transit_key condition/lock protects us against the race
|
||||||
|
@ -250,13 +277,20 @@ class TransitReceiver:
|
||||||
self._have_transit_key.notify_all()
|
self._have_transit_key.notify_all()
|
||||||
self._have_transit_key.release()
|
self._have_transit_key.release()
|
||||||
|
|
||||||
def add_sender_direct_hints(self, hints):
|
def _start_outbound(self):
|
||||||
self.sender_direct_hints = hints # TODO ignored
|
sender_handshake = build_sender_handshake(self._transit_key) + "go\n"
|
||||||
def add_sender_relay_hints(self, hints):
|
receiver_handshake = build_receiver_handshake(self._transit_key)
|
||||||
self.sender_relay_hints = hints # TODO ignored
|
self.connectors = []
|
||||||
|
for hint in self._their_direct_hints:
|
||||||
|
t = threading.Thread(target=connector,
|
||||||
|
args=(self, hint, # SWAPPED
|
||||||
|
receiver_handshake, sender_handshake))
|
||||||
|
t.daemon = True
|
||||||
|
t.start()
|
||||||
|
|
||||||
def establish_connection(self):
|
def establish_connection(self):
|
||||||
self.winning_skt = None
|
self.winning_skt = None
|
||||||
|
self._start_outbound()
|
||||||
|
|
||||||
# we sit here until one of our inbound or outbound sockets succeeds
|
# we sit here until one of our inbound or outbound sockets succeeds
|
||||||
flag = self.winning.wait(TIMEOUT)
|
flag = self.winning.wait(TIMEOUT)
|
||||||
|
|
Loading…
Reference in New Issue
Block a user