diff --git a/examples/block-download/src/main.rs b/examples/block-download/src/main.rs index 271cf9b..b5ed4e6 100644 --- a/examples/block-download/src/main.rs +++ b/examples/block-download/src/main.rs @@ -2,7 +2,7 @@ use pallas::network::{ miniprotocols::{ blockfetch, handshake::{self, n2n::VersionTable}, - Point, TESTNET_MAGIC, + Point, PROTOCOL_N2N_BLOCK_FETCH, PROTOCOL_N2N_HANDSHAKE, TESTNET_MAGIC, }, multiplexer::{bearers::Bearer, StdPlexer}, }; @@ -13,14 +13,14 @@ fn main() { let bearer = Bearer::connect_tcp("relays-new.cardano-testnet.iohkdev.io:3001").unwrap(); let mut plexer = StdPlexer::new(bearer); - let channel0 = plexer.use_channel(0); - let channel3 = plexer.use_channel(3); + let handshake = plexer.use_channel(PROTOCOL_N2N_HANDSHAKE); + let blockfetch = plexer.use_channel(PROTOCOL_N2N_BLOCK_FETCH); plexer.muxer.spawn(); plexer.demuxer.spawn(); let versions = VersionTable::v4_and_above(TESTNET_MAGIC); - let mut hs_client = handshake::N2NClient::new(channel0); + let mut hs_client = handshake::N2NClient::new(handshake); let handshake = hs_client.handshake(versions).unwrap(); assert!(matches!(handshake, handshake::Confirmation::Accepted(..))); @@ -30,7 +30,7 @@ fn main() { hex::decode("3f3d81c7b88f0fa28867541c5fea8794125cccf6d6c9ee0037a1dbb064130dfd").unwrap(), ); - let mut bf_client = blockfetch::Client::new(channel3); + let mut bf_client = blockfetch::Client::new(blockfetch); let block = bf_client.fetch_single(point).unwrap(); diff --git a/examples/n2c-miniprotocols/src/main.rs b/examples/n2c-miniprotocols/src/main.rs index 2916418..1b945a7 100644 --- a/examples/n2c-miniprotocols/src/main.rs +++ b/examples/n2c-miniprotocols/src/main.rs @@ -1,5 +1,8 @@ use pallas::network::{ - miniprotocols::{chainsync, handshake, localstate, Point, MAINNET_MAGIC}, + miniprotocols::{ + chainsync, handshake, localstate, Point, MAINNET_MAGIC, PROTOCOL_N2C_CHAIN_SYNC, + PROTOCOL_N2C_HANDSHAKE, PROTOCOL_N2C_STATE_QUERY, + }, multiplexer::{self, bearers::Bearer}, }; @@ -75,19 +78,19 @@ fn main() { // setup the multiplexer by specifying the bearer and the IDs of the // miniprotocols to use let mut plexer = multiplexer::StdPlexer::new(bearer); - let channel0 = plexer.use_channel(0); - let channel7 = plexer.use_channel(7); - let channel5 = plexer.use_channel(5); + let handshake = plexer.use_channel(PROTOCOL_N2C_HANDSHAKE); + let statequery = plexer.use_channel(PROTOCOL_N2C_STATE_QUERY); + let chainsync = plexer.use_channel(PROTOCOL_N2C_CHAIN_SYNC); plexer.muxer.spawn(); plexer.demuxer.spawn(); // execute the required handshake against the relay - do_handshake(channel0); + do_handshake(handshake); // execute an arbitrary "Local State" query against the node - do_localstate_query(channel7); + do_localstate_query(statequery); // execute the chainsync flow from an arbitrary point in the chain - do_chainsync(channel5); + do_chainsync(chainsync); } diff --git a/examples/n2n-miniprotocols/src/main.rs b/examples/n2n-miniprotocols/src/main.rs index 30e5600..c54bb2b 100644 --- a/examples/n2n-miniprotocols/src/main.rs +++ b/examples/n2n-miniprotocols/src/main.rs @@ -1,5 +1,8 @@ use pallas::network::{ - miniprotocols::{blockfetch, chainsync, handshake, Point, MAINNET_MAGIC}, + miniprotocols::{ + blockfetch, chainsync, handshake, Point, MAINNET_MAGIC, PROTOCOL_N2N_BLOCK_FETCH, + PROTOCOL_N2N_CHAIN_SYNC, PROTOCOL_N2N_HANDSHAKE, + }, multiplexer::{bearers::Bearer, StdChannel, StdPlexer}, }; @@ -83,19 +86,19 @@ fn main() { // setup the multiplexer by specifying the bearer and the IDs of the // miniprotocols to use let mut plexer = StdPlexer::new(bearer); - let channel0 = plexer.use_channel(0); - let channel3 = plexer.use_channel(3); - let channel2 = plexer.use_channel(2); + let handshake = plexer.use_channel(PROTOCOL_N2N_HANDSHAKE); + let blockfetch = plexer.use_channel(PROTOCOL_N2N_BLOCK_FETCH); + let chainsync = plexer.use_channel(PROTOCOL_N2N_CHAIN_SYNC); plexer.muxer.spawn(); plexer.demuxer.spawn(); // execute the required handshake against the relay - do_handshake(channel0); + do_handshake(handshake); // fetch an arbitrary batch of block - do_blockfetch(channel3); + do_blockfetch(blockfetch); // execute the chainsync flow from an arbitrary point in the chain - do_chainsync(channel2); + do_chainsync(chainsync); } diff --git a/pallas-crypto/src/key/ed25519.rs b/pallas-crypto/src/key/ed25519.rs index 4d7a3af..f09e7bc 100644 --- a/pallas-crypto/src/key/ed25519.rs +++ b/pallas-crypto/src/key/ed25519.rs @@ -7,7 +7,6 @@ //! //! However, only the [`SecretKeyExtended`] can be used for HD derivation //! (using [ed25519_bip32] or otherwise). -//! use crate::memsec::Scrubbed as _; use cryptoxide::ed25519::{ @@ -18,13 +17,13 @@ use std::{any::type_name, convert::TryFrom, fmt, str::FromStr}; use thiserror::Error; /// Ed25519 Secret Key -/// #[derive(Clone)] pub struct SecretKey([u8; Self::SIZE]); /// Ed25519 Extended Secret Key /// -/// unlike [`SecretKey`], an extended key can be derived see [`pallas_crypto::derivation`] +/// unlike [`SecretKey`], an extended key can be derived see +/// [`pallas_crypto::derivation`] #[derive(Clone)] pub struct SecretKeyExtended([u8; Self::SIZE]); @@ -77,7 +76,6 @@ impl_size_zero!(Signature, SIGNATURE_LENGTH); impl SecretKey { /// generate a new [`SecretKey`] with the given random number generator - /// pub fn new(mut rng: Rng) -> Self where Rng: RngCore + CryptoRng, @@ -106,8 +104,8 @@ impl SecretKey { /// create a [`Signature`] for the given message with this [`SecretKey`]. /// - /// The [`Signature`] can then be verified against the associated [`PublicKey`] - /// and the original message. + /// The [`Signature`] can then be verified against the associated + /// [`PublicKey`] and the original message. pub fn sign(&self, msg: T) -> Signature where T: AsRef<[u8]>, @@ -125,8 +123,8 @@ impl SecretKey { } impl SecretKeyExtended { - /// generate a new [`SecretKeyExtended`] with the given random number generator - /// + /// generate a new [`SecretKeyExtended`] with the given random number + /// generator pub fn new(mut rng: Rng) -> Self where Rng: RngCore + CryptoRng, @@ -180,7 +178,6 @@ impl SecretKeyExtended { impl PublicKey { /// verify the cryptographic [`Signature`] against the `message` and the /// [`PublicKey`] `self`. - /// #[inline] pub fn verify(&self, message: T, signature: &Signature) -> bool where @@ -438,11 +435,12 @@ mod tests { signature: Signature, message: Vec, ) -> bool { - // NOTE: this test may fail but it is impossible to see this happening in normal condition. - // we are generating 32 random bytes of public key and 64 random bytes - // of signature with an randomly generated message of a random number - // of bytes in. If the message were empty, the probability to have - // a signature that matches the verify key would still be 1 out of 2^96. + // NOTE: this test may fail but it is impossible to see this happening in normal + // condition. we are generating 32 random bytes of public key and + // 64 random bytes of signature with an randomly generated message + // of a random number of bytes in. If the message were empty, the + // probability to have a signature that matches the verify key + // would still be 1 out of 2^96. // // if this test fails and it is not a bug, go buy a lottery ticket. !public_key.verify(message, &signature) diff --git a/pallas-miniprotocols/Cargo.toml b/pallas-miniprotocols/Cargo.toml index 21842b9..9264749 100644 --- a/pallas-miniprotocols/Cargo.toml +++ b/pallas-miniprotocols/Cargo.toml @@ -8,7 +8,10 @@ homepage = "https://github.com/txpipe/pallas" documentation = "https://docs.rs/pallas-machines" license = "Apache-2.0" readme = "README.md" -authors = ["Santiago Carmuega "] +authors = [ + "Santiago Carmuega ", + "Pi Lanningham " +] [dependencies] pallas-codec = { version = "0.18.0", path = "../pallas-codec/" } diff --git a/pallas-miniprotocols/README.md b/pallas-miniprotocols/README.md index 991b06f..a1ca5b8 100644 --- a/pallas-miniprotocols/README.md +++ b/pallas-miniprotocols/README.md @@ -71,7 +71,7 @@ bearer.set_keepalive_ms(Some(30_000u32)).unwrap(); let mut muxer = Multiplexer::setup(bearer, &[0]).unwrap(); // get a handle for the handhsake mini-protocol handle -let mut channel = muxer.use_channel(0); +let mut channel = muxer.use_channel(pallas_miniprotocols::PROTOCOL_N2N_HANDSHAKE); // create a handshake client agent with an initial state let agent = handshake::Client::initial(VersionTable::v4_and_above(MAINNET_MAGIC)); diff --git a/pallas-miniprotocols/src/common.rs b/pallas-miniprotocols/src/common.rs index 0093381..efd46b2 100644 --- a/pallas-miniprotocols/src/common.rs +++ b/pallas-miniprotocols/src/common.rs @@ -14,6 +14,33 @@ pub const PREVIEW_MAGIC: u64 = 2; /// Well-known magic for pre-production pub const PRE_PRODUCTION_MAGIC: u64 = 1; +/// Protocol channel number for node-to-node handshakes +pub const PROTOCOL_N2N_HANDSHAKE: u16 = 0; + +/// Protocol channel number for node-to-node chain-sync +pub const PROTOCOL_N2N_CHAIN_SYNC: u16 = 2; + +/// Protocol channel number for node-to-node block-fetch +pub const PROTOCOL_N2N_BLOCK_FETCH: u16 = 3; + +/// Protocol channel number for node-to-node tx-submission +pub const PROTOCOL_N2N_TX_SUBMISSION: u16 = 4; + +/// Protocol channel number for node-to-node Keep-alive +pub const PROTOCOL_N2N_KEEP_ALIVE: u16 = 8; + +/// Protocol channel number for node-to-client handshakes +pub const PROTOCOL_N2C_HANDSHAKE: u16 = 0; + +/// Protocol channel number for node-to-client chain-sync +pub const PROTOCOL_N2C_CHAIN_SYNC: u16 = 5; + +/// Protocol channel number for node-to-client tx-submission +pub const PROTOCOL_N2C_TX_SUBMISSION: u16 = 6; + +// Protocol channel number for node-to-client state queries +pub const PROTOCOL_N2C_STATE_QUERY: u16 = 7; + /// A point within a chain #[derive(Clone, Eq, PartialEq, Hash)] pub enum Point { diff --git a/pallas-miniprotocols/src/txsubmission/client.rs b/pallas-miniprotocols/src/txsubmission/client.rs index b666464..d791220 100644 --- a/pallas-miniprotocols/src/txsubmission/client.rs +++ b/pallas-miniprotocols/src/txsubmission/client.rs @@ -31,7 +31,8 @@ where self.0 == State::Done } - // NOTE(pi): as of this writing, the network spec has a typo; this is the correct behavior + // NOTE(pi): as of this writing, the network spec has a typo; this is the + // correct behavior fn has_agency(&self) -> bool { !matches!(self.state(), State::Idle) } diff --git a/pallas-miniprotocols/src/txsubmission/server.rs b/pallas-miniprotocols/src/txsubmission/server.rs index f42e7da..a71bb1b 100644 --- a/pallas-miniprotocols/src/txsubmission/server.rs +++ b/pallas-miniprotocols/src/txsubmission/server.rs @@ -31,7 +31,8 @@ where self.0 == State::Done } - // NOTE(pi): as of this writing, the network spec has a typo; this is the correct behavior + // NOTE(pi): as of this writing, the network spec has a typo; this is the + // correct behavior fn has_agency(&self) -> bool { matches!(self.state(), State::Idle) } diff --git a/pallas-miniprotocols/tests/integration.rs b/pallas-miniprotocols/tests/integration.rs index d513fbd..0ffde5c 100644 --- a/pallas-miniprotocols/tests/integration.rs +++ b/pallas-miniprotocols/tests/integration.rs @@ -3,29 +3,30 @@ use pallas_miniprotocols::{ chainsync::{self, NextResponse}, handshake::{self, Confirmation}, txsubmission::{self, Reply}, - Point, + Point, PROTOCOL_N2N_BLOCK_FETCH, PROTOCOL_N2N_CHAIN_SYNC, PROTOCOL_N2N_HANDSHAKE, + PROTOCOL_N2N_TX_SUBMISSION, }; use pallas_multiplexer::{bearers::Bearer, StdChannel, StdPlexer}; struct N2NChannels { - channel2: StdChannel, - channel3: StdChannel, - channel4: StdChannel, + chainsync: StdChannel, + blockfetch: StdChannel, + txsubmission: StdChannel, } fn setup_n2n_client_connection() -> N2NChannels { let bearer = Bearer::connect_tcp("preview-node.world.dev.cardano.org:30002").unwrap(); let mut plexer = StdPlexer::new(bearer); - let channel0 = plexer.use_channel(0); - let channel2 = plexer.use_channel(2); - let channel3 = plexer.use_channel(3); - let channel4 = plexer.use_channel(4); + let handshake = plexer.use_channel(PROTOCOL_N2N_HANDSHAKE); + let chainsync = plexer.use_channel(PROTOCOL_N2N_CHAIN_SYNC); + let blockfetch = plexer.use_channel(PROTOCOL_N2N_BLOCK_FETCH); + let txsubmission = plexer.use_channel(PROTOCOL_N2N_TX_SUBMISSION); plexer.muxer.spawn(); plexer.demuxer.spawn(); - let mut client = handshake::N2NClient::new(channel0); + let mut client = handshake::N2NClient::new(handshake); let confirmation = client .handshake(handshake::n2n::VersionTable::v7_and_above(2)) @@ -38,23 +39,23 @@ fn setup_n2n_client_connection() -> N2NChannels { } N2NChannels { - channel2, - channel3, - channel4, + chainsync, + blockfetch, + txsubmission, } } #[test] #[ignore] pub fn chainsync_history_happy_path() { - let N2NChannels { channel2, .. } = setup_n2n_client_connection(); + let N2NChannels { chainsync, .. } = setup_n2n_client_connection(); let known_point = Point::Specific( 1654413, hex::decode("7de1f036df5a133ce68a82877d14354d0ba6de7625ab918e75f3e2ecb29771c2").unwrap(), ); - let mut client = chainsync::N2NClient::new(channel2); + let mut client = chainsync::N2NClient::new(chainsync); let (point, _) = client.find_intersect(vec![known_point.clone()]).unwrap(); @@ -93,9 +94,9 @@ pub fn chainsync_history_happy_path() { #[test] #[ignore] pub fn chainsync_tip_happy_path() { - let N2NChannels { channel2, .. } = setup_n2n_client_connection(); + let N2NChannels { chainsync, .. } = setup_n2n_client_connection(); - let mut client = chainsync::N2NClient::new(channel2); + let mut client = chainsync::N2NClient::new(chainsync); client.intersect_tip().unwrap(); @@ -132,14 +133,14 @@ pub fn chainsync_tip_happy_path() { #[test] #[ignore] pub fn blockfetch_happy_path() { - let N2NChannels { channel3, .. } = setup_n2n_client_connection(); + let N2NChannels { blockfetch, .. } = setup_n2n_client_connection(); let known_point = Point::Specific( 1654413, hex::decode("7de1f036df5a133ce68a82877d14354d0ba6de7625ab918e75f3e2ecb29771c2").unwrap(), ); - let mut client = blockfetch::Client::new(channel3); + let mut client = blockfetch::Client::new(blockfetch); let range_ok = client.request_range((known_point.clone(), known_point.clone())); @@ -170,13 +171,14 @@ pub fn blockfetch_happy_path() { #[test] #[ignore] pub fn txsubmission_server_happy_path() { - // TODO(pi): Note that the below doesn't work; we need a node to connect *to us* during the integration test - // which seems awkward; - // Alternatively, we can just set up both a client and server connecting to themselves for testing! + // TODO(pi): Note that the below doesn't work; we need a node to connect *to us* + // during the integration test which seems awkward; + // Alternatively, we can just set up both a client and server connecting to + // themselves for testing! - let N2NChannels { channel4, .. } = setup_n2n_client_connection(); + let N2NChannels { txsubmission, .. } = setup_n2n_client_connection(); - let mut server = txsubmission::Server::new(channel4); + let mut server = txsubmission::Server::new(txsubmission); assert!(matches!(server.wait_for_init(), Ok(_))); @@ -209,7 +211,8 @@ pub fn txsubmission_server_happy_path() { assert!(matches!(reply, Ok(Reply::Txs(_)))); let Ok(Reply::Txs(second_txs)) = reply else { unreachable!() }; - // Make sure we receive the second and third tx again, indicating we sent the `acknowledge 1` bit correctly + // Make sure we receive the second and third tx again, indicating we sent the + // `acknowledge 1` bit correctly assert_eq!(second_txs[0], first_txs[1]); assert_eq!(second_txs[1], first_txs[2]); diff --git a/pallas-multiplexer/README.md b/pallas-multiplexer/README.md index ad1ec1c..cc06406 100644 --- a/pallas-multiplexer/README.md +++ b/pallas-multiplexer/README.md @@ -34,13 +34,13 @@ let bearer = UnixStream::connect("/tmp/pallas").unwrap(); let muxer = Multiplexer::setup(tcp, &[0, 2]) // Ask the multiplexer to provide us with the channel for the miniprotocol #0. -let mut channel_0 = muxer.use_channel(0); +let mut handshake = muxer.use_channel(PROTOCOL_N2N_HANDSHAKE); // Spawn a thread and pass the ownership of the channel. thread::spawn(move || { // Deconstruct the channel to get a handle for sending data into the muxer // ingress and a handle to receive data from the demuxer egress. - let Channel(mux_tx, demux_rx) = channel_0; + let Channel(mux_tx, demux_rx) = handshake; // Do something with the channel. In this case, we just keep sending // dumb data every 50 millis. @@ -51,14 +51,14 @@ thread::spawn(move || { } }); -// Ask the multiplexer to provide us with the channel for the miniprotocol #2. -let mut channel_2 = muxer.use_channel(2); +// Ask the multiplexer to provide us with the channel for the chainsync miniprotocol. +let mut chainsync = muxer.use_channel(PROTOCOL_N2N_CHAINSYNC); // Spawn a different thread and pass the ownership of the 2nd channel. thread::spawn(move || { // Deconstruct the channel to get a handle for sending data into the muxer // ingress and a handle to receive data from the demuxer egress. - let Channel(mux_tx, demux_rx) = channel_2; + let Channel(mux_tx, demux_rx) = chainsync; // Do something with the channel. In this case, we just print in stdout // whatever get received for this mini-protocol. diff --git a/pallas-primitives/src/alonzo/model.rs b/pallas-primitives/src/alonzo/model.rs index bf16dd4..d3103f1 100644 --- a/pallas-primitives/src/alonzo/model.rs +++ b/pallas-primitives/src/alonzo/model.rs @@ -844,7 +844,8 @@ impl AsRef<[u8]> for PlutusScript { } } -/// Defined to encode PlutusData bytestring as it is done in the canonical plutus implementation +/// Defined to encode PlutusData bytestring as it is done in the canonical +/// plutus implementation #[derive(Serialize, Deserialize, Clone, Debug, PartialEq, Eq, PartialOrd, Ord)] #[serde(into = "String")] #[serde(try_from = "String")] @@ -899,7 +900,8 @@ impl Encode for BoundedBytes { e: &mut minicbor::Encoder, _: &mut C, ) -> Result<(), minicbor::encode::Error> { - // we match the haskell implementation by encoding bytestrings longer than 64 bytes as indefinite lists of bytes + // we match the haskell implementation by encoding bytestrings longer than 64 + // bytes as indefinite lists of bytes const CHUNK_SIZE: usize = 64; let bs: &Vec = self.deref(); if bs.len() <= 64 { @@ -1086,8 +1088,8 @@ impl minicbor::encode::Encode for PlutusData { e.encode_with(a, ctx)?; } Self::Map(a) => { - // we use definite array to match the approach used by haskell's plutus implementation - // https://github.com/input-output-hk/plutus/blob/9538fc9829426b2ecb0628d352e2d7af96ec8204/plutus-core/plutus-core/src/PlutusCore/Data.hs#L152 + // we use definite array to match the approach used by haskell's plutus + // implementation https://github.com/input-output-hk/plutus/blob/9538fc9829426b2ecb0628d352e2d7af96ec8204/plutus-core/plutus-core/src/PlutusCore/Data.hs#L152 e.map(a.len().try_into().unwrap())?; for (k, v) in a.iter() { k.encode(e, ctx)?; @@ -1101,8 +1103,8 @@ impl minicbor::encode::Encode for PlutusData { e.encode_with(a, ctx)?; } Self::Array(a) => { - // we use definite array for empty array or indef array otherwise to match haskell implementation - // https://github.com/input-output-hk/plutus/blob/9538fc9829426b2ecb0628d352e2d7af96ec8204/plutus-core/plutus-core/src/PlutusCore/Data.hs#L153 + // we use definite array for empty array or indef array otherwise to match + // haskell implementation https://github.com/input-output-hk/plutus/blob/9538fc9829426b2ecb0628d352e2d7af96ec8204/plutus-core/plutus-core/src/PlutusCore/Data.hs#L153 // default encoder for a list: // https://github.com/well-typed/cborg/blob/4bdc818a1f0b35f38bc118a87944630043b58384/serialise/src/Codec/Serialise/Class.hs#L181 encode_list(a, e, ctx)?; @@ -1172,15 +1174,16 @@ where e.array(2)?; e.encode_with(self.any_constructor.unwrap_or_default(), ctx)?; - // we use definite array for empty array or indef array otherwise to match haskell implementation - // https://github.com/input-output-hk/plutus/blob/9538fc9829426b2ecb0628d352e2d7af96ec8204/plutus-core/plutus-core/src/PlutusCore/Data.hs#L144 + // we use definite array for empty array or indef array otherwise to match + // haskell implementation https://github.com/input-output-hk/plutus/blob/9538fc9829426b2ecb0628d352e2d7af96ec8204/plutus-core/plutus-core/src/PlutusCore/Data.hs#L144 // default encoder for a list: // https://github.com/well-typed/cborg/blob/4bdc818a1f0b35f38bc118a87944630043b58384/serialise/src/Codec/Serialise/Class.hs#L181 encode_list(&self.fields, e, ctx)?; Ok(()) } _ => { - // we use definite array for empty array or indef array otherwise to match haskell implementation. See above reference. + // we use definite array for empty array or indef array otherwise to match + // haskell implementation. See above reference. encode_list(&self.fields, e, ctx)?; Ok(()) } diff --git a/pallas-traverse/src/tx.rs b/pallas-traverse/src/tx.rs index 6dec870..05022f2 100644 --- a/pallas-traverse/src/tx.rs +++ b/pallas-traverse/src/tx.rs @@ -232,14 +232,15 @@ impl<'b> MultiEraTx<'b> { } } - /// Returns a list of tuples of the outputs produced by the Tx with their indexes + /// Returns a list of tuples of the outputs produced by the Tx with their + /// indexes /// /// Helper method to abstract the logic of which outputs are produced /// depending on the validity of the Tx. If the Tx is valid, this method /// will return the list of outputs. If the Tx is invalid it will return the - /// collateral return if one is present or an empty list if not. Note that the - /// collateral return output index is defined as the next available index after - /// the txouts (Babbage spec, ch 4). + /// collateral return if one is present or an empty list if not. Note that + /// the collateral return output index is defined as the next available + /// index after the txouts (Babbage spec, ch 4). pub fn produces(&self) -> Vec<(usize, MultiEraOutput)> { match self.is_valid() { true => self.outputs().into_iter().enumerate().collect(),