diff --git a/swap/src/protocol/bob/state.rs b/swap/src/protocol/bob/state.rs index aa0045ea..9bb5f8a3 100644 --- a/swap/src/protocol/bob/state.rs +++ b/swap/src/protocol/bob/state.rs @@ -495,6 +495,30 @@ impl State4 { self.b.encsign(self.S_a_bitcoin, tx_redeem.digest()) } + pub async fn check_for_tx_redeem( + &self, + bitcoin_wallet: &bitcoin::Wallet, + ) -> Result { + let tx_redeem = + bitcoin::TxRedeem::new(&self.tx_lock, &self.redeem_address, self.tx_redeem_fee); + let tx_redeem_encsig = self.b.encsign(self.S_a_bitcoin, tx_redeem.digest()); + + let tx_redeem_candidate = bitcoin_wallet.get_raw_transaction(tx_redeem.txid()).await?; + + let tx_redeem_sig = + tx_redeem.extract_signature_by_key(tx_redeem_candidate, self.b.public())?; + let s_a = bitcoin::recover(self.S_a_bitcoin, tx_redeem_sig, tx_redeem_encsig)?; + let s_a = monero::private_key_from_secp256k1_scalar(s_a.into()); + + Ok(State5 { + s_a, + s_b: self.s_b, + v: self.v, + tx_lock: self.tx_lock.clone(), + monero_wallet_restore_blockheight: self.monero_wallet_restore_blockheight, + }) + } + pub async fn watch_for_redeem_btc(&self, bitcoin_wallet: &bitcoin::Wallet) -> Result { let tx_redeem = bitcoin::TxRedeem::new(&self.tx_lock, &self.redeem_address, self.tx_redeem_fee); diff --git a/swap/src/protocol/bob/swap.rs b/swap/src/protocol/bob/swap.rs index 667dae6e..19f91a58 100644 --- a/swap/src/protocol/bob/swap.rs +++ b/swap/src/protocol/bob/swap.rs @@ -185,7 +185,9 @@ async fn next_state( BobState::XmrLocked(state) => { let tx_lock_status = bitcoin_wallet.subscribe_to(state.tx_lock.clone()).await; - if let ExpiredTimelocks::None { .. } = state.expired_timelock(bitcoin_wallet).await? { + if let Ok(state5) = state.check_for_tx_redeem(bitcoin_wallet).await { + BobState::BtcRedeemed(state5) + } else if let ExpiredTimelocks::None { .. } = state.expired_timelock(bitcoin_wallet).await? { // Alice has locked Xmr // Bob sends Alice his key