diff --git a/Cargo.lock b/Cargo.lock index 144a840b..897bda93 100755 --- a/Cargo.lock +++ b/Cargo.lock @@ -10,14 +10,13 @@ checksum = "f26201604c87b1e01bd3d98f8d5d9a8fcbb815e8cedb41ffccbeb4bf593a35fe" [[package]] name = "aes" -version = "0.7.5" +version = "0.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9e8b47f52ea9bae42228d07ec09eb676433d7c4ed1ebdf0f1d1c29ed446f1ab8" +checksum = "bfe0133578c0986e1fe3dfcd4af1cc5b2dd6c3dbf534d69916ce16a2701d40ba" dependencies = [ "cfg-if", "cipher", "cpufeatures", - "opaque-debug", ] [[package]] @@ -220,9 +219,9 @@ dependencies = [ [[package]] name = "cfb8" -version = "0.7.1" +version = "0.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c3a4b6c43bf284e617a659ce5dc149676680530a3a4a9bb6b278d1a9ed5b229d" +checksum = "014c0a0e1ad0dae6a86c082db2f9bd7fe8c2c734227047d0d8b4d4a3a094a1e1" dependencies = [ "cipher", ] @@ -245,11 +244,12 @@ dependencies = [ [[package]] name = "cipher" -version = "0.3.0" +version = "0.4.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7ee52072ec15386f770805afd189a01c8841be8696bed250fa2f13c4c0d6dfb7" +checksum = "d1873270f8f7942c191139cb8a40fd228da6c3fd2fc376d7e92d47aa14aeb59e" dependencies = [ - "generic-array", + "crypto-common", + "inout", ] [[package]] @@ -581,6 +581,15 @@ dependencies = [ "unicode-normalization", ] +[[package]] +name = "inout" +version = "0.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a0c10553d664a4d0bcff9f4215d0aac67a639cc68ef660840afe309b807bc9f5" +dependencies = [ + "generic-array", +] + [[package]] name = "instant" version = "0.1.12" @@ -848,12 +857,6 @@ version = "11.1.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0ab1bc2a289d34bd04a330323ac98a1b4bc82c9d9fcb1e66b63caa84da26b575" -[[package]] -name = "opaque-debug" -version = "0.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "624a8340c38c1b80fd549087862da4ba43e08858af025b236e509b6649fc13d5" - [[package]] name = "packet-macros" version = "0.1.0" diff --git a/azalea-auth/Cargo.toml b/azalea-auth/Cargo.toml index 6279d903..5f62991b 100755 --- a/azalea-auth/Cargo.toml +++ b/azalea-auth/Cargo.toml @@ -6,8 +6,8 @@ version = "0.1.0" # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html [dependencies] -aes = "0.7.4" -cfb8 = "0.7.1" +aes = "0.8.1" +cfb8 = "0.8.1" num-bigint = "^0.4.3" rand = {version = "^0.8.4", features = ["getrandom"]} rsa_public_encrypt_pkcs1 = "0.4.0" diff --git a/azalea-auth/src/encryption.rs b/azalea-auth/src/encryption.rs index 6f2e43a8..dc2620cc 100644 --- a/azalea-auth/src/encryption.rs +++ b/azalea-auth/src/encryption.rs @@ -1,8 +1,11 @@ +use aes::cipher::inout::InOutBuf; +use aes::cipher::BlockEncrypt; use aes::{ - cipher::{AsyncStreamCipher, NewCipher}, + cipher::{ + generic_array::GenericArray, AsyncStreamCipher, BlockDecryptMut, BlockEncryptMut, KeyIvInit, + }, Aes128, }; -use cfb8::Cfb8; use rand::{rngs::OsRng, RngCore}; use sha1::{Digest, Sha1}; @@ -57,17 +60,26 @@ pub fn encrypt(public_key: &[u8], nonce: &[u8]) -> Result } // TODO: update the aes and cfb8 crates -pub type Aes128Cfb = Cfb8; +pub type Aes128CfbEnc = cfb8::Encryptor; +pub type Aes128CfbDec = cfb8::Decryptor; -pub fn create_cipher(key: &[u8]) -> Aes128Cfb { - Aes128Cfb::new_from_slices(&key, &key).unwrap() +pub fn create_cipher(key: &[u8]) -> (Aes128CfbEnc, Aes128CfbDec) { + ( + Aes128CfbEnc::new_from_slices(key, key).unwrap(), + Aes128CfbDec::new_from_slices(key, key).unwrap(), + ) } -pub fn encrypt_packet(cipher: &mut Aes128Cfb, packet: &mut [u8]) { - cipher.encrypt(packet); +// wow this is terrible +pub fn encrypt_packet(cipher: &mut Aes128CfbEnc, packet: &mut [u8]) { + let (chunks, rest) = InOutBuf::from(packet).into_chunks(); + assert!(rest.is_empty()); + cipher.encrypt_blocks_inout_mut(chunks); } -pub fn decrypt_packet(cipher: &mut Aes128Cfb, packet: &mut [u8]) { - cipher.decrypt(packet); +pub fn decrypt_packet(cipher: &mut Aes128CfbDec, packet: &mut [u8]) { + let (chunks, rest) = InOutBuf::from(packet).into_chunks(); + assert!(rest.is_empty()); + cipher.decrypt_blocks_inout_mut(chunks); } #[cfg(test)] diff --git a/azalea-protocol/src/connect.rs b/azalea-protocol/src/connect.rs index e81bc368..c55f2e90 100755 --- a/azalea-protocol/src/connect.rs +++ b/azalea-protocol/src/connect.rs @@ -7,7 +7,7 @@ use crate::packets::status::StatusPacket; use crate::read::read_packet; use crate::write::write_packet; use crate::ServerIpAddress; -use azalea_auth::encryption::Aes128Cfb; +use azalea_auth::encryption::{Aes128CfbDec, Aes128CfbEnc}; use tokio::net::TcpStream; pub enum PacketFlow { @@ -26,7 +26,8 @@ pub struct GameConnection { /// The buffered writer pub stream: TcpStream, pub compression_threshold: Option, - pub cipher: Option, + pub enc_cipher: Option, + pub dec_cipher: Option, } pub struct StatusConnection { @@ -40,7 +41,8 @@ pub struct LoginConnection { /// The buffered writer pub stream: TcpStream, pub compression_threshold: Option, - pub cipher: Option, + pub enc_cipher: Option, + pub dec_cipher: Option, } impl HandshakeConnection { @@ -68,7 +70,8 @@ impl HandshakeConnection { flow: self.flow, stream: self.stream, compression_threshold: None, - cipher: None, + enc_cipher: None, + dec_cipher: None, } } @@ -95,7 +98,7 @@ impl GameConnection { &self.flow, &mut self.stream, self.compression_threshold, - &mut self.cipher, + &mut self.dec_cipher, ) .await } @@ -106,7 +109,7 @@ impl GameConnection { packet, &mut self.stream, self.compression_threshold, - &mut self.cipher, + &mut self.enc_cipher, ) .await; } @@ -129,7 +132,7 @@ impl LoginConnection { &self.flow, &mut self.stream, self.compression_threshold, - &mut self.cipher, + &mut self.dec_cipher, ) .await } @@ -140,7 +143,7 @@ impl LoginConnection { packet, &mut self.stream, self.compression_threshold, - &mut self.cipher, + &mut self.enc_cipher, ) .await; } @@ -156,8 +159,9 @@ impl LoginConnection { pub fn set_encryption_key(&mut self, key: [u8; 16]) { // minecraft has a cipher decoder and encoder, i don't think it matters though? - let cipher = azalea_auth::encryption::create_cipher(&key); - self.cipher = Some(cipher); + let (enc_cipher, dec_cipher) = azalea_auth::encryption::create_cipher(&key); + self.enc_cipher = Some(enc_cipher); + self.dec_cipher = Some(dec_cipher); } pub fn game(self) -> GameConnection { @@ -165,7 +169,8 @@ impl LoginConnection { flow: self.flow, stream: self.stream, compression_threshold: self.compression_threshold, - cipher: self.cipher, + enc_cipher: self.enc_cipher, + dec_cipher: self.dec_cipher, } } } diff --git a/azalea-protocol/src/read.rs b/azalea-protocol/src/read.rs index 1e308cfb..88fe95cf 100755 --- a/azalea-protocol/src/read.rs +++ b/azalea-protocol/src/read.rs @@ -2,7 +2,7 @@ use std::{cell::Cell, pin::Pin}; use crate::{connect::PacketFlow, mc_buf::Readable, packets::ProtocolPacket}; use async_compression::tokio::bufread::ZlibDecoder; -use azalea_auth::encryption::Aes128Cfb; +use azalea_auth::encryption::Aes128CfbDec; use tokio::io::{AsyncRead, AsyncReadExt}; async fn frame_splitter(mut stream: &mut R) -> Result, String> @@ -97,7 +97,7 @@ struct EncryptedStream<'a, R> where R: AsyncRead + std::marker::Unpin + std::marker::Send, { - cipher: Cell<&'a mut Option>, + cipher: Cell<&'a mut Option>, stream: &'a mut Pin<&'a mut R>, } @@ -133,7 +133,7 @@ pub async fn read_packet<'a, P: ProtocolPacket, R>( flow: &PacketFlow, stream: &'a mut R, compression_threshold: Option, - cipher: &mut Option, + cipher: &mut Option, ) -> Result where R: AsyncRead + std::marker::Unpin + std::marker::Send + std::marker::Sync, diff --git a/azalea-protocol/src/write.rs b/azalea-protocol/src/write.rs index e72a74b1..e39ce18e 100755 --- a/azalea-protocol/src/write.rs +++ b/azalea-protocol/src/write.rs @@ -1,8 +1,9 @@ use crate::{mc_buf::Writable, packets::ProtocolPacket, read::MAXIMUM_UNCOMPRESSED_LENGTH}; use async_compression::tokio::bufread::ZlibEncoder; -use azalea_auth::encryption::Aes128Cfb; +use azalea_auth::encryption::Aes128CfbEnc; +use std::fmt::Debug; use tokio::{ - io::{AsyncReadExt, AsyncWriteExt}, + io::{AsyncReadExt, AsyncWrite, AsyncWriteExt}, net::TcpStream, }; @@ -51,13 +52,14 @@ async fn compression_encoder(data: &[u8], compression_threshold: u32) -> Result< } } -pub async fn write_packet

( +pub async fn write_packet( packet: P, - stream: &mut TcpStream, + stream: &mut W, compression_threshold: Option, - cipher: &mut Option, + cipher: &mut Option, ) where - P: ProtocolPacket + std::fmt::Debug, + P: ProtocolPacket + Debug, + W: AsyncWrite + Unpin + Send, { let mut buf = packet_encoder(&packet).unwrap(); if let Some(threshold) = compression_threshold { diff --git a/bot/src/main.rs b/bot/src/main.rs index fc278c28..199000e5 100644 --- a/bot/src/main.rs +++ b/bot/src/main.rs @@ -3,7 +3,7 @@ async fn main() { println!("Hello, world!"); // let address = "95.111.249.143:10000"; - let address = "localhost:63097"; + let address = "localhost:50332"; // let response = azalea_client::ping::ping_server(&address.try_into().unwrap()) // .await // .unwrap();