From 58f9e0a0005aab59dfd987bddb09952f3a5c195b Mon Sep 17 00:00:00 2001 From: Lizzy Fleckenstein Date: Wed, 15 Feb 2023 23:44:21 +0100 Subject: Add wrappers around mt_rudp --- src/conn.rs | 104 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 104 insertions(+) create mode 100644 src/conn.rs (limited to 'src/conn.rs') diff --git a/src/conn.rs b/src/conn.rs new file mode 100644 index 0000000..3fc0e55 --- /dev/null +++ b/src/conn.rs @@ -0,0 +1,104 @@ +use super::PktInfo; +use delegate::delegate; +use mt_ser::{DefCfg, MtDeserialize, MtSerialize}; +use std::{borrow::Cow, io}; +use thiserror::Error; + +pub trait Remote { + type UdpSender: mt_rudp::UdpSender; + type PktFrom: MtDeserialize; + type PktTo: MtSerialize + PktInfo; +} + +#[cfg(feature = "client")] +pub struct RemoteSrv; + +#[cfg(feature = "client")] +impl Remote for RemoteSrv { + type UdpSender = mt_rudp::ToSrv; + type PktTo = crate::ToSrvPkt; + type PktFrom = crate::ToCltPkt; +} + +#[cfg(feature = "client")] +pub async fn connect(addr: &str) -> io::Result<(MtSender, MtReceiver)> { + let (tx, rx) = mt_rudp::connect(addr).await?; + Ok((MtSender(tx), MtReceiver(rx))) +} + +/* + +pub struct RemoteClt; +impl Remote for RemoteClt { + type Sender = mt_rudp::ToClt; + type To = crate::ToCltPkt; + type From = crate::ToSrvPkt; +} + +*/ + +pub struct MtSender(pub mt_rudp::RudpSender); +pub struct MtReceiver(pub mt_rudp::RudpReceiver); + +#[derive(Error, Debug)] +pub enum RecvError { + #[error("connection error: {0}")] + ConnError(#[from] mt_rudp::Error), + #[error("deserialize error: {0}")] + DeserializeError(#[from] mt_ser::DeserializeError), +} + +#[derive(Error, Debug)] +pub enum SendError { + #[error("connection error: {0}")] + ConnError(#[from] io::Error), + #[error("serialize error: {0}")] + SerializeError(#[from] mt_ser::SerializeError), +} + +macro_rules! impl_delegate { + ($T:ident) => { + impl $T { + delegate! { + to self.0 { + pub async fn peer_id(&self) -> u16; + pub async fn is_server(&self) -> bool; + pub async fn close(self); + } + } + } + }; +} + +impl_delegate!(MtSender); +impl_delegate!(MtReceiver); + +impl MtReceiver { + pub async fn recv(&mut self) -> Option> { + self.0.recv().await.map(|res| { + res.map_err(RecvError::from).and_then(|pkt| { + // TODO: warn on trailing data + R::PktFrom::mt_deserialize::(&mut io::Cursor::new(pkt.data)) + .map_err(RecvError::from) + }) + }) + } +} + +impl MtSender { + pub async fn send(&self, pkt: &R::PktTo) -> Result<(), SendError> { + let mut writer = Vec::new(); + pkt.mt_serialize::(&mut writer)?; + + let (chan, unrel) = pkt.pkt_info(); + self.0 + .send(mt_rudp::Pkt { + chan, + unrel, + data: Cow::Borrowed(&writer), + }) + .await?; + + Ok(()) + } +} -- cgit v1.2.3