Much code, many rewrite

This commit is contained in:
2019-12-14 20:08:34 +01:00
parent 3bdd78b61c
commit 2166a30aa9
34 changed files with 852 additions and 58 deletions

3
network/__init__.py Normal file
View File

@@ -0,0 +1,3 @@
from . import enums
from . import compression

50
network/compression.py Normal file
View File

@@ -0,0 +1,50 @@
import logging
from objects import glob
# Found @ addr 0x004C88E0
LOOKUP_TABLE = b"\xb4b\x07\xe5\x9d\xafc\xdd\xe3\xd0\xcc\xfe\xdc\xdbk.j@\xabG\xc9\xd1S\xd5 \x91\xa5\x0eJ\xdf\x18\x89\xfdo%\x12\xb7\x13w\x00e6mI\xecW*\xa9\x11_\xfax\x95\xa4\xbd\x1e\xd9yD\xcd\xde\x81\xeb\t>\xf6\xee\xda\x7f\xa3\x1a\xa7-\xa6\xad\xc1F\x93\xd2\x1b\x9c\xaa\xd7NKML\xf3\xb84\xc0\xca\x88\xf4\x94\xcb\x0490\x82\xd6s\xb0\xbf\"\x01AnH,\xa8u\xb1\n\xae\x9f\'\x80\x10\xce\xf0)(\x85\r\x05\xf75\xbb\xbc\x15\x06\xf5`q\x03\x1f\xeaZ3\x92\x8d\xe7\x90[\xe9\xcf\x9e\xd3]\xed1\x1c\x0bR\x16Q\x0f\x86\xc5h\x9b!\x0c\x8bB\x87\xffO\xbe\xc8\xe8\xc7\xd4z\xe0U/\x8a\x8e\xba\x987\xe4\xb28\xa1\xb62\x83:{\x84<a\xfb\x8c\x14=C;\x1d\xc3\xa2\x96\xb3\xf8\xc4\xf2&+\xd8|\xfc#$f\xefidPTY\xf1\xa0t\xac\xc6}\xb5\xe6\xe2\xc2~g\x17^\xe1\xb9?lp\x08\x99EVv\xf9\x9a\x97\x19r\\\x02\x8fX"
logger = logging.getLogger(__name__)
def uncompress(byteStream: bytes) -> bytearray:
"""Uncompress client packet.
This is actually a deobfuscation as there is no compression involved anymore
as zlib was removed and just swapped with this implementation after the leak.
Arguments:
byteStream {bytes} -- Bytes sent by client
"""
checksum, data = byteStream[0], bytearray(byteStream[1:])
data = xor_every_other_byte(get_port_xor_key(), data)
data = run_though_lookup_table(data)
if checksum != calc_checksum(data):
logger.error("Checksum failed!\n\tExpected: %d\n\tGot: %d" % (checksum, calc_checksum(data)))
raise Exception("Checksum failed!")
return data
def xor_every_other_byte(xor, byteStream: bytearray):
# xor: (server_port ^ 0xCCCC) & 0xFF
for i in range(1, len(byteStream), 2):
byteStream[i] = byteStream[i] ^ xor
return byteStream
def run_though_lookup_table(byteStream: bytes):
return bytearray([LOOKUP_TABLE[b] for b in byteStream])
def calc_checksum(byteStream: bytes):
checksum = 0
for i in range(len(byteStream)):
checksum = checksum ^ byteStream[i] & 0xAA
return checksum
# It should be faster to call a function and do an if, then to read the property of a dict and do bit operations after
_port_xor_key = None
def get_port_xor_key():
global _port_xor_key
if _port_xor_key is None:
_port_xor_key = (glob.config["port"] ^ 0xCCCC) & 0xFF
return _port_xor_key

View File

@@ -0,0 +1,2 @@
MTU_SIZE = 576
UDP_HEADER_SIZE = 28

View File

@@ -0,0 +1,4 @@
from . import packetTypeRaknet
from . import packetTypeSamp
from . import packetRPC
from . import types

137
network/enums/packetRPC.py Normal file
View File

@@ -0,0 +1,137 @@
# netrpc (client)
RPC_ServerJoin = "xy"
RPC_ServerQuit = "ab"
RPC_InitGame = "ac"
RPC_VehicleSpawn = "am"
RPC_VehicleDestroy = "an"
RPC_SetCheckpoint = "ao"
RPC_DisableCheckpoint = "ap"
RPC_SetRaceCheckpoint = "aq"
RPC_DisableRaceCheckpoint = "ar"
RPC_GameModeRestart = "at"
RPC_ConnectionRejected = "au"
RPC_ClientMessage = "av"
RPC_WorldTime = "aw"
RPC_Pickup = "ax"
RPC_DestroyPickup = "ay"
RPC_DestroyWeaponPickup = "az"
RPC_Weather = "bb"
RPC_Instagib = "bc"
RPC_SetTimeEx = "be"
RPC_ToggleClock = "bf"
# netrpc (both)
RPC_Chat = "ad"
RPC_Privmsg = "ae"
RPC_TeamPrivmsg = "af"
RPC_RequestClass = "ag"
RPC_RequestSpawn = "ah"
RPC_Spawn = "ai"
RPC_Death = "aj"
RPC_EnterVehicle = "ak"
RPC_ExitVehicle = "al"
RPC_UpdateScoresPingsIPs = "as"
RPC_SvrStats = "em"
RPC_ScmEvent = "ba"
# scriptrpc
RPC_ScrSetSpawnInfo = "bg"
RPC_ScrSetPlayerTeam = "bh"
RPC_ScrSetPlayerSkin = "bi"
RPC_ScrSetPlayerName = "bj"
RPC_ScrSetPlayerPos = "bk"
RPC_ScrSetPlayerPosFindZ = "bl"
RPC_ScrSetPlayerHealth = "bm"
RPC_ScrPutPlayerInVehicle = "bn"
RPC_ScrRemovePlayerFromVehicle = "bo"
RPC_ScrSetPlayerColor = "bp"
RPC_ScrDisplayGameText = "bq"
RPC_ScrSetInterior = "br"
RPC_ScrSetCameraPos = "bs"
RPC_ScrSetCameraLookAt = "bt"
RPC_ScrSetVehiclePos = "bu"
RPC_ScrSetVehicleZAngle = "bv"
RPC_ScrVehicleParams = "bw"
RPC_ScrSetCameraBehindPlayer = "bx"
RPC_ScrTogglePlayerControllable = "by"
RPC_ScrPlaySound = "bz"
RPC_ScrSetWorldBounds = "ca"
RPC_ScrHaveSomeMoney = "cb"
RPC_ScrSetPlayerFacingAngle = "cc"
RPC_ScrResetMoney = "cd"
RPC_ScrResetPlayerWeapons = "ce"
RPC_ScrGivePlayerWeapon = "cf"
RPC_ScrRespawnVehicle = "cg"
RPC_ScrLinkVehicle = "ch"
RPC_ScrSetPlayerArmour = "ci"
RPC_ScrDeathMessage = "cj"
RPC_ScrSetMapIcon = "ck"
RPC_ScrDisableMapIcon = "cl"
RPC_ScrSetWeaponAmmo = "cm"
RPC_ScrSetGravity = "cn"
RPC_ScrSetVehicleHealth = "co"
RPC_ScrAttachTrailerToVehicle = "cp"
RPC_ScrDetachTrailerFromVehicle = "cq"
RPC_ScrCreateObject = "cr"
RPC_ScrSetObjectPos = "cs"
RPC_ScrSetObjectRotation = "ct"
RPC_ScrDestroyObject = "cu"
RPC_ScrSetPlayerVirtualWorld = "cv"
RPC_ScrSetVehicleVirtualWorld = "cw"
RPC_ScrCreateExplosion = "cx"
RPC_ScrShowNameTag = "cy"
RPC_ScrMoveObject = "cz"
RPC_ScrStopObject = "da"
RPC_ScrNumberPlate = "db"
RPC_ScrTogglePlayerSpectating = "dc"
RPC_ScrSetPlayerSpectating = "dd"
RPC_ScrPlayerSpectatePlayer = "de"
RPC_ScrPlayerSpectateVehicle = "df"
RPC_ScrRemoveComponent = "dg"
RPC_ScrForceSpawnSelection = "dh"
RPC_ScrAttachObjectToPlayer = "dt"
RPC_ScrInitMenu = "du"
RPC_ScrShowMenu = "dv"
RPC_ScrHideMenu = "dw"
RPC_ScrSetPlayerWantedLevel = "dz"
RPC_ScrShowTextDraw = "ea"
RPC_ScrHideTextDraw = "eb"
RPC_ScrEditTextDraw = "ee"
RPC_ScrAddGangZone = "ef"
RPC_ScrRemoveGangZone = "eg"
RPC_ScrFlashGangZone = "eh"
RPC_ScrStopFlashGangZone = "ei"
RPC_ScrApplyAnimation = "eo"
RPC_ScrClearAnimations = "eq"
RPC_ScrSetSpecialAction = "ep"
RPC_ScrEnableStuntBonus = "ec"
RPC_ScrUsePlayerPedAnims = "a1"
RPC_ScrToggleVehicleMarker = "a4"
RPC_ScrMoveTextdraw = "a5"
RPC_ScrSetPlayerVisibleInScoreBoard = "a6"
# netrpc (server)
RPC_ClientJoin = "xx"
RPC_ServerCommand = "dj"
RPC_SetInteriorId = "dk"
RPC_ClickMap = "dl"
RPC_VehicleDestroyed = "dm"
RPC_PickedUpWeapon = "dn"
RPC_PickedUpPickup = "do"
RPC_MenuSelect = "dx"
RPC_MenuQuit = "dy"
RPC_UnderMapTeleport = "a2"
RPC_ResolutionChanged = "a3"
# rcon
RPC_RconConnect = "dp"
RPC_RconCommand = "dq"
RPC_RconEvent = "dr"
RPC_RconPlayerInfo = "ds"
# anticheat
RPC_ACAuthRequest = "ej"
RPC_ACAuthResponse = "ek"
RPC_ACAuthEngineLoaded = "el"
RPC_ACServerProtected = "bd"

View File

@@ -0,0 +1,113 @@
INTERNAL_PING = 0x00
PING = 0x01
PING_OPEN_CONNECTIONS = 0x02
CONNECTED_PONG = 0x03
REQUEST_STATIC_DATA = 0x04
CONNECTION_REQUEST = 0x05
SECURED_CONNECTION_RESPONSE = 0x06
SECURED_CONNECTION_CONFIRMATION = 0x07
RPC_MAPPING = 0x08
DETECT_LOST_CONNECTIONS = 0x09
OPEN_CONNECTION_REQUEST = 0x0a
OPEN_CONNECTION_REPLY = 0x0b
RPC = 0x0c
RPC_REPLY = 0x0d
BROADCAST_PINGS = 0x0e
SET_RANDOM_NUMBER_SEED = 0x0f
CONNECTION_REQUEST_ACCEPTED = 0x10
CONNECTION_ATTEMPT_FAILED = 0x11
NEW_INCOMING_CONNECTION = 0x18
NO_FREE_INCOMING_CONNECTIONS = 0x13
DISCONNECTION_NOTIFICATION = 0x14
CONNECTION_LOST = 0x15
RSA_PUBLIC_KEY_MISMATCH = 0x16
CONNECTION_BANNED = 0x17
INVALID_PASSWORD = 0x18
MODIFIED_PACKET = 0x19
TIMESTAMP = 0x1a
PONG = 0x1b
RECEIVED_STATIC_DATA = 0x1c
REMOTE_DISCONNECTION_NOTIFICATION = 0x1d
REMOTE_CONNECTION_LOST = 0x1e
REMOTE_NEW_INCOMING_CONNECTION = 0x1f
REMOTE_EXISTING_CONNECTION = 0x20
REMOTE_STATIC_DATA = 0x21
FILE_LIST_TRANSFER_HEADER = 0x22
FILE_LIST_TRANSFER_FILE = 0x23
DDT_DOWNLOAD_REQUEST = 0x24
QUERY_MASTER_SERVER = 0x25
MASTER_SERVER_DELIST_SERVER = 0x26
MASTER_SERVER_UPDATE_SERVER = 0x27
MASTER_SERVER_SET_SERVER = 0x28
RELAYED_CONNECTION_NOTIFICATION = 0x29
ADVERTISE_SYSTEM = 0x2a
TRANSPORT_STRING = 0x2b
REPLICA_MANAGER_CONSTRUCTION = 0x2c
REPLICA_MANAGER_DESTRUCTION = 0x2d
REPLICA_MANAGER_SCOPE_CHANGE = 0x2e
REPLICA_MANAGER_SERIALIZE = 0x2f
REPLICA_MANAGER_DOWNLOAD_COMPLETE = 0x30
CONNECTION_GRAPH_REQUEST = 0x31
CONNECTION_GRAPH_REPLY = 0x32
CONNECTION_GRAPH_UPDATE = 0x33
CONNECTION_GRAPH_NEW_CONNECTION = 0x34
CONNECTION_GRAPH_CONNECTION_LOST = 0x35
CONNECTION_GRAPH_DISCONNECTION_NOTIFICATION = 0x36
ROUTE_AND_MULTICAST = 0x37
RAKVOICE_OPEN_CHANNEL_REQUEST = 0x38
RAKVOICE_OPEN_CHANNEL_REPLY = 0x39
RAKVOICE_CLOSE_CHANNEL = 0x3a
RAKVOICE_DATA = 0x3b
AUTOPATCHER_GET_CHANGELIST_SINCE_DATE = 0x3c
AUTOPATCHER_CREATION_LIST = 0x3d
AUTOPATCHER_DELETION_LIST = 0x3e
AUTOPATCHER_GET_PATCH = 0x3f
AUTOPATCHER_PATCH_LIST = 0x40
AUTOPATCHER_REPOSITORY_FATAL_ERROR = 0x41
AUTOPATCHER_FINISHED = 0x42
AUTOPATCHER_RESTART_APPLICATION = 0x43
NAT_PUNCHTHROUGH_REQUEST = 0x44
NAT_TARGET_NOT_CONNECTED = 0x45
NAT_TARGET_CONNECTION_LOST = 0x46
NAT_CONNECT_AT_TIME = 0x47
NAT_SEND_OFFLINE_MESSAGE_AT_TIME = 0x48
DATABASE_QUERY_REQUEST = 0x49
DATABASE_UPDATE_ROW = 0x4a
DATABASE_REMOVE_ROW = 0x4b
DATABASE_QUERY_REPLY = 0x4c
DATABASE_UNKNOWN_TABLE = 0x4d
DATABASE_INCORRECT_PASSWORD = 0x4e

View File

20
network/enums/types.py Normal file
View File

@@ -0,0 +1,20 @@
SIZEOF_CHAR = 1
SIZEOF_SHORT = 2
SIZEOF_INT = 4
SIZEOF_LONG = 4
SIZEOF_LONG_LONG = 8
SIZEOF_FLOAT = 4
SIZEOF_DOUBLE = 8
MAX_CHAR = 0x7F
MAX_UCHAR = 0xFF
MAX_SHORT = 0x7FFF
MAX_USHORT = 0xFFFF
MAX_INT = 0x7FFFFFFF
MAX_UINT = 0xFFFFFFFF # 1 << SIZEOF_INT * 8 - 1 (I had a dream of doing it this way.. but Robin said no >.>)
MAX_LONG = 0x7FFFFFFF
MAX_ULONG = 0xFFFFFFFF
MAX_LONG_LONG = 0x7FFFFFFFFFFFFFFF
MAX_ULONG_LONG = 0xFFFFFFFFFFFFFFFF