def should_join_circuit(self, create_payload, previous_node_address): """ Check whether we should join a circuit. Returns a deferred that fires with a boolean. """ if self.settings.max_joined_circuits <= len(self.relay_from_to) + len(self.exit_sockets): self.logger.warning("too many relays (%d)", (len(self.relay_from_to) + len(self.exit_sockets))) return succeed(False) # Check whether we have a random open slot, if so, allocate this to this request. circuit_id = create_payload.circuit_id for index, slot in enumerate(self.random_slots): if not slot: self.random_slots[index] = circuit_id return succeed(True) # No random slots but this user might be allocated a competing slot. # Next, we request the token balance of the circuit initiator. balance_deferred = Deferred() self.request_cache.add(BalanceRequestCache(self, circuit_id, balance_deferred)) # Temporarily add these values, otherwise we are unable to communicate with the previous hop. self.directions[circuit_id] = EXIT_NODE shared_secret, _, _ = self.crypto.generate_diffie_shared_secret(create_payload.key) self.relay_session_keys[circuit_id] = self.crypto.generate_session_keys(shared_secret) self.send_cell([Peer(create_payload.node_public_key, previous_node_address)], u"balance-request", BalanceRequestPayload(circuit_id)) self.directions.pop(circuit_id, None) self.relay_session_keys.pop(circuit_id, None) return balance_deferred
def on_balance_request_cell(self, source_address, data, _): payload = self._ez_unpack_noauth(BalanceRequestPayload, data, global_time=False) circuit_id = payload.circuit_id request = self.request_cache.get(u"anon-circuit", circuit_id) if request.should_forward: forwarding_relay = RelayRoute(request.from_circuit_id, request.peer) self.send_cell([forwarding_relay.peer.address], u"relay-balance-request", BalanceRequestPayload(forwarding_relay.circuit_id)) else: self.on_balance_request(payload)
def on_balance_request_cell(self, source_address, data, _): _, payload = self._ez_unpack_noauth(BalanceRequestPayload, data) circuit_id = payload.circuit_id request = self.request_cache.get(u"anon-circuit", circuit_id) if request.should_forward: forwarding_relay = RelayRoute(request.from_circuit_id, request.candidate_sock_addr, mid=request.candidate_mid) self.send_cell([forwarding_relay.sock_addr], u"relay-balance-request", BalanceRequestPayload(forwarding_relay.circuit_id)) else: self.on_balance_request(payload)
def on_balance_request_cell(self, source_address, data, _): payload = self._ez_unpack_noauth(BalanceRequestPayload, data, global_time=False) if self.request_cache.has(u"create", payload.circuit_id): request = self.request_cache.get(u"create", payload.circuit_id) forwarding_relay = RelayRoute(request.from_circuit_id, request.peer) self.send_cell([forwarding_relay.peer.address], u"relay-balance-request", BalanceRequestPayload(forwarding_relay.circuit_id)) elif self.request_cache.has(u"circuit", payload.circuit_id): self.on_balance_request(payload) else: self.logger.warning("Circuit creation cache for id %s not found!", payload.circuit_id)