Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

improve framing-sv2 modularization #847

Closed
wants to merge 2 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions protocols/v2/codec-sv2/src/decoder.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,11 +8,11 @@ pub use buffer_sv2::AeadBuffer;
pub use const_sv2::{SV2_FRAME_CHUNK_SIZE, SV2_FRAME_HEADER_SIZE};
use core::marker::PhantomData;
#[cfg(feature = "noise_sv2")]
use framing_sv2::framing2::HandShakeFrame;
use framing_sv2::framing::either_frame::HandShakeFrame;
#[cfg(feature = "noise_sv2")]
use framing_sv2::header::NoiseHeader;
use framing_sv2::{
framing2::{EitherFrame, Frame as F_, Sv2Frame},
framing::{either_frame::EitherFrame, frame::Frame as F_, sv2_frame::Sv2Frame},
header::Header,
};
#[cfg(feature = "noise_sv2")]
Expand Down
4 changes: 2 additions & 2 deletions protocols/v2/codec-sv2/src/encoder.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,8 @@ pub use const_sv2::{AEAD_MAC_LEN, SV2_FRAME_CHUNK_SIZE, SV2_FRAME_HEADER_SIZE};
use core::convert::TryInto;
use core::marker::PhantomData;
#[cfg(feature = "noise_sv2")]
use framing_sv2::framing2::{EitherFrame, HandShakeFrame};
use framing_sv2::framing2::{Frame as F_, Sv2Frame};
use framing_sv2::framing::either_frame::{EitherFrame, HandShakeFrame};
use framing_sv2::framing::{frame::Frame as F_, sv2_frame::Sv2Frame};
#[allow(unused_imports)]
pub use framing_sv2::header::NoiseHeader;

Expand Down
6 changes: 3 additions & 3 deletions protocols/v2/codec-sv2/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -21,16 +21,16 @@ pub use encoder::Encoder;
#[cfg(feature = "noise_sv2")]
pub use encoder::NoiseEncoder;

pub use framing_sv2::framing2::{Frame, Sv2Frame};
#[cfg(feature = "noise_sv2")]
pub use framing_sv2::framing2::{HandShakeFrame, NoiseFrame};
pub use framing_sv2::framing::{either_frame::HandShakeFrame, noise_frame::NoiseFrame};
pub use framing_sv2::framing::{frame::Frame, sv2_frame::Sv2Frame};

#[cfg(feature = "noise_sv2")]
pub use noise_sv2::{self, Initiator, NoiseCodec, Responder};

pub use buffer_sv2;

pub use framing_sv2::{self, framing2::handshake_message_to_frame as h2f};
pub use framing_sv2::{self, framing::noise_frame::handshake_message_to_frame as h2f};

#[cfg(feature = "noise_sv2")]
#[derive(Debug)]
Expand Down
46 changes: 46 additions & 0 deletions protocols/v2/framing-sv2/src/framing/either_frame.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
use crate::{
framing::{frame::Frame, noise_frame::NoiseFrame, sv2_frame::Sv2Frame},
Error,
};
use binary_sv2::{GetSize, Serialize};
use core::convert::TryFrom;

pub type HandShakeFrame = NoiseFrame;

#[derive(Debug)]
pub enum EitherFrame<T, B> {
HandShake(HandShakeFrame),
Sv2(Sv2Frame<T, B>),
}

impl<T: Serialize + GetSize, B: AsMut<[u8]> + AsRef<[u8]>> EitherFrame<T, B> {
pub fn encoded_length(&self) -> usize {
match &self {
Self::HandShake(frame) => frame.encoded_length(),
Self::Sv2(frame) => frame.encoded_length(),
}
}
}

impl<T, B> TryFrom<EitherFrame<T, B>> for HandShakeFrame {
type Error = Error;

fn try_from(v: EitherFrame<T, B>) -> Result<Self, Error> {
match v {
EitherFrame::HandShake(frame) => Ok(frame),
EitherFrame::Sv2(_) => Err(Error::ExpectedHandshakeFrame),
}
}
}

impl<T, B> From<HandShakeFrame> for EitherFrame<T, B> {
fn from(v: HandShakeFrame) -> Self {
Self::HandShake(v)
}
}

impl<T, B> From<Sv2Frame<T, B>> for EitherFrame<T, B> {
fn from(v: Sv2Frame<T, B>) -> Self {
Self::Sv2(v)
}
}
40 changes: 40 additions & 0 deletions protocols/v2/framing-sv2/src/framing/frame.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
use crate::Error;

use binary_sv2::{GetSize, Serialize};

pub trait Frame<'a, T: Serialize + GetSize>: Sized {
type Buffer: AsMut<[u8]>;
type Deserialized;

/// Serialize the frame into dst if the frame is already serialized it just swap dst with
/// itself
fn serialize(self, dst: &mut [u8]) -> Result<(), Error>;

//fn deserialize(&'a mut self) -> Result<Self::Deserialized, serde_sv2::Error>;

fn payload(&'a mut self) -> &'a mut [u8];

/// If is an Sv2 frame return the Some(header) if it is a noise frame return None
fn get_header(&self) -> Option<crate::header::Header>;

/// Try to build an Frame frame from raw bytes.
/// It return the frame or the number of the bytes needed to complete the frame
/// The resulting frame is just a header plus a payload with the right number of bytes nothing
/// is said about the correctness of the payload
fn from_bytes(bytes: Self::Buffer) -> Result<Self, isize>;

fn from_bytes_unchecked(bytes: Self::Buffer) -> Self;

fn size_hint(bytes: &[u8]) -> isize;

fn encoded_length(&self) -> usize;

/// Try to build an Frame frame from a serializable payload.
/// It return a Frame if the size of the payload fit in the frame, if not it return None
fn from_message(
message: T,
message_type: u8,
extension_type: u16,
channel_msg: bool,
) -> Option<Self>;
}
4 changes: 4 additions & 0 deletions protocols/v2/framing-sv2/src/framing/mod.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
pub mod either_frame;
pub mod frame;
pub mod noise_frame;
pub mod sv2_frame;
104 changes: 104 additions & 0 deletions protocols/v2/framing-sv2/src/framing/noise_frame.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,104 @@
use crate::{framing::frame::Frame, header::NoiseHeader, Error};

use alloc::vec::Vec;

const NOISE_MAX_LEN: usize = const_sv2::NOISE_FRAME_MAX_SIZE;

#[cfg(not(feature = "with_buffer_pool"))]
type Slice = Vec<u8>;
#[cfg(feature = "with_buffer_pool")]
type Slice = buffer_sv2::Slice;

#[derive(Debug)]
pub struct NoiseFrame {
payload: Slice,
}

impl NoiseFrame {
pub fn get_payload_when_handshaking(&self) -> Vec<u8> {
self.payload[0..].to_vec()
}
}

impl<'a> Frame<'a, Slice> for NoiseFrame {
type Buffer = Slice;
type Deserialized = &'a mut [u8];

/// Serialize the frame into dst if the frame is already serialized it just swap dst with
/// itself
#[inline]
fn serialize(mut self, dst: &mut [u8]) -> Result<(), Error> {
dst.swap_with_slice(self.payload.as_mut());
Ok(())
}

#[inline]
fn payload(&'a mut self) -> &'a mut [u8] {
&mut self.payload[NoiseHeader::HEADER_SIZE..]
}

/// If is an Sv2 frame return the Some(header) if it is a noise frame return None
fn get_header(&self) -> Option<crate::header::Header> {
None
}

// For a NoiseFrame from_bytes is the same of from_bytes_unchecked
fn from_bytes(bytes: Self::Buffer) -> Result<Self, isize> {
Ok(Self::from_bytes_unchecked(bytes))
}

#[inline]
fn from_bytes_unchecked(bytes: Self::Buffer) -> Self {
Self { payload: bytes }
}

#[inline]
fn size_hint(bytes: &[u8]) -> isize {
if bytes.len() < NoiseHeader::HEADER_SIZE {
return (NoiseHeader::HEADER_SIZE - bytes.len()) as isize;
};

let len_b = &bytes[NoiseHeader::LEN_OFFSET..NoiseHeader::HEADER_SIZE];
let expected_len = u16::from_le_bytes([len_b[0], len_b[1]]) as usize;

if bytes.len() - NoiseHeader::HEADER_SIZE == expected_len {
0
} else {
expected_len as isize - (bytes.len() - NoiseHeader::HEADER_SIZE) as isize
}
}

#[inline]
fn encoded_length(&self) -> usize {
self.payload.len()
}

/// Try to build a `Frame` frame from a serializable payload.
/// It returns a Frame if the size of the payload fits in the frame, if not it returns None
/// Inneficient should be used only to build `HandShakeFrames`
/// TODO check if is used only to build `HandShakeFrames`
#[allow(clippy::useless_conversion)]
fn from_message(
message: Slice,
_message_type: u8,
_extension_type: u16,
_channel_msg: bool,
) -> Option<Self> {
if message.len() <= NOISE_MAX_LEN {
Some(Self {
payload: message.into(),
})
} else {
None
}
}
}

#[allow(clippy::useless_conversion)]
pub fn handshake_message_to_frame<T: AsRef<[u8]>>(message: T) -> NoiseFrame {
let mut payload = Vec::new();
payload.extend_from_slice(message.as_ref());
NoiseFrame {
payload: payload.into(),
}
}
Loading
Loading