From f970c4bc129e7d4f783495b2d0ae27cda5dfc161 Mon Sep 17 00:00:00 2001 From: Snowiiii Date: Mon, 14 Oct 2024 12:01:35 +0200 Subject: [PATCH] Minior Code cleanups --- .github/workflows/rust.yml | 1 + docs/developer/networking.md | 3 + fuzz/Cargo.toml | 21 +++ fuzz/fuzz_targets/client.rs | 7 + .../src/cylindrical_chunk_iterator.rs | 18 ++- pumpkin/src/client/authentication.rs | 19 ++- pumpkin/src/client/client_packet.rs | 125 +++++++++--------- pumpkin/src/client/container.rs | 2 +- pumpkin/src/client/mod.rs | 25 ++-- pumpkin/src/client/player_packet.rs | 54 +++----- pumpkin/src/commands/arg_player.rs | 4 +- pumpkin/src/commands/dispatcher.rs | 7 +- pumpkin/src/commands/mod.rs | 6 +- pumpkin/src/entity/player.rs | 35 +++-- pumpkin/src/main.rs | 8 +- pumpkin/src/rcon/mod.rs | 9 +- pumpkin/src/server/connection_cache.rs | 2 +- pumpkin/src/server/key_store.rs | 4 +- pumpkin/src/util/mod.rs | 1 - 19 files changed, 169 insertions(+), 182 deletions(-) create mode 100644 fuzz/Cargo.toml create mode 100644 fuzz/fuzz_targets/client.rs delete mode 100644 pumpkin/src/util/mod.rs diff --git a/.github/workflows/rust.yml b/.github/workflows/rust.yml index 25f8444ee..2b69bb11f 100644 --- a/.github/workflows/rust.yml +++ b/.github/workflows/rust.yml @@ -70,6 +70,7 @@ jobs: uses: actions/upload-artifact@v4 with: name: pumpkin-${{ matrix.os }} + compression-level: 9 path: target/${{ matrix.target }}/release/pumpkin* clippy_release: name: Run lints in release mode diff --git a/docs/developer/networking.md b/docs/developer/networking.md index 824c5045d..334363d9f 100644 --- a/docs/developer/networking.md +++ b/docs/developer/networking.md @@ -266,6 +266,9 @@ For Players: } ``` +### Compression +Minecraft Packets **can** use the ZLib compression for decoding/encoding there is usally a threshold set when compression is applied, This most often affects Chunk Packets. + ### Porting To port to a new Minecraft version, You can compare difference in Protocol on wiki.vg https://wiki.vg/index.php?title=Protocol&action=history diff --git a/fuzz/Cargo.toml b/fuzz/Cargo.toml new file mode 100644 index 000000000..5379b3616 --- /dev/null +++ b/fuzz/Cargo.toml @@ -0,0 +1,21 @@ +[package] +name = "pumpkin-fuzz" +version = "0.0.0" +publish = false +edition = "2021" + +[package.metadata] +cargo-fuzz = true + +[dependencies] +pumpkin = { path = "../"} + +libfuzzer-sys = "0.4" + + +[[bin]] +name = "fuzz_target_1" +path = "fuzz_targets/fuzz_target_1.rs" +test = false +doc = false +bench = false diff --git a/fuzz/fuzz_targets/client.rs b/fuzz/fuzz_targets/client.rs new file mode 100644 index 000000000..43a88c14f --- /dev/null +++ b/fuzz/fuzz_targets/client.rs @@ -0,0 +1,7 @@ +#![no_main] + +use libfuzzer_sys::fuzz_target; + +fuzz_target!(|data: &[u8]| { + // fuzzed code goes here +}); diff --git a/pumpkin-world/src/cylindrical_chunk_iterator.rs b/pumpkin-world/src/cylindrical_chunk_iterator.rs index 24c49c9da..bb7ca9bf3 100644 --- a/pumpkin-world/src/cylindrical_chunk_iterator.rs +++ b/pumpkin-world/src/cylindrical_chunk_iterator.rs @@ -22,12 +22,10 @@ impl Cylindrical { just_removed: impl FnMut(Vector2), ignore: bool, ) { - let min_x = old_cylindrical.get_left().min(new_cylindrical.get_left()); - let max_x = old_cylindrical.get_right().max(new_cylindrical.get_right()); - let min_z = old_cylindrical - .get_bottom() - .min(new_cylindrical.get_bottom()); - let max_z = old_cylindrical.get_top().max(new_cylindrical.get_top()); + let min_x = old_cylindrical.left().min(new_cylindrical.left()); + let max_x = old_cylindrical.right().max(new_cylindrical.right()); + let min_z = old_cylindrical.bottom().min(new_cylindrical.bottom()); + let max_z = old_cylindrical.top().max(new_cylindrical.top()); for x in min_x..=max_x { for z in min_z..=max_z { @@ -55,19 +53,19 @@ impl Cylindrical { } } - fn get_left(&self) -> i32 { + fn left(&self) -> i32 { self.center.x - self.view_distance - 1 } - fn get_bottom(&self) -> i32 { + fn bottom(&self) -> i32 { self.center.z - self.view_distance - 1 } - fn get_right(&self) -> i32 { + fn right(&self) -> i32 { self.center.x + self.view_distance + 1 } - fn get_top(&self) -> i32 { + fn top(&self) -> i32 { self.center.z + self.view_distance + 1 } diff --git a/pumpkin/src/client/authentication.rs b/pumpkin/src/client/authentication.rs index ade959cc3..d6aaa5963 100644 --- a/pumpkin/src/client/authentication.rs +++ b/pumpkin/src/client/authentication.rs @@ -1,4 +1,4 @@ -use std::{collections::HashMap, net::IpAddr, sync::Arc}; +use std::{collections::HashMap, net::IpAddr}; use base64::{engine::general_purpose, Engine}; use pumpkin_config::{auth::TextureConfig, ADVANCED_CONFIG}; @@ -9,8 +9,6 @@ use serde::Deserialize; use thiserror::Error; use uuid::Uuid; -use crate::server::Server; - #[derive(Deserialize, Clone, Debug)] #[expect(dead_code)] #[serde(rename_all = "camelCase")] @@ -55,10 +53,9 @@ pub async fn authenticate( username: &str, server_hash: &str, ip: &IpAddr, - server: &Arc, + auth_client: &reqwest::Client, ) -> Result { assert!(ADVANCED_CONFIG.authentication.enabled); - assert!(server.auth_client.is_some()); let address = if ADVANCED_CONFIG.authentication.prevent_proxy_connections { ADVANCED_CONFIG .authentication @@ -73,10 +70,6 @@ pub async fn authenticate( .replace("{username}", username) .replace("{server_hash}", server_hash) }; - let auth_client = server - .auth_client - .as_ref() - .ok_or(AuthError::MissingAuthClient)?; let response = auth_client .get(address) @@ -92,7 +85,7 @@ pub async fn authenticate( Ok(profile) } -pub fn unpack_textures(property: &Property, config: &TextureConfig) -> Result<(), TextureError> { +pub fn validate_textures(property: &Property, config: &TextureConfig) -> Result<(), TextureError> { let from64 = general_purpose::STANDARD .decode(&property.value) .map_err(|e| TextureError::DecodeError(e.to_string()))?; @@ -134,6 +127,12 @@ pub enum AuthError { FailedResponse, #[error("Failed to verify username")] UnverifiedUsername, + #[error("You are banned from Authentication servers")] + Banned, + #[error("Texture Error {0}")] + TextureError(TextureError), + #[error("You have disallowed actions from Authentication servers")] + DisallowedAction, #[error("Failed to parse JSON into Game Profile")] FailedParse, #[error("Unknown Status Code")] diff --git a/pumpkin/src/client/client_packet.rs b/pumpkin/src/client/client_packet.rs index bcdb541dd..d185438e6 100644 --- a/pumpkin/src/client/client_packet.rs +++ b/pumpkin/src/client/client_packet.rs @@ -1,5 +1,3 @@ -use std::sync::Arc; - use num_traits::FromPrimitive; use pumpkin_config::{ADVANCED_CONFIG, BASIC_CONFIG}; use pumpkin_core::text::TextComponent; @@ -20,20 +18,20 @@ use pumpkin_protocol::{ use uuid::Uuid; use crate::{ - client::authentication::{self, GameProfile}, + client::authentication::{self, validate_textures, GameProfile}, entity::player::{ChatMode, Hand}, proxy::velocity::velocity_login, server::{Server, CURRENT_MC_VERSION}, }; -use super::{authentication::unpack_textures, Client, PlayerConfig}; +use super::{authentication::AuthError, Client, PlayerConfig}; /// Processes incoming Packets from the Client to the Server /// Implements the `Client` Packets /// NEVER TRUST THE CLIENT. HANDLE EVERY ERROR, UNWRAP/EXPECT /// TODO: REMOVE ALL UNWRAPS impl Client { - pub fn handle_handshake(&self, _server: &Arc, handshake: SHandShake) { + pub fn handle_handshake(&self, handshake: SHandShake) { dbg!("handshake"); let version = handshake.protocol_version.0; self.protocol_version @@ -54,11 +52,11 @@ impl Client { } } - pub fn handle_status_request(&self, server: &Arc, _status_request: SStatusRequest) { + pub fn handle_status_request(&self, server: &Server, _status_request: SStatusRequest) { self.send_packet(&server.get_status()); } - pub fn handle_ping_request(&self, _server: &Arc, ping_request: SStatusPingRequest) { + pub fn handle_ping_request(&self, ping_request: SStatusPingRequest) { dbg!("ping"); self.send_packet(&CPingResponse::new(ping_request.payload)); self.close(); @@ -71,7 +69,7 @@ impl Client { .all(|c| c > 32_u8 as char && c < 127_u8 as char) } - pub fn handle_login_start(&self, server: &Arc, login_start: SLoginStart) { + pub fn handle_login_start(&self, server: &Server, login_start: SLoginStart) { log::debug!("login start, State {:?}", self.connection_state); if !Self::is_valid_player_name(&login_start.name) { @@ -102,7 +100,7 @@ impl Client { pub async fn handle_encryption_response( &self, - server: &Arc, + server: &Server, encryption_response: SEncryptionResponse, ) { let shared_secret = server.decrypt(&encryption_response.shared_secret).unwrap(); @@ -113,49 +111,16 @@ impl Client { let mut gameprofile = self.gameprofile.lock(); if BASIC_CONFIG.online_mode { - let hash = server.digest_secret(&shared_secret); - let ip = self.address.lock().ip(); - - match authentication::authenticate( - &gameprofile.as_ref().unwrap().name, - &hash, - &ip, - server, - ) - .await + match self + .autenticate(server, &shared_secret, &gameprofile.as_ref().unwrap().name) + .await { - Ok(profile) => { - // Check if player should join - if let Some(actions) = &profile.profile_actions { - if !ADVANCED_CONFIG - .authentication - .player_profile - .allow_banned_players - { - if !actions.is_empty() { - self.kick("Your account can't join"); - } - } else { - for allowed in &ADVANCED_CONFIG - .authentication - .player_profile - .allowed_actions - { - if !actions.contains(allowed) { - self.kick("Your account can't join"); - } - } - } - } - *gameprofile = Some(profile); + Ok(profile) => *gameprofile = Some(profile), + Err(e) => { + self.kick(&e.to_string()); } - Err(e) => self.kick(&e.to_string()), } } - for property in &gameprofile.as_ref().unwrap().properties { - unpack_textures(property, &ADVANCED_CONFIG.authentication.textures) - .unwrap_or_else(|e| self.kick(&e.to_string())); - } // enable compression if ADVANCED_CONFIG.packet_compression.enabled { @@ -172,16 +137,54 @@ impl Client { } } - pub fn handle_plugin_response( + async fn autenticate( &self, - _server: &Arc, - _plugin_response: SLoginPluginResponse, - ) { + server: &Server, + shared_secret: &[u8], + username: &str, + ) -> Result { + if let Some(auth_client) = &server.auth_client { + let hash = server.digest_secret(shared_secret); + let ip = self.address.lock().ip(); + + let profile = authentication::authenticate(username, &hash, &ip, auth_client).await?; + // Check if player should join + if let Some(actions) = &profile.profile_actions { + if !ADVANCED_CONFIG + .authentication + .player_profile + .allow_banned_players + { + if !actions.is_empty() { + self.kick("Your account can't join"); + } + } else { + for allowed in &ADVANCED_CONFIG + .authentication + .player_profile + .allowed_actions + { + if !actions.contains(allowed) { + self.kick("Your account can't join"); + } + } + } + } + // validate textures + for property in &profile.properties { + validate_textures(property, &ADVANCED_CONFIG.authentication.textures) + .map_err(AuthError::TextureError)?; + } + return Ok(profile); + } + Err(AuthError::MissingAuthClient) } + pub fn handle_plugin_response(&self, _plugin_response: SLoginPluginResponse) {} + pub fn handle_login_acknowledged( &self, - server: &Arc, + server: &Server, _login_acknowledged: SLoginAcknowledged, ) { self.connection_state.store(ConnectionState::Config); @@ -215,11 +218,7 @@ impl Client { }])); dbg!("login acknowledged"); } - pub fn handle_client_information_config( - &self, - _server: &Arc, - client_information: SClientInformationConfig, - ) { + pub fn handle_client_information_config(&self, client_information: SClientInformationConfig) { dbg!("got client settings"); if let (Some(main_hand), Some(chat_mode)) = ( Hand::from_i32(client_information.main_hand.into()), @@ -240,7 +239,7 @@ impl Client { } } - pub fn handle_plugin_message(&self, _server: &Arc, plugin_message: SPluginMessage) { + pub fn handle_plugin_message(&self, plugin_message: SPluginMessage) { if plugin_message.channel.starts_with("minecraft:brand") || plugin_message.channel.starts_with("MC|Brand") { @@ -252,7 +251,7 @@ impl Client { } } - pub fn handle_known_packs(&self, server: &Arc, _config_acknowledged: SKnownPacks) { + pub fn handle_known_packs(&self, server: &Server, _config_acknowledged: SKnownPacks) { for registry in &server.cached_registry { self.send_packet(&CRegistryData::new( ®istry.registry_id, @@ -265,11 +264,7 @@ impl Client { self.send_packet(&CFinishConfig::new()); } - pub async fn handle_config_acknowledged( - &self, - _server: &Arc, - _config_acknowledged: SAcknowledgeFinishConfig, - ) { + pub async fn handle_config_acknowledged(&self, _config_acknowledged: SAcknowledgeFinishConfig) { dbg!("config acknowledged"); self.connection_state.store(ConnectionState::Play); self.make_player diff --git a/pumpkin/src/client/container.rs b/pumpkin/src/client/container.rs index bd1cf5db0..0768aa0b0 100644 --- a/pumpkin/src/client/container.rs +++ b/pumpkin/src/client/container.rs @@ -20,7 +20,7 @@ use pumpkin_world::item::ItemStack; use std::sync::Arc; impl Player { - pub fn open_container(&self, server: &Arc, minecraft_menu_id: &str) { + pub fn open_container(&self, server: &Server, minecraft_menu_id: &str) { let inventory = self.inventory.lock(); inventory .state_id diff --git a/pumpkin/src/client/mod.rs b/pumpkin/src/client/mod.rs index 500030174..d29899d28 100644 --- a/pumpkin/src/client/mod.rs +++ b/pumpkin/src/client/mod.rs @@ -222,9 +222,7 @@ impl Client { packet: &mut RawPacket, ) -> Result<(), DeserializerError> { match self.connection_state.load() { - pumpkin_protocol::ConnectionState::HandShake => { - self.handle_handshake_packet(server, packet) - } + pumpkin_protocol::ConnectionState::HandShake => self.handle_handshake_packet(packet), pumpkin_protocol::ConnectionState::Status => self.handle_status_packet(server, packet), // TODO: Check config if transfer is enabled pumpkin_protocol::ConnectionState::Login @@ -241,15 +239,11 @@ impl Client { } } - fn handle_handshake_packet( - &self, - server: &Arc, - packet: &mut RawPacket, - ) -> Result<(), DeserializerError> { + fn handle_handshake_packet(&self, packet: &mut RawPacket) -> Result<(), DeserializerError> { let bytebuf = &mut packet.bytebuf; match packet.id.0 { SHandShake::PACKET_ID => { - self.handle_handshake(server, SHandShake::read(bytebuf)?); + self.handle_handshake(SHandShake::read(bytebuf)?); Ok(()) } _ => { @@ -274,7 +268,7 @@ impl Client { Ok(()) } SStatusPingRequest::PACKET_ID => { - self.handle_ping_request(server, SStatusPingRequest::read(bytebuf)?); + self.handle_ping_request(SStatusPingRequest::read(bytebuf)?); Ok(()) } _ => { @@ -304,7 +298,7 @@ impl Client { Ok(()) } SLoginPluginResponse::PACKET_ID => { - self.handle_plugin_response(server, SLoginPluginResponse::read(bytebuf)?); + self.handle_plugin_response(SLoginPluginResponse::read(bytebuf)?); Ok(()) } SLoginAcknowledged::PACKET_ID => { @@ -329,18 +323,15 @@ impl Client { let bytebuf = &mut packet.bytebuf; match packet.id.0 { SClientInformationConfig::PACKET_ID => { - self.handle_client_information_config( - server, - SClientInformationConfig::read(bytebuf)?, - ); + self.handle_client_information_config(SClientInformationConfig::read(bytebuf)?); Ok(()) } SPluginMessage::PACKET_ID => { - self.handle_plugin_message(server, SPluginMessage::read(bytebuf)?); + self.handle_plugin_message(SPluginMessage::read(bytebuf)?); Ok(()) } SAcknowledgeFinishConfig::PACKET_ID => { - self.handle_config_acknowledged(server, SAcknowledgeFinishConfig::read(bytebuf)?) + self.handle_config_acknowledged(SAcknowledgeFinishConfig::read(bytebuf)?) .await; Ok(()) } diff --git a/pumpkin/src/client/player_packet.rs b/pumpkin/src/client/player_packet.rs index fd8a31a1a..b6ef5e5bf 100644 --- a/pumpkin/src/client/player_packet.rs +++ b/pumpkin/src/client/player_packet.rs @@ -1,4 +1,4 @@ -use std::{f32::consts::PI, sync::Arc}; +use std::f32::consts::PI; use crate::{ commands::CommandSender, @@ -41,11 +41,7 @@ fn modulus(a: f32, b: f32) -> f32 { /// Handles all Play Packets send by a real Player /// NEVER TRUST THE CLIENT. HANDLE EVERY ERROR, UNWRAP/EXPECT ARE FORBIDDEN impl Player { - pub fn handle_confirm_teleport( - &self, - _server: &Arc, - confirm_teleport: SConfirmTeleport, - ) { + pub fn handle_confirm_teleport(&self, confirm_teleport: SConfirmTeleport) { let mut awaiting_teleport = self.awaiting_teleport.lock(); if let Some((id, position)) = awaiting_teleport.as_ref() { if id == &confirm_teleport.teleport_id { @@ -73,7 +69,7 @@ impl Player { pos.clamp(-2.0E7, 2.0E7) } - pub async fn handle_position(&self, _server: &Arc, position: SPlayerPosition) { + pub async fn handle_position(&self, position: SPlayerPosition) { if position.x.is_nan() || position.feet_y.is_nan() || position.z.is_nan() { self.kick(TextComponent::text("Invalid movement")); return; @@ -121,11 +117,7 @@ impl Player { player_chunker::update_position(entity, self).await; } - pub async fn handle_position_rotation( - &self, - _server: &Arc, - position_rotation: SPlayerPositionRotation, - ) { + pub async fn handle_position_rotation(&self, position_rotation: SPlayerPositionRotation) { if position_rotation.x.is_nan() || position_rotation.feet_y.is_nan() || position_rotation.z.is_nan() @@ -197,7 +189,7 @@ impl Player { player_chunker::update_position(entity, self).await; } - pub async fn handle_rotation(&self, _server: &Arc, rotation: SPlayerRotation) { + pub async fn handle_rotation(&self, rotation: SPlayerRotation) { if !rotation.yaw.is_finite() || !rotation.pitch.is_finite() { self.kick(TextComponent::text("Invalid rotation")); return; @@ -224,7 +216,7 @@ impl Player { world.broadcast_packet_expect(&[self.client.token], &packet); } - pub fn handle_chat_command(&self, server: &Arc, command: SChatCommand) { + pub fn handle_chat_command(&self, server: &Server, command: SChatCommand) { let dispatcher = server.command_dispatcher.clone(); dispatcher.handle_command(&mut CommandSender::Player(self), server, &command.command); if ADVANCED_CONFIG.commands.log_console { @@ -236,14 +228,14 @@ impl Player { } } - pub fn handle_player_ground(&self, _server: &Arc, ground: SSetPlayerGround) { + pub fn handle_player_ground(&self, ground: SSetPlayerGround) { self.living_entity .entity .on_ground .store(ground.on_ground, std::sync::atomic::Ordering::Relaxed); } - pub async fn handle_player_command(&self, _server: &Arc, command: SPlayerCommand) { + pub async fn handle_player_command(&self, command: SPlayerCommand) { if command.entity_id != self.entity_id().into() { return; } @@ -291,7 +283,7 @@ impl Player { } } - pub async fn handle_swing_arm(&self, _server: &Arc, swing_arm: SSwingArm) { + pub async fn handle_swing_arm(&self, swing_arm: SSwingArm) { match Hand::from_i32(swing_arm.hand.0) { Some(hand) => { let animation = match hand { @@ -311,7 +303,7 @@ impl Player { }; } - pub async fn handle_chat_message(&self, _server: &Arc, chat_message: SChatMessage) { + pub async fn handle_chat_message(&self, chat_message: SChatMessage) { dbg!("got message"); let message = chat_message.message; @@ -351,11 +343,7 @@ impl Player { ) */ } - pub fn handle_client_information_play( - &self, - _server: &Arc, - client_information: SClientInformationPlay, - ) { + pub fn handle_client_information_play(&self, client_information: SClientInformationPlay) { if let (Some(main_hand), Some(chat_mode)) = ( Hand::from_i32(client_information.main_hand.into()), ChatMode::from_i32(client_information.chat_mode.into()), @@ -375,7 +363,7 @@ impl Player { } } - pub async fn handle_interact(&self, _: &Arc, interact: SInteract) { + pub async fn handle_interact(&self, _: &Server, interact: SInteract) { let sneaking = interact.sneaking; let entity = &self.living_entity.entity; if entity.sneaking.load(std::sync::atomic::Ordering::Relaxed) != sneaking { @@ -443,7 +431,7 @@ impl Player { None => self.kick(TextComponent::text("Invalid action type")), } } - pub async fn handle_player_action(&self, _server: &Arc, player_action: SPlayerAction) { + pub async fn handle_player_action(&self, player_action: SPlayerAction) { match Status::from_i32(player_action.status.0) { Some(status) => match status { Status::StartedDigging => { @@ -507,12 +495,12 @@ impl Player { } } - pub fn handle_play_ping_request(&self, _server: &Arc, request: SPlayPingRequest) { + pub fn handle_play_ping_request(&self, request: SPlayPingRequest) { self.client .send_packet(&CPingResponse::new(request.payload)); } - pub async fn handle_use_item_on(&self, _server: &Arc, use_item_on: SUseItemOn) { + pub async fn handle_use_item_on(&self, use_item_on: SUseItemOn) { let location = use_item_on.location; if !self.can_interact_with_block_at(&location, 1.0) { @@ -547,12 +535,12 @@ impl Player { } } - pub fn handle_use_item(&self, _server: &Arc, _use_item: SUseItem) { + pub fn handle_use_item(&self, _use_item: SUseItem) { // TODO: handle packet correctly log::error!("An item was used(SUseItem), but the packet is not implemented yet"); } - pub fn handle_set_held_item(&self, _server: &Arc, held: SSetHeldItem) { + pub fn handle_set_held_item(&self, held: SSetHeldItem) { let slot = held.slot; if !(0..=8).contains(&slot) { self.kick(TextComponent::text("Invalid held slot")) @@ -560,11 +548,7 @@ impl Player { self.inventory.lock().set_selected(slot as usize); } - pub fn handle_set_creative_slot( - &self, - _server: &Arc, - packet: SSetCreativeSlot, - ) -> Result<(), InventoryError> { + pub fn handle_set_creative_slot(&self, packet: SSetCreativeSlot) -> Result<(), InventoryError> { if self.gamemode.load() != GameMode::Creative { return Err(InventoryError::PermissionError); } @@ -576,7 +560,7 @@ impl Player { // TODO: // This function will in the future be used to keep track of if the client is in a valid state. // But this is not possible yet - pub fn handle_close_container(&self, server: &Arc, packet: SCloseContainer) { + pub fn handle_close_container(&self, server: &Server, packet: SCloseContainer) { // window_id 0 represents both 9x1 Generic AND inventory here self.inventory .lock() diff --git a/pumpkin/src/commands/arg_player.rs b/pumpkin/src/commands/arg_player.rs index 11e1fe3b6..24c91a7c4 100644 --- a/pumpkin/src/commands/arg_player.rs +++ b/pumpkin/src/commands/arg_player.rs @@ -1,5 +1,3 @@ -use std::sync::Arc; - use crate::commands::dispatcher::InvalidTreeError; use crate::commands::dispatcher::InvalidTreeError::InvalidConsumptionError; use crate::commands::tree::{ConsumedArgs, RawArgs}; @@ -32,7 +30,7 @@ pub fn consume_arg_player(src: &CommandSender, args: &mut RawArgs) -> Option( src: &'a mut CommandSender, - _server: &Arc, + _server: &Server, arg_name: &str, consumed_args: &ConsumedArgs, ) -> Result<&'a crate::entity::player::Player, InvalidTreeError> { diff --git a/pumpkin/src/commands/dispatcher.rs b/pumpkin/src/commands/dispatcher.rs index e22f709df..a636e8144 100644 --- a/pumpkin/src/commands/dispatcher.rs +++ b/pumpkin/src/commands/dispatcher.rs @@ -7,7 +7,6 @@ use crate::commands::tree::{Command, CommandTree, ConsumedArgs, NodeType, RawArg use crate::commands::CommandSender; use crate::server::Server; use std::collections::HashMap; -use std::sync::Arc; #[derive(Debug)] pub(crate) enum InvalidTreeError { @@ -27,7 +26,7 @@ pub struct CommandDispatcher<'a> { /// Stores registered [CommandTree]s and dispatches commands to them. impl<'a> CommandDispatcher<'a> { - pub fn handle_command(&self, sender: &mut CommandSender, server: &Arc, cmd: &str) { + pub fn handle_command(&self, sender: &mut CommandSender, server: &Server, cmd: &str) { if let Err(err) = self.dispatch(sender, server, cmd) { sender.send_message( TextComponent::text(&err).color_named(pumpkin_core::text::color::NamedColor::Red), @@ -39,7 +38,7 @@ impl<'a> CommandDispatcher<'a> { pub(crate) fn dispatch( &'a self, src: &mut CommandSender, - server: &Arc, + server: &Server, cmd: &str, ) -> Result<(), String> { let mut parts = cmd.split_ascii_whitespace(); @@ -87,7 +86,7 @@ impl<'a> CommandDispatcher<'a> { fn try_is_fitting_path( src: &mut CommandSender, - server: &Arc, + server: &Server, path: Vec, tree: &CommandTree, mut raw_args: RawArgs, diff --git a/pumpkin/src/commands/mod.rs b/pumpkin/src/commands/mod.rs index 322b96202..a0e10041f 100644 --- a/pumpkin/src/commands/mod.rs +++ b/pumpkin/src/commands/mod.rs @@ -1,5 +1,3 @@ -use std::sync::Arc; - use dispatcher::InvalidTreeError; use pumpkin_core::text::TextComponent; use tree::ConsumedArgs; @@ -81,5 +79,5 @@ pub fn default_dispatcher<'a>() -> CommandDispatcher<'a> { dispatcher } -type RunFunctionType = (dyn Fn(&mut CommandSender, &Arc, &ConsumedArgs) -> Result<(), InvalidTreeError> - + Sync); +type RunFunctionType = + (dyn Fn(&mut CommandSender, &Server, &ConsumedArgs) -> Result<(), InvalidTreeError> + Sync); diff --git a/pumpkin/src/entity/player.rs b/pumpkin/src/entity/player.rs index 496cedfe0..8aafce798 100644 --- a/pumpkin/src/entity/player.rs +++ b/pumpkin/src/entity/player.rs @@ -294,7 +294,7 @@ impl Player { let bytebuf = &mut packet.bytebuf; match packet.id.0 { SConfirmTeleport::PACKET_ID => { - self.handle_confirm_teleport(server, SConfirmTeleport::read(bytebuf)?); + self.handle_confirm_teleport(SConfirmTeleport::read(bytebuf)?); Ok(()) } SChatCommand::PACKET_ID => { @@ -302,41 +302,37 @@ impl Player { Ok(()) } SPlayerPosition::PACKET_ID => { - self.handle_position(server, SPlayerPosition::read(bytebuf)?) - .await; + self.handle_position(SPlayerPosition::read(bytebuf)?).await; Ok(()) } SPlayerPositionRotation::PACKET_ID => { - self.handle_position_rotation(server, SPlayerPositionRotation::read(bytebuf)?) + self.handle_position_rotation(SPlayerPositionRotation::read(bytebuf)?) .await; Ok(()) } SPlayerRotation::PACKET_ID => { - self.handle_rotation(server, SPlayerRotation::read(bytebuf)?) - .await; + self.handle_rotation(SPlayerRotation::read(bytebuf)?).await; Ok(()) } SSetPlayerGround::PACKET_ID => { - self.handle_player_ground(server, SSetPlayerGround::read(bytebuf)?); + self.handle_player_ground(SSetPlayerGround::read(bytebuf)?); Ok(()) } SPlayerCommand::PACKET_ID => { - self.handle_player_command(server, SPlayerCommand::read(bytebuf)?) + self.handle_player_command(SPlayerCommand::read(bytebuf)?) .await; Ok(()) } SSwingArm::PACKET_ID => { - self.handle_swing_arm(server, SSwingArm::read(bytebuf)?) - .await; + self.handle_swing_arm(SSwingArm::read(bytebuf)?).await; Ok(()) } SChatMessage::PACKET_ID => { - self.handle_chat_message(server, SChatMessage::read(bytebuf)?) - .await; + self.handle_chat_message(SChatMessage::read(bytebuf)?).await; Ok(()) } SClientInformationPlay::PACKET_ID => { - self.handle_client_information_play(server, SClientInformationPlay::read(bytebuf)?); + self.handle_client_information_play(SClientInformationPlay::read(bytebuf)?); Ok(()) } SInteract::PACKET_ID => { @@ -345,30 +341,29 @@ impl Player { Ok(()) } SPlayerAction::PACKET_ID => { - self.handle_player_action(server, SPlayerAction::read(bytebuf)?) + self.handle_player_action(SPlayerAction::read(bytebuf)?) .await; Ok(()) } SUseItemOn::PACKET_ID => { - self.handle_use_item_on(server, SUseItemOn::read(bytebuf)?) - .await; + self.handle_use_item_on(SUseItemOn::read(bytebuf)?).await; Ok(()) } SUseItem::PACKET_ID => { - self.handle_use_item(server, SUseItem::read(bytebuf)?); + self.handle_use_item(SUseItem::read(bytebuf)?); Ok(()) } SSetHeldItem::PACKET_ID => { - self.handle_set_held_item(server, SSetHeldItem::read(bytebuf)?); + self.handle_set_held_item(SSetHeldItem::read(bytebuf)?); Ok(()) } SSetCreativeSlot::PACKET_ID => { - self.handle_set_creative_slot(server, SSetCreativeSlot::read(bytebuf)?) + self.handle_set_creative_slot(SSetCreativeSlot::read(bytebuf)?) .unwrap(); Ok(()) } SPlayPingRequest::PACKET_ID => { - self.handle_play_ping_request(server, SPlayPingRequest::read(bytebuf)?); + self.handle_play_ping_request(SPlayPingRequest::read(bytebuf)?); Ok(()) } SClickContainer::PACKET_ID => { diff --git a/pumpkin/src/main.rs b/pumpkin/src/main.rs index 8cf3c0153..a2778aceb 100644 --- a/pumpkin/src/main.rs +++ b/pumpkin/src/main.rs @@ -36,7 +36,6 @@ pub mod entity; pub mod proxy; pub mod rcon; pub mod server; -pub mod util; pub mod world; fn init_logger() { @@ -154,7 +153,7 @@ fn main() -> io::Result<()> { if rcon.enabled { let server = server.clone(); tokio::spawn(async move { - RCONServer::new(&rcon, server).await.unwrap(); + RCONServer::new(&rcon, &server).await.unwrap(); }); } loop { @@ -167,7 +166,7 @@ fn main() -> io::Result<()> { for event in events.iter() { match event.token() { - SERVER => loop { + s if s == SERVER => loop { // Received an event for the TCP server socket, which // indicates we can accept an connection. let (mut connection, address) = match listener.accept() { @@ -236,7 +235,7 @@ fn main() -> io::Result<()> { }, // Maybe received an event for a TCP connection. token => { - // Poll Players + // poll Player if let Some(player) = players.get_mut(&token) { player.client.poll(event).await; let closed = player @@ -269,7 +268,6 @@ fn main() -> io::Result<()> { .load(std::sync::atomic::Ordering::Relaxed), ) } else { - // Sporadic events happen, we can safely ignore them. (false, false) }; if done || make_player { diff --git a/pumpkin/src/rcon/mod.rs b/pumpkin/src/rcon/mod.rs index a508f941a..76c7dee38 100644 --- a/pumpkin/src/rcon/mod.rs +++ b/pumpkin/src/rcon/mod.rs @@ -2,7 +2,6 @@ use std::{ collections::HashMap, io::{self, Read, Write}, net::SocketAddr, - sync::Arc, }; use mio::{ @@ -32,7 +31,7 @@ const SERVER: Token = Token(0); pub struct RCONServer; impl RCONServer { - pub async fn new(config: &RCONConfig, server: Arc) -> Result { + pub async fn new(config: &RCONConfig, server: &Server) -> Result { assert!(config.enabled, "RCON is not enabled"); let mut poll = Poll::new().unwrap(); let mut listener = TcpListener::bind(config.address).unwrap(); @@ -91,7 +90,7 @@ impl RCONServer { token => { let done = if let Some(client) = connections.get_mut(&token) { - client.handle(&server, &password).await + client.handle(server, &password).await } else { false }; @@ -139,7 +138,7 @@ impl RCONClient { } } - pub async fn handle(&mut self, server: &Arc, password: &str) -> bool { + pub async fn handle(&mut self, server: &Server, password: &str) -> bool { if !self.closed { loop { match self.read_bytes() { @@ -162,7 +161,7 @@ impl RCONClient { self.closed } - async fn poll(&mut self, server: &Arc, password: &str) -> Result<(), PacketError> { + async fn poll(&mut self, server: &Server, password: &str) -> Result<(), PacketError> { loop { let packet = match self.receive_packet().await? { Some(p) => p, diff --git a/pumpkin/src/server/connection_cache.rs b/pumpkin/src/server/connection_cache.rs index c87091fc8..1a57dffed 100644 --- a/pumpkin/src/server/connection_cache.rs +++ b/pumpkin/src/server/connection_cache.rs @@ -83,7 +83,7 @@ impl CachedStatus { } } - fn load_icon(path: &str) -> String { + fn load_icon>(path: P) -> String { let icon = png::Decoder::new(File::open(path).expect("Failed to load icon")); let mut reader = icon.read_info().unwrap(); let info = reader.info(); diff --git a/pumpkin/src/server/key_store.rs b/pumpkin/src/server/key_store.rs index 12bfb829c..becedf55d 100644 --- a/pumpkin/src/server/key_store.rs +++ b/pumpkin/src/server/key_store.rs @@ -1,5 +1,6 @@ use num_bigint::BigInt; use pumpkin_protocol::client::login::CEncryptionRequest; +use rand::rngs::OsRng; use rsa::{traits::PublicKeyParts as _, Pkcs1v15Encrypt, RsaPrivateKey, RsaPublicKey}; use sha1::Sha1; use sha2::Digest; @@ -30,7 +31,8 @@ impl KeyStore { } fn generate_keys() -> (RsaPublicKey, RsaPrivateKey) { - let mut rng = rand::thread_rng(); + // Found out that OsRng is faster than rand::thread_rng here + let mut rng = OsRng; let priv_key = RsaPrivateKey::new(&mut rng, 1024).expect("failed to generate a key"); let pub_key = RsaPublicKey::from(&priv_key); diff --git a/pumpkin/src/util/mod.rs b/pumpkin/src/util/mod.rs deleted file mode 100644 index 8b1378917..000000000 --- a/pumpkin/src/util/mod.rs +++ /dev/null @@ -1 +0,0 @@ -