The UDP query protocol includes a list of all players on the server. For even moderately sized servers it is very easy for this list to exceed the MTU of the network (1500 bytes on the internet). This causes the packet to be dropped and the server to appear offline.
Comments 4
Is this still a issue in the latest version of the game(currently 1.13.1)?
If so, please add it to the affected versions, thanks!
I was able to confirm this as of 26.1.2, the easiest approach to confirming this is by either using a bot framework or having a populated server.
Steps to Reproduce (bash commands):
1 - Set up a Minecraft vanilla server and edit server.properties:
enable-query=true
query.port=25565
online-mode=false
max-players=200
view-distance=2
simulation-distance=2
enable-rcon=false
motd=test2 - Install the Rust bot framework (azalea) inside the server
curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh -s -- -y --default-toolchain nightly
source ~/.cargo/env3 - Create the bot project:
mkdir ~/mcbots && cd ~/mcbots && cargo init
4 - Write the Cargo.toml file:
[package]
name = "mcbots"
version = "0.1.0"
edition = "2021"
[dependencies]
azalea = { git = "https://github.com/azalea-rs/azalea" }
tokio = { version = "1", features = ["full"] }
anyhow = "1"
5 - Write the bot:
use azalea::prelude::*;
use azalea::swarm::prelude::*;
#[derive(Default, Clone, Component)]
struct State;
#[derive(Default, Clone, Resource)]
struct SwarmState;
#[tokio::main]
async fn main() {
let accounts: Vec<Account> = (0..150u32)
.map(|i| Account::offline(&format!("BotFace{:04}", i)))
.collect();
SwarmBuilder::new()
.set_handler(handle)
.set_swarm_handler(swarm_handler)
.add_accounts(accounts)
.start("127.0.0.1")
.await;
}
async fn handle(_bot: Client, _event: Event, _state: State) -> anyhow::Result<()> {
Ok(())
}
async fn swarm_handler(_swarm: Swarm, _event: SwarmEvent, _state: SwarmState) -> anyhow::Result<()> {
Ok(())
}
6 - Start the server
7 - Build the bots:
cargo build --release 2>&1 | tail -58 - Run the bots:
~/mcbots/target/release/mcbots &
sleep 20 && grep -c "logged in" ~/mcserver/server.log9 - Create the query script:
import socket, struct
def query(host, port):
s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
s.settimeout(5)
s.sendto(b'\xFE\xFD\x09\x00\x00\x00\x01', (host, port))
challenge_data, _ = s.recvfrom(1024)
challenge = struct.pack('>i', int(challenge_data[5:-1]))
payload = b'\xFE\xFD\x00\x00\x00\x00\x01' + challenge + b'\x00\x00\x00\x00'
s.sendto(payload, (host, port))
response = b''
while True:
try:
chunk, _ = s.recvfrom(4096)
response += chunk
except socket.timeout:
break
s.close()
print(f"Total response size: {len(response)} bytes")
print(f"Exceeds MTU (1500): {len(response) > 1500}")
return response
query('127.0.0.1', 25565)
10 - Run the query script:
python3 ~/query.pyOutput:
Total response size: 1969 bytes
Exceeds MTU (1500): True
Is this still an issue in the most recent versions (currently that is 1.12.2, or the latest 1.13 development snapshot 18w20c) of Minecraft? If so, please update the affected versions and help us keeping this ticket updated from time to time. If you are the owner/reporter of this ticket, you can modify the affected version(s) yourself.