Changeset View
Changeset View
Standalone View
Standalone View
test/functional/abc_p2p_compactproofs.py
#!/usr/bin/env python3 | #!/usr/bin/env python3 | ||||
# Copyright (c) 2022 The Bitcoin developers | # Copyright (c) 2022 The Bitcoin developers | ||||
# Distributed under the MIT software license, see the accompanying | # Distributed under the MIT software license, see the accompanying | ||||
# file COPYING or http://www.opensource.org/licenses/mit-license.php. | # file COPYING or http://www.opensource.org/licenses/mit-license.php. | ||||
""" | """ | ||||
Test proof inventory relaying | Test proof inventory relaying | ||||
""" | """ | ||||
import random | import random | ||||
import time | import time | ||||
from test_framework.avatools import ( | from test_framework.avatools import ( | ||||
AvaP2PInterface, | AvaP2PInterface, | ||||
NoHandshakeAvaP2PInterface, | |||||
build_msg_avaproofs, | build_msg_avaproofs, | ||||
gen_proof, | gen_proof, | ||||
get_ava_p2p_interface, | get_ava_p2p_interface, | ||||
get_proof_ids, | get_proof_ids, | ||||
wait_for_proof, | wait_for_proof, | ||||
) | ) | ||||
from test_framework.messages import ( | from test_framework.messages import ( | ||||
NODE_AVALANCHE, | NODE_AVALANCHE, | ||||
▲ Show 20 Lines • Show All 46 Lines • ▼ Show 20 Lines | class CompactProofsTest(BitcoinTestFramework): | ||||
def test_send_outbound_getavaproofs(self): | def test_send_outbound_getavaproofs(self): | ||||
self.log.info( | self.log.info( | ||||
"Check we send a getavaproofs message to our avalanche outbound peers") | "Check we send a getavaproofs message to our avalanche outbound peers") | ||||
node = self.nodes[0] | node = self.nodes[0] | ||||
p2p_idx = 0 | p2p_idx = 0 | ||||
non_avapeers = [] | non_avapeers = [] | ||||
for i in range(4): | for _ in range(4): | ||||
peer = P2PInterface() | peer = P2PInterface() | ||||
node.add_outbound_p2p_connection( | node.add_outbound_p2p_connection( | ||||
peer, | peer, | ||||
p2p_idx=p2p_idx, | p2p_idx=p2p_idx, | ||||
connection_type="outbound-full-relay", | connection_type="outbound-full-relay", | ||||
services=NODE_NETWORK, | services=NODE_NETWORK, | ||||
) | ) | ||||
non_avapeers.append(peer) | non_avapeers.append(peer) | ||||
p2p_idx += 1 | p2p_idx += 1 | ||||
inbound_avapeers = [ | inbound_avapeers = [ | ||||
node.add_p2p_connection( | node.add_p2p_connection( | ||||
AvaP2PInterface()) for _ in range(4)] | NoHandshakeAvaP2PInterface()) for _ in range(4)] | ||||
outbound_avapeers = [] | outbound_avapeers = [] | ||||
for i in range(4): | # With a proof and the service bit set | ||||
peer = P2PInterface() | for _ in range(4): | ||||
peer = AvaP2PInterface(node) | |||||
node.add_outbound_p2p_connection( | node.add_outbound_p2p_connection( | ||||
peer, | peer, | ||||
p2p_idx=p2p_idx, | p2p_idx=p2p_idx, | ||||
connection_type="avalanche", | connection_type="avalanche", | ||||
services=NODE_NETWORK | NODE_AVALANCHE, | services=NODE_NETWORK | NODE_AVALANCHE, | ||||
) | ) | ||||
outbound_avapeers.append(peer) | outbound_avapeers.append(peer) | ||||
p2p_idx += 1 | p2p_idx += 1 | ||||
# Without a proof and no service bit set | |||||
for _ in range(4): | |||||
peer = AvaP2PInterface() | |||||
node.add_outbound_p2p_connection( | |||||
peer, | |||||
p2p_idx=p2p_idx, | |||||
connection_type="outbound-full-relay", | |||||
services=NODE_NETWORK, | |||||
) | |||||
outbound_avapeers.append(peer) | |||||
p2p_idx += 1 | |||||
def all_peers_received_getavaproofs(): | def all_peers_received_getavaproofs(): | ||||
with p2p_lock: | with p2p_lock: | ||||
return all([p.last_message.get("getavaproofs") | return all([p.last_message.get("getavaproofs") | ||||
for p in outbound_avapeers]) | for p in outbound_avapeers]) | ||||
self.wait_until(all_peers_received_getavaproofs) | self.wait_until(all_peers_received_getavaproofs) | ||||
with p2p_lock: | with p2p_lock: | ||||
assert all([p.message_count.get( | assert all([p.message_count.get( | ||||
Show All 22 Lines | def test_send_outbound_getavaproofs(self): | ||||
assert all([p.message_count.get( | assert all([p.message_count.get( | ||||
"getavaproofs", 0) == 0 for p in non_avapeers]) | "getavaproofs", 0) == 0 for p in non_avapeers]) | ||||
assert all([p.message_count.get( | assert all([p.message_count.get( | ||||
"getavaproofs", 0) == 0 for p in inbound_avapeers]) | "getavaproofs", 0) == 0 for p in inbound_avapeers]) | ||||
self.log.info( | self.log.info( | ||||
"After the first avaproofs has been received, all the peers are requested periodically") | "After the first avaproofs has been received, all the peers are requested periodically") | ||||
responding_outbound_avapeer = P2PInterface() | responding_outbound_avapeer = AvaP2PInterface(node) | ||||
node.add_outbound_p2p_connection( | node.add_outbound_p2p_connection( | ||||
responding_outbound_avapeer, | responding_outbound_avapeer, | ||||
p2p_idx=p2p_idx, | p2p_idx=p2p_idx, | ||||
connection_type="avalanche", | connection_type="avalanche", | ||||
services=NODE_NETWORK | NODE_AVALANCHE, | services=NODE_NETWORK | NODE_AVALANCHE, | ||||
) | ) | ||||
p2p_idx += 1 | p2p_idx += 1 | ||||
responding_outbound_avapeer_id = node.getpeerinfo()[-1]['id'] | responding_outbound_avapeer_id = node.getpeerinfo()[-1]['id'] | ||||
▲ Show 20 Lines • Show All 42 Lines • ▼ Show 20 Lines | def test_send_manual_getavaproofs(self): | ||||
def added_node_connected(ip_port): | def added_node_connected(ip_port): | ||||
added_node_info = node.getaddednodeinfo(ip_port) | added_node_info = node.getaddednodeinfo(ip_port) | ||||
return len( | return len( | ||||
added_node_info) == 1 and added_node_info[0]['connected'] | added_node_info) == 1 and added_node_info[0]['connected'] | ||||
def connect_callback(address, port): | def connect_callback(address, port): | ||||
self.log.debug("Connecting to {}:{}".format(address, port)) | self.log.debug("Connecting to {}:{}".format(address, port)) | ||||
p = AvaP2PInterface() | p = AvaP2PInterface(node) | ||||
p2p_idx = 1 | p2p_idx = 1 | ||||
p.peer_accept_connection( | p.peer_accept_connection( | ||||
connect_cb=connect_callback, | connect_cb=connect_callback, | ||||
connect_id=p2p_idx, | connect_id=p2p_idx, | ||||
net=node.chain, | net=node.chain, | ||||
timeout_factor=node.timeout_factor, | timeout_factor=node.timeout_factor, | ||||
services=NODE_NETWORK | NODE_AVALANCHE, | services=NODE_NETWORK | NODE_AVALANCHE, | ||||
)() | )() | ||||
Show All 18 Lines | def test_respond_getavaproofs(self): | ||||
avaproofs = self.received_avaproofs(peer) | avaproofs = self.received_avaproofs(peer) | ||||
assert_equal(len(avaproofs.shortids), expected_len) | assert_equal(len(avaproofs.shortids), expected_len) | ||||
# Initially the node has 0 peer | # Initially the node has 0 peer | ||||
self.restart_node(0) | self.restart_node(0) | ||||
assert_equal(len(get_proof_ids(node)), 0) | assert_equal(len(get_proof_ids(node)), 0) | ||||
peer = node.add_p2p_connection(AvaP2PInterface()) | peer = node.add_p2p_connection(NoHandshakeAvaP2PInterface()) | ||||
send_getavaproof_check_shortid_len(peer, 0) | send_getavaproof_check_shortid_len(peer, 0) | ||||
# Add some proofs | # Add some proofs | ||||
sending_peer = node.add_p2p_connection(AvaP2PInterface()) | sending_peer = node.add_p2p_connection(NoHandshakeAvaP2PInterface()) | ||||
for _ in range(50): | for _ in range(50): | ||||
_, proof = gen_proof(node) | _, proof = gen_proof(node) | ||||
sending_peer.send_avaproof(proof) | sending_peer.send_avaproof(proof) | ||||
wait_for_proof(node, f"{proof.proofid:0{64}x}") | wait_for_proof(node, f"{proof.proofid:0{64}x}") | ||||
proofids = get_proof_ids(node) | proofids = get_proof_ids(node) | ||||
assert_equal(len(proofids), 50) | assert_equal(len(proofids), 50) | ||||
receiving_peer = node.add_p2p_connection(AvaP2PInterface()) | receiving_peer = node.add_p2p_connection(NoHandshakeAvaP2PInterface()) | ||||
send_getavaproof_check_shortid_len(receiving_peer, len(proofids)) | send_getavaproof_check_shortid_len(receiving_peer, len(proofids)) | ||||
avaproofs = self.received_avaproofs(receiving_peer) | avaproofs = self.received_avaproofs(receiving_peer) | ||||
expected_shortids = [ | expected_shortids = [ | ||||
calculate_shortid( | calculate_shortid( | ||||
avaproofs.key0, | avaproofs.key0, | ||||
avaproofs.key1, | avaproofs.key1, | ||||
proofid) for proofid in sorted(proofids)] | proofid) for proofid in sorted(proofids)] | ||||
Show All 36 Lines | def test_request_missing_proofs(self): | ||||
with p2p_lock: | with p2p_lock: | ||||
return peer.last_message.get("avaproofsreq") | return peer.last_message.get("avaproofsreq") | ||||
p2p_idx = 0 | p2p_idx = 0 | ||||
def add_avalanche_p2p_outbound(): | def add_avalanche_p2p_outbound(): | ||||
nonlocal p2p_idx | nonlocal p2p_idx | ||||
peer = P2PInterface() | peer = AvaP2PInterface(node) | ||||
node.add_outbound_p2p_connection( | node.add_outbound_p2p_connection( | ||||
peer, | peer, | ||||
p2p_idx=p2p_idx, | p2p_idx=p2p_idx, | ||||
connection_type="avalanche", | connection_type="avalanche", | ||||
services=NODE_NETWORK | NODE_AVALANCHE, | services=NODE_NETWORK | NODE_AVALANCHE, | ||||
) | ) | ||||
p2p_idx += 1 | p2p_idx += 1 | ||||
▲ Show 20 Lines • Show All 305 Lines • Show Last 20 Lines |