mirror of
https://github.com/timvisee/lazymc.git
synced 2025-05-19 04:40:22 -07:00
Hijack login start packet to disconnect payer if server is sleeping
This commit is contained in:
parent
645ea892cb
commit
d742eca632
@ -5,7 +5,11 @@ pub const ADDRESS_PUBLIC: &str = "127.0.0.1:9090";
|
|||||||
pub const ADDRESS_PROXY: &str = "127.0.0.1:9091";
|
pub const ADDRESS_PROXY: &str = "127.0.0.1:9091";
|
||||||
|
|
||||||
/// Server description shown when server is starting.
|
/// Server description shown when server is starting.
|
||||||
pub const LABEL_SERVER_SLEEPING: &str = "Server sleeping...\nJoin to start it up §c♥";
|
pub const LABEL_SERVER_SLEEPING: &str = "☠ Server is sleeping...\n§2☻ Join to start it up";
|
||||||
|
|
||||||
/// Server description shown when server is starting.
|
/// Server description shown when server is starting.
|
||||||
pub const LABEL_SERVER_STARTING: &str = "Server starting...\nPlease wait §c♥";
|
pub const LABEL_SERVER_STARTING: &str = "§2☻ Server is starting...\n§7⌛ Please wait...";
|
||||||
|
|
||||||
|
/// Kick message shown when user tries to connect to starting server.
|
||||||
|
pub const LABEL_SERVER_STARTING_MESSAGE: &str =
|
||||||
|
"Server is starting... §c♥§r\n\nThis may take some time.\n\nPlease try to reconnect in a minute.";
|
||||||
|
29
src/main.rs
29
src/main.rs
@ -9,6 +9,7 @@ use minecraft_protocol::data::server_status::*;
|
|||||||
use minecraft_protocol::decoder::Decoder;
|
use minecraft_protocol::decoder::Decoder;
|
||||||
use minecraft_protocol::encoder::Encoder;
|
use minecraft_protocol::encoder::Encoder;
|
||||||
use minecraft_protocol::version::v1_14_4::handshake::Handshake;
|
use minecraft_protocol::version::v1_14_4::handshake::Handshake;
|
||||||
|
use minecraft_protocol::version::v1_14_4::login::LoginDisconnect;
|
||||||
use minecraft_protocol::version::v1_14_4::status::StatusResponse;
|
use minecraft_protocol::version::v1_14_4::status::StatusResponse;
|
||||||
use tokio::io;
|
use tokio::io;
|
||||||
use tokio::io::AsyncReadExt;
|
use tokio::io::AsyncReadExt;
|
||||||
@ -34,12 +35,15 @@ async fn main() -> Result<(), ()> {
|
|||||||
// Proxy all incomming connections
|
// Proxy all incomming connections
|
||||||
while let Ok((inbound, _)) = listener.accept().await {
|
while let Ok((inbound, _)) = listener.accept().await {
|
||||||
let client = Client::default();
|
let client = Client::default();
|
||||||
eprintln!("New client");
|
eprintln!("Client connected");
|
||||||
|
|
||||||
let transfer = proxy(client, inbound, ADDRESS_PROXY.to_string()).map(|r| {
|
let transfer = proxy(client, inbound, ADDRESS_PROXY.to_string()).map(|r| {
|
||||||
if let Err(e) = r {
|
if let Err(e) = r {
|
||||||
println!("Failed to proxy: {:?}", e);
|
println!("Failed to proxy: {:?}", e);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// TODO: proxy isn't closed for disconnected clients!
|
||||||
|
eprintln!("Client disconnected");
|
||||||
});
|
});
|
||||||
|
|
||||||
tokio::spawn(transfer);
|
tokio::spawn(transfer);
|
||||||
@ -109,13 +113,15 @@ async fn proxy(client: Client, mut inbound: TcpStream, addr_target: String) -> R
|
|||||||
|
|
||||||
let (client_send_queue, mut client_to_send) = unbounded_channel::<Vec<u8>>();
|
let (client_send_queue, mut client_to_send) = unbounded_channel::<Vec<u8>>();
|
||||||
|
|
||||||
|
let server_available = false;
|
||||||
|
|
||||||
let client_to_server = async {
|
let client_to_server = async {
|
||||||
// Incoming buffer
|
// Incoming buffer
|
||||||
let mut buf = BytesMut::new();
|
let mut buf = BytesMut::new();
|
||||||
|
|
||||||
loop {
|
loop {
|
||||||
// In login state, proxy raw data
|
// In login state, proxy raw data
|
||||||
if client.state() == ClientState::Login {
|
if server_available && client.state() == ClientState::Login {
|
||||||
eprintln!("STARTED FULL PROXY");
|
eprintln!("STARTED FULL PROXY");
|
||||||
|
|
||||||
wo.writable().await.map_err(|_| ())?;
|
wo.writable().await.map_err(|_| ())?;
|
||||||
@ -149,6 +155,25 @@ async fn proxy(client: Client, mut inbound: TcpStream, addr_target: String) -> R
|
|||||||
eprintln!("PACKET ID: {}", packet.id);
|
eprintln!("PACKET ID: {}", packet.id);
|
||||||
eprintln!("PACKET DATA: {:?}", packet.data);
|
eprintln!("PACKET DATA: {:?}", packet.data);
|
||||||
|
|
||||||
|
// Hijack login start
|
||||||
|
if client.state() == ClientState::Login
|
||||||
|
&& packet.id == protocol::LOGIN_PACKET_ID_LOGIN_START
|
||||||
|
{
|
||||||
|
let packet = LoginDisconnect {
|
||||||
|
reason: Message::new(Payload::text(LABEL_SERVER_STARTING_MESSAGE)),
|
||||||
|
};
|
||||||
|
|
||||||
|
let mut data = Vec::new();
|
||||||
|
packet.encode(&mut data).map_err(|_| ())?;
|
||||||
|
|
||||||
|
let response = RawPacket::new(0, data).encode()?;
|
||||||
|
client_send_queue
|
||||||
|
.send(response)
|
||||||
|
.expect("failed to queue logout response");
|
||||||
|
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
// Hijack handshake
|
// Hijack handshake
|
||||||
if client.state() == ClientState::Handshake
|
if client.state() == ClientState::Handshake
|
||||||
&& packet.id == protocol::STATUS_PACKET_ID_STATUS
|
&& packet.id == protocol::STATUS_PACKET_ID_STATUS
|
||||||
|
@ -4,6 +4,7 @@ use crate::types;
|
|||||||
|
|
||||||
pub const STATUS_PACKET_ID_STATUS: i32 = 0;
|
pub const STATUS_PACKET_ID_STATUS: i32 = 0;
|
||||||
pub const STATUS_PACKET_ID_PING: i32 = 1;
|
pub const STATUS_PACKET_ID_PING: i32 = 1;
|
||||||
|
pub const LOGIN_PACKET_ID_LOGIN_START: i32 = 0;
|
||||||
|
|
||||||
/// Client state.
|
/// Client state.
|
||||||
// TODO: add encryption/compression state
|
// TODO: add encryption/compression state
|
||||||
|
Loading…
x
Reference in New Issue
Block a user