add p2p messages

This commit is contained in:
hinto.janai 2024-09-23 20:50:05 -04:00
parent 96099eb5cc
commit 4dc3b2c66f
No known key found for this signature in database
GPG key ID: D47CE05FA175A499
5 changed files with 163 additions and 4 deletions

View file

@ -11,13 +11,12 @@ use futures::StreamExt;
use monero_serai::block::Block; use monero_serai::block::Block;
use tower::{Service, ServiceExt}; use tower::{Service, ServiceExt};
use cuprate_consensus::BlockchainResponse;
use cuprate_helper::{ use cuprate_helper::{
cast::{u64_to_usize, usize_to_u64}, cast::{u64_to_usize, usize_to_u64},
map::split_u128_into_low_high_bits, map::split_u128_into_low_high_bits,
}; };
use cuprate_types::{ use cuprate_types::{
blockchain::{BlockchainReadRequest, BlockchainWriteRequest}, blockchain::{BlockchainReadRequest, BlockchainResponse, BlockchainWriteRequest},
Chain, ExtendedBlockHeader, HardFork, OutputOnChain, VerifiedBlockInformation, Chain, ExtendedBlockHeader, HardFork, OutputOnChain, VerifiedBlockInformation,
}; };

View file

@ -2,6 +2,7 @@
use std::{ use std::{
collections::{HashMap, HashSet}, collections::{HashMap, HashSet},
convert::Infallible,
sync::Arc, sync::Arc,
}; };
@ -10,11 +11,15 @@ use futures::StreamExt;
use monero_serai::block::Block; use monero_serai::block::Block;
use tower::{Service, ServiceExt}; use tower::{Service, ServiceExt};
use cuprate_consensus::BlockchainResponse;
use cuprate_helper::{ use cuprate_helper::{
cast::{u64_to_usize, usize_to_u64}, cast::{u64_to_usize, usize_to_u64},
map::split_u128_into_low_high_bits, map::split_u128_into_low_high_bits,
}; };
use cuprate_p2p_core::{
client::handshaker::builder::DummyAddressBook,
services::{AddressBookRequest, AddressBookResponse},
AddressBook, ClearNet,
};
use cuprate_types::{ use cuprate_types::{
blockchain::{BlockchainReadRequest, BlockchainWriteRequest}, blockchain::{BlockchainReadRequest, BlockchainWriteRequest},
Chain, ExtendedBlockHeader, HardFork, OutputOnChain, VerifiedBlockInformation, Chain, ExtendedBlockHeader, HardFork, OutputOnChain, VerifiedBlockInformation,
@ -22,4 +27,93 @@ use cuprate_types::{
use crate::rpc::{CupratedRpcHandler, CupratedRpcHandlerState}; use crate::rpc::{CupratedRpcHandler, CupratedRpcHandlerState};
impl CupratedRpcHandlerState {} #[expect(clippy::needless_pass_by_ref_mut, reason = "TODO: remove after impl")]
impl CupratedRpcHandlerState {
/// [`AddressBookRequest::PeerlistSize`]
pub(super) async fn peerlist_size(&mut self) -> Result<(u64, u64), Error> {
let AddressBookResponse::<ClearNet>::PeerlistSize { white, grey } =
<DummyAddressBook as tower::ServiceExt<AddressBookRequest<ClearNet>>>::ready(
&mut DummyAddressBook,
)
.await
.expect("TODO")
.call(AddressBookRequest::PeerlistSize)
.await
.expect("TODO")
else {
unreachable!();
};
Ok((usize_to_u64(white), usize_to_u64(grey)))
}
/// [`AddressBookRequest::ConnectionCount`]
pub(super) async fn connection_count(&mut self) -> Result<(u64, u64), Error> {
let AddressBookResponse::<ClearNet>::ConnectionCount { incoming, outgoing } =
<DummyAddressBook as tower::ServiceExt<AddressBookRequest<ClearNet>>>::ready(
&mut DummyAddressBook,
)
.await
.expect("TODO")
.call(AddressBookRequest::ConnectionCount)
.await
.expect("TODO")
else {
unreachable!();
};
Ok((usize_to_u64(incoming), usize_to_u64(outgoing)))
}
/// [`AddressBookRequest::SetBan`]
pub(super) async fn set_ban(&mut self, peer: Infallible) -> Result<(), Error> {
let AddressBookResponse::<ClearNet>::Ok = <DummyAddressBook as tower::ServiceExt<
AddressBookRequest<ClearNet>,
>>::ready(&mut DummyAddressBook)
.await
.expect("TODO")
.call(AddressBookRequest::SetBan(peer))
.await
.expect("TODO") else {
unreachable!();
};
Ok(())
}
/// [`AddressBookRequest::GetBan`]
pub(super) async fn get_ban(&mut self, peer: Infallible) -> Result<(), Error> {
let AddressBookResponse::<ClearNet>::GetBan(ban) =
<DummyAddressBook as tower::ServiceExt<AddressBookRequest<ClearNet>>>::ready(
&mut DummyAddressBook,
)
.await
.expect("TODO")
.call(AddressBookRequest::GetBan(peer))
.await
.expect("TODO")
else {
unreachable!();
};
Ok(())
}
/// [`AddressBookRequest::GetBans`]
pub(super) async fn get_bans(&mut self) -> Result<(), Error> {
let AddressBookResponse::<ClearNet>::GetBans(bans) =
<DummyAddressBook as tower::ServiceExt<AddressBookRequest<ClearNet>>>::ready(
&mut DummyAddressBook,
)
.await
.expect("TODO")
.call(AddressBookRequest::GetBans)
.await
.expect("TODO")
else {
unreachable!();
};
Ok(todo!())
}
}

View file

@ -411,6 +411,11 @@ impl<Z: BorshNetworkZone> Service<AddressBookRequest<Z>> for AddressBook<Z> {
AddressBookRequest::IsPeerBanned(addr) => Ok(AddressBookResponse::IsPeerBanned( AddressBookRequest::IsPeerBanned(addr) => Ok(AddressBookResponse::IsPeerBanned(
self.is_peer_banned(&addr), self.is_peer_banned(&addr),
)), )),
AddressBookRequest::PeerlistSize
| AddressBookRequest::ConnectionCount
| AddressBookRequest::SetBan(_)
| AddressBookRequest::GetBan(_)
| AddressBookRequest::GetBans => todo!(),
}; };
ready(response) ready(response)

View file

@ -128,6 +128,11 @@ impl<N: NetworkZone> Service<AddressBookRequest<N>> for DummyAddressBook {
AddressBookResponse::Ok AddressBookResponse::Ok
} }
AddressBookRequest::IsPeerBanned(_) => AddressBookResponse::IsPeerBanned(false), AddressBookRequest::IsPeerBanned(_) => AddressBookResponse::IsPeerBanned(false),
AddressBookRequest::PeerlistSize
| AddressBookRequest::ConnectionCount
| AddressBookRequest::SetBan(_)
| AddressBookRequest::GetBan(_)
| AddressBookRequest::GetBans => todo!(),
})) }))
} }
} }

View file

@ -108,16 +108,20 @@ pub enum AddressBookRequest<Z: NetworkZone> {
/// The peers rpc credits per hash /// The peers rpc credits per hash
rpc_credits_per_hash: u32, rpc_credits_per_hash: u32,
}, },
/// Tells the address book about a peer list received from a peer. /// Tells the address book about a peer list received from a peer.
IncomingPeerList(Vec<ZoneSpecificPeerListEntryBase<Z::Addr>>), IncomingPeerList(Vec<ZoneSpecificPeerListEntryBase<Z::Addr>>),
/// Takes a random white peer from the peer list. If height is specified /// Takes a random white peer from the peer list. If height is specified
/// then the peer list should retrieve a peer that should have a full /// then the peer list should retrieve a peer that should have a full
/// block at that height according to it's pruning seed /// block at that height according to it's pruning seed
TakeRandomWhitePeer { height: Option<usize> }, TakeRandomWhitePeer { height: Option<usize> },
/// Takes a random gray peer from the peer list. If height is specified /// Takes a random gray peer from the peer list. If height is specified
/// then the peer list should retrieve a peer that should have a full /// then the peer list should retrieve a peer that should have a full
/// block at that height according to it's pruning seed /// block at that height according to it's pruning seed
TakeRandomGrayPeer { height: Option<usize> }, TakeRandomGrayPeer { height: Option<usize> },
/// Takes a random peer from the peer list. If height is specified /// Takes a random peer from the peer list. If height is specified
/// then the peer list should retrieve a peer that should have a full /// then the peer list should retrieve a peer that should have a full
/// block at that height according to it's pruning seed. /// block at that height according to it's pruning seed.
@ -125,17 +129,69 @@ pub enum AddressBookRequest<Z: NetworkZone> {
/// The address book will look in the white peer list first, then the gray /// The address book will look in the white peer list first, then the gray
/// one if no peer is found. /// one if no peer is found.
TakeRandomPeer { height: Option<usize> }, TakeRandomPeer { height: Option<usize> },
/// Gets the specified number of white peers, or less if we don't have enough. /// Gets the specified number of white peers, or less if we don't have enough.
GetWhitePeers(usize), GetWhitePeers(usize),
/// Checks if the given peer is banned. /// Checks if the given peer is banned.
IsPeerBanned(Z::Addr), IsPeerBanned(Z::Addr),
/// TODO
PeerlistSize,
/// TODO
ConnectionCount,
/// TODO: `cuprate_rpc_types::json::SetBanRequest` input
SetBan(std::convert::Infallible),
/// TODO
GetBan(std::convert::Infallible),
/// TODO
GetBans,
} }
/// A response from the address book service. /// A response from the address book service.
pub enum AddressBookResponse<Z: NetworkZone> { pub enum AddressBookResponse<Z: NetworkZone> {
/// TODO
///
/// Response to:
/// - [`AddressBookRequest::NewConnection`]
/// - [`AddressBookRequest::IncomingPeerList`]
Ok, Ok,
/// Response to:
/// - [`AddressBookRequest::TakeRandomWhitePeer`]
/// - [`AddressBookRequest::TakeRandomGrayPeer`]
/// - [`AddressBookRequest::TakeRandomPeer`]
Peer(ZoneSpecificPeerListEntryBase<Z::Addr>), Peer(ZoneSpecificPeerListEntryBase<Z::Addr>),
/// Response to [`AddressBookRequest::GetWhitePeers`].
Peers(Vec<ZoneSpecificPeerListEntryBase<Z::Addr>>), Peers(Vec<ZoneSpecificPeerListEntryBase<Z::Addr>>),
/// Response to [`AddressBookRequest::IsPeerBanned`].
///
/// Contains `true` if the peer is banned. /// Contains `true` if the peer is banned.
IsPeerBanned(bool), IsPeerBanned(bool),
/// Response to [`AddressBookRequest::PeerlistSize`].
///
/// TODO
PeerlistSize { white: usize, grey: usize },
/// Response to [`AddressBookRequest::ConnectionCount`].
///
/// TODO
ConnectionCount { incoming: usize, outgoing: usize },
/// Response to [`AddressBookRequest::GetBan`].
///
/// TODO
GetBan(std::convert::Infallible),
/// Response to [`AddressBookRequest::GetBans`].
///
/// TODO
GetBans(std::convert::Infallible),
} }