mirror of
https://github.com/hinto-janai/cuprate.git
synced 2024-12-31 16:09:58 +00:00
Compare commits
6 commits
de7abfc3f0
...
a3fa638d91
Author | SHA1 | Date | |
---|---|---|---|
|
a3fa638d91 | ||
|
1a079c856e | ||
|
8d5f779ec3 | ||
|
ff48fb4679 | ||
|
916d593024 | ||
|
1ffa86c5ae |
18 changed files with 110 additions and 190 deletions
|
@ -31,7 +31,7 @@ cuprate-txpool = { workspace = true }
|
||||||
cuprate-database = { workspace = true }
|
cuprate-database = { workspace = true }
|
||||||
cuprate-pruning = { workspace = true }
|
cuprate-pruning = { workspace = true }
|
||||||
cuprate-test-utils = { workspace = true }
|
cuprate-test-utils = { workspace = true }
|
||||||
cuprate-types = { workspace = true }
|
cuprate-types = { workspace = true, features = ["json"] }
|
||||||
cuprate-json-rpc = { workspace = true }
|
cuprate-json-rpc = { workspace = true }
|
||||||
cuprate-rpc-interface = { workspace = true }
|
cuprate-rpc-interface = { workspace = true }
|
||||||
cuprate-rpc-types = { workspace = true }
|
cuprate-rpc-types = { workspace = true }
|
||||||
|
|
|
@ -140,7 +140,7 @@ pub type BlockchainManagerHandle = cuprate_database_service::DatabaseReadService
|
||||||
/// TODO
|
/// TODO
|
||||||
#[derive(Clone)]
|
#[derive(Clone)]
|
||||||
pub struct CupratedRpcHandler {
|
pub struct CupratedRpcHandler {
|
||||||
/// Should this RPC server be [restricted](RpcHandler::restricted)?
|
/// Should this RPC server be [restricted](RpcHandler::is_restricted)?
|
||||||
///
|
///
|
||||||
/// This is not `pub` on purpose, as it should not be mutated after [`Self::new`].
|
/// This is not `pub` on purpose, as it should not be mutated after [`Self::new`].
|
||||||
restricted: bool,
|
restricted: bool,
|
||||||
|
|
|
@ -6,15 +6,13 @@
|
||||||
//! These build on-top of [`crate::rpc::request`] functions.
|
//! These build on-top of [`crate::rpc::request`] functions.
|
||||||
|
|
||||||
use anyhow::{anyhow, Error};
|
use anyhow::{anyhow, Error};
|
||||||
use monero_serai::block::Block;
|
|
||||||
|
|
||||||
use cuprate_consensus::{BlockChainContext, BlockChainContextService};
|
|
||||||
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_rpc_types::misc::{BlockHeader, KeyImageSpentStatus};
|
use cuprate_rpc_types::misc::{BlockHeader, KeyImageSpentStatus};
|
||||||
use cuprate_types::{ExtendedBlockHeader, HardFork};
|
use cuprate_types::HardFork;
|
||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
rpc::request::{blockchain, blockchain_context},
|
rpc::request::{blockchain, blockchain_context},
|
||||||
|
@ -142,7 +140,7 @@ pub(super) async fn check_height(
|
||||||
|
|
||||||
if height > top_height {
|
if height > top_height {
|
||||||
return Err(anyhow!(
|
return Err(anyhow!(
|
||||||
"Requested block height: {height} greater than current top block height: {top_height}",
|
"Requested block height: {height} greater than top block height: {top_height}",
|
||||||
));
|
));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -150,6 +148,7 @@ pub(super) async fn check_height(
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Parse a hexadecimal [`String`] as a 32-byte hash.
|
/// Parse a hexadecimal [`String`] as a 32-byte hash.
|
||||||
|
#[expect(clippy::needless_pass_by_value)]
|
||||||
pub(super) fn hex_to_hash(hex: String) -> Result<[u8; 32], Error> {
|
pub(super) fn hex_to_hash(hex: String) -> Result<[u8; 32], Error> {
|
||||||
let error = || anyhow!("Failed to parse hex representation of hash. Hex = {hex}.");
|
let error = || anyhow!("Failed to parse hex representation of hash. Hex = {hex}.");
|
||||||
|
|
||||||
|
@ -164,7 +163,7 @@ pub(super) fn hex_to_hash(hex: String) -> Result<[u8; 32], Error> {
|
||||||
Ok(hash)
|
Ok(hash)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// [`BlockchainResponse::ChainHeight`] minus 1.
|
/// [`cuprate_types::blockchain::BlockchainResponse::ChainHeight`] minus 1.
|
||||||
pub(super) async fn top_height(state: &mut CupratedRpcHandler) -> Result<(u64, [u8; 32]), Error> {
|
pub(super) async fn top_height(state: &mut CupratedRpcHandler) -> Result<(u64, [u8; 32]), Error> {
|
||||||
let (chain_height, hash) = blockchain::chain_height(&mut state.blockchain_read).await?;
|
let (chain_height, hash) = blockchain::chain_height(&mut state.blockchain_read).await?;
|
||||||
let height = chain_height.saturating_sub(1);
|
let height = chain_height.saturating_sub(1);
|
||||||
|
|
|
@ -1,17 +1,19 @@
|
||||||
//! RPC request handler functions (JSON-RPC).
|
//! RPC request handler functions (JSON-RPC).
|
||||||
//!
|
//!
|
||||||
//! TODO:
|
//! TODO:
|
||||||
//! Many handlers have `todo!()`s for internals that must be completed, see:
|
//! Many handlers have `todo!()`s for other Cuprate internals that must be completed, see:
|
||||||
//! <https://github.com/Cuprate/cuprate/pull/308>
|
//! <https://github.com/Cuprate/cuprate/pull/308>
|
||||||
|
|
||||||
use std::time::{Duration, Instant};
|
use std::{
|
||||||
|
net::{IpAddr, Ipv4Addr, SocketAddr, SocketAddrV4},
|
||||||
|
num::NonZero,
|
||||||
|
time::{Duration, Instant},
|
||||||
|
};
|
||||||
|
|
||||||
use anyhow::{anyhow, Error};
|
use anyhow::{anyhow, Error};
|
||||||
use monero_serai::block::Block;
|
use monero_serai::block::Block;
|
||||||
use strum::{EnumCount, VariantArray};
|
use strum::{EnumCount, VariantArray};
|
||||||
use tower::{Service, ServiceExt};
|
|
||||||
|
|
||||||
use cuprate_consensus::{BlockchainReadRequest, BlockchainResponse};
|
|
||||||
use cuprate_constants::{
|
use cuprate_constants::{
|
||||||
build::RELEASE,
|
build::RELEASE,
|
||||||
rpc::{RESTRICTED_BLOCK_COUNT, RESTRICTED_BLOCK_HEADER_RANGE},
|
rpc::{RESTRICTED_BLOCK_COUNT, RESTRICTED_BLOCK_HEADER_RANGE},
|
||||||
|
@ -114,9 +116,6 @@ pub(super) async fn map_request(
|
||||||
Req::GetTransactionPoolBacklog(r) => {
|
Req::GetTransactionPoolBacklog(r) => {
|
||||||
Resp::GetTransactionPoolBacklog(get_transaction_pool_backlog(state, r).await?)
|
Resp::GetTransactionPoolBacklog(get_transaction_pool_backlog(state, r).await?)
|
||||||
}
|
}
|
||||||
Req::GetOutputDistribution(r) => {
|
|
||||||
Resp::GetOutputDistribution(get_output_distribution(state, r).await?)
|
|
||||||
}
|
|
||||||
Req::GetMinerData(r) => Resp::GetMinerData(get_miner_data(state, r).await?),
|
Req::GetMinerData(r) => Resp::GetMinerData(get_miner_data(state, r).await?),
|
||||||
Req::PruneBlockchain(r) => Resp::PruneBlockchain(prune_blockchain(state, r).await?),
|
Req::PruneBlockchain(r) => Resp::PruneBlockchain(prune_blockchain(state, r).await?),
|
||||||
Req::CalcPow(r) => Resp::CalcPow(calc_pow(state, r).await?),
|
Req::CalcPow(r) => Resp::CalcPow(calc_pow(state, r).await?),
|
||||||
|
@ -129,7 +128,7 @@ pub(super) async fn map_request(
|
||||||
/// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L1790-L1804>
|
/// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L1790-L1804>
|
||||||
async fn get_block_count(
|
async fn get_block_count(
|
||||||
mut state: CupratedRpcHandler,
|
mut state: CupratedRpcHandler,
|
||||||
request: GetBlockCountRequest,
|
_: GetBlockCountRequest,
|
||||||
) -> Result<GetBlockCountResponse, Error> {
|
) -> Result<GetBlockCountResponse, Error> {
|
||||||
Ok(GetBlockCountResponse {
|
Ok(GetBlockCountResponse {
|
||||||
base: ResponseBase::OK,
|
base: ResponseBase::OK,
|
||||||
|
@ -367,7 +366,7 @@ async fn get_block(
|
||||||
/// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L2729-L2738>
|
/// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L2729-L2738>
|
||||||
async fn get_connections(
|
async fn get_connections(
|
||||||
state: CupratedRpcHandler,
|
state: CupratedRpcHandler,
|
||||||
request: GetConnectionsRequest,
|
_: GetConnectionsRequest,
|
||||||
) -> Result<GetConnectionsResponse, Error> {
|
) -> Result<GetConnectionsResponse, Error> {
|
||||||
let connections = address_book::connection_info::<ClearNet>(&mut DummyAddressBook).await?;
|
let connections = address_book::connection_info::<ClearNet>(&mut DummyAddressBook).await?;
|
||||||
|
|
||||||
|
@ -380,7 +379,7 @@ async fn get_connections(
|
||||||
/// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L501-L582>
|
/// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L501-L582>
|
||||||
async fn get_info(
|
async fn get_info(
|
||||||
mut state: CupratedRpcHandler,
|
mut state: CupratedRpcHandler,
|
||||||
request: GetInfoRequest,
|
_: GetInfoRequest,
|
||||||
) -> Result<GetInfoResponse, Error> {
|
) -> Result<GetInfoResponse, Error> {
|
||||||
let restricted = state.is_restricted();
|
let restricted = state.is_restricted();
|
||||||
let context = blockchain_context::context(&mut state.blockchain_context).await?;
|
let context = blockchain_context::context(&mut state.blockchain_context).await?;
|
||||||
|
@ -403,7 +402,7 @@ async fn get_info(
|
||||||
let (bootstrap_daemon_address, was_bootstrap_ever_used) = if restricted {
|
let (bootstrap_daemon_address, was_bootstrap_ever_used) = if restricted {
|
||||||
(String::new(), false)
|
(String::new(), false)
|
||||||
} else {
|
} else {
|
||||||
todo!()
|
todo!("support bootstrap daemon")
|
||||||
};
|
};
|
||||||
let busy_syncing = blockchain_manager::syncing(&mut state.blockchain_manager).await?;
|
let busy_syncing = blockchain_manager::syncing(&mut state.blockchain_manager).await?;
|
||||||
let (cumulative_difficulty, cumulative_difficulty_top64) =
|
let (cumulative_difficulty, cumulative_difficulty_top64) =
|
||||||
|
@ -548,7 +547,12 @@ async fn set_bans(
|
||||||
request: SetBansRequest,
|
request: SetBansRequest,
|
||||||
) -> Result<SetBansResponse, Error> {
|
) -> Result<SetBansResponse, Error> {
|
||||||
for peer in request.bans {
|
for peer in request.bans {
|
||||||
let address = todo!();
|
// TODO: support non-clearnet addresses.
|
||||||
|
|
||||||
|
// <https://architecture.cuprate.org/oddities/le-ipv4.html>
|
||||||
|
let [a, b, c, d] = peer.ip.to_le_bytes();
|
||||||
|
let ip = Ipv4Addr::new(a, b, c, d);
|
||||||
|
let address = SocketAddr::V4(SocketAddrV4::new(ip, 0));
|
||||||
|
|
||||||
let ban = if peer.ban {
|
let ban = if peer.ban {
|
||||||
Some(Duration::from_secs(peer.seconds.into()))
|
Some(Duration::from_secs(peer.seconds.into()))
|
||||||
|
@ -567,16 +571,15 @@ async fn set_bans(
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L2768-L2801>
|
/// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L2768-L2801>
|
||||||
async fn get_bans(
|
async fn get_bans(state: CupratedRpcHandler, _: GetBansRequest) -> Result<GetBansResponse, Error> {
|
||||||
state: CupratedRpcHandler,
|
|
||||||
request: GetBansRequest,
|
|
||||||
) -> Result<GetBansResponse, Error> {
|
|
||||||
let now = Instant::now();
|
let now = Instant::now();
|
||||||
|
|
||||||
|
// TODO: support non-clearnet addresses.
|
||||||
|
|
||||||
let bans = address_book::get_bans::<ClearNet>(&mut DummyAddressBook)
|
let bans = address_book::get_bans::<ClearNet>(&mut DummyAddressBook)
|
||||||
.await?
|
.await?
|
||||||
.into_iter()
|
.into_iter()
|
||||||
.map(|ban| {
|
.filter_map(|ban| {
|
||||||
let seconds = if let Some(instant) = ban.unban_instant {
|
let seconds = if let Some(instant) = ban.unban_instant {
|
||||||
instant
|
instant
|
||||||
.checked_duration_since(now)
|
.checked_duration_since(now)
|
||||||
|
@ -588,11 +591,17 @@ async fn get_bans(
|
||||||
0
|
0
|
||||||
};
|
};
|
||||||
|
|
||||||
GetBan {
|
// <https://architecture.cuprate.org/oddities/le-ipv4.html>
|
||||||
|
let ip = match ban.address.ip() {
|
||||||
|
IpAddr::V4(v4) => u32::from_le_bytes(v4.octets()),
|
||||||
|
IpAddr::V6(v6) => return None,
|
||||||
|
};
|
||||||
|
|
||||||
|
Some(GetBan {
|
||||||
host: ban.address.to_string(),
|
host: ban.address.to_string(),
|
||||||
ip: todo!(),
|
ip,
|
||||||
seconds,
|
seconds,
|
||||||
}
|
})
|
||||||
})
|
})
|
||||||
.collect();
|
.collect();
|
||||||
|
|
||||||
|
@ -607,7 +616,7 @@ async fn banned(
|
||||||
state: CupratedRpcHandler,
|
state: CupratedRpcHandler,
|
||||||
request: BannedRequest,
|
request: BannedRequest,
|
||||||
) -> Result<BannedResponse, Error> {
|
) -> Result<BannedResponse, Error> {
|
||||||
let peer = match request.address.parse::<std::net::SocketAddr>() {
|
let peer = match request.address.parse::<SocketAddr>() {
|
||||||
Ok(p) => p,
|
Ok(p) => p,
|
||||||
Err(e) => {
|
Err(e) => {
|
||||||
return Err(anyhow!(
|
return Err(anyhow!(
|
||||||
|
@ -716,7 +725,7 @@ async fn get_coinbase_tx_sum(
|
||||||
/// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L2981-L2996>
|
/// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L2981-L2996>
|
||||||
async fn get_version(
|
async fn get_version(
|
||||||
mut state: CupratedRpcHandler,
|
mut state: CupratedRpcHandler,
|
||||||
request: GetVersionRequest,
|
_: GetVersionRequest,
|
||||||
) -> Result<GetVersionResponse, Error> {
|
) -> Result<GetVersionResponse, Error> {
|
||||||
let current_height = helper::top_height(&mut state).await?.0;
|
let current_height = helper::top_height(&mut state).await?.0;
|
||||||
let target_height = blockchain_manager::target_height(&mut state.blockchain_manager).await?;
|
let target_height = blockchain_manager::target_height(&mut state.blockchain_manager).await?;
|
||||||
|
@ -766,7 +775,7 @@ async fn get_fee_estimate(
|
||||||
/// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L3033-L3064>
|
/// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L3033-L3064>
|
||||||
async fn get_alternate_chains(
|
async fn get_alternate_chains(
|
||||||
mut state: CupratedRpcHandler,
|
mut state: CupratedRpcHandler,
|
||||||
request: GetAlternateChainsRequest,
|
_: GetAlternateChainsRequest,
|
||||||
) -> Result<GetAlternateChainsResponse, Error> {
|
) -> Result<GetAlternateChainsResponse, Error> {
|
||||||
let chains = blockchain::alt_chains(&mut state.blockchain_read)
|
let chains = blockchain::alt_chains(&mut state.blockchain_read)
|
||||||
.await?
|
.await?
|
||||||
|
@ -813,7 +822,7 @@ async fn relay_tx(
|
||||||
/// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L3306-L3330>
|
/// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L3306-L3330>
|
||||||
async fn sync_info(
|
async fn sync_info(
|
||||||
mut state: CupratedRpcHandler,
|
mut state: CupratedRpcHandler,
|
||||||
request: SyncInfoRequest,
|
_: SyncInfoRequest,
|
||||||
) -> Result<SyncInfoResponse, Error> {
|
) -> Result<SyncInfoResponse, Error> {
|
||||||
let height = usize_to_u64(
|
let height = usize_to_u64(
|
||||||
blockchain_context::context(&mut state.blockchain_context)
|
blockchain_context::context(&mut state.blockchain_context)
|
||||||
|
@ -854,7 +863,7 @@ async fn sync_info(
|
||||||
/// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L3332-L3350>
|
/// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L3332-L3350>
|
||||||
async fn get_transaction_pool_backlog(
|
async fn get_transaction_pool_backlog(
|
||||||
mut state: CupratedRpcHandler,
|
mut state: CupratedRpcHandler,
|
||||||
request: GetTransactionPoolBacklogRequest,
|
_: GetTransactionPoolBacklogRequest,
|
||||||
) -> Result<GetTransactionPoolBacklogResponse, Error> {
|
) -> Result<GetTransactionPoolBacklogResponse, Error> {
|
||||||
let backlog = txpool::backlog(&mut state.txpool_read)
|
let backlog = txpool::backlog(&mut state.txpool_read)
|
||||||
.await?
|
.await?
|
||||||
|
@ -908,7 +917,7 @@ async fn get_output_distribution(
|
||||||
/// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L1998-L2033>
|
/// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L1998-L2033>
|
||||||
async fn get_miner_data(
|
async fn get_miner_data(
|
||||||
mut state: CupratedRpcHandler,
|
mut state: CupratedRpcHandler,
|
||||||
request: GetMinerDataRequest,
|
_: GetMinerDataRequest,
|
||||||
) -> Result<GetMinerDataResponse, Error> {
|
) -> Result<GetMinerDataResponse, Error> {
|
||||||
let context = blockchain_context::context(&mut state.blockchain_context).await?;
|
let context = blockchain_context::context(&mut state.blockchain_context).await?;
|
||||||
let c = context.unchecked_blockchain_context();
|
let c = context.unchecked_blockchain_context();
|
||||||
|
@ -963,27 +972,28 @@ async fn prune_blockchain(
|
||||||
/// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L2035-L2070>
|
/// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L2035-L2070>
|
||||||
async fn calc_pow(
|
async fn calc_pow(
|
||||||
mut state: CupratedRpcHandler,
|
mut state: CupratedRpcHandler,
|
||||||
mut request: CalcPowRequest,
|
request: CalcPowRequest,
|
||||||
) -> Result<CalcPowResponse, Error> {
|
) -> Result<CalcPowResponse, Error> {
|
||||||
let hardfork = HardFork::from_version(request.major_version)?;
|
let hardfork = HardFork::from_version(request.major_version)?;
|
||||||
let mut block_blob: Vec<u8> = hex::decode(request.block_blob)?;
|
let block_blob: Vec<u8> = hex::decode(request.block_blob)?;
|
||||||
let block = Block::read(&mut block_blob.as_slice())?;
|
let block = Block::read(&mut block_blob.as_slice())?;
|
||||||
let seed_hash = helper::hex_to_hash(request.seed_hash)?;
|
let seed_hash = helper::hex_to_hash(request.seed_hash)?;
|
||||||
|
|
||||||
let block_weight = todo!("calculate block weight");
|
// let block_weight = todo!();
|
||||||
|
|
||||||
let median_for_block_reward = blockchain_context::context(&mut state.blockchain_context)
|
// let median_for_block_reward = blockchain_context::context(&mut state.blockchain_context)
|
||||||
.await?
|
// .await?
|
||||||
.unchecked_blockchain_context()
|
// .unchecked_blockchain_context()
|
||||||
.context_to_verify_block
|
// .context_to_verify_block
|
||||||
.median_weight_for_block_reward;
|
// .median_weight_for_block_reward;
|
||||||
|
|
||||||
if cuprate_consensus_rules::blocks::check_block_weight(block_weight, median_for_block_reward)
|
// if cuprate_consensus_rules::blocks::check_block_weight(block_weight, median_for_block_reward)
|
||||||
.is_err()
|
// .is_err()
|
||||||
{
|
// {
|
||||||
return Err(anyhow!("Block blob size is too big, rejecting block"));
|
// return Err(anyhow!("Block blob size is too big, rejecting block"));
|
||||||
}
|
// }
|
||||||
|
|
||||||
|
// TODO: will `CalculatePow` do the above checks?
|
||||||
let pow_hash = blockchain_context::calculate_pow(
|
let pow_hash = blockchain_context::calculate_pow(
|
||||||
&mut state.blockchain_context,
|
&mut state.blockchain_context,
|
||||||
hardfork,
|
hardfork,
|
||||||
|
@ -1019,12 +1029,12 @@ async fn add_aux_pow(
|
||||||
|
|
||||||
/// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L2072-L2207>
|
/// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L2072-L2207>
|
||||||
fn add_aux_pow_inner(
|
fn add_aux_pow_inner(
|
||||||
mut state: CupratedRpcHandler,
|
state: CupratedRpcHandler,
|
||||||
request: AddAuxPowRequest,
|
request: AddAuxPowRequest,
|
||||||
) -> Result<AddAuxPowResponse, Error> {
|
) -> Result<AddAuxPowResponse, Error> {
|
||||||
if request.aux_pow.is_empty() {
|
let Some(non_zero_len) = NonZero::<usize>::new(request.aux_pow.len()) else {
|
||||||
return Err(anyhow!("Empty `aux_pow` vector"));
|
return Err(anyhow!("Empty `aux_pow` vector"));
|
||||||
}
|
};
|
||||||
|
|
||||||
let aux_pow = request
|
let aux_pow = request
|
||||||
.aux_pow
|
.aux_pow
|
||||||
|
@ -1040,21 +1050,41 @@ fn add_aux_pow_inner(
|
||||||
// Boxed slices are used over `Vec` to slightly
|
// Boxed slices are used over `Vec` to slightly
|
||||||
// safe-guard against accidently pushing to it.
|
// safe-guard against accidently pushing to it.
|
||||||
|
|
||||||
// --- BEGIN AUX POW IMPL ---
|
|
||||||
|
|
||||||
// Original impl:
|
|
||||||
// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L2110-L2206>
|
|
||||||
|
|
||||||
let len = aux_pow.len();
|
|
||||||
|
|
||||||
// TODO: why is this here? it does nothing:
|
// TODO: why is this here? it does nothing:
|
||||||
// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L2110-L2112>
|
// <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L2110-L2112>
|
||||||
let mut path_domain = 1_usize;
|
// let mut path_domain = 1_usize;
|
||||||
while 1 << path_domain < len {
|
// while 1 << path_domain < len {
|
||||||
path_domain += 1;
|
// path_domain += 1;
|
||||||
}
|
// }
|
||||||
|
|
||||||
|
fn find_nonce(
|
||||||
|
aux_pow: &[cuprate_types::AuxPow],
|
||||||
|
non_zero_len: NonZero<usize>,
|
||||||
|
aux_pow_len: usize,
|
||||||
|
) -> Result<(u32, Box<[u32]>), Error> {
|
||||||
|
/// <https://github.com/monero-project/monero/blob/893916ad091a92e765ce3241b94e706ad012b62a/src/cryptonote_basic/merge_mining.cpp#L48>
|
||||||
|
fn get_aux_slot(id: &[u8; 32], nonce: u32, n_aux_chains: NonZero<u32>) -> u32 {
|
||||||
|
const HASH_SIZE: usize = 32;
|
||||||
|
|
||||||
|
let mut buf = [0; HASH_SIZE + size_of::<u32>() + 1];
|
||||||
|
buf[..HASH_SIZE].copy_from_slice(id);
|
||||||
|
|
||||||
|
let v: [u8; 4] = nonce.to_le_bytes();
|
||||||
|
buf[HASH_SIZE..HASH_SIZE + size_of::<u32>()].copy_from_slice(&v);
|
||||||
|
|
||||||
|
const HASH_KEY_MM_SLOT: u8 = b'm';
|
||||||
|
buf[HASH_SIZE + size_of::<u32>()] = HASH_KEY_MM_SLOT;
|
||||||
|
|
||||||
|
fn sha256sum(buf: &[u8]) -> [u8; 32] {
|
||||||
|
todo!()
|
||||||
|
}
|
||||||
|
let res = sha256sum(&buf);
|
||||||
|
|
||||||
|
let v = u32::from_le_bytes(res[..4].try_into().unwrap());
|
||||||
|
|
||||||
|
v % n_aux_chains.get()
|
||||||
|
}
|
||||||
|
|
||||||
fn find_nonce(aux_pow_len: usize) -> Result<(u32, Box<[u32]>), Error> {
|
|
||||||
// INVARIANT: this must be the same `.len()` as `aux_pow`
|
// INVARIANT: this must be the same `.len()` as `aux_pow`
|
||||||
let mut slots: Box<[u32]> = vec![u32::MAX; aux_pow_len].into_boxed_slice();
|
let mut slots: Box<[u32]> = vec![u32::MAX; aux_pow_len].into_boxed_slice();
|
||||||
let mut slot_seen: Box<[bool]> = vec![false; aux_pow_len].into_boxed_slice();
|
let mut slot_seen: Box<[bool]> = vec![false; aux_pow_len].into_boxed_slice();
|
||||||
|
@ -1063,7 +1093,12 @@ fn add_aux_pow_inner(
|
||||||
|
|
||||||
for nonce in 0..=MAX_NONCE {
|
for nonce in 0..=MAX_NONCE {
|
||||||
for i in &mut slots {
|
for i in &mut slots {
|
||||||
let slot_u32: u32 = todo!("const uint32_t slot = cryptonote::get_aux_slot(aux_pow[idx].first, nonce, aux_pow.size());");
|
let slot_u32 = get_aux_slot(
|
||||||
|
&aux_pow[u32_to_usize(*i)].id,
|
||||||
|
nonce,
|
||||||
|
non_zero_len.try_into().unwrap(),
|
||||||
|
);
|
||||||
|
|
||||||
let slot = u32_to_usize(slot_u32);
|
let slot = u32_to_usize(slot_u32);
|
||||||
|
|
||||||
if slot >= aux_pow_len {
|
if slot >= aux_pow_len {
|
||||||
|
@ -1084,7 +1119,8 @@ fn add_aux_pow_inner(
|
||||||
Err(anyhow!("Failed to find a suitable nonce"))
|
Err(anyhow!("Failed to find a suitable nonce"))
|
||||||
}
|
}
|
||||||
|
|
||||||
let (nonce, slots) = find_nonce(len)?;
|
let len = non_zero_len.get();
|
||||||
|
let (nonce, slots) = find_nonce(&aux_pow, non_zero_len, len)?;
|
||||||
|
|
||||||
// FIXME: use iterator version.
|
// FIXME: use iterator version.
|
||||||
let (aux_pow_id_raw, aux_pow_raw) = {
|
let (aux_pow_id_raw, aux_pow_raw) = {
|
||||||
|
@ -1135,7 +1171,7 @@ fn add_aux_pow_inner(
|
||||||
};
|
};
|
||||||
|
|
||||||
fn tree_hash(aux_pow_raw: &[[u8; 32]]) -> [u8; 32] {
|
fn tree_hash(aux_pow_raw: &[[u8; 32]]) -> [u8; 32] {
|
||||||
todo!("https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/rpc/core_rpc_server.cpp#L2163")
|
todo!("https://github.com/serai-dex/serai/pull/629")
|
||||||
}
|
}
|
||||||
|
|
||||||
fn encode_mm_depth(aux_pow_len: usize, nonce: u32) -> u64 {
|
fn encode_mm_depth(aux_pow_len: usize, nonce: u32) -> u64 {
|
||||||
|
@ -1189,8 +1225,6 @@ fn add_aux_pow_inner(
|
||||||
})
|
})
|
||||||
.collect::<Vec<AuxPow>>();
|
.collect::<Vec<AuxPow>>();
|
||||||
|
|
||||||
// --- END AUX POW IMPL ---
|
|
||||||
|
|
||||||
Ok(AddAuxPowResponse {
|
Ok(AddAuxPowResponse {
|
||||||
base: ResponseBase::OK,
|
base: ResponseBase::OK,
|
||||||
blocktemplate_blob,
|
blocktemplate_blob,
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
//! Functions for TODO: doc enum message.
|
//! Functions to send [`AddressBookRequest`]s.
|
||||||
|
|
||||||
use anyhow::{anyhow, Error};
|
use anyhow::{anyhow, Error};
|
||||||
use tower::ServiceExt;
|
use tower::ServiceExt;
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
//! Functions for [`BlockchainReadRequest`].
|
//! Functions to send [`BlockchainReadRequest`]s.
|
||||||
|
|
||||||
use std::{
|
use std::{
|
||||||
collections::{HashMap, HashSet},
|
collections::{HashMap, HashSet},
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
//! Functions for [`BlockChainContextRequest`] and [`BlockChainContextResponse`].
|
//! Functions to send [`BlockChainContextRequest`]s.
|
||||||
|
|
||||||
use anyhow::{anyhow, Error};
|
use anyhow::{anyhow, Error};
|
||||||
use monero_serai::block::Block;
|
use monero_serai::block::Block;
|
||||||
|
@ -8,7 +8,6 @@ use cuprate_consensus_context::{
|
||||||
BlockChainContext, BlockChainContextRequest, BlockChainContextResponse,
|
BlockChainContext, BlockChainContextRequest, BlockChainContextResponse,
|
||||||
BlockChainContextService,
|
BlockChainContextService,
|
||||||
};
|
};
|
||||||
use cuprate_helper::cast::u64_to_usize;
|
|
||||||
use cuprate_types::{FeeEstimate, HardFork, HardForkInfo};
|
use cuprate_types::{FeeEstimate, HardFork, HardForkInfo};
|
||||||
|
|
||||||
// FIXME: use `anyhow::Error` over `tower::BoxError` in blockchain context.
|
// FIXME: use `anyhow::Error` over `tower::BoxError` in blockchain context.
|
||||||
|
@ -77,7 +76,7 @@ pub(crate) async fn calculate_pow(
|
||||||
seed_hash: [u8; 32],
|
seed_hash: [u8; 32],
|
||||||
) -> Result<[u8; 32], Error> {
|
) -> Result<[u8; 32], Error> {
|
||||||
let Some(height) = block.number() else {
|
let Some(height) = block.number() else {
|
||||||
return Err(anyhow!("block is missing height"));
|
return Err(anyhow!("Block is missing height"));
|
||||||
};
|
};
|
||||||
|
|
||||||
let block = Box::new(block);
|
let block = Box::new(block);
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
//! Functions for [`BlockchainManagerRequest`] & [`BlockchainManagerResponse`].
|
//! Functions to send [`BlockchainManagerRequest`]s.
|
||||||
|
|
||||||
use anyhow::Error;
|
use anyhow::Error;
|
||||||
use monero_serai::block::Block;
|
use monero_serai::block::Block;
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
//! Functions for [`TxpoolReadRequest`].
|
//! Functions to send [`TxpoolReadRequest`]s.
|
||||||
|
|
||||||
use std::convert::Infallible;
|
use std::convert::Infallible;
|
||||||
|
|
||||||
|
|
|
@ -424,8 +424,7 @@ impl<Z: BorshNetworkZone> Service<AddressBookRequest<Z>> for AddressBook<Z> {
|
||||||
| AddressBookRequest::ConnectionCount
|
| AddressBookRequest::ConnectionCount
|
||||||
| AddressBookRequest::SetBan(_)
|
| AddressBookRequest::SetBan(_)
|
||||||
| AddressBookRequest::GetBans
|
| AddressBookRequest::GetBans
|
||||||
| AddressBookRequest::ConnectionInfo
|
| AddressBookRequest::ConnectionInfo => {
|
||||||
| AddressBookRequest::NextNeededPruningSeed => {
|
|
||||||
todo!("finish https://github.com/Cuprate/cuprate/pull/297")
|
todo!("finish https://github.com/Cuprate/cuprate/pull/297")
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
|
@ -112,8 +112,7 @@ impl<N: NetworkZone> Service<AddressBookRequest<N>> for DummyAddressBook {
|
||||||
| AddressBookRequest::ConnectionCount
|
| AddressBookRequest::ConnectionCount
|
||||||
| AddressBookRequest::SetBan(_)
|
| AddressBookRequest::SetBan(_)
|
||||||
| AddressBookRequest::GetBans
|
| AddressBookRequest::GetBans
|
||||||
| AddressBookRequest::ConnectionInfo
|
| AddressBookRequest::ConnectionInfo => {
|
||||||
| AddressBookRequest::NextNeededPruningSeed => {
|
|
||||||
todo!("finish https://github.com/Cuprate/cuprate/pull/297")
|
todo!("finish https://github.com/Cuprate/cuprate/pull/297")
|
||||||
}
|
}
|
||||||
}))
|
}))
|
||||||
|
|
|
@ -132,9 +132,6 @@ pub enum AddressBookRequest<Z: NetworkZone> {
|
||||||
|
|
||||||
/// Get the state of all bans.
|
/// Get the state of all bans.
|
||||||
GetBans,
|
GetBans,
|
||||||
|
|
||||||
/// Get the next [`PruningSeed`] needed for a pruned sync.
|
|
||||||
NextNeededPruningSeed,
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// A response from the address book service.
|
/// A response from the address book service.
|
||||||
|
@ -172,7 +169,4 @@ pub enum AddressBookResponse<Z: NetworkZone> {
|
||||||
|
|
||||||
/// Response to [`AddressBookRequest::GetBans`].
|
/// Response to [`AddressBookRequest::GetBans`].
|
||||||
GetBans(Vec<BanState<Z::Addr>>),
|
GetBans(Vec<BanState<Z::Addr>>),
|
||||||
|
|
||||||
/// Response to [`AddressBookRequest::NextNeededPruningSeed`].
|
|
||||||
NextNeededPruningSeed(PruningSeed),
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -59,7 +59,7 @@ The error type must always be [`anyhow::Error`].
|
||||||
The `RpcHandler` must also hold some state that is required
|
The `RpcHandler` must also hold some state that is required
|
||||||
for RPC server operation.
|
for RPC server operation.
|
||||||
|
|
||||||
The only state currently needed is [`RpcHandler::restricted`], which determines if an RPC
|
The only state currently needed is [`RpcHandler::is_restricted`], which determines if an RPC
|
||||||
server is restricted or not, and thus, if some endpoints/methods are allowed or not.
|
server is restricted or not, and thus, if some endpoints/methods are allowed or not.
|
||||||
|
|
||||||
# Unknown endpoint behavior
|
# Unknown endpoint behavior
|
||||||
|
|
|
@ -31,7 +31,7 @@ use crate::rpc_handler::RpcHandler;
|
||||||
#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
|
#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
|
||||||
#[cfg_attr(feature = "serde", derive(Deserialize, Serialize))]
|
#[cfg_attr(feature = "serde", derive(Deserialize, Serialize))]
|
||||||
pub struct RpcHandlerDummy {
|
pub struct RpcHandlerDummy {
|
||||||
/// Should this RPC server be [restricted](RpcHandler::restricted)?
|
/// Should this RPC server be [restricted](RpcHandler::is_restricted)?
|
||||||
///
|
///
|
||||||
/// The dummy will honor this [`bool`]
|
/// The dummy will honor this [`bool`]
|
||||||
/// on restricted methods/endpoints.
|
/// on restricted methods/endpoints.
|
||||||
|
@ -85,7 +85,6 @@ impl Service<JsonRpcRequest> for RpcHandlerDummy {
|
||||||
Req::GetTransactionPoolBacklog(_) => {
|
Req::GetTransactionPoolBacklog(_) => {
|
||||||
Resp::GetTransactionPoolBacklog(Default::default())
|
Resp::GetTransactionPoolBacklog(Default::default())
|
||||||
}
|
}
|
||||||
Req::GetOutputDistribution(_) => Resp::GetOutputDistribution(Default::default()),
|
|
||||||
Req::GetMinerData(_) => Resp::GetMinerData(Default::default()),
|
Req::GetMinerData(_) => Resp::GetMinerData(Default::default()),
|
||||||
Req::PruneBlockchain(_) => Resp::PruneBlockchain(Default::default()),
|
Req::PruneBlockchain(_) => Resp::PruneBlockchain(Default::default()),
|
||||||
Req::CalcPow(_) => Resp::CalcPow(Default::default()),
|
Req::CalcPow(_) => Resp::CalcPow(Default::default()),
|
||||||
|
|
|
@ -1623,7 +1623,6 @@ pub enum JsonRpcRequest {
|
||||||
RelayTx(RelayTxRequest),
|
RelayTx(RelayTxRequest),
|
||||||
SyncInfo(SyncInfoRequest),
|
SyncInfo(SyncInfoRequest),
|
||||||
GetTransactionPoolBacklog(GetTransactionPoolBacklogRequest),
|
GetTransactionPoolBacklog(GetTransactionPoolBacklogRequest),
|
||||||
GetOutputDistribution(GetOutputDistributionRequest),
|
|
||||||
GetMinerData(GetMinerDataRequest),
|
GetMinerData(GetMinerDataRequest),
|
||||||
PruneBlockchain(PruneBlockchainRequest),
|
PruneBlockchain(PruneBlockchainRequest),
|
||||||
CalcPow(CalcPowRequest),
|
CalcPow(CalcPowRequest),
|
||||||
|
@ -1649,7 +1648,6 @@ impl RpcCallValue for JsonRpcRequest {
|
||||||
Self::GetVersion(x) => x.is_restricted(),
|
Self::GetVersion(x) => x.is_restricted(),
|
||||||
Self::GetFeeEstimate(x) => x.is_restricted(),
|
Self::GetFeeEstimate(x) => x.is_restricted(),
|
||||||
Self::GetTransactionPoolBacklog(x) => x.is_restricted(),
|
Self::GetTransactionPoolBacklog(x) => x.is_restricted(),
|
||||||
Self::GetOutputDistribution(x) => x.is_restricted(),
|
|
||||||
Self::GetMinerData(x) => x.is_restricted(),
|
Self::GetMinerData(x) => x.is_restricted(),
|
||||||
Self::AddAuxPow(x) => x.is_restricted(),
|
Self::AddAuxPow(x) => x.is_restricted(),
|
||||||
Self::GetTxIdsLoose(x) => x.is_restricted(),
|
Self::GetTxIdsLoose(x) => x.is_restricted(),
|
||||||
|
@ -1685,7 +1683,6 @@ impl RpcCallValue for JsonRpcRequest {
|
||||||
Self::GetVersion(x) => x.is_empty(),
|
Self::GetVersion(x) => x.is_empty(),
|
||||||
Self::GetFeeEstimate(x) => x.is_empty(),
|
Self::GetFeeEstimate(x) => x.is_empty(),
|
||||||
Self::GetTransactionPoolBacklog(x) => x.is_empty(),
|
Self::GetTransactionPoolBacklog(x) => x.is_empty(),
|
||||||
Self::GetOutputDistribution(x) => x.is_empty(),
|
|
||||||
Self::GetMinerData(x) => x.is_empty(),
|
Self::GetMinerData(x) => x.is_empty(),
|
||||||
Self::AddAuxPow(x) => x.is_empty(),
|
Self::AddAuxPow(x) => x.is_empty(),
|
||||||
Self::GetTxIdsLoose(x) => x.is_empty(),
|
Self::GetTxIdsLoose(x) => x.is_empty(),
|
||||||
|
@ -1758,7 +1755,6 @@ pub enum JsonRpcResponse {
|
||||||
RelayTx(RelayTxResponse),
|
RelayTx(RelayTxResponse),
|
||||||
SyncInfo(SyncInfoResponse),
|
SyncInfo(SyncInfoResponse),
|
||||||
GetTransactionPoolBacklog(GetTransactionPoolBacklogResponse),
|
GetTransactionPoolBacklog(GetTransactionPoolBacklogResponse),
|
||||||
GetOutputDistribution(GetOutputDistributionResponse),
|
|
||||||
GetMinerData(GetMinerDataResponse),
|
GetMinerData(GetMinerDataResponse),
|
||||||
PruneBlockchain(PruneBlockchainResponse),
|
PruneBlockchain(PruneBlockchainResponse),
|
||||||
CalcPow(CalcPowResponse),
|
CalcPow(CalcPowResponse),
|
||||||
|
|
|
@ -1,97 +0,0 @@
|
||||||
//! Types of network addresses; used in P2P.
|
|
||||||
|
|
||||||
use cuprate_epee_encoding::Marker;
|
|
||||||
|
|
||||||
#[cfg(feature = "serde")]
|
|
||||||
use serde::{Deserialize, Serialize};
|
|
||||||
|
|
||||||
#[cfg(feature = "epee")]
|
|
||||||
use cuprate_epee_encoding::{
|
|
||||||
error,
|
|
||||||
macros::bytes::{Buf, BufMut},
|
|
||||||
EpeeValue,
|
|
||||||
};
|
|
||||||
|
|
||||||
/// Used in [`crate::misc::ConnectionInfo::address_type`].
|
|
||||||
#[doc = crate::macros::monero_definition_link!(
|
|
||||||
cc73fe71162d564ffda8e549b79a350bca53c454,
|
|
||||||
"epee/include/net/enums.h",
|
|
||||||
39..=47
|
|
||||||
)]
|
|
||||||
#[derive(Copy, Clone, Default, Debug, PartialEq, Eq, PartialOrd, Ord, Hash)]
|
|
||||||
#[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
|
|
||||||
#[cfg_attr(feature = "serde", serde(untagged))]
|
|
||||||
#[repr(u8)]
|
|
||||||
pub enum AddressType {
|
|
||||||
#[default]
|
|
||||||
Invalid,
|
|
||||||
Ipv4,
|
|
||||||
Ipv6,
|
|
||||||
I2p,
|
|
||||||
Tor,
|
|
||||||
}
|
|
||||||
|
|
||||||
impl AddressType {
|
|
||||||
/// Convert [`Self`] to a [`u8`].
|
|
||||||
///
|
|
||||||
/// ```rust
|
|
||||||
/// use cuprate_rpc_types::misc::AddressType as A;
|
|
||||||
///
|
|
||||||
/// assert_eq!(A::Invalid.to_u8(), 0);
|
|
||||||
/// assert_eq!(A::Ipv4.to_u8(), 1);
|
|
||||||
/// assert_eq!(A::Ipv6.to_u8(), 2);
|
|
||||||
/// assert_eq!(A::I2p.to_u8(), 3);
|
|
||||||
/// assert_eq!(A::Tor.to_u8(), 4);
|
|
||||||
/// ```
|
|
||||||
pub const fn to_u8(self) -> u8 {
|
|
||||||
self as u8
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Convert a [`u8`] to a [`Self`].
|
|
||||||
///
|
|
||||||
/// # Errors
|
|
||||||
/// This returns [`None`] if `u > 4`.
|
|
||||||
///
|
|
||||||
/// ```rust
|
|
||||||
/// use cuprate_rpc_types::misc::AddressType as A;
|
|
||||||
///
|
|
||||||
/// assert_eq!(A::from_u8(0), Some(A::Invalid));
|
|
||||||
/// assert_eq!(A::from_u8(1), Some(A::Ipv4));
|
|
||||||
/// assert_eq!(A::from_u8(2), Some(A::Ipv6));
|
|
||||||
/// assert_eq!(A::from_u8(3), Some(A::I2p));
|
|
||||||
/// assert_eq!(A::from_u8(4), Some(A::Tor));
|
|
||||||
/// assert_eq!(A::from_u8(5), None);
|
|
||||||
/// ```
|
|
||||||
pub const fn from_u8(u: u8) -> Option<Self> {
|
|
||||||
Some(match u {
|
|
||||||
0 => Self::Invalid,
|
|
||||||
1 => Self::Ipv4,
|
|
||||||
2 => Self::Ipv6,
|
|
||||||
3 => Self::I2p,
|
|
||||||
4 => Self::Tor,
|
|
||||||
_ => return None,
|
|
||||||
})
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl From<AddressType> for u8 {
|
|
||||||
fn from(value: AddressType) -> Self {
|
|
||||||
value.to_u8()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
#[cfg(feature = "epee")]
|
|
||||||
impl EpeeValue for AddressType {
|
|
||||||
const MARKER: Marker = u8::MARKER;
|
|
||||||
|
|
||||||
fn read<B: Buf>(r: &mut B, marker: &Marker) -> error::Result<Self> {
|
|
||||||
let u = u8::read(r, marker)?;
|
|
||||||
Self::from_u8(u).ok_or(error::Error::Format("u8 was greater than 4"))
|
|
||||||
}
|
|
||||||
|
|
||||||
fn write<B: BufMut>(self, w: &mut B) -> error::Result<()> {
|
|
||||||
let u = self.to_u8();
|
|
||||||
u8::write(u, w)?;
|
|
||||||
Ok(())
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -12,7 +12,6 @@
|
||||||
)]
|
)]
|
||||||
|
|
||||||
//---------------------------------------------------------------------------------------------------- Mod
|
//---------------------------------------------------------------------------------------------------- Mod
|
||||||
mod address_type;
|
|
||||||
mod binary_string;
|
mod binary_string;
|
||||||
mod distribution;
|
mod distribution;
|
||||||
mod key_image_spent_status;
|
mod key_image_spent_status;
|
||||||
|
@ -22,7 +21,6 @@ mod pool_info_extent;
|
||||||
mod status;
|
mod status;
|
||||||
mod tx_entry;
|
mod tx_entry;
|
||||||
|
|
||||||
pub use address_type::AddressType;
|
|
||||||
pub use binary_string::BinaryString;
|
pub use binary_string::BinaryString;
|
||||||
pub use distribution::{Distribution, DistributionCompressedBinary, DistributionUncompressed};
|
pub use distribution::{Distribution, DistributionCompressedBinary, DistributionUncompressed};
|
||||||
pub use key_image_spent_status::KeyImageSpentStatus;
|
pub use key_image_spent_status::KeyImageSpentStatus;
|
||||||
|
|
|
@ -16,7 +16,7 @@ use strum::{
|
||||||
|
|
||||||
/// An enumeration of address types.
|
/// An enumeration of address types.
|
||||||
///
|
///
|
||||||
/// Used in `cuprate_p2p` and `cuprate_types`
|
/// Used in `cuprate-p2p`, `cuprate-rpc-types`.
|
||||||
///
|
///
|
||||||
/// Original definition:
|
/// Original definition:
|
||||||
/// - <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/epee/include/net/enums.h/#L49>
|
/// - <https://github.com/monero-project/monero/blob/cc73fe71162d564ffda8e549b79a350bca53c454/src/epee/include/net/enums.h/#L49>
|
||||||
|
|
Loading…
Reference in a new issue