diff --git a/examples/combat.rs b/examples/combat.rs index 6b80b57..93080fd 100644 --- a/examples/combat.rs +++ b/examples/combat.rs @@ -71,6 +71,7 @@ impl Config for Game { &self, _server: &SharedServer, _remote_addr: SocketAddr, + _protocol_version: i32, ) -> ServerListPing { ServerListPing::Respond { online_players: self.player_count.load(Ordering::SeqCst) as i32, diff --git a/examples/conway.rs b/examples/conway.rs index e3ee86a..eed5ade 100644 --- a/examples/conway.rs +++ b/examples/conway.rs @@ -84,6 +84,7 @@ impl Config for Game { &self, _server: &SharedServer, _remote_addr: SocketAddr, + _protocol_version: i32, ) -> ServerListPing { ServerListPing::Respond { online_players: self.player_count.load(Ordering::SeqCst) as i32, diff --git a/examples/cow_sphere.rs b/examples/cow_sphere.rs index 47cf3ea..5304e09 100644 --- a/examples/cow_sphere.rs +++ b/examples/cow_sphere.rs @@ -64,6 +64,7 @@ impl Config for Game { &self, _server: &SharedServer, _remote_addr: SocketAddr, + _protocol_version: i32, ) -> ServerListPing { ServerListPing::Respond { online_players: self.player_count.load(Ordering::SeqCst) as i32, diff --git a/examples/raycast.rs b/examples/raycast.rs index c7dd6bb..6510e52 100644 --- a/examples/raycast.rs +++ b/examples/raycast.rs @@ -59,6 +59,7 @@ impl Config for Game { &self, _server: &SharedServer, _remote_addr: SocketAddr, + _protocol_version: i32, ) -> ServerListPing { ServerListPing::Respond { online_players: self.player_count.load(Ordering::SeqCst) as i32, diff --git a/examples/terrain.rs b/examples/terrain.rs index dd222da..7c9eda5 100644 --- a/examples/terrain.rs +++ b/examples/terrain.rs @@ -69,6 +69,7 @@ impl Config for Game { &self, _server: &SharedServer, _remote_addr: SocketAddr, + _protocol_version: i32, ) -> ServerListPing { ServerListPing::Respond { online_players: self.player_count.load(Ordering::SeqCst) as i32, diff --git a/src/config.rs b/src/config.rs index 2e2bfa8..6e55602 100644 --- a/src/config.rs +++ b/src/config.rs @@ -177,6 +177,7 @@ pub trait Config: 'static + Sized + Send + Sync + UnwindSafe + RefUnwindSafe { &self, shared: &SharedServer, remote_addr: SocketAddr, + protocol_version: i32, ) -> ServerListPing { ServerListPing::Ignore } diff --git a/src/protocol_inner/packets.rs b/src/protocol_inner/packets.rs index 4bc90d9..7dc632a 100644 --- a/src/protocol_inner/packets.rs +++ b/src/protocol_inner/packets.rs @@ -391,10 +391,16 @@ pub(crate) mod test { use super::*; def_struct! { - TestPacket 0xfff { + TestPacket { first: String, second: Vec, third: u64 } } + + def_packet_group! { + TestPacketGroup { + TestPacket = 12345, + } + } } diff --git a/src/server.rs b/src/server.rs index 0273285..1a9ffb8 100644 --- a/src/server.rs +++ b/src/server.rs @@ -547,11 +547,13 @@ async fn handle_connection( // TODO: peek stream for 0xFE legacy ping - match c.dec.read_packet::().await?.next_state { - HandshakeNextState::Status => handle_status(server, &mut c, remote_addr) + let handshake = c.dec.read_packet::().await?; + + match handshake.next_state { + HandshakeNextState::Status => handle_status(server, &mut c, remote_addr, handshake) .await .context("error during status"), - HandshakeNextState::Login => match handle_login(&server, &mut c, remote_addr) + HandshakeNextState::Login => match handle_login(&server, &mut c, remote_addr, handshake) .await .context("error during login")? { @@ -567,10 +569,16 @@ async fn handle_status( server: SharedServer, c: &mut Codec, remote_addr: SocketAddr, + handshake: Handshake, ) -> anyhow::Result<()> { c.dec.read_packet::().await?; - match server.0.cfg.server_list_ping(&server, remote_addr).await { + match server + .0 + .cfg + .server_list_ping(&server, remote_addr, handshake.protocol_version.0) + .await + { ServerListPing::Respond { online_players, max_players, @@ -619,7 +627,13 @@ async fn handle_login( server: &SharedServer, c: &mut Codec, remote_addr: SocketAddr, + handshake: Handshake, ) -> anyhow::Result> { + if handshake.protocol_version.0 != PROTOCOL_VERSION { + // TODO: send translated disconnect msg? + return Ok(None); + } + let LoginStart { username: BoundedString(username), sig_data: _, // TODO