diff --git a/chain/src/txhashset/bitmap_accumulator.rs b/chain/src/txhashset/bitmap_accumulator.rs index 2990d21e6..49b472716 100644 --- a/chain/src/txhashset/bitmap_accumulator.rs +++ b/chain/src/txhashset/bitmap_accumulator.rs @@ -233,7 +233,7 @@ impl Readable for BitmapChunk { /// Reading is not currently supported, just return an empty one for now. /// We store the underlying roaring bitmap externally for the bitmap accumulator /// and the "hash only" backend means we never actually read these chunks. - fn read(_reader: &mut dyn Reader) -> Result<BitmapChunk, ser::Error> { + fn read<R: Reader>(_reader: &mut R) -> Result<BitmapChunk, ser::Error> { Ok(BitmapChunk::new()) } } diff --git a/chain/src/types.rs b/chain/src/types.rs index 9e3155ddd..12e2d78b6 100644 --- a/chain/src/types.rs +++ b/chain/src/types.rs @@ -312,7 +312,7 @@ pub struct CommitPos { } impl Readable for CommitPos { - fn read(reader: &mut dyn Reader) -> Result<CommitPos, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<CommitPos, ser::Error> { let pos = reader.read_u64()?; let height = reader.read_u64()?; Ok(CommitPos { pos, height }) @@ -384,7 +384,7 @@ impl ser::Writeable for Tip { } impl ser::Readable for Tip { - fn read(reader: &mut dyn ser::Reader) -> Result<Tip, ser::Error> { + fn read<R: ser::Reader>(reader: &mut R) -> Result<Tip, ser::Error> { let height = reader.read_u64()?; let last = Hash::read(reader)?; let prev = Hash::read(reader)?; diff --git a/core/src/core/block.rs b/core/src/core/block.rs index f916c156f..e892e2709 100644 --- a/core/src/core/block.rs +++ b/core/src/core/block.rs @@ -132,7 +132,7 @@ pub struct HeaderEntry { } impl Readable for HeaderEntry { - fn read(reader: &mut dyn Reader) -> Result<HeaderEntry, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<HeaderEntry, ser::Error> { let hash = Hash::read(reader)?; let timestamp = reader.read_u64()?; let total_difficulty = Difficulty::read(reader)?; @@ -192,7 +192,7 @@ impl Writeable for HeaderVersion { } impl Readable for HeaderVersion { - fn read(reader: &mut dyn Reader) -> Result<HeaderVersion, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<HeaderVersion, ser::Error> { let version = reader.read_u16()?; Ok(HeaderVersion(version)) } @@ -280,7 +280,7 @@ impl Writeable for BlockHeader { } } -fn read_block_header(reader: &mut dyn Reader) -> Result<BlockHeader, ser::Error> { +fn read_block_header<R: Reader>(reader: &mut R) -> Result<BlockHeader, ser::Error> { let version = HeaderVersion::read(reader)?; let (height, timestamp) = ser_multiread!(reader, read_u64, read_i64); let prev_hash = Hash::read(reader)?; @@ -316,7 +316,7 @@ fn read_block_header(reader: &mut dyn Reader) -> Result<BlockHeader, ser::Error> /// Deserialization of a block header impl Readable for BlockHeader { - fn read(reader: &mut dyn Reader) -> Result<BlockHeader, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<BlockHeader, ser::Error> { read_block_header(reader) } } @@ -413,7 +413,7 @@ pub struct UntrustedBlockHeader(BlockHeader); /// Deserialization of an untrusted block header impl Readable for UntrustedBlockHeader { - fn read(reader: &mut dyn Reader) -> Result<UntrustedBlockHeader, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<UntrustedBlockHeader, ser::Error> { let header = read_block_header(reader)?; if header.timestamp > Utc::now() + Duration::seconds(12 * (consensus::BLOCK_TIME_SEC as i64)) @@ -490,7 +490,7 @@ impl Writeable for Block { /// Implementation of Readable for a block, defines how to read a full block /// from a binary stream. impl Readable for Block { - fn read(reader: &mut dyn Reader) -> Result<Block, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<Block, ser::Error> { let header = BlockHeader::read(reader)?; let body = TransactionBody::read(reader)?; Ok(Block { header, body }) @@ -828,7 +828,7 @@ pub struct UntrustedBlock(Block); /// Deserialization of an untrusted block header impl Readable for UntrustedBlock { - fn read(reader: &mut dyn Reader) -> Result<UntrustedBlock, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<UntrustedBlock, ser::Error> { // we validate header here before parsing the body let header = UntrustedBlockHeader::read(reader)?; let body = TransactionBody::read(reader)?; diff --git a/core/src/core/block_sums.rs b/core/src/core/block_sums.rs index fa50fbd68..b6b05c886 100644 --- a/core/src/core/block_sums.rs +++ b/core/src/core/block_sums.rs @@ -41,7 +41,7 @@ impl Writeable for BlockSums { } impl Readable for BlockSums { - fn read(reader: &mut dyn Reader) -> Result<BlockSums, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<BlockSums, ser::Error> { Ok(BlockSums { utxo_sum: Commitment::read(reader)?, kernel_sum: Commitment::read(reader)?, diff --git a/core/src/core/compact_block.rs b/core/src/core/compact_block.rs index 8a4b088af..128c1e1e7 100644 --- a/core/src/core/compact_block.rs +++ b/core/src/core/compact_block.rs @@ -82,7 +82,7 @@ impl CompactBlockBody { } impl Readable for CompactBlockBody { - fn read(reader: &mut dyn Reader) -> Result<CompactBlockBody, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<CompactBlockBody, ser::Error> { let (out_full_len, kern_full_len, kern_id_len) = ser_multiread!(reader, read_u64, read_u64, read_u64); @@ -215,7 +215,7 @@ impl Writeable for CompactBlock { /// Implementation of Readable for a compact block, defines how to read a /// compact block from a binary stream. impl Readable for CompactBlock { - fn read(reader: &mut dyn Reader) -> Result<CompactBlock, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<CompactBlock, ser::Error> { let header = BlockHeader::read(reader)?; let nonce = reader.read_u64()?; let body = CompactBlockBody::read(reader)?; @@ -241,7 +241,7 @@ pub struct UntrustedCompactBlock(CompactBlock); /// Implementation of Readable for an untrusted compact block, defines how to read a /// compact block from a binary stream. impl Readable for UntrustedCompactBlock { - fn read(reader: &mut dyn Reader) -> Result<UntrustedCompactBlock, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<UntrustedCompactBlock, ser::Error> { let header = UntrustedBlockHeader::read(reader)?; let nonce = reader.read_u64()?; let body = CompactBlockBody::read(reader)?; diff --git a/core/src/core/hash.rs b/core/src/core/hash.rs index 34c17fc55..2dc968fa4 100644 --- a/core/src/core/hash.rs +++ b/core/src/core/hash.rs @@ -131,7 +131,7 @@ impl AsRef<[u8]> for Hash { } impl Readable for Hash { - fn read(reader: &mut dyn Reader) -> Result<Hash, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<Hash, ser::Error> { let v = reader.read_fixed_bytes(32)?; let mut a = [0; 32]; a.copy_from_slice(&v[..]); diff --git a/core/src/core/id.rs b/core/src/core/id.rs index af97709f4..dec4fea2c 100644 --- a/core/src/core/id.rs +++ b/core/src/core/id.rs @@ -91,7 +91,7 @@ impl AsRef<[u8]> for ShortId { } impl Readable for ShortId { - fn read(reader: &mut dyn Reader) -> Result<ShortId, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<ShortId, ser::Error> { let v = reader.read_fixed_bytes(SHORT_ID_SIZE)?; let mut a = [0; SHORT_ID_SIZE]; a.copy_from_slice(&v[..]); diff --git a/core/src/core/merkle_proof.rs b/core/src/core/merkle_proof.rs index 813a87d7f..8711ab5fc 100644 --- a/core/src/core/merkle_proof.rs +++ b/core/src/core/merkle_proof.rs @@ -47,7 +47,7 @@ impl Writeable for MerkleProof { } impl Readable for MerkleProof { - fn read(reader: &mut dyn Reader) -> Result<MerkleProof, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<MerkleProof, ser::Error> { let mmr_size = reader.read_u64()?; let path_len = reader.read_u64()?; let mut path = Vec::with_capacity(path_len as usize); diff --git a/core/src/core/transaction.rs b/core/src/core/transaction.rs index 2da44cb5a..1502323dc 100644 --- a/core/src/core/transaction.rs +++ b/core/src/core/transaction.rs @@ -133,7 +133,7 @@ impl KernelFeatures { // Always read feature byte, 8 bytes for fee and 8 bytes for lock height. // Fee and lock height may be unused for some kernel variants but we need // to read these bytes and verify they are 0 if unused. - fn read_v1(reader: &mut dyn Reader) -> Result<KernelFeatures, ser::Error> { + fn read_v1<R: Reader>(reader: &mut R) -> Result<KernelFeatures, ser::Error> { let feature_byte = reader.read_u8()?; let fee = reader.read_u64()?; let lock_height = reader.read_u64()?; @@ -164,7 +164,7 @@ impl KernelFeatures { // V2 kernels only expect bytes specific to each variant. // Coinbase kernels have no associated fee and we do not serialize a fee for these. - fn read_v2(reader: &mut dyn Reader) -> Result<KernelFeatures, ser::Error> { + fn read_v2<R: Reader>(reader: &mut R) -> Result<KernelFeatures, ser::Error> { let features = match reader.read_u8()? { KernelFeatures::PLAIN_U8 => { let fee = reader.read_u64()?; @@ -202,7 +202,7 @@ impl Writeable for KernelFeatures { } impl Readable for KernelFeatures { - fn read(reader: &mut dyn Reader) -> Result<KernelFeatures, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<KernelFeatures, ser::Error> { match reader.protocol_version().value() { 0..=1 => KernelFeatures::read_v1(reader), 2..=ProtocolVersion::MAX => KernelFeatures::read_v2(reader), @@ -336,7 +336,7 @@ impl Writeable for TxKernel { } impl Readable for TxKernel { - fn read(reader: &mut dyn Reader) -> Result<TxKernel, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<TxKernel, ser::Error> { Ok(TxKernel { features: KernelFeatures::read(reader)?, excess: Commitment::read(reader)?, @@ -534,7 +534,7 @@ impl Writeable for TransactionBody { /// Implementation of Readable for a body, defines how to read a /// body from a binary stream. impl Readable for TransactionBody { - fn read(reader: &mut dyn Reader) -> Result<TransactionBody, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<TransactionBody, ser::Error> { let (input_len, output_len, kernel_len) = ser_multiread!(reader, read_u64, read_u64, read_u64); @@ -908,7 +908,7 @@ impl Writeable for Transaction { /// Implementation of Readable for a transaction, defines how to read a full /// transaction from a binary stream. impl Readable for Transaction { - fn read(reader: &mut dyn Reader) -> Result<Transaction, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<Transaction, ser::Error> { let offset = BlindingFactor::read(reader)?; let body = TransactionBody::read(reader)?; let tx = Transaction { offset, body }; @@ -1294,7 +1294,7 @@ impl Writeable for Input { /// Implementation of Readable for a transaction Input, defines how to read /// an Input from a binary stream. impl Readable for Input { - fn read(reader: &mut dyn Reader) -> Result<Input, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<Input, ser::Error> { let features = OutputFeatures::read(reader)?; let commit = Commitment::read(reader)?; Ok(Input::new(features, commit)) @@ -1352,7 +1352,7 @@ impl Writeable for OutputFeatures { } impl Readable for OutputFeatures { - fn read(reader: &mut dyn Reader) -> Result<OutputFeatures, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<OutputFeatures, ser::Error> { let features = OutputFeatures::from_u8(reader.read_u8()?).ok_or(ser::Error::CorruptedData)?; Ok(features) @@ -1410,7 +1410,7 @@ impl Writeable for Output { /// Implementation of Readable for a transaction Output, defines how to read /// an Output from a binary stream. impl Readable for Output { - fn read(reader: &mut dyn Reader) -> Result<Output, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<Output, ser::Error> { Ok(Output { features: OutputFeatures::read(reader)?, commit: Commitment::read(reader)?, @@ -1545,7 +1545,7 @@ impl Writeable for OutputIdentifier { } impl Readable for OutputIdentifier { - fn read(reader: &mut dyn Reader) -> Result<OutputIdentifier, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<OutputIdentifier, ser::Error> { Ok(OutputIdentifier { features: OutputFeatures::read(reader)?, commit: Commitment::read(reader)?, diff --git a/core/src/pow/types.rs b/core/src/pow/types.rs index 001f57a8b..c03f3a203 100644 --- a/core/src/pow/types.rs +++ b/core/src/pow/types.rs @@ -150,7 +150,7 @@ impl Writeable for Difficulty { } impl Readable for Difficulty { - fn read(reader: &mut dyn Reader) -> Result<Difficulty, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<Difficulty, ser::Error> { let data = reader.read_u64()?; Ok(Difficulty { num: data }) } @@ -249,7 +249,7 @@ impl Writeable for ProofOfWork { } impl Readable for ProofOfWork { - fn read(reader: &mut dyn Reader) -> Result<ProofOfWork, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<ProofOfWork, ser::Error> { let total_difficulty = Difficulty::read(reader)?; let secondary_scaling = reader.read_u32()?; let nonce = reader.read_u64()?; @@ -425,7 +425,7 @@ fn read_number(bits: &[u8], bit_start: usize, bit_count: usize) -> u64 { } impl Readable for Proof { - fn read(reader: &mut dyn Reader) -> Result<Proof, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<Proof, ser::Error> { let edge_bits = reader.read_u8()?; if edge_bits == 0 || edge_bits > 63 { return Err(ser::Error::CorruptedData); diff --git a/core/src/ser.rs b/core/src/ser.rs index 0dd583347..a99229565 100644 --- a/core/src/ser.rs +++ b/core/src/ser.rs @@ -224,17 +224,17 @@ pub trait Writeable { } /// Reader that exposes an Iterator interface. -pub struct IteratingReader<'a, T> { +pub struct IteratingReader<'a, T, R: Reader> { count: u64, curr: u64, - reader: &'a mut dyn Reader, + reader: &'a mut R, _marker: marker::PhantomData<T>, } -impl<'a, T> IteratingReader<'a, T> { +impl<'a, T, R: Reader> IteratingReader<'a, T, R> { /// Constructor to create a new iterating reader for the provided underlying reader. /// Takes a count so we know how many to iterate over. - pub fn new(reader: &'a mut dyn Reader, count: u64) -> IteratingReader<'a, T> { + pub fn new(reader: &'a mut R, count: u64) -> Self { let curr = 0; IteratingReader { count, @@ -245,9 +245,10 @@ impl<'a, T> IteratingReader<'a, T> { } } -impl<'a, T> Iterator for IteratingReader<'a, T> +impl<'a, T, R> Iterator for IteratingReader<'a, T, R> where T: Readable, + R: Reader, { type Item = T; @@ -261,9 +262,10 @@ where } /// Reads multiple serialized items into a Vec. -pub fn read_multi<T>(reader: &mut dyn Reader, count: u64) -> Result<Vec<T>, Error> +pub fn read_multi<T, R>(reader: &mut R, count: u64) -> Result<Vec<T>, Error> where T: Readable, + R: Reader, { // Very rudimentary check to ensure we do not overflow anything // attempting to read huge amounts of data. @@ -331,7 +333,7 @@ impl Writeable for ProtocolVersion { } impl Readable for ProtocolVersion { - fn read(reader: &mut dyn Reader) -> Result<ProtocolVersion, Error> { + fn read<R: Reader>(reader: &mut R) -> Result<ProtocolVersion, Error> { let version = reader.read_u32()?; Ok(ProtocolVersion(version)) } @@ -345,12 +347,12 @@ where Self: Sized, { /// Reads the data necessary to this Readable from the provided reader - fn read(reader: &mut dyn Reader) -> Result<Self, Error>; + fn read<R: Reader>(reader: &mut R) -> Result<Self, Error>; } /// Deserializes a Readable from any std::io::Read implementation. -pub fn deserialize<T: Readable>( - source: &mut dyn Read, +pub fn deserialize<T: Readable, R: Read>( + source: &mut R, version: ProtocolVersion, ) -> Result<T, Error> { let mut reader = BinReader::new(source, version); @@ -358,7 +360,7 @@ pub fn deserialize<T: Readable>( } /// Deserialize a Readable based on our default "local" protocol version. -pub fn deserialize_default<T: Readable>(source: &mut dyn Read) -> Result<T, Error> { +pub fn deserialize_default<T: Readable, R: Read>(source: &mut R) -> Result<T, Error> { deserialize(source, ProtocolVersion::local()) } @@ -386,14 +388,14 @@ pub fn ser_vec<W: Writeable>(thing: &W, version: ProtocolVersion) -> Result<Vec< } /// Utility to read from a binary source -pub struct BinReader<'a> { - source: &'a mut dyn Read, +pub struct BinReader<'a, R: Read> { + source: &'a mut R, version: ProtocolVersion, } -impl<'a> BinReader<'a> { +impl<'a, R: Read> BinReader<'a, R> { /// Constructor for a new BinReader for the provided source and protocol version. - pub fn new(source: &'a mut dyn Read, version: ProtocolVersion) -> BinReader<'a> { + pub fn new(source: &'a mut R, version: ProtocolVersion) -> Self { BinReader { source, version } } } @@ -404,7 +406,7 @@ fn map_io_err(err: io::Error) -> Error { /// Utility wrapper for an underlying byte Reader. Defines higher level methods /// to read numbers, byte vectors, hashes, etc. -impl<'a> Reader for BinReader<'a> { +impl<'a, R: Read> Reader for BinReader<'a, R> { fn read_u8(&mut self) -> Result<u8, Error> { self.source.read_u8().map_err(map_io_err) } @@ -544,7 +546,7 @@ impl<'a> Reader for StreamingReader<'a> { } impl Readable for Commitment { - fn read(reader: &mut dyn Reader) -> Result<Commitment, Error> { + fn read<R: Reader>(reader: &mut R) -> Result<Commitment, Error> { let a = reader.read_fixed_bytes(PEDERSEN_COMMITMENT_SIZE)?; let mut c = [0; PEDERSEN_COMMITMENT_SIZE]; c[..PEDERSEN_COMMITMENT_SIZE].clone_from_slice(&a[..PEDERSEN_COMMITMENT_SIZE]); @@ -565,7 +567,7 @@ impl Writeable for BlindingFactor { } impl Readable for BlindingFactor { - fn read(reader: &mut dyn Reader) -> Result<BlindingFactor, Error> { + fn read<R: Reader>(reader: &mut R) -> Result<BlindingFactor, Error> { let bytes = reader.read_fixed_bytes(SECRET_KEY_SIZE)?; Ok(BlindingFactor::from_slice(&bytes)) } @@ -578,7 +580,7 @@ impl Writeable for Identifier { } impl Readable for Identifier { - fn read(reader: &mut dyn Reader) -> Result<Identifier, Error> { + fn read<R: Reader>(reader: &mut R) -> Result<Identifier, Error> { let bytes = reader.read_fixed_bytes(IDENTIFIER_SIZE)?; Ok(Identifier::from_bytes(&bytes)) } @@ -591,7 +593,7 @@ impl Writeable for RangeProof { } impl Readable for RangeProof { - fn read(reader: &mut dyn Reader) -> Result<RangeProof, Error> { + fn read<R: Reader>(reader: &mut R) -> Result<RangeProof, Error> { let len = reader.read_u64()?; let max_len = cmp::min(len as usize, MAX_PROOF_SIZE); let p = reader.read_fixed_bytes(max_len)?; @@ -618,7 +620,7 @@ impl PMMRable for RangeProof { } impl Readable for Signature { - fn read(reader: &mut dyn Reader) -> Result<Signature, Error> { + fn read<R: Reader>(reader: &mut R) -> Result<Signature, Error> { let a = reader.read_fixed_bytes(AGG_SIGNATURE_SIZE)?; let mut c = [0; AGG_SIGNATURE_SIZE]; c[..AGG_SIGNATURE_SIZE].clone_from_slice(&a[..AGG_SIGNATURE_SIZE]); @@ -643,7 +645,7 @@ impl Writeable for PublicKey { impl Readable for PublicKey { // Read the public key in compressed form - fn read(reader: &mut dyn Reader) -> Result<Self, Error> { + fn read<R: Reader>(reader: &mut R) -> Result<Self, Error> { let buf = reader.read_fixed_bytes(COMPRESSED_PUBLIC_KEY_SIZE)?; let secp = Secp256k1::with_caps(ContextFlag::None); let pk = PublicKey::from_slice(&secp, &buf).map_err(|_| Error::CorruptedData)?; @@ -715,7 +717,7 @@ macro_rules! impl_int { } impl Readable for $int { - fn read(reader: &mut dyn Reader) -> Result<$int, Error> { + fn read<R: Reader>(reader: &mut R) -> Result<$int, Error> { reader.$r_fn() } } @@ -733,7 +735,7 @@ impl<T> Readable for Vec<T> where T: Readable, { - fn read(reader: &mut dyn Reader) -> Result<Vec<T>, Error> { + fn read<R: Reader>(reader: &mut R) -> Result<Vec<T>, Error> { let mut buf = Vec::new(); loop { let elem = T::read(reader); @@ -775,7 +777,7 @@ impl<A: Writeable, B: Writeable> Writeable for (A, B) { } impl<A: Readable, B: Readable> Readable for (A, B) { - fn read(reader: &mut dyn Reader) -> Result<(A, B), Error> { + fn read<R: Reader>(reader: &mut R) -> Result<(A, B), Error> { Ok((Readable::read(reader)?, Readable::read(reader)?)) } } @@ -798,7 +800,7 @@ impl<A: Writeable, B: Writeable, C: Writeable, D: Writeable> Writeable for (A, B } impl<A: Readable, B: Readable, C: Readable> Readable for (A, B, C) { - fn read(reader: &mut dyn Reader) -> Result<(A, B, C), Error> { + fn read<R: Reader>(reader: &mut R) -> Result<(A, B, C), Error> { Ok(( Readable::read(reader)?, Readable::read(reader)?, @@ -808,7 +810,7 @@ impl<A: Readable, B: Readable, C: Readable> Readable for (A, B, C) { } impl<A: Readable, B: Readable, C: Readable, D: Readable> Readable for (A, B, C, D) { - fn read(reader: &mut dyn Reader) -> Result<(A, B, C, D), Error> { + fn read<R: Reader>(reader: &mut R) -> Result<(A, B, C, D), Error> { Ok(( Readable::read(reader)?, Readable::read(reader)?, diff --git a/core/tests/common.rs b/core/tests/common.rs index d184beea6..758577393 100644 --- a/core/tests/common.rs +++ b/core/tests/common.rs @@ -155,7 +155,7 @@ impl Writeable for TestElem { } impl Readable for TestElem { - fn read(reader: &mut dyn Reader) -> Result<TestElem, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<TestElem, ser::Error> { Ok(TestElem([ reader.read_u32()?, reader.read_u32()?, diff --git a/p2p/src/conn.rs b/p2p/src/conn.rs index f848e746a..f1a7c9b35 100644 --- a/p2p/src/conn.rs +++ b/p2p/src/conn.rs @@ -48,9 +48,9 @@ const BODY_IO_TIMEOUT: Duration = Duration::from_millis(60000); /// A trait to be implemented in order to receive messages from the /// connection. Allows providing an optional response. pub trait MessageHandler: Send + 'static { - fn consume<'a>( + fn consume<'a, R: Read>( &self, - msg: Message<'a>, + msg: Message<'a, R>, stopped: Arc<AtomicBool>, tracker: Arc<Tracker>, ) -> Result<Option<Msg>, Error>; @@ -88,18 +88,14 @@ macro_rules! try_header { /// A message as received by the connection. Provides access to the message /// header lazily consumes the message body, handling its deserialization. -pub struct Message<'a> { +pub struct Message<'a, R: Read> { pub header: MsgHeader, - stream: &'a mut dyn Read, + stream: &'a mut R, version: ProtocolVersion, } -impl<'a> Message<'a> { - fn from_header( - header: MsgHeader, - stream: &'a mut dyn Read, - version: ProtocolVersion, - ) -> Message<'a> { +impl<'a, R: Read> Message<'a, R> { + fn from_header(header: MsgHeader, stream: &'a mut R, version: ProtocolVersion) -> Self { Message { header, stream, diff --git a/p2p/src/msg.rs b/p2p/src/msg.rs index c41498281..0907bf048 100644 --- a/p2p/src/msg.rs +++ b/p2p/src/msg.rs @@ -146,21 +146,21 @@ impl Msg { /// /// Note: We return a MsgHeaderWrapper here as we may encounter an unknown msg type. /// -pub fn read_header( - stream: &mut dyn Read, +pub fn read_header<R: Read>( + stream: &mut R, version: ProtocolVersion, ) -> Result<MsgHeaderWrapper, Error> { let mut head = vec![0u8; MsgHeader::LEN]; stream.read_exact(&mut head)?; - let header = ser::deserialize::<MsgHeaderWrapper>(&mut &head[..], version)?; + let header: MsgHeaderWrapper = ser::deserialize(&mut &head[..], version)?; Ok(header) } /// Read a single item from the provided stream, always blocking until we /// have a result (or timeout). /// Returns the item and the total bytes read. -pub fn read_item<T: Readable>( - stream: &mut dyn Read, +pub fn read_item<T: Readable, R: Read>( + stream: &mut R, version: ProtocolVersion, ) -> Result<(T, u64), Error> { let mut reader = StreamingReader::new(stream, version); @@ -170,9 +170,9 @@ pub fn read_item<T: Readable>( /// Read a message body from the provided stream, always blocking /// until we have a result (or timeout). -pub fn read_body<T: Readable>( +pub fn read_body<T: Readable, R: Read>( h: &MsgHeader, - stream: &mut dyn Read, + stream: &mut R, version: ProtocolVersion, ) -> Result<T, Error> { let mut body = vec![0u8; h.msg_len as usize]; @@ -181,15 +181,15 @@ pub fn read_body<T: Readable>( } /// Read (an unknown) message from the provided stream and discard it. -pub fn read_discard(msg_len: u64, stream: &mut dyn Read) -> Result<(), Error> { +pub fn read_discard<R: Read>(msg_len: u64, stream: &mut R) -> Result<(), Error> { let mut buffer = vec![0u8; msg_len as usize]; stream.read_exact(&mut buffer)?; Ok(()) } /// Reads a full message from the underlying stream. -pub fn read_message<T: Readable>( - stream: &mut dyn Read, +pub fn read_message<T: Readable, R: Read>( + stream: &mut R, version: ProtocolVersion, msg_type: Type, ) -> Result<T, Error> { @@ -208,8 +208,8 @@ pub fn read_message<T: Readable>( } } -pub fn write_message( - stream: &mut dyn Write, +pub fn write_message<W: Write>( + stream: &mut W, msg: &Msg, tracker: Arc<Tracker>, ) -> Result<(), Error> { @@ -285,7 +285,7 @@ impl Writeable for MsgHeader { } impl Readable for MsgHeaderWrapper { - fn read(reader: &mut dyn Reader) -> Result<MsgHeaderWrapper, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<MsgHeaderWrapper, ser::Error> { let m = magic(); reader.expect_u8(m[0])?; reader.expect_u8(m[1])?; @@ -371,7 +371,7 @@ impl Writeable for Hand { } impl Readable for Hand { - fn read(reader: &mut dyn Reader) -> Result<Hand, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<Hand, ser::Error> { let version = ProtocolVersion::read(reader)?; let (capab, nonce) = ser_multiread!(reader, read_u32, read_u64); let capabilities = Capabilities::from_bits_truncate(capab); @@ -422,7 +422,7 @@ impl Writeable for Shake { } impl Readable for Shake { - fn read(reader: &mut dyn Reader) -> Result<Shake, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<Shake, ser::Error> { let version = ProtocolVersion::read(reader)?; let capab = reader.read_u32()?; let capabilities = Capabilities::from_bits_truncate(capab); @@ -453,7 +453,7 @@ impl Writeable for GetPeerAddrs { } impl Readable for GetPeerAddrs { - fn read(reader: &mut dyn Reader) -> Result<GetPeerAddrs, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<GetPeerAddrs, ser::Error> { let capab = reader.read_u32()?; let capabilities = Capabilities::from_bits_truncate(capab); Ok(GetPeerAddrs { capabilities }) @@ -478,7 +478,7 @@ impl Writeable for PeerAddrs { } impl Readable for PeerAddrs { - fn read(reader: &mut dyn Reader) -> Result<PeerAddrs, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<PeerAddrs, ser::Error> { let peer_count = reader.read_u32()?; if peer_count > MAX_PEER_ADDRS { return Err(ser::Error::TooLargeReadErr); @@ -510,7 +510,7 @@ impl Writeable for PeerError { } impl Readable for PeerError { - fn read(reader: &mut dyn Reader) -> Result<PeerError, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<PeerError, ser::Error> { let code = reader.read_u32()?; let msg = reader.read_bytes_len_prefix()?; let message = String::from_utf8(msg).map_err(|_| ser::Error::CorruptedData)?; @@ -538,7 +538,7 @@ impl Writeable for Locator { } impl Readable for Locator { - fn read(reader: &mut dyn Reader) -> Result<Locator, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<Locator, ser::Error> { let len = reader.read_u8()?; if len > (MAX_LOCATORS as u8) { return Err(ser::Error::TooLargeReadErr); @@ -583,7 +583,7 @@ impl Writeable for Ping { } impl Readable for Ping { - fn read(reader: &mut dyn Reader) -> Result<Ping, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<Ping, ser::Error> { let total_difficulty = Difficulty::read(reader)?; let height = reader.read_u64()?; Ok(Ping { @@ -610,7 +610,7 @@ impl Writeable for Pong { } impl Readable for Pong { - fn read(reader: &mut dyn Reader) -> Result<Pong, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<Pong, ser::Error> { let total_difficulty = Difficulty::read(reader)?; let height = reader.read_u64()?; Ok(Pong { @@ -635,7 +635,7 @@ impl Writeable for BanReason { } impl Readable for BanReason { - fn read(reader: &mut dyn Reader) -> Result<BanReason, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<BanReason, ser::Error> { let ban_reason_i32 = match reader.read_i32() { Ok(h) => h, Err(_) => 0, @@ -665,7 +665,7 @@ impl Writeable for TxHashSetRequest { } impl Readable for TxHashSetRequest { - fn read(reader: &mut dyn Reader) -> Result<TxHashSetRequest, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<TxHashSetRequest, ser::Error> { Ok(TxHashSetRequest { hash: Hash::read(reader)?, height: reader.read_u64()?, @@ -693,7 +693,7 @@ impl Writeable for TxHashSetArchive { } impl Readable for TxHashSetArchive { - fn read(reader: &mut dyn Reader) -> Result<TxHashSetArchive, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<TxHashSetArchive, ser::Error> { let hash = Hash::read(reader)?; let (height, bytes) = ser_multiread!(reader, read_u64, read_u64); diff --git a/p2p/src/protocol.rs b/p2p/src/protocol.rs index b8cd75b58..bfdf4b56d 100644 --- a/p2p/src/protocol.rs +++ b/p2p/src/protocol.rs @@ -25,7 +25,7 @@ use chrono::prelude::Utc; use rand::{thread_rng, Rng}; use std::cmp; use std::fs::{self, File, OpenOptions}; -use std::io::BufWriter; +use std::io::{BufWriter, Read}; use std::sync::atomic::{AtomicBool, Ordering}; use std::sync::Arc; use std::time::Instant; @@ -51,9 +51,9 @@ impl Protocol { } impl MessageHandler for Protocol { - fn consume( + fn consume<R: Read>( &self, - mut msg: Message, + mut msg: Message<R>, stopped: Arc<AtomicBool>, tracker: Arc<Tracker>, ) -> Result<Option<Msg>, Error> { diff --git a/p2p/src/store.rs b/p2p/src/store.rs index e3627786c..baba718c9 100644 --- a/p2p/src/store.rs +++ b/p2p/src/store.rs @@ -75,7 +75,7 @@ impl Writeable for PeerData { } impl Readable for PeerData { - fn read(reader: &mut dyn Reader) -> Result<PeerData, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<PeerData, ser::Error> { let addr = PeerAddr::read(reader)?; let capab = reader.read_u32()?; let ua = reader.read_bytes_len_prefix()?; diff --git a/p2p/src/types.rs b/p2p/src/types.rs index 8e24d624d..24066f6d3 100644 --- a/p2p/src/types.rs +++ b/p2p/src/types.rs @@ -138,7 +138,7 @@ impl Writeable for PeerAddr { } impl Readable for PeerAddr { - fn read(reader: &mut dyn Reader) -> Result<PeerAddr, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<PeerAddr, ser::Error> { let v4_or_v6 = reader.read_u8()?; if v4_or_v6 == 0 { let ip = reader.read_fixed_bytes(4)?; diff --git a/store/src/types.rs b/store/src/types.rs index c1621cc6e..0b2c7a633 100644 --- a/store/src/types.rs +++ b/store/src/types.rs @@ -44,7 +44,7 @@ impl SizeEntry { } impl Readable for SizeEntry { - fn read(reader: &mut dyn Reader) -> Result<SizeEntry, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<SizeEntry, ser::Error> { Ok(SizeEntry { offset: reader.read_u64()?, size: reader.read_u16()?, diff --git a/store/tests/lmdb.rs b/store/tests/lmdb.rs index 0f37916cb..a8d1e397c 100644 --- a/store/tests/lmdb.rs +++ b/store/tests/lmdb.rs @@ -35,7 +35,7 @@ impl PhatChunkStruct { } impl Readable for PhatChunkStruct { - fn read(reader: &mut dyn Reader) -> Result<PhatChunkStruct, ser::Error> { + fn read<R: Reader>(reader: &mut R) -> Result<PhatChunkStruct, ser::Error> { let mut retval = PhatChunkStruct::new(); for _ in 0..TEST_ALLOC_SIZE { retval.phatness = reader.read_u64()?; diff --git a/store/tests/pmmr.rs b/store/tests/pmmr.rs index 931e7c432..7e4e9bbe0 100644 --- a/store/tests/pmmr.rs +++ b/store/tests/pmmr.rs @@ -982,7 +982,7 @@ impl Writeable for TestElem { } } impl Readable for TestElem { - fn read(reader: &mut dyn Reader) -> Result<TestElem, Error> { + fn read<R: Reader>(reader: &mut R) -> Result<TestElem, Error> { Ok(TestElem(reader.read_u32()?)) } }