Skip to content

Commit 5b6f970

Browse files
committed
Merge #20171: Add functional test test_txid_inv_delay
bc4a230 Remove redundant p2p lock tacking for tx download functional tests (Antoine Riard) d3b5eac Add mutation for functional test test_preferred_inv (Antoine Riard) 06efb31 Add functional test test_txid_inv_delay (Antoine Riard) a07910a test: Makes wtxidrelay support a generic P2PInterface option (Antoine Riard) Pull request description: This is a simple functional test to increase coverage of #19988, checking that txid announcements from txid-relay peers are delayed by TXID_RELAY_DELAY, assuming we have at least another wtxid-relay peer. You can verify new test with the following diff : ``` diff --git a/src/net_processing.cpp b/src/net_processing.cpp index f14db37..2a2805df5 100644 --- a/src/net_processing.cpp +++ b/src/net_processing.cpp @@ -773,7 +773,7 @@ void PeerManager::AddTxAnnouncement(const CNode& node, const GenTxid& gtxid, std auto delay = std::chrono::microseconds{0}; const bool preferred = state->fPreferredDownload; if (!preferred) delay += NONPREF_PEER_TX_DELAY; - if (!gtxid.IsWtxid() && g_wtxid_relay_peers > 0) delay += TXID_RELAY_DELAY; + //if (!gtxid.IsWtxid() && g_wtxid_relay_peers > 0) delay += TXID_RELAY_DELAY; const bool overloaded = !node.HasPermission(PF_RELAY) && m_txrequest.CountInFlight(nodeid) >= MAX_PEER_TX_REQUEST_IN_FLIGHT; if (overloaded) delay += OVERLOADED_PEER_TX_DELAY; ``` ACKs for top commit: laanwj: ACK bc4a230 Tree-SHA512: 150e806bc5289feda94738756ab375c7fdd23c80c12bd417d3112043e26a91a717dc325a01079ebd02a88b90975ead5bd397ec86eb745c7870ebec379a8aa711
2 parents ad3d4b3 + bc4a230 commit 5b6f970

File tree

3 files changed

+44
-26
lines changed

3 files changed

+44
-26
lines changed

test/functional/p2p_segwit.py

Lines changed: 1 addition & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,6 @@
3737
msg_tx,
3838
msg_block,
3939
msg_no_witness_tx,
40-
msg_verack,
4140
ser_uint256,
4241
ser_vector,
4342
sha256,
@@ -146,7 +145,7 @@ def test_witness_block(node, p2p, block, accepted, with_witness=True, reason=Non
146145

147146
class TestP2PConn(P2PInterface):
148147
def __init__(self, wtxidrelay=False):
149-
super().__init__()
148+
super().__init__(wtxidrelay=wtxidrelay)
150149
self.getdataset = set()
151150
self.last_wtxidrelay = []
152151
self.lastgetdata = []
@@ -157,13 +156,6 @@ def __init__(self, wtxidrelay=False):
157156
def on_inv(self, message):
158157
pass
159158

160-
def on_version(self, message):
161-
if self.wtxidrelay:
162-
super().on_version(message)
163-
else:
164-
self.send_message(msg_verack())
165-
self.nServices = message.nServices
166-
167159
def on_getdata(self, message):
168160
self.lastgetdata = message.inv
169161
for inv in message.inv:

test/functional/p2p_tx_download.py

Lines changed: 38 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -30,8 +30,8 @@
3030

3131

3232
class TestP2PConn(P2PInterface):
33-
def __init__(self):
34-
super().__init__()
33+
def __init__(self, wtxidrelay=True):
34+
super().__init__(wtxidrelay=wtxidrelay)
3535
self.tx_getdata_count = 0
3636

3737
def on_getdata(self, message):
@@ -47,6 +47,7 @@ def on_getdata(self, message):
4747
OVERLOADED_PEER_DELAY = 2 # seconds
4848
MAX_GETDATA_IN_FLIGHT = 100
4949
MAX_PEER_TX_ANNOUNCEMENTS = 5000
50+
NONPREF_PEER_TX_DELAY = 2
5051

5152
# Python test constants
5253
NUM_INBOUND = 10
@@ -168,8 +169,6 @@ def test_expiry_fallback(self):
168169
assert_equal(peer_fallback.tx_getdata_count, 0)
169170
self.nodes[0].setmocktime(int(time.time()) + GETDATA_TX_INTERVAL + 1) # Wait for request to peer_expiry to expire
170171
peer_fallback.wait_until(lambda: peer_fallback.tx_getdata_count >= 1, timeout=1)
171-
with p2p_lock:
172-
assert_equal(peer_fallback.tx_getdata_count, 1)
173172
self.restart_node(0) # reset mocktime
174173

175174
def test_disconnect_fallback(self):
@@ -187,8 +186,6 @@ def test_disconnect_fallback(self):
187186
peer_disconnect.peer_disconnect()
188187
peer_disconnect.wait_for_disconnect()
189188
peer_fallback.wait_until(lambda: peer_fallback.tx_getdata_count >= 1, timeout=1)
190-
with p2p_lock:
191-
assert_equal(peer_fallback.tx_getdata_count, 1)
192189

193190
def test_notfound_fallback(self):
194191
self.log.info('Check that notfounds will select another peer for download immediately')
@@ -204,17 +201,42 @@ def test_notfound_fallback(self):
204201
assert_equal(peer_fallback.tx_getdata_count, 0)
205202
peer_notfound.send_and_ping(msg_notfound(vec=[CInv(MSG_WTX, WTXID)])) # Send notfound, so that fallback peer is selected
206203
peer_fallback.wait_until(lambda: peer_fallback.tx_getdata_count >= 1, timeout=1)
207-
with p2p_lock:
208-
assert_equal(peer_fallback.tx_getdata_count, 1)
209204

210-
def test_preferred_inv(self):
211-
self.log.info('Check that invs from preferred peers are downloaded immediately')
212-
self.restart_node(0, extra_args=['[email protected]'])
205+
def test_preferred_inv(self, preferred=False):
206+
if preferred:
207+
self.log.info('Check invs from preferred peers are downloaded immediately')
208+
self.restart_node(0, extra_args=['[email protected]'])
209+
else:
210+
self.log.info('Check invs from non-preferred peers are downloaded after {} s'.format(NONPREF_PEER_TX_DELAY))
211+
mock_time = int(time.time() + 1)
212+
self.nodes[0].setmocktime(mock_time)
213213
peer = self.nodes[0].add_p2p_connection(TestP2PConn())
214214
peer.send_message(msg_inv([CInv(t=MSG_WTX, h=0xff00ff00)]))
215-
peer.wait_until(lambda: peer.tx_getdata_count >= 1, timeout=1)
215+
peer.sync_with_ping()
216+
if preferred:
217+
peer.wait_until(lambda: peer.tx_getdata_count >= 1, timeout=1)
218+
else:
219+
with p2p_lock:
220+
assert_equal(peer.tx_getdata_count, 0)
221+
self.nodes[0].setmocktime(mock_time + NONPREF_PEER_TX_DELAY)
222+
peer.wait_until(lambda: peer.tx_getdata_count >= 1, timeout=1)
223+
224+
def test_txid_inv_delay(self, glob_wtxid=False):
225+
self.log.info('Check that inv from a txid-relay peers are delayed by {} s, with a wtxid peer {}'.format(TXID_RELAY_DELAY, glob_wtxid))
226+
self.restart_node(0, extra_args=['[email protected]'])
227+
mock_time = int(time.time() + 1)
228+
self.nodes[0].setmocktime(mock_time)
229+
peer = self.nodes[0].add_p2p_connection(TestP2PConn(wtxidrelay=False))
230+
if glob_wtxid:
231+
# Add a second wtxid-relay connection otherwise TXID_RELAY_DELAY is waived in
232+
# lack of wtxid-relay peers
233+
self.nodes[0].add_p2p_connection(TestP2PConn(wtxidrelay=True))
234+
peer.send_message(msg_inv([CInv(t=MSG_TX, h=0xff11ff11)]))
235+
peer.sync_with_ping()
216236
with p2p_lock:
217-
assert_equal(peer.tx_getdata_count, 1)
237+
assert_equal(peer.tx_getdata_count, 0 if glob_wtxid else 1)
238+
self.nodes[0].setmocktime(mock_time + TXID_RELAY_DELAY)
239+
peer.wait_until(lambda: peer.tx_getdata_count >= 1, timeout=1)
218240

219241
def test_large_inv_batch(self):
220242
self.log.info('Test how large inv batches are handled with relay permission')
@@ -229,8 +251,6 @@ def test_large_inv_batch(self):
229251
peer.send_message(msg_inv([CInv(t=MSG_WTX, h=wtxid) for wtxid in range(MAX_PEER_TX_ANNOUNCEMENTS + 1)]))
230252
peer.wait_until(lambda: peer.tx_getdata_count == MAX_PEER_TX_ANNOUNCEMENTS)
231253
peer.sync_with_ping()
232-
with p2p_lock:
233-
assert_equal(peer.tx_getdata_count, MAX_PEER_TX_ANNOUNCEMENTS)
234254

235255
def test_spurious_notfound(self):
236256
self.log.info('Check that spurious notfound is ignored')
@@ -242,6 +262,9 @@ def run_test(self):
242262
self.test_disconnect_fallback()
243263
self.test_notfound_fallback()
244264
self.test_preferred_inv()
265+
self.test_preferred_inv(True)
266+
self.test_txid_inv_delay()
267+
self.test_txid_inv_delay(True)
245268
self.test_large_inv_batch()
246269
self.test_spurious_notfound()
247270

test/functional/test_framework/p2p.py

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -289,7 +289,7 @@ class P2PInterface(P2PConnection):
289289
290290
Individual testcases should subclass this and override the on_* methods
291291
if they want to alter message handling behaviour."""
292-
def __init__(self, support_addrv2=False):
292+
def __init__(self, support_addrv2=False, wtxidrelay=True):
293293
super().__init__()
294294

295295
# Track number of messages of each type received.
@@ -309,6 +309,9 @@ def __init__(self, support_addrv2=False):
309309

310310
self.support_addrv2 = support_addrv2
311311

312+
# If the peer supports wtxid-relay
313+
self.wtxidrelay = wtxidrelay
314+
312315
def peer_connect(self, *args, services=NODE_NETWORK|NODE_WITNESS, send_version=True, **kwargs):
313316
create_conn = super().peer_connect(*args, **kwargs)
314317

@@ -394,7 +397,7 @@ def on_verack(self, message):
394397

395398
def on_version(self, message):
396399
assert message.nVersion >= MIN_VERSION_SUPPORTED, "Version {} received. Test framework only supports versions greater than {}".format(message.nVersion, MIN_VERSION_SUPPORTED)
397-
if message.nVersion >= 70016:
400+
if message.nVersion >= 70016 and self.wtxidrelay:
398401
self.send_message(msg_wtxidrelay())
399402
if self.support_addrv2:
400403
self.send_message(msg_sendaddrv2())

0 commit comments

Comments
 (0)