Skip to content

Instantly share code, notes, and snippets.

@brandon15811
Last active February 5, 2021 09:07
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save brandon15811/a396951a63b41cca416a to your computer and use it in GitHub Desktop.
Save brandon15811/a396951a63b41cca416a to your computer and use it in GitHub Desktop.
PocketMine Server Query in Bash
#!/bin/bash
MAGIC='fefd'
SESSIONTYPE='09'
SESSION='01020304'
LONG="0"
while getopts ":l" opt; do
case $opt in
l)
LONG="1"
;;
\?)
echo "Invalid option: -$OPTARG" >&2
;;
esac
done
shift $((OPTIND-1))
HOST=$1
PORT=$2
SESSIONREQ=${MAGIC}${SESSIONTYPE}${SESSION}
echo "Sending Packet: "$SESSIONREQ
SESSIONRES=$(echo -en $SESSIONREQ | xxd -r -p | nc -w 1 -u $HOST $PORT | xxd -p);
echo "Received Packet: "$SESSIONRES
if [ -z "$SESSIONRES" ]; then
echo "Info Request failed"
exit 1
fi
#echo -n "0: "$SESSIONRES | xxd -r -p -g 0 | xxd -g 1
SESSIONID=${SESSIONRES:2:8}
###CHALLENGE=$(printf "%.8x" ${SESSIONRES:5})
CHALLENGENUM=${SESSIONRES:10:-2}
#if [ "$CHALLENGENUM" -ge '2147483648' ];
#then
# CHALLENGENUM=$(echo -n "$CHALLENGENUM - 4294967296" | bc)
#fi
#http://stackoverflow.com/a/9955198/1951549
CHALLENGE=$(echo -n $CHALLENGENUM | xxd -p -r | printf "%.8x" $(cat -))
INFOTYPE='00'
if [ "$LONG" = "1" ]; then
LONGINFO='00000000'
fi
INFOREQ=${MAGIC}${INFOTYPE}${SESSION}${CHALLENGE}${LONGINFO}
echo "Sending Packet: "$INFOREQ
INFORES=$(echo -n $INFOREQ | xxd -r -p | nc -i 1 -w 1 -u $HOST $PORT | xxd -p)
echo "Received Packet: "$INFORES
if [ -z "$INFORES" ]; then
echo "Info Request failed"
exit 1
fi
if [ "$LONG" = "1" ]; then
INFOSPLIT=${INFORES:32}
INFOKEY="0"
PLUGINS="0"
INFOEND="0"
PLAYERSTART="0"
PLAYERSKIP="0"
echo $INFOSPLIT | xxd -p -r | xargs -0 -I {} echo {} 2>/dev/null| while read name; do
if [ "$INFOEND" = "0" ]; then
#End info and start parsing players
if [ -z "$name" ]; then
INFOEND="1"
echo "Players: "
continue
fi
#Parse plugin list
if [ "$name" = "plugins" ]; then
PLUGINS="1"
continue
fi
if [ "$PLUGINS" = "1" ]; then
echo -n "Server Mod: "
echo -n $name | cut -d ':' -f1
echo "Plugins: "
echo -n $name | cut -d ':' -f2 | xargs -d ';' -I {} echo -e '\t{}'
PLUGINS="0"
continue
fi
if [ "$INFOKEY" = "0" ]; then
echo -n "$name: "
INFOKEY="1"
else
echo $name
INFOKEY="0"
fi
else
if [ "$(echo -n $name | xxd -p)" = "01706c617965725f" ]; then
PLAYERSTART="1"
continue
fi
if [ -z "$name" ]; then
if [ "$PLAYERSKIP" = "0" ]; then
PLAYERSKIP="1"
continue
fi
fi
if [ -z "$name" ]; then
if [ "$PLAYERSKIP" = "1" ]; then
continue
fi
fi
if [ "$PLAYERSTART" = "1" ]; then
echo -e "\t$name"
fi
fi
#echo "derpxxd: " $(echo -n $name | xxd -g 1)
done
#echo $INFORES | xxd -p -r | xxd -g 1
else
INFOSTRIP=$(echo -n ${INFORES:10} | xxd -r -p | xxd -p)
SERVERNAME=$(echo -n $INFOSTRIP | xxd -r -p | cut -d $'\x00' -f1)
GAMETYPE=$(echo -n $INFOSTRIP | xxd -r -p | cut -d $'\x00' -f2)
WORLDNAME=$(echo -n $INFOSTRIP | xxd -r -p | cut -d $'\x00' -f3)
NUMPLAYERS=$(echo -n $INFOSTRIP | xxd -r -p | cut -d $'\x00' -f4)
MAXPLAYERS=$(echo -n $INFOSTRIP | xxd -r -p | cut -d $'\x00' -f5)
SERVERPORT=$(echo -n $INFOSTRIP | xxd -r -p | cut -d $'\x00' -f6 | tr -d '\n' | xxd -p)
#http://stackoverflow.com/a/9955198/1951549
SERVERPORT=$(echo $SERVERPORT | tr '[a-z]' '[A-Z]' | sed -E 's/(..)(..)/\2\1/' | xargs echo "ibase=16; " | bc)
printf "Server Name: %s
Game type: %s
World Name: %s
Number of Players: %d
Max Players: %d
Server Port: %d\n" "$SERVERNAME" "$GAMETYPE" "$WORLDNAME" "$NUMPLAYERS" "$MAXPLAYERS" "$SERVERPORT"
fi
#Just in case of an infinite loop
sleep 1
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment