Bubble up an event when Bob receives message 3 response

Before this patch Bob is not sending message 3. This is because we are not
polling Bob's swarm correctly. To fix it we can just mimic the other NB's and
bubble up an event when Bob receives message 3 response from Alice, this way we
can `await` upon this event which triggers polling, making Bob's swarm send the
message.
This commit is contained in:
Tobin C. Harding 2020-10-30 09:26:52 +11:00 committed by Lucas Soriano del Pino
parent a37f43a1ba
commit 4d4acde476
6 changed files with 49 additions and 16 deletions

View File

@ -78,10 +78,15 @@ pub async fn swap(
#[derive(Debug)] #[derive(Debug)]
struct UnexpectedMessage; struct UnexpectedMessage;
tracing::debug!("Receiving bitcoin redeem encsig");
(|| async { (|| async {
let mut guard = self.swarm.lock().await; let mut guard = self.swarm.lock().await;
let encsig = match guard.next().await { let encsig = match guard.next().await {
OutEvent::Message3(msg) => msg.tx_redeem_encsig, OutEvent::Message3(msg) => {
tracing::debug!("Got redeem encsig from Bob");
msg.tx_redeem_encsig
}
other => { other => {
warn!("Expected Bob's Message3, got: {:?}", other); warn!("Expected Bob's Message3, got: {:?}", other);
return Err(backoff::Error::Transient(UnexpectedMessage)); return Err(backoff::Error::Transient(UnexpectedMessage));

View File

@ -73,6 +73,7 @@ impl NetworkBehaviourEventProcess<RequestResponseEvent<BobToAlice, AliceToBob>>
.. ..
} => { } => {
if let BobToAlice::Message3(msg) = request { if let BobToAlice::Message3(msg) = request {
tracing::debug!("Alice: got message 3 from Bob");
self.events.push_back(OutEvent::Msg(msg)); self.events.push_back(OutEvent::Msg(msg));
// Send back empty response so that the request/response protocol completes. // Send back empty response so that the request/response protocol completes.
self.rr.send_response(channel, AliceToBob::Message3); self.rr.send_response(channel, AliceToBob::Message3);

View File

@ -29,7 +29,7 @@ use crate::{
peer_tracker::{self, PeerTracker}, peer_tracker::{self, PeerTracker},
transport, TokioExecutor, transport, TokioExecutor,
}, },
Cmd, Never, Rsp, SwapAmounts, PUNISH_TIMELOCK, REFUND_TIMELOCK, Cmd, Rsp, SwapAmounts, PUNISH_TIMELOCK, REFUND_TIMELOCK,
}; };
use xmr_btc::{ use xmr_btc::{
alice, alice,
@ -64,7 +64,10 @@ pub async fn swap(
(|| async { (|| async {
let proof = match future.clone().await { let proof = match future.clone().await {
OutEvent::Message2(msg) => msg.tx_lock_proof, OutEvent::Message2(msg) => {
debug!("Got transfer proof from Alice");
msg.tx_lock_proof
}
other => { other => {
warn!("Expected Alice's Message2, got: {:?}", other); warn!("Expected Alice's Message2, got: {:?}", other);
return Err(backoff::Error::Transient(UnexpectedMessage)); return Err(backoff::Error::Transient(UnexpectedMessage));
@ -164,7 +167,14 @@ pub async fn swap(
} }
GeneratorState::Yielded(bob::Action::SendBtcRedeemEncsig(tx_redeem_encsig)) => { GeneratorState::Yielded(bob::Action::SendBtcRedeemEncsig(tx_redeem_encsig)) => {
let mut guard = network.as_ref().lock().await; let mut guard = network.as_ref().lock().await;
debug!("Bob: sending message 3");
guard.0.send_message3(alice.clone(), tx_redeem_encsig); guard.0.send_message3(alice.clone(), tx_redeem_encsig);
match guard.0.next().shared().await {
OutEvent::Message3 => {
debug!("Got message 3 response from Alice");
}
other => panic!("unexpected event: {:?}", other),
};
} }
GeneratorState::Yielded(bob::Action::CreateXmrWalletForOutput { GeneratorState::Yielded(bob::Action::CreateXmrWalletForOutput {
spend_key, spend_key,
@ -227,6 +237,7 @@ pub enum OutEvent {
Message0(alice::Message0), Message0(alice::Message0),
Message1(alice::Message1), Message1(alice::Message1),
Message2(alice::Message2), Message2(alice::Message2),
Message3,
} }
impl From<peer_tracker::OutEvent> for OutEvent { impl From<peer_tracker::OutEvent> for OutEvent {
@ -271,9 +282,11 @@ impl From<message2::OutEvent> for OutEvent {
} }
} }
impl From<Never> for OutEvent { impl From<message3::OutEvent> for OutEvent {
fn from(_: Never) -> Self { fn from(event: message3::OutEvent) -> Self {
panic!("not ever") match event {
message3::OutEvent::Msg => OutEvent::Message3,
}
} }
} }

View File

@ -7,38 +7,46 @@ use libp2p::{
NetworkBehaviour, PeerId, NetworkBehaviour, PeerId,
}; };
use std::{ use std::{
collections::VecDeque,
task::{Context, Poll}, task::{Context, Poll},
time::Duration, time::Duration,
}; };
use tracing::{debug, error}; use tracing::error;
use crate::{ use crate::network::request_response::{AliceToBob, BobToAlice, Codec, Message3Protocol, TIMEOUT};
network::request_response::{AliceToBob, BobToAlice, Codec, Message3Protocol, TIMEOUT},
Never,
};
use xmr_btc::bob; use xmr_btc::bob;
#[derive(Debug)]
pub enum OutEvent {
Msg,
}
/// A `NetworkBehaviour` that represents sending message 3 to Alice. /// A `NetworkBehaviour` that represents sending message 3 to Alice.
#[derive(NetworkBehaviour)] #[derive(NetworkBehaviour)]
#[behaviour(out_event = "Never", poll_method = "poll")] #[behaviour(out_event = "OutEvent", poll_method = "poll")]
#[allow(missing_debug_implementations)] #[allow(missing_debug_implementations)]
pub struct Message3 { pub struct Message3 {
rr: RequestResponse<Codec<Message3Protocol>>, rr: RequestResponse<Codec<Message3Protocol>>,
#[behaviour(ignore)]
events: VecDeque<OutEvent>,
} }
impl Message3 { impl Message3 {
pub fn send(&mut self, alice: PeerId, msg: bob::Message3) { pub fn send(&mut self, alice: PeerId, msg: bob::Message3) {
let msg = BobToAlice::Message3(msg); let msg = BobToAlice::Message3(msg);
tracing::debug!("sending ...");
let _id = self.rr.send_request(&alice, msg); let _id = self.rr.send_request(&alice, msg);
} }
// TODO: Do we need a custom implementation if we are not bubbling any out
// events?
fn poll( fn poll(
&mut self, &mut self,
_: &mut Context<'_>, _: &mut Context<'_>,
_: &mut impl PollParameters, _: &mut impl PollParameters,
) -> Poll<NetworkBehaviourAction<RequestProtocol<Codec<Message3Protocol>>, Never>> { ) -> Poll<NetworkBehaviourAction<RequestProtocol<Codec<Message3Protocol>>, OutEvent>> {
if let Some(event) = self.events.pop_front() {
return Poll::Ready(NetworkBehaviourAction::GenerateEvent(event));
}
Poll::Pending Poll::Pending
} }
} }
@ -55,6 +63,7 @@ impl Default for Message3 {
vec![(Message3Protocol, ProtocolSupport::Full)], vec![(Message3Protocol, ProtocolSupport::Full)],
config, config,
), ),
events: Default::default(),
} }
} }
} }
@ -71,7 +80,8 @@ impl NetworkBehaviourEventProcess<RequestResponseEvent<BobToAlice, AliceToBob>>
.. ..
} => { } => {
if let AliceToBob::Message3 = response { if let AliceToBob::Message3 = response {
debug!("Alice correctly responded to message 3"); self.events.push_back(OutEvent::Msg);
tracing::debug!("Alice correctly responded to message 3");
} }
} }
RequestResponseEvent::InboundFailure { error, .. } => { RequestResponseEvent::InboundFailure { error, .. } => {

View File

@ -175,6 +175,8 @@ where
} }
}; };
tracing::debug!("select returned redeem encsig from message");
tx_redeem_encsig tx_redeem_encsig
}; };

View File

@ -152,6 +152,8 @@ where
Either::Right(_) => return Err(SwapFailed::AfterBtcLock(Reason::BtcExpired)), Either::Right(_) => return Err(SwapFailed::AfterBtcLock(Reason::BtcExpired)),
}; };
tracing::debug!("select returned transfer proof from message");
transfer_proof transfer_proof
}; };