diff options
author | Joey Sacchini <joey@sacchini.net> | 2020-12-07 17:57:14 -0500 |
---|---|---|
committer | Joey Sacchini <joey@sacchini.net> | 2020-12-07 17:57:14 -0500 |
commit | 2ce7b7b52b3ec2dd8a4b7aa08c9b341f31fbf745 (patch) | |
tree | 6df624815efe9f78a9814d22e5e578ae3d3fe6ef /src | |
parent | 171a93a33c7cc282a1726851eebb69ad4fffe5fc (diff) | |
download | mcproto-rs-2ce7b7b52b3ec2dd8a4b7aa08c9b341f31fbf745.tar.gz mcproto-rs-2ce7b7b52b3ec2dd8a4b7aa08c9b341f31fbf745.tar.bz2 mcproto-rs-2ce7b7b52b3ec2dd8a4b7aa08c9b341f31fbf745.zip |
packet kind enum
Diffstat (limited to 'src')
-rw-r--r-- | src/protocol.rs | 105 | ||||
-rw-r--r-- | src/v1_15_2.rs | 2 | ||||
-rw-r--r-- | src/v1_16_3.rs | 2 |
3 files changed, 81 insertions, 28 deletions
diff --git a/src/protocol.rs b/src/protocol.rs index dbdbc6b..8f155fc 100644 --- a/src/protocol.rs +++ b/src/protocol.rs @@ -87,6 +87,15 @@ pub struct ProtocolPacketField { pub kind: String, } +pub trait HasPacketKind { + type Kind: PacketKind; + + fn kind(&self) -> Self::Kind; +} + +pub trait PacketKind: HasPacketId + Clone + Copy + PartialEq + Eq { +} + pub trait HasPacketId { fn id(&self) -> Id; @@ -237,7 +246,7 @@ macro_rules! proto_struct { #[macro_export] macro_rules! define_protocol { - ($version: literal, $packett: ident, $rawpackett: ident, $rawdt: ident => { + ($version: literal, $packett: ident, $rawpackett: ident, $rawdt: ident, $kindt: ident => { $($nam: ident, $id: literal, $state: ident, $direction: ident => $body: ident { $($fnam: ident: $ftyp: ty),* }),* } @@ -256,19 +265,30 @@ macro_rules! define_protocol { } } + $crate::as_item! { + #[derive(Debug, PartialEq, Eq, Hash, Clone, Copy)] + pub enum $kindt { + $($nam),*, + } + } + + impl crate::protocol::HasPacketKind for $packett { + type Kind = $kindt; + + fn kind(&self) -> Self::Kind { + match self { + $($packett::$nam(_) => $kindt::$nam),*, + } + } + } + impl crate::protocol::HasPacketId for $packett { fn version() -> crate::types::VarInt { crate::types::VarInt($version) } fn id(&self) -> crate::protocol::Id { - use self::$packett::*; - use crate::protocol::State::*; - use crate::protocol::PacketDirection::*; - - match self { - $($nam(_) => ($id, $state, $direction)),* - }.into() + crate::protocol::HasPacketKind::kind(self).id() } } @@ -306,15 +326,19 @@ macro_rules! define_protocol { } } - impl<'a> crate::protocol::HasPacketId for $rawpackett<'a> { - fn id(&self) -> crate::protocol::Id { - use self::$rawpackett::*; - use crate::protocol::State::*; - use crate::protocol::PacketDirection::*; + impl<'a> crate::protocol::HasPacketKind for $rawpackett<'a> { + type Kind = $kindt; + fn kind(&self) -> Self::Kind { match self { - $($nam(_) => ($id, $state, $direction)),* - }.into() + $($rawpackett::$nam(_) => $kindt::$nam),*, + } + } + } + + impl<'a> crate::protocol::HasPacketId for $rawpackett<'a> { + fn id(&self) -> crate::protocol::Id { + crate::protocol::HasPacketKind::kind(self).id() } fn version() -> crate::types::VarInt { @@ -327,17 +351,10 @@ macro_rules! define_protocol { type Packet = $packett; fn create(id: crate::protocol::Id, data: &'a[u8]) -> Result<Self, crate::protocol::PacketErr> { - use self::$rawpackett::*; - use crate::protocol::State::*; - use crate::protocol::PacketDirection::*; - use crate::protocol::PacketErr::UnknownId; - - match (id.id, id.state, id.direction) { - $(($id, $state, $direction) => Ok($nam($rawdt{ - data, - _typ: core::marker::PhantomData, - }))),*, - other => Err(UnknownId(other.into())) + if let Some(kind) = $kindt::from_id(id) { + Ok(kind.with_body_data(data)) + } else { + Err(crate::protocol::PacketErr::UnknownId(id)) } } @@ -386,6 +403,42 @@ macro_rules! define_protocol { } } + impl crate::protocol::HasPacketId for $kindt { + fn id(&self) -> crate::protocol::Id { + use self::$kindt::*; + use crate::protocol::State::*; + use crate::protocol::PacketDirection::*; + + match self { + $($nam => ($id, $state, $direction)),* + }.into() + } + + fn version() -> crate::types::VarInt { + crate::types::VarInt($version) + } + } + + impl $kindt { + pub fn from_id(id: crate::protocol::Id) -> Option<Self> { + match (id.id, id.state, id.direction) { + $(($id, crate::protocol::State::$state, crate::protocol::PacketDirection::$direction) => Some($kindt::$nam)),*, + _ => None + } + } + + pub fn with_body_data<'a>(self, data: &'a [u8]) -> $rawpackett<'a> { + match self { + $($kindt::$nam => $rawpackett::$nam($rawdt{ + data, + _typ: core::marker::PhantomData, + })),*, + } + } + } + + impl crate::protocol::PacketKind for $kindt {} + $($crate::proto_struct!($body { $($fnam: $ftyp),* });)* }; } diff --git a/src/v1_15_2.rs b/src/v1_15_2.rs index 402d853..fae1cb8 100644 --- a/src/v1_15_2.rs +++ b/src/v1_15_2.rs @@ -6,7 +6,7 @@ use fmt::Debug; #[cfg(all(test, feature = "std"))] use crate::protocol::TestRandom; -define_protocol!(578, Packet578, RawPacket578, RawPacket578Body => { +define_protocol!(578, Packet578, RawPacket578, RawPacket578Body, Packet578Kind => { // handshaking Handshake, 0x00, Handshaking, ServerBound => HandshakeSpec { version: VarInt, diff --git a/src/v1_16_3.rs b/src/v1_16_3.rs index 7c7b4d8..b9743d4 100644 --- a/src/v1_16_3.rs +++ b/src/v1_16_3.rs @@ -6,7 +6,7 @@ use fmt::Debug; #[cfg(all(test, feature = "std"))] use crate::protocol::TestRandom; -define_protocol!(753, Packet753, RawPacket753, RawPacket753Body => { +define_protocol!(753, Packet753, RawPacket753, RawPacket753Body, Packet753Kind => { // handshaking Handshake, 0x00, Handshaking, ServerBound => HandshakeSpec { version: VarInt, |