net: Store recipient node address in private broadcast

This commit is contained in:
Andrew Toth 2026-01-25 13:17:52 -05:00
parent 64294c8909
commit 573bb542be
No known key found for this signature in database
GPG Key ID: 60007AFC8938B018
4 changed files with 14 additions and 9 deletions

View File

@ -3531,7 +3531,7 @@ void PeerManagerImpl::PushPrivateBroadcastTx(CNode& node)
{
Assume(node.IsPrivateBroadcastConn());
const auto opt_tx{m_tx_for_private_broadcast.PickTxForSend(node.GetId())};
const auto opt_tx{m_tx_for_private_broadcast.PickTxForSend(node.GetId(), CService{node.addr})};
if (!opt_tx) {
LogDebug(BCLog::PRIVBROADCAST, "Disconnecting: no more transactions for private broadcast (connected in vain), peer=%d%s", node.GetId(), node.LogIP(fLogIPs));
node.fDisconnect = true;

View File

@ -31,7 +31,7 @@ std::optional<size_t> PrivateBroadcast::Remove(const CTransactionRef& tx)
return std::nullopt;
}
std::optional<CTransactionRef> PrivateBroadcast::PickTxForSend(const NodeId& will_send_to_nodeid)
std::optional<CTransactionRef> PrivateBroadcast::PickTxForSend(const NodeId& will_send_to_nodeid, const CService& will_send_to_address)
EXCLUSIVE_LOCKS_REQUIRED(!m_mutex)
{
LOCK(m_mutex);
@ -43,7 +43,7 @@ std::optional<CTransactionRef> PrivateBroadcast::PickTxForSend(const NodeId& wil
if (it != m_transactions.end()) {
auto& [tx, sent_to]{*it};
sent_to.emplace_back(will_send_to_nodeid, NodeClock::now());
sent_to.emplace_back(will_send_to_nodeid, will_send_to_address, NodeClock::now());
return tx;
}

View File

@ -54,9 +54,11 @@ public:
* and oldest send/confirm times.
* @param[in] will_send_to_nodeid Will remember that the returned transaction
* was picked for sending to this node.
* @param[in] will_send_to_address Address of the peer to which this transaction
* will be sent.
* @return Most urgent transaction or nullopt if there are no transactions.
*/
std::optional<CTransactionRef> PickTxForSend(const NodeId& will_send_to_nodeid)
std::optional<CTransactionRef> PickTxForSend(const NodeId& will_send_to_nodeid, const CService& will_send_to_address)
EXCLUSIVE_LOCKS_REQUIRED(!m_mutex);
/**
@ -99,10 +101,11 @@ private:
/// Status of a transaction sent to a given node.
struct SendStatus {
const NodeId nodeid; /// Node to which the transaction will be sent (or was sent).
const CService address; /// Address of the node.
const NodeClock::time_point picked; ///< When was the transaction picked for sending to the node.
std::optional<NodeClock::time_point> confirmed; ///< When was the transaction reception confirmed by the node (by PONG).
SendStatus(const NodeId& nodeid, const NodeClock::time_point& picked) : nodeid{nodeid}, picked{picked} {}
SendStatus(const NodeId& nodeid, const CService& address, const NodeClock::time_point& picked) : nodeid{nodeid}, address{address}, picked{picked} {}
};
/// Cumulative stats from all the send attempts for a transaction. Used to prioritize transactions.

View File

@ -29,9 +29,10 @@ BOOST_AUTO_TEST_CASE(basic)
PrivateBroadcast pb;
const NodeId recipient1{1};
const CService addr1{};
// No transactions initially.
BOOST_CHECK(!pb.PickTxForSend(/*will_send_to_nodeid=*/recipient1).has_value());
BOOST_CHECK(!pb.PickTxForSend(/*will_send_to_nodeid=*/recipient1, /*will_send_to_address=*/addr1).has_value());
BOOST_CHECK_EQUAL(pb.GetStale().size(), 0);
BOOST_CHECK(!pb.HavePendingTransactions());
@ -48,12 +49,13 @@ BOOST_AUTO_TEST_CASE(basic)
BOOST_CHECK(pb.Add(tx2));
const auto tx_for_recipient1{pb.PickTxForSend(/*will_send_to_nodeid=*/recipient1).value()};
const auto tx_for_recipient1{pb.PickTxForSend(/*will_send_to_nodeid=*/recipient1, /*will_send_to_address=*/addr1).value()};
BOOST_CHECK(tx_for_recipient1 == tx1 || tx_for_recipient1 == tx2);
// A second pick must return the other transaction.
const NodeId recipient2{2};
const auto tx_for_recipient2{pb.PickTxForSend(/*will_send_to_nodeid=*/recipient2).value()};
const CService addr2{};
const auto tx_for_recipient2{pb.PickTxForSend(/*will_send_to_nodeid=*/recipient2, /*will_send_to_address=*/addr2).value()};
BOOST_CHECK(tx_for_recipient2 == tx1 || tx_for_recipient2 == tx2);
BOOST_CHECK_NE(tx_for_recipient1, tx_for_recipient2);
@ -90,7 +92,7 @@ BOOST_AUTO_TEST_CASE(basic)
BOOST_CHECK_EQUAL(pb.Remove(tx_for_recipient2).value(), 0);
BOOST_CHECK(!pb.Remove(tx_for_recipient2).has_value());
BOOST_CHECK(!pb.PickTxForSend(/*will_send_to_nodeid=*/nonexistent_recipient).has_value());
BOOST_CHECK(!pb.PickTxForSend(/*will_send_to_nodeid=*/nonexistent_recipient, /*will_send_to_address=*/CService{}).has_value());
}
BOOST_AUTO_TEST_SUITE_END()