From 736f073b3cfa7ceb27a39f2f54c1ec84df3ce350 Mon Sep 17 00:00:00 2001 From: Connor <83981186+utfunderscore@users.noreply.github.com> Date: Fri, 22 Aug 2025 07:57:55 +0000 Subject: [PATCH] fix: Remove liftimes from CStatusResponse and CPlayerPosition (#1128) * fix: Remove liftimes from CStatusResponse and CPlayerPosition * fix: Add lifetimes to CachedBranding and fix tests * fix: Remove lifetimes from CLoginDisconnect packet, data is dropped immediately after the packet is constructed * fix: Apply formatting to packet_encoder.rs --------- Co-authored-by: Alexander Medvedev --- .../src/java/client/login/login_disconnect.rs | 8 ++++---- .../src/java/client/play/player_position.rs | 16 ++++++++-------- .../src/java/client/status/status_response.rs | 8 ++++---- pumpkin-protocol/src/java/packet_encoder.rs | 18 +++++++++++------- pumpkin/src/entity/player.rs | 2 +- pumpkin/src/net/java/mod.rs | 2 +- pumpkin/src/net/java/play.rs | 4 ++-- pumpkin/src/server/connection_cache.rs | 10 +++++----- 8 files changed, 36 insertions(+), 32 deletions(-) diff --git a/pumpkin-protocol/src/java/client/login/login_disconnect.rs b/pumpkin-protocol/src/java/client/login/login_disconnect.rs index baed47c6e..cee3b9b8d 100644 --- a/pumpkin-protocol/src/java/client/login/login_disconnect.rs +++ b/pumpkin-protocol/src/java/client/login/login_disconnect.rs @@ -4,13 +4,13 @@ use serde::{Deserialize, Serialize}; #[derive(Serialize, Deserialize)] #[packet(LOGIN_LOGIN_DISCONNECT)] -pub struct CLoginDisconnect<'a> { - pub json_reason: &'a str, +pub struct CLoginDisconnect { + pub json_reason: String, } -impl<'a> CLoginDisconnect<'a> { +impl CLoginDisconnect { // input json! - pub fn new(json_reason: &'a str) -> Self { + pub fn new(json_reason: String) -> Self { Self { json_reason } } } diff --git a/pumpkin-protocol/src/java/client/play/player_position.rs b/pumpkin-protocol/src/java/client/play/player_position.rs index 3051e892e..9d0e5c767 100644 --- a/pumpkin-protocol/src/java/client/play/player_position.rs +++ b/pumpkin-protocol/src/java/client/play/player_position.rs @@ -10,23 +10,23 @@ use crate::{ }; #[packet(PLAY_PLAYER_POSITION)] -pub struct CPlayerPosition<'a> { +pub struct CPlayerPosition { pub teleport_id: VarInt, pub position: Vector3, pub delta: Vector3, pub yaw: f32, pub pitch: f32, - pub releatives: &'a [PositionFlag], + pub releatives: Vec, } -impl<'a> CPlayerPosition<'a> { +impl CPlayerPosition { pub fn new( teleport_id: VarInt, position: Vector3, delta: Vector3, yaw: f32, pitch: f32, - releatives: &'a [PositionFlag], + releatives: Vec, ) -> Self { Self { teleport_id, @@ -40,7 +40,7 @@ impl<'a> CPlayerPosition<'a> { } // TODO: Do we need a custom impl? -impl ClientPacket for CPlayerPosition<'_> { +impl ClientPacket for CPlayerPosition { fn write_packet_data(&self, write: impl Write) -> Result<(), WritingError> { let mut write = write; @@ -54,11 +54,11 @@ impl ClientPacket for CPlayerPosition<'_> { write.write_f32_be(self.yaw)?; write.write_f32_be(self.pitch)?; // not sure about that - write.write_i32_be(PositionFlag::get_bitfield(self.releatives)) + write.write_i32_be(PositionFlag::get_bitfield(self.releatives.as_slice())) } } -impl ServerPacket for CPlayerPosition<'_> { +impl ServerPacket for CPlayerPosition { fn read(mut read: impl std::io::Read) -> Result { Ok(Self { teleport_id: read.get_var_int()?, @@ -67,7 +67,7 @@ impl ServerPacket for CPlayerPosition<'_> { delta: Vector3::new(0.0, 0.0, 0.0), yaw: 0.0, pitch: 0.0, - releatives: &[], + releatives: Vec::new(), }) } } diff --git a/pumpkin-protocol/src/java/client/status/status_response.rs b/pumpkin-protocol/src/java/client/status/status_response.rs index 6f72c6f1d..3ebdd2fd0 100644 --- a/pumpkin-protocol/src/java/client/status/status_response.rs +++ b/pumpkin-protocol/src/java/client/status/status_response.rs @@ -4,11 +4,11 @@ use serde::{Deserialize, Serialize}; #[derive(Serialize, Deserialize)] #[packet(STATUS_STATUS_RESPONSE)] -pub struct CStatusResponse<'a> { - pub json_response: &'a str, // 32767 +pub struct CStatusResponse { + pub json_response: String, // 32767 } -impl<'a> CStatusResponse<'a> { - pub fn new(json_response: &'a str) -> Self { +impl CStatusResponse { + pub fn new(json_response: String) -> Self { Self { json_response } } } diff --git a/pumpkin-protocol/src/java/packet_encoder.rs b/pumpkin-protocol/src/java/packet_encoder.rs index 3c87ae136..3044bed35 100644 --- a/pumpkin-protocol/src/java/packet_encoder.rs +++ b/pumpkin-protocol/src/java/packet_encoder.rs @@ -350,7 +350,8 @@ mod tests { #[tokio::test] async fn test_encode_without_compression_and_encryption() { // Create a CStatusResponse packet - let packet = CStatusResponse::new("{\"description\": \"A Minecraft Server\"}"); + let packet = + CStatusResponse::new(String::from("{\"description\": \"A Minecraft Server\"}")); // Build the packet without compression and encryption let packet_bytes = build_packet_with_encoder(&packet, None, None).await; @@ -382,7 +383,8 @@ mod tests { #[tokio::test] async fn test_encode_with_compression() { // Create a CStatusResponse packet - let packet = CStatusResponse::new("{\"description\": \"A Minecraft Server\"}"); + let packet = + CStatusResponse::new("{\"description\": \"A Minecraft Server\"}".parse().unwrap()); // Build the packet with compression enabled let packet_bytes = build_packet_with_encoder(&packet, Some((0, 6)), None).await; @@ -429,7 +431,8 @@ mod tests { #[tokio::test] async fn test_encode_with_encryption() { // Create a CStatusResponse packet - let packet = CStatusResponse::new("{\"description\": \"A Minecraft Server\"}"); + let packet = + CStatusResponse::new("{\"description\": \"A Minecraft Server\"}".parse().unwrap()); // Encryption key and IV (IV is the same as key in this case) let key = [0x00u8; 16]; // Example key @@ -465,7 +468,8 @@ mod tests { #[tokio::test] async fn test_encode_with_compression_and_encryption() { // Create a CStatusResponse packet - let packet = CStatusResponse::new("{\"description\": \"A Minecraft Server\"}"); + let packet = + CStatusResponse::new("{\"description\": \"A Minecraft Server\"}".parse().unwrap()); // Encryption key and IV (IV is the same as key in this case) let key = [0x01u8; 16]; // Example key @@ -519,7 +523,7 @@ mod tests { #[tokio::test] async fn test_encode_with_zero_length_payload() { // Create a CStatusResponse packet with empty payload - let packet = CStatusResponse::new(""); + let packet = CStatusResponse::new(String::from("")); // Build the packet without compression and encryption let packet_bytes = build_packet_with_encoder(&packet, None, None).await; @@ -557,7 +561,7 @@ mod tests { // Maximum allowed string length is 32767 bytes let max_string_length = 32767; let payload_str = "A".repeat(max_string_length); - let packet = CStatusResponse::new(&payload_str); + let packet = CStatusResponse::new(payload_str); // Build the packet without compression and encryption let packet_bytes = build_packet_with_encoder(&packet, None, None).await; @@ -608,7 +612,7 @@ mod tests { #[tokio::test] async fn test_encode_small_payload_no_compression() { // Create a CStatusResponse packet with small payload - let packet = CStatusResponse::new("Hi"); + let packet = CStatusResponse::new(String::from("Hi")); // Build the packet with compression enabled // Compression threshold is set to a value higher than payload length diff --git a/pumpkin/src/entity/player.rs b/pumpkin/src/entity/player.rs index 2925b83dc..876478ab8 100644 --- a/pumpkin/src/entity/player.rs +++ b/pumpkin/src/entity/player.rs @@ -1177,7 +1177,7 @@ impl Player { yaw, pitch, // TODO - &[], + Vec::new(), )).await; } }} diff --git a/pumpkin/src/net/java/mod.rs b/pumpkin/src/net/java/mod.rs index c4e570ccd..616bfe61d 100644 --- a/pumpkin/src/net/java/mod.rs +++ b/pumpkin/src/net/java/mod.rs @@ -255,7 +255,7 @@ impl JavaClient { ConnectionState::Login => { // TextComponent implements Serialize and writes in bytes instead of String, that's the reasib we only use content self.send_packet_now(&CLoginDisconnect::new( - &serde_json::to_string(&reason.0).unwrap_or_else(|_| String::new()), + serde_json::to_string(&reason.0).unwrap_or_else(|_| String::new()), )) .await; } diff --git a/pumpkin/src/net/java/play.rs b/pumpkin/src/net/java/play.rs index 7fdde2c34..984417a25 100644 --- a/pumpkin/src/net/java/play.rs +++ b/pumpkin/src/net/java/play.rs @@ -350,7 +350,7 @@ impl JavaClient { Vector3::new(0.0, 0.0, 0.0), player.living_entity.entity.yaw.load(), player.living_entity.entity.pitch.load(), - &[], + Vec::new(), )).await; } }} @@ -483,7 +483,7 @@ impl JavaClient { Vector3::new(0.0, 0.0, 0.0), player.living_entity.entity.yaw.load(), player.living_entity.entity.pitch.load(), - &[], + Vec::new(), )) .await; } diff --git a/pumpkin/src/server/connection_cache.rs b/pumpkin/src/server/connection_cache.rs index cb9f97d1a..d75d6a62a 100644 --- a/pumpkin/src/server/connection_cache.rs +++ b/pumpkin/src/server/connection_cache.rs @@ -39,7 +39,7 @@ pub struct CachedBranding { cached_server_brand: Box<[u8]>, } -impl CachedBranding { +impl<'a> CachedBranding { pub fn new() -> Self { let cached_server_brand = Self::build_brand(); Self { @@ -49,8 +49,8 @@ impl CachedBranding { pub fn get_branding(&self) -> CPluginMessage<'_> { CPluginMessage::new("minecraft:brand", &self.cached_server_brand) } - const BRAND: &str = "Pumpkin"; - const BRAND_BYTES: &[u8] = Self::BRAND.as_bytes(); + const BRAND: &'a str = "Pumpkin"; + const BRAND_BYTES: &'a [u8] = Self::BRAND.as_bytes(); fn build_brand() -> Box<[u8]> { let mut buf = Vec::new(); @@ -73,8 +73,8 @@ impl CachedStatus { } } - pub fn get_status(&self) -> CStatusResponse<'_> { - CStatusResponse::new(&self.status_response_json) + pub fn get_status(&self) -> CStatusResponse { + CStatusResponse::new(self.status_response_json.clone()) } // TODO: Player samples