From d9494ccf1ea9178ce93dbb2374bddd221d8650e6 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Thu, 19 Sep 2013 21:35:33 +0200 Subject: ProtoProxy: Removed the per-packet sleep from the DEBUG version. It is now enabled by defining a macro, by default off. --- Tools/ProtoProxy/Connection.cpp | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) (limited to 'Tools') diff --git a/Tools/ProtoProxy/Connection.cpp b/Tools/ProtoProxy/Connection.cpp index e985c2ff6..aa4dde977 100644 --- a/Tools/ProtoProxy/Connection.cpp +++ b/Tools/ProtoProxy/Connection.cpp @@ -15,7 +15,14 @@ -#ifdef _DEBUG +/// When defined, the following macro causes a sleep after each parsed packet (DEBUG-mode only) +// #define SLEEP_AFTER_PACKET + + + + + +#if defined(_DEBUG) && defined(SLEEP_AFTER_PACKET) #define DebugSleep Sleep #else #define DebugSleep(X) @@ -299,7 +306,7 @@ void cConnection::Run(void) Log("Cannot connect to server; aborting"); return; } - + while (true) { fd_set ReadFDs; -- cgit v1.2.3 From 19bfab9eca655ce1637f72910c3e1dcc9ab1b138 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Thu, 19 Sep 2013 21:51:59 +0200 Subject: ProtoProxy: Added handling for the Explosion packet. This will help #129. --- Tools/ProtoProxy/Connection.cpp | 45 +++++++++++++++++++++++++++++++++++++++++ Tools/ProtoProxy/Connection.h | 1 + 2 files changed, 46 insertions(+) (limited to 'Tools') diff --git a/Tools/ProtoProxy/Connection.cpp b/Tools/ProtoProxy/Connection.cpp index aa4dde977..c4776949e 100644 --- a/Tools/ProtoProxy/Connection.cpp +++ b/Tools/ProtoProxy/Connection.cpp @@ -189,6 +189,7 @@ enum PACKET_BLOCK_CHANGE = 0x35, PACKET_BLOCK_ACTION = 0x36, PACKET_MAP_CHUNK_BULK = 0x38, + PACKET_EXPLOSION = 0x3c, PACKET_SOUND_EFFECT = 0x3d, PACKET_NAMED_SOUND_EFFECT = 0x3e, PACKET_CHANGE_GAME_STATE = 0x46, @@ -701,6 +702,7 @@ bool cConnection::DecodeServersPackets(const char * a_Data, int a_Size) case PACKET_ENTITY_STATUS: HANDLE_SERVER_READ(HandleServerEntityStatus); break; case PACKET_ENTITY_TELEPORT: HANDLE_SERVER_READ(HandleServerEntityTeleport); break; case PACKET_ENTITY_VELOCITY: HANDLE_SERVER_READ(HandleServerEntityVelocity); break; + case PACKET_EXPLOSION: HANDLE_SERVER_READ(HandleServerExplosion); break; case PACKET_INCREMENT_STATISTIC: HANDLE_SERVER_READ(HandleServerIncrementStatistic); break; case PACKET_KEEPALIVE: HANDLE_SERVER_READ(HandleServerKeepAlive); break; case PACKET_KICK: HANDLE_SERVER_READ(HandleServerKick); break; @@ -1593,6 +1595,49 @@ bool cConnection::HandleServerEntityVelocity(void) +bool cConnection::HandleServerExplosion(void) +{ + HANDLE_SERVER_PACKET_READ(ReadBEDouble, double, PosX); + HANDLE_SERVER_PACKET_READ(ReadBEDouble, double, PosY); + HANDLE_SERVER_PACKET_READ(ReadBEDouble, double, PosZ); + HANDLE_SERVER_PACKET_READ(ReadBEFloat, float, Force); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, NumRecords); + struct sCoords + { + int x, y, z; + + sCoords(int a_X, int a_Y, int a_Z) : x(a_X), y(a_Y), z(a_Z) {} + } ; + std::vector Records; + Records.reserve(NumRecords); + int PosXI = (int)PosX, PosYI = (int)PosY, PosZI = (int)PosZ; + for (int i = 0; i < NumRecords; i++) + { + HANDLE_SERVER_PACKET_READ(ReadChar, char, rx); + HANDLE_SERVER_PACKET_READ(ReadChar, char, ry); + HANDLE_SERVER_PACKET_READ(ReadChar, char, rz); + Records.push_back(sCoords(PosXI + rx, PosYI + ry, PosZI + rz)); + } + HANDLE_SERVER_PACKET_READ(ReadBEFloat, float, PlayerMotionX); + HANDLE_SERVER_PACKET_READ(ReadBEFloat, float, PlayerMotionY); + HANDLE_SERVER_PACKET_READ(ReadBEFloat, float, PlayerMotionZ); + Log("Received a PACKET_EXPLOSION from the server:"); + Log(" Pos = {%.02f, %.02f, %.02f}", PosX, PosY, PosZ); + Log(" Force = %.02f", Force); + Log(" NumRecords = %d", NumRecords); + for (int i = 0; i < NumRecords; i++) + { + Log(" Records[%d] = {%d, %d, %d}", i, Records[i].x, Records[i].y, Records[i].z); + } + Log(" Player motion = <%.02f, %.02f, %.02f>", PlayerMotionX, PlayerMotionY, PlayerMotionZ); + COPY_TO_CLIENT(); + return true; +} + + + + + bool cConnection::HandleServerIncrementStatistic(void) { // 0xc8 diff --git a/Tools/ProtoProxy/Connection.h b/Tools/ProtoProxy/Connection.h index c30a28727..6093408d6 100644 --- a/Tools/ProtoProxy/Connection.h +++ b/Tools/ProtoProxy/Connection.h @@ -158,6 +158,7 @@ protected: bool HandleServerEntityStatus(void); bool HandleServerEntityTeleport(void); bool HandleServerEntityVelocity(void); + bool HandleServerExplosion(void); bool HandleServerIncrementStatistic(void); bool HandleServerKeepAlive(void); bool HandleServerKick(void); -- cgit v1.2.3 From b88a70963cedda7b4a0da81d6083ca59b71790ec Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Fri, 11 Oct 2013 12:53:05 +0200 Subject: Updated BiomeVisualiser to compile again. --- Tools/BiomeVisualiser/.gitignore | 3 +++ Tools/BiomeVisualiser/BiomeViewWnd.cpp | 2 +- Tools/BiomeVisualiser/BiomeVisualiser.vcproj | 28 ++++++++++++++++++++-------- 3 files changed, 24 insertions(+), 9 deletions(-) create mode 100644 Tools/BiomeVisualiser/.gitignore (limited to 'Tools') diff --git a/Tools/BiomeVisualiser/.gitignore b/Tools/BiomeVisualiser/.gitignore new file mode 100644 index 000000000..b4e15dc3c --- /dev/null +++ b/Tools/BiomeVisualiser/.gitignore @@ -0,0 +1,3 @@ +Debug/ +logs/ +Release/ diff --git a/Tools/BiomeVisualiser/BiomeViewWnd.cpp b/Tools/BiomeVisualiser/BiomeViewWnd.cpp index 3dd1bb4e0..7d4db58c0 100644 --- a/Tools/BiomeVisualiser/BiomeViewWnd.cpp +++ b/Tools/BiomeVisualiser/BiomeViewWnd.cpp @@ -45,7 +45,7 @@ bool cBiomeViewWnd::Create(HWND a_ParentWnd, LPCTSTR a_Title) cIniFile IniFile; cBiomeGen * BioGen = new cBioGenMultiStepMap(2); - BioGen->Initialize(IniFile); + BioGen->InitializeBiomeGen(IniFile); m_Renderer.SetSource(new cGeneratorBiomeSource(BioGen)); return true; diff --git a/Tools/BiomeVisualiser/BiomeVisualiser.vcproj b/Tools/BiomeVisualiser/BiomeVisualiser.vcproj index 522606d60..5f840129d 100644 --- a/Tools/BiomeVisualiser/BiomeVisualiser.vcproj +++ b/Tools/BiomeVisualiser/BiomeVisualiser.vcproj @@ -331,6 +331,22 @@ RelativePath="..\..\source\ChunkDef.h" > + + + + + + + + @@ -363,6 +379,10 @@ RelativePath="..\..\source\Globals.h" > + + @@ -434,14 +454,6 @@ RelativePath="..\..\source\OSSupport\IsThread.h" > - - - - -- cgit v1.2.3 From 4fdb1c1aafcede34bb496bdc8425d300fe619df6 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Sat, 12 Oct 2013 11:27:06 +0200 Subject: BiomeVisualiser: fixed crash at shutdown caused by bad logging --- Tools/BiomeVisualiser/BiomeVisualiser.cpp | 4 ++-- Tools/BiomeVisualiser/BiomeVisualiser.h | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) (limited to 'Tools') diff --git a/Tools/BiomeVisualiser/BiomeVisualiser.cpp b/Tools/BiomeVisualiser/BiomeVisualiser.cpp index e1d379f83..a36111d77 100644 --- a/Tools/BiomeVisualiser/BiomeVisualiser.cpp +++ b/Tools/BiomeVisualiser/BiomeVisualiser.cpp @@ -21,8 +21,8 @@ int WINAPI WinMain(HINSTANCE a_Instance, HINSTANCE a_PrevInstance, LPSTR a_CmdLi -cBiomeVisualiser::cBiomeVisualiser(void) - // : m_Logger(Printf("BiomeVisualiser_%08x", time(NULL))) +cBiomeVisualiser::cBiomeVisualiser(void) : + m_Logger(new cMCLogger(Printf("BiomeVisualiser_%08x.log", time(NULL)))) { } diff --git a/Tools/BiomeVisualiser/BiomeVisualiser.h b/Tools/BiomeVisualiser/BiomeVisualiser.h index 3fa90646b..4f8ce7513 100644 --- a/Tools/BiomeVisualiser/BiomeVisualiser.h +++ b/Tools/BiomeVisualiser/BiomeVisualiser.h @@ -23,7 +23,7 @@ public: protected: cBiomeViewWnd m_MainWnd; - cMCLogger m_Logger; + cMCLogger * m_Logger; } ; -- cgit v1.2.3 From fd85ac23c1160910042c0887ea7e4e3460d1cb71 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Mon, 28 Oct 2013 21:12:49 +0100 Subject: ProtoProxy: Fixed compilation after the previous cByteBuffer changes. --- Tools/ProtoProxy/Globals.h | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'Tools') diff --git a/Tools/ProtoProxy/Globals.h b/Tools/ProtoProxy/Globals.h index 3b154b866..8424aca81 100644 --- a/Tools/ProtoProxy/Globals.h +++ b/Tools/ProtoProxy/Globals.h @@ -70,6 +70,10 @@ typedef long long Int64; typedef int Int32; typedef short Int16; +typedef unsigned long long UInt64; +typedef unsigned int UInt32; +typedef unsigned short UInt16; + -- cgit v1.2.3 From fe82ada08459578556adb3b304ea548d8a2db936 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Mon, 28 Oct 2013 23:05:53 +0100 Subject: ProtoProxy: Implemented 1.7.2 status request / response / ping. --- Tools/ProtoProxy/Connection.cpp | 378 ++++++++++++++++++++++++++++------------ Tools/ProtoProxy/Connection.h | 7 + 2 files changed, 272 insertions(+), 113 deletions(-) (limited to 'Tools') diff --git a/Tools/ProtoProxy/Connection.cpp b/Tools/ProtoProxy/Connection.cpp index c4776949e..b22e61816 100644 --- a/Tools/ProtoProxy/Connection.cpp +++ b/Tools/ProtoProxy/Connection.cpp @@ -144,15 +144,20 @@ typedef unsigned char Byte; enum { - PACKET_KEEPALIVE = 0x00, - PACKET_LOGIN = 0x01, - PACKET_HANDSHAKE = 0x02, - PACKET_CHAT_MESSAGE = 0x03, - PACKET_TIME_UPDATE = 0x04, - PACKET_ENTITY_EQUIPMENT = 0x05, - PACKET_COMPASS = 0x06, + // client-bound packets: + PACKET_C_KEEPALIVE = 0x00, + PACKET_C_JOIN_GAME = 0x01, + PACKET_C_CHAT_MESSAGE = 0x02, + + // server-bound packets: + PACKET_S_KEEPALIVE = 0x00, // Also the initial handshake, as the very first packet + PACKET_S_CHAT_MESSAGE = 0x01, + + PACKET_TIME_UPDATE = 0x03, + PACKET_ENTITY_EQUIPMENT = 0x04, + PACKET_SPAWN_POSITION = 0x05, + PACKET_UPDATE_HEALTH = 0x06, PACKET_USE_ENTITY = 0x07, - PACKET_UPDATE_HEALTH = 0x08, PACKET_PLAYER_ON_GROUND = 0x0a, PACKET_PLAYER_POSITION = 0x0b, PACKET_PLAYER_LOOK = 0x0c, @@ -270,7 +275,8 @@ cConnection::cConnection(SOCKET a_ClientSocket, cServer & a_Server) : m_Nonce(0), m_ClientBuffer(1024 KiB), m_ServerBuffer(1024 KiB), - m_HasClientPinged(false) + m_HasClientPinged(false), + m_ProtocolState(-1) { // Create the Logs subfolder, if not already created: #if defined(_WIN32) @@ -279,7 +285,7 @@ cConnection::cConnection(SOCKET a_ClientSocket, cServer & a_Server) : mkdir("Logs", 0777); #endif - Printf(m_LogNameBase, "Logs/Log_%d", (int)time(NULL)); + Printf(m_LogNameBase, "Logs/Log_%d_%d", (int)time(NULL), a_ClientSocket); AString fnam(m_LogNameBase); fnam.append(".log"); m_LogFile = fopen(fnam.c_str(), "w"); @@ -517,7 +523,7 @@ double cConnection::GetRelativeTime(void) bool cConnection::SendData(SOCKET a_Socket, const char * a_Data, int a_Size, const char * a_Peer) { - DataLog(a_Data, a_Size, "Sending data to %s", a_Peer); + DataLog(a_Data, a_Size, "Sending data to %s, %d bytes", a_Peer, a_Size); int res = send(a_Socket, a_Data, a_Size, 0); if (res <= 0) @@ -590,38 +596,77 @@ bool cConnection::DecodeClientsPackets(const char * a_Data, int a_Size) while (m_ClientBuffer.CanReadBytes(1)) { - unsigned char PacketType; - m_ClientBuffer.ReadByte(PacketType); - Log("Decoding client's packets, there are now %d bytes in the queue; next packet is 0x%02x", m_ClientBuffer.GetReadableSpace(), PacketType); - switch (PacketType) + UInt32 PacketLen; + if ( + !m_ClientBuffer.ReadVarInt(PacketLen) || + !m_ClientBuffer.CanReadBytes(PacketLen) + ) { - case PACKET_BLOCK_DIG: HANDLE_CLIENT_READ(HandleClientBlockDig); break; - case PACKET_BLOCK_PLACE: HANDLE_CLIENT_READ(HandleClientBlockPlace); break; - case PACKET_CHAT_MESSAGE: HANDLE_CLIENT_READ(HandleClientChatMessage); break; - case PACKET_CLIENT_STATUSES: HANDLE_CLIENT_READ(HandleClientClientStatuses); break; - case PACKET_CREATIVE_INVENTORY_ACTION: HANDLE_CLIENT_READ(HandleClientCreativeInventoryAction); break; - case PACKET_DISCONNECT: HANDLE_CLIENT_READ(HandleClientDisconnect); break; - case PACKET_ENCRYPTION_KEY_RESPONSE: HANDLE_CLIENT_READ(HandleClientEncryptionKeyResponse); break; - case PACKET_ENTITY_ACTION: HANDLE_CLIENT_READ(HandleClientEntityAction); break; - case PACKET_HANDSHAKE: HANDLE_CLIENT_READ(HandleClientHandshake); break; - case PACKET_KEEPALIVE: HANDLE_CLIENT_READ(HandleClientKeepAlive); break; - case PACKET_LOCALE_AND_VIEW: HANDLE_CLIENT_READ(HandleClientLocaleAndView); break; - case PACKET_PING: HANDLE_CLIENT_READ(HandleClientPing); break; - case PACKET_PLAYER_ABILITIES: HANDLE_CLIENT_READ(HandleClientPlayerAbilities); break; - case PACKET_PLAYER_ANIMATION: HANDLE_CLIENT_READ(HandleClientAnimation); break; - case PACKET_PLAYER_LOOK: HANDLE_CLIENT_READ(HandleClientPlayerLook); break; - case PACKET_PLAYER_ON_GROUND: HANDLE_CLIENT_READ(HandleClientPlayerOnGround); break; - case PACKET_PLAYER_POSITION: HANDLE_CLIENT_READ(HandleClientPlayerPosition); break; - case PACKET_PLAYER_POSITION_LOOK: HANDLE_CLIENT_READ(HandleClientPlayerPositionLook); break; - case PACKET_PLUGIN_MESSAGE: HANDLE_CLIENT_READ(HandleClientPluginMessage); break; - case PACKET_SLOT_SELECT: HANDLE_CLIENT_READ(HandleClientSlotSelect); break; - case PACKET_TAB_COMPLETION: HANDLE_CLIENT_READ(HandleClientTabCompletion); break; - case PACKET_UPDATE_SIGN: HANDLE_CLIENT_READ(HandleClientUpdateSign); break; - case PACKET_USE_ENTITY: HANDLE_CLIENT_READ(HandleClientUseEntity); break; - case PACKET_WINDOW_CLICK: HANDLE_CLIENT_READ(HandleClientWindowClick); break; - case PACKET_WINDOW_CLOSE: HANDLE_CLIENT_READ(HandleClientWindowClose); break; + // Not a complete packet yet + break; + } + UInt32 PacketType; + VERIFY(m_ClientBuffer.ReadVarInt(PacketType)); + Log("Decoding client's packets, there are now %d bytes in the queue; next packet is 0x%0x, %u bytes long", m_ClientBuffer.GetReadableSpace(), PacketType, PacketLen); + switch (m_ProtocolState) + { + case -1: + { + // No initial handshake received yet + switch (PacketType) + { + case 0: HANDLE_CLIENT_READ(HandleClientHandshake); break; + } + break; + } // case -1 + + case 1: + { + // Status query + switch (PacketType) + { + case 0: HANDLE_CLIENT_READ(HandleClientStatusRequest); break; + case 1: HANDLE_CLIENT_READ(HandleClientStatusPing); break; + } + break; + } + + case 2: + { + // Login / game + switch (PacketType) + { + case PACKET_BLOCK_DIG: HANDLE_CLIENT_READ(HandleClientBlockDig); break; + case PACKET_BLOCK_PLACE: HANDLE_CLIENT_READ(HandleClientBlockPlace); break; + case PACKET_S_CHAT_MESSAGE: HANDLE_CLIENT_READ(HandleClientChatMessage); break; + case PACKET_CLIENT_STATUSES: HANDLE_CLIENT_READ(HandleClientClientStatuses); break; + case PACKET_CREATIVE_INVENTORY_ACTION: HANDLE_CLIENT_READ(HandleClientCreativeInventoryAction); break; + case PACKET_DISCONNECT: HANDLE_CLIENT_READ(HandleClientDisconnect); break; + case PACKET_ENCRYPTION_KEY_RESPONSE: HANDLE_CLIENT_READ(HandleClientEncryptionKeyResponse); break; + case PACKET_ENTITY_ACTION: HANDLE_CLIENT_READ(HandleClientEntityAction); break; + case PACKET_S_KEEPALIVE: HANDLE_CLIENT_READ(HandleClientKeepAlive); break; + case PACKET_LOCALE_AND_VIEW: HANDLE_CLIENT_READ(HandleClientLocaleAndView); break; + case PACKET_PING: HANDLE_CLIENT_READ(HandleClientPing); break; + case PACKET_PLAYER_ABILITIES: HANDLE_CLIENT_READ(HandleClientPlayerAbilities); break; + case PACKET_PLAYER_ANIMATION: HANDLE_CLIENT_READ(HandleClientAnimation); break; + case PACKET_PLAYER_LOOK: HANDLE_CLIENT_READ(HandleClientPlayerLook); break; + case PACKET_PLAYER_ON_GROUND: HANDLE_CLIENT_READ(HandleClientPlayerOnGround); break; + case PACKET_PLAYER_POSITION: HANDLE_CLIENT_READ(HandleClientPlayerPosition); break; + case PACKET_PLAYER_POSITION_LOOK: HANDLE_CLIENT_READ(HandleClientPlayerPositionLook); break; + case PACKET_PLUGIN_MESSAGE: HANDLE_CLIENT_READ(HandleClientPluginMessage); break; + case PACKET_SLOT_SELECT: HANDLE_CLIENT_READ(HandleClientSlotSelect); break; + case PACKET_TAB_COMPLETION: HANDLE_CLIENT_READ(HandleClientTabCompletion); break; + case PACKET_UPDATE_SIGN: HANDLE_CLIENT_READ(HandleClientUpdateSign); break; + case PACKET_USE_ENTITY: HANDLE_CLIENT_READ(HandleClientUseEntity); break; + case PACKET_WINDOW_CLICK: HANDLE_CLIENT_READ(HandleClientWindowClick); break; + case PACKET_WINDOW_CLOSE: HANDLE_CLIENT_READ(HandleClientWindowClose); break; + } + break; + } // case 2 + default: { + // TODO: Move this elsewhere if (m_ClientState == csEncryptedUnderstood) { Log("****************** Unknown packet 0x%02x from the client while encrypted; continuing to relay blind only", PacketType); @@ -646,10 +691,10 @@ bool cConnection::DecodeClientsPackets(const char * a_Data, int a_Size) Log("Unknown packet 0x%02x from the client while unencrypted; aborting connection", PacketType); return false; } - } - } // switch (PacketType) + } // default + } // switch (m_ProtocolState) m_ClientBuffer.CommitRead(); - } // while (CanReadBytes(1)) + } // while (true) return true; } @@ -673,66 +718,102 @@ bool cConnection::DecodeServersPackets(const char * a_Data, int a_Size) // Client hasn't finished encryption handshake yet, don't send them any data yet } - while (m_ServerBuffer.CanReadBytes(1)) + while (true) { - unsigned char PacketType; - m_ServerBuffer.ReadByte(PacketType); - Log("Decoding server's packets, there are now %d bytes in the queue; next packet is 0x%02x", m_ServerBuffer.GetReadableSpace(), PacketType); + UInt32 PacketLen; + if ( + !m_ServerBuffer.ReadVarInt(PacketLen) || + !m_ServerBuffer.CanReadBytes(PacketLen) + ) + { + // Not a complete packet yet + break; + } + UInt32 PacketType; + VERIFY(m_ServerBuffer.ReadVarInt(PacketType)); + Log("Decoding server's packets, there are now %d bytes in the queue; next packet is 0x%0x, %u bytes long", m_ServerBuffer.GetReadableSpace(), PacketType, PacketLen); LogFlush(); - switch (PacketType) + switch (m_ProtocolState) { - case PACKET_ATTACH_ENTITY: HANDLE_SERVER_READ(HandleServerAttachEntity); break; - case PACKET_BLOCK_ACTION: HANDLE_SERVER_READ(HandleServerBlockAction); break; - case PACKET_BLOCK_CHANGE: HANDLE_SERVER_READ(HandleServerBlockChange); break; - case PACKET_CHANGE_GAME_STATE: HANDLE_SERVER_READ(HandleServerChangeGameState); break; - case PACKET_CHAT_MESSAGE: HANDLE_SERVER_READ(HandleServerChatMessage); break; - case PACKET_COLLECT_PICKUP: HANDLE_SERVER_READ(HandleServerCollectPickup); break; - case PACKET_COMPASS: HANDLE_SERVER_READ(HandleServerCompass); break; - case PACKET_DESTROY_ENTITIES: HANDLE_SERVER_READ(HandleServerDestroyEntities); break; - case PACKET_ENCRYPTION_KEY_REQUEST: HANDLE_SERVER_READ(HandleServerEncryptionKeyRequest); break; - case PACKET_ENCRYPTION_KEY_RESPONSE: HANDLE_SERVER_READ(HandleServerEncryptionKeyResponse); break; - case PACKET_ENTITY: HANDLE_SERVER_READ(HandleServerEntity); break; - case PACKET_ENTITY_EQUIPMENT: HANDLE_SERVER_READ(HandleServerEntityEquipment); break; - case PACKET_ENTITY_HEAD_LOOK: HANDLE_SERVER_READ(HandleServerEntityHeadLook); break; - case PACKET_ENTITY_LOOK: HANDLE_SERVER_READ(HandleServerEntityLook); break; - case PACKET_ENTITY_METADATA: HANDLE_SERVER_READ(HandleServerEntityMetadata); break; - case PACKET_ENTITY_PROPERTIES: HANDLE_SERVER_READ(HandleServerEntityProperties); break; - case PACKET_ENTITY_RELATIVE_MOVE: HANDLE_SERVER_READ(HandleServerEntityRelativeMove); break; - case PACKET_ENTITY_RELATIVE_MOVE_LOOK: HANDLE_SERVER_READ(HandleServerEntityRelativeMoveLook); break; - case PACKET_ENTITY_STATUS: HANDLE_SERVER_READ(HandleServerEntityStatus); break; - case PACKET_ENTITY_TELEPORT: HANDLE_SERVER_READ(HandleServerEntityTeleport); break; - case PACKET_ENTITY_VELOCITY: HANDLE_SERVER_READ(HandleServerEntityVelocity); break; - case PACKET_EXPLOSION: HANDLE_SERVER_READ(HandleServerExplosion); break; - case PACKET_INCREMENT_STATISTIC: HANDLE_SERVER_READ(HandleServerIncrementStatistic); break; - case PACKET_KEEPALIVE: HANDLE_SERVER_READ(HandleServerKeepAlive); break; - case PACKET_KICK: HANDLE_SERVER_READ(HandleServerKick); break; - case PACKET_LOGIN: HANDLE_SERVER_READ(HandleServerLogin); break; - case PACKET_MAP_CHUNK: HANDLE_SERVER_READ(HandleServerMapChunk); break; - case PACKET_MAP_CHUNK_BULK: HANDLE_SERVER_READ(HandleServerMapChunkBulk); break; - case PACKET_MULTI_BLOCK_CHANGE: HANDLE_SERVER_READ(HandleServerMultiBlockChange); break; - case PACKET_NAMED_SOUND_EFFECT: HANDLE_SERVER_READ(HandleServerNamedSoundEffect); break; - case PACKET_PLAYER_ABILITIES: HANDLE_SERVER_READ(HandleServerPlayerAbilities); break; - case PACKET_PLAYER_ANIMATION: HANDLE_SERVER_READ(HandleServerPlayerAnimation); break; - case PACKET_PLAYER_LIST_ITEM: HANDLE_SERVER_READ(HandleServerPlayerListItem); break; - case PACKET_PLAYER_POSITION_LOOK: HANDLE_SERVER_READ(HandleServerPlayerPositionLook); break; - case PACKET_PLUGIN_MESSAGE: HANDLE_SERVER_READ(HandleServerPluginMessage); break; - case PACKET_SET_EXPERIENCE: HANDLE_SERVER_READ(HandleServerSetExperience); break; - case PACKET_SET_SLOT: HANDLE_SERVER_READ(HandleServerSetSlot); break; - case PACKET_SLOT_SELECT: HANDLE_SERVER_READ(HandleServerSlotSelect); break; - case PACKET_SOUND_EFFECT: HANDLE_SERVER_READ(HandleServerSoundEffect); break; - case PACKET_SPAWN_MOB: HANDLE_SERVER_READ(HandleServerSpawnMob); break; - case PACKET_SPAWN_NAMED_ENTITY: HANDLE_SERVER_READ(HandleServerSpawnNamedEntity); break; - case PACKET_SPAWN_OBJECT_VEHICLE: HANDLE_SERVER_READ(HandleServerSpawnObjectVehicle); break; - case PACKET_SPAWN_PAINTING: HANDLE_SERVER_READ(HandleServerSpawnPainting); break; - case PACKET_SPAWN_PICKUP: HANDLE_SERVER_READ(HandleServerSpawnPickup); break; - case PACKET_TAB_COMPLETION: HANDLE_SERVER_READ(HandleServerTabCompletion); break; - case PACKET_TIME_UPDATE: HANDLE_SERVER_READ(HandleServerTimeUpdate); break; - case PACKET_UPDATE_HEALTH: HANDLE_SERVER_READ(HandleServerUpdateHealth); break; - case PACKET_UPDATE_SIGN: HANDLE_SERVER_READ(HandleServerUpdateSign); break; - case PACKET_UPDATE_TILE_ENTITY: HANDLE_SERVER_READ(HandleServerUpdateTileEntity); break; - case PACKET_WINDOW_CLOSE: HANDLE_SERVER_READ(HandleServerWindowClose); break; - case PACKET_WINDOW_CONTENTS: HANDLE_SERVER_READ(HandleServerWindowContents); break; - case PACKET_WINDOW_OPEN: HANDLE_SERVER_READ(HandleServerWindowOpen); break; + case -1: + { + Log("Receiving data from the server without an initial handshake message!"); + break; + } + + case 1: + { + // Status query: + switch (PacketType) + { + case 0: HANDLE_SERVER_READ(HandleServerStatusResponse); break; + case 1: HANDLE_SERVER_READ(HandleServerStatusPing); break; + } + break; + } + + case 2: + { + // Login / game: + switch (PacketType) + { + case PACKET_ATTACH_ENTITY: HANDLE_SERVER_READ(HandleServerAttachEntity); break; + case PACKET_BLOCK_ACTION: HANDLE_SERVER_READ(HandleServerBlockAction); break; + case PACKET_BLOCK_CHANGE: HANDLE_SERVER_READ(HandleServerBlockChange); break; + case PACKET_CHANGE_GAME_STATE: HANDLE_SERVER_READ(HandleServerChangeGameState); break; + case PACKET_C_CHAT_MESSAGE: HANDLE_SERVER_READ(HandleServerChatMessage); break; + case PACKET_COLLECT_PICKUP: HANDLE_SERVER_READ(HandleServerCollectPickup); break; + case PACKET_DESTROY_ENTITIES: HANDLE_SERVER_READ(HandleServerDestroyEntities); break; + case PACKET_ENCRYPTION_KEY_REQUEST: HANDLE_SERVER_READ(HandleServerEncryptionKeyRequest); break; + case PACKET_ENCRYPTION_KEY_RESPONSE: HANDLE_SERVER_READ(HandleServerEncryptionKeyResponse); break; + case PACKET_ENTITY: HANDLE_SERVER_READ(HandleServerEntity); break; + case PACKET_ENTITY_EQUIPMENT: HANDLE_SERVER_READ(HandleServerEntityEquipment); break; + case PACKET_ENTITY_HEAD_LOOK: HANDLE_SERVER_READ(HandleServerEntityHeadLook); break; + case PACKET_ENTITY_LOOK: HANDLE_SERVER_READ(HandleServerEntityLook); break; + case PACKET_ENTITY_METADATA: HANDLE_SERVER_READ(HandleServerEntityMetadata); break; + case PACKET_ENTITY_PROPERTIES: HANDLE_SERVER_READ(HandleServerEntityProperties); break; + case PACKET_ENTITY_RELATIVE_MOVE: HANDLE_SERVER_READ(HandleServerEntityRelativeMove); break; + case PACKET_ENTITY_RELATIVE_MOVE_LOOK: HANDLE_SERVER_READ(HandleServerEntityRelativeMoveLook); break; + case PACKET_ENTITY_STATUS: HANDLE_SERVER_READ(HandleServerEntityStatus); break; + case PACKET_ENTITY_TELEPORT: HANDLE_SERVER_READ(HandleServerEntityTeleport); break; + case PACKET_ENTITY_VELOCITY: HANDLE_SERVER_READ(HandleServerEntityVelocity); break; + case PACKET_EXPLOSION: HANDLE_SERVER_READ(HandleServerExplosion); break; + case PACKET_INCREMENT_STATISTIC: HANDLE_SERVER_READ(HandleServerIncrementStatistic); break; + case PACKET_C_JOIN_GAME: HANDLE_SERVER_READ(HandleServerLogin); break; + case PACKET_C_KEEPALIVE: HANDLE_SERVER_READ(HandleServerKeepAlive); break; + case PACKET_KICK: HANDLE_SERVER_READ(HandleServerKick); break; + case PACKET_MAP_CHUNK: HANDLE_SERVER_READ(HandleServerMapChunk); break; + case PACKET_MAP_CHUNK_BULK: HANDLE_SERVER_READ(HandleServerMapChunkBulk); break; + case PACKET_MULTI_BLOCK_CHANGE: HANDLE_SERVER_READ(HandleServerMultiBlockChange); break; + case PACKET_NAMED_SOUND_EFFECT: HANDLE_SERVER_READ(HandleServerNamedSoundEffect); break; + case PACKET_PLAYER_ABILITIES: HANDLE_SERVER_READ(HandleServerPlayerAbilities); break; + case PACKET_PLAYER_ANIMATION: HANDLE_SERVER_READ(HandleServerPlayerAnimation); break; + case PACKET_PLAYER_LIST_ITEM: HANDLE_SERVER_READ(HandleServerPlayerListItem); break; + case PACKET_PLAYER_POSITION_LOOK: HANDLE_SERVER_READ(HandleServerPlayerPositionLook); break; + case PACKET_PLUGIN_MESSAGE: HANDLE_SERVER_READ(HandleServerPluginMessage); break; + case PACKET_SET_EXPERIENCE: HANDLE_SERVER_READ(HandleServerSetExperience); break; + case PACKET_SET_SLOT: HANDLE_SERVER_READ(HandleServerSetSlot); break; + case PACKET_SLOT_SELECT: HANDLE_SERVER_READ(HandleServerSlotSelect); break; + case PACKET_SOUND_EFFECT: HANDLE_SERVER_READ(HandleServerSoundEffect); break; + case PACKET_SPAWN_MOB: HANDLE_SERVER_READ(HandleServerSpawnMob); break; + case PACKET_SPAWN_NAMED_ENTITY: HANDLE_SERVER_READ(HandleServerSpawnNamedEntity); break; + case PACKET_SPAWN_OBJECT_VEHICLE: HANDLE_SERVER_READ(HandleServerSpawnObjectVehicle); break; + case PACKET_SPAWN_PAINTING: HANDLE_SERVER_READ(HandleServerSpawnPainting); break; + case PACKET_SPAWN_PICKUP: HANDLE_SERVER_READ(HandleServerSpawnPickup); break; + case PACKET_SPAWN_POSITION: HANDLE_SERVER_READ(HandleServerCompass); break; + case PACKET_TAB_COMPLETION: HANDLE_SERVER_READ(HandleServerTabCompletion); break; + case PACKET_TIME_UPDATE: HANDLE_SERVER_READ(HandleServerTimeUpdate); break; + case PACKET_UPDATE_HEALTH: HANDLE_SERVER_READ(HandleServerUpdateHealth); break; + case PACKET_UPDATE_SIGN: HANDLE_SERVER_READ(HandleServerUpdateSign); break; + case PACKET_UPDATE_TILE_ENTITY: HANDLE_SERVER_READ(HandleServerUpdateTileEntity); break; + case PACKET_WINDOW_CLOSE: HANDLE_SERVER_READ(HandleServerWindowClose); break; + case PACKET_WINDOW_CONTENTS: HANDLE_SERVER_READ(HandleServerWindowContents); break; + case PACKET_WINDOW_OPEN: HANDLE_SERVER_READ(HandleServerWindowOpen); break; + } // switch (PacketType) + break; + } // case 2 + + // TODO: Move this elsewhere default: { if (m_ServerState == csEncryptedUnderstood) @@ -760,7 +841,8 @@ bool cConnection::DecodeServersPackets(const char * a_Data, int a_Size) return false; } } - } // switch (PacketType) + } // switch (m_ProtocolState) + m_ServerBuffer.CommitRead(); } // while (CanReadBytes(1)) return true; @@ -937,27 +1019,33 @@ bool cConnection::HandleClientEntityAction(void) bool cConnection::HandleClientHandshake(void) { // Read the packet from the client: - HANDLE_CLIENT_PACKET_READ(ReadByte, Byte, ProtocolVersion); - HANDLE_CLIENT_PACKET_READ(ReadBEUTF16String16, AString, Username); - HANDLE_CLIENT_PACKET_READ(ReadBEUTF16String16, AString, ServerHost); - HANDLE_CLIENT_PACKET_READ(ReadBEInt, int, ServerPort); + HANDLE_CLIENT_PACKET_READ(ReadVarInt, UInt32, ProtocolVersion); + HANDLE_CLIENT_PACKET_READ(ReadVarUTF8String, AString, ServerHost); + HANDLE_CLIENT_PACKET_READ(ReadBEShort, short, ServerPort); + HANDLE_CLIENT_PACKET_READ(ReadVarInt, UInt32, NextState); m_ClientBuffer.CommitRead(); - Log("Received a PACKET_HANDSHAKE from the client:"); - Log(" ProtocolVersion = %d", ProtocolVersion); - Log(" Username = \"%s\"", Username.c_str()); + Log("Received an initial handshake packet from the client:"); + Log(" ProtocolVersion = %u", ProtocolVersion); Log(" ServerHost = \"%s\"", ServerHost.c_str()); Log(" ServerPort = %d", ServerPort); + Log(" NextState = %u", NextState); // Send the same packet to the server, but with our port: + cByteBuffer Packet(512); + Packet.WriteVarInt(0); // Packet type - initial handshake + Packet.WriteVarInt(ProtocolVersion); + Packet.WriteVarUTF8String(ServerHost); + Packet.WriteBEShort(m_Server.GetConnectPort()); + Packet.WriteVarInt(NextState); + AString Pkt; + Packet.ReadAll(Pkt); cByteBuffer ToServer(512); - ToServer.WriteByte (PACKET_HANDSHAKE); - ToServer.WriteByte (ProtocolVersion); - ToServer.WriteBEUTF16String16(Username); - ToServer.WriteBEUTF16String16(ServerHost); - ToServer.WriteBEInt (m_Server.GetConnectPort()); + ToServer.WriteVarUTF8String(Pkt); SERVERSEND(ToServer); + m_ProtocolState = (int)NextState; + return true; } @@ -1124,6 +1212,30 @@ bool cConnection::HandleClientSlotSelect(void) +bool cConnection::HandleClientStatusPing(void) +{ + HANDLE_CLIENT_PACKET_READ(ReadBEInt64, Int64, Time); + Log("Received the status ping packet from the client:"); + Log(" Time = %lld", Time); + COPY_TO_SERVER(); + return true; +} + + + + + +bool cConnection::HandleClientStatusRequest(void) +{ + Log("Received the status request packet from the client"); + COPY_TO_SERVER(); + return true; +} + + + + + bool cConnection::HandleClientTabCompletion(void) { HANDLE_CLIENT_PACKET_READ(ReadBEUTF16String16, AString, Query); @@ -2267,6 +2379,46 @@ bool cConnection::HandleServerSpawnPickup(void) +bool cConnection::HandleServerStatusPing(void) +{ + HANDLE_SERVER_PACKET_READ(ReadBEInt64, Int64, Time); + Log("Received server's ping response:"); + Log(" Time = %lld", Time); + COPY_TO_CLIENT(); + return true; +} + + + + + +bool cConnection::HandleServerStatusResponse(void) +{ + HANDLE_SERVER_PACKET_READ(ReadVarUTF8String, AString, Response); + Log("Received server's status response:"); + Log(" Response: %s", Response.c_str()); + + // Modify the response to show that it's being proto-proxied: + size_t idx = Response.find("\"description\":\""); + if (idx != AString::npos) + { + Response.assign(Response.substr(0, idx + 15) + "ProtoProxy: " + Response.substr(idx + 15)); + } + cByteBuffer Packet(1000); + Packet.WriteVarInt(0); // Packet type - status response + Packet.WriteVarUTF8String(Response); + AString Pkt; + Packet.ReadAll(Pkt); + cByteBuffer ToClient(1000); + ToClient.WriteVarUTF8String(Pkt); + CLIENTSEND(ToClient); + return true; +} + + + + + bool cConnection::HandleServerTabCompletion(void) { HANDLE_SERVER_PACKET_READ(ReadBEUTF16String16, AString, Results); diff --git a/Tools/ProtoProxy/Connection.h b/Tools/ProtoProxy/Connection.h index 6093408d6..d1006c95a 100644 --- a/Tools/ProtoProxy/Connection.h +++ b/Tools/ProtoProxy/Connection.h @@ -79,6 +79,9 @@ protected: /// Set to true when PACKET_PING is received from the client; will cause special parsing for server kick bool m_HasClientPinged; + + /// State the protocol is in (as defined by the initial handshake), -1 if no initial handshake received yet + int m_ProtocolState; bool ConnectToServer(void); @@ -130,6 +133,8 @@ protected: bool HandleClientPlayerPositionLook(void); bool HandleClientPluginMessage(void); bool HandleClientSlotSelect(void); + bool HandleClientStatusPing(void); + bool HandleClientStatusRequest(void); bool HandleClientTabCompletion(void); bool HandleClientUpdateSign(void); bool HandleClientUseEntity(void); @@ -181,6 +186,8 @@ protected: bool HandleServerSpawnObjectVehicle(void); bool HandleServerSpawnPainting(void); bool HandleServerSpawnPickup(void); + bool HandleServerStatusPing(void); + bool HandleServerStatusResponse(void); bool HandleServerTabCompletion(void); bool HandleServerTimeUpdate(void); bool HandleServerUpdateHealth(void); -- cgit v1.2.3 From 21192e5eada7bd1606bedd81a2306d4e801de742 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Tue, 29 Oct 2013 15:47:22 +0100 Subject: ProtoProxy: The login part of the protocol is implemented. --- Tools/ProtoProxy/Connection.cpp | 401 +++++++++++++++++++--------------------- Tools/ProtoProxy/Connection.h | 48 +++-- 2 files changed, 229 insertions(+), 220 deletions(-) (limited to 'Tools') diff --git a/Tools/ProtoProxy/Connection.cpp b/Tools/ProtoProxy/Connection.cpp index b22e61816..4b3442858 100644 --- a/Tools/ProtoProxy/Connection.cpp +++ b/Tools/ProtoProxy/Connection.cpp @@ -52,7 +52,7 @@ #define CLIENTSEND(...) SendData(m_ClientSocket, __VA_ARGS__, "Client") #define SERVERSEND(...) SendData(m_ServerSocket, __VA_ARGS__, "Server") -#define CLIENTENCRYPTSEND(...) SendEncryptedData(m_ClientSocket, m_ClientEncryptor, __VA_ARGS__, "Client") +#define CLIENTENCRYPTSEND(...) SendData(m_ClientSocket, __VA_ARGS__, "Client") // The client conn is always unencrypted #define SERVERENCRYPTSEND(...) SendEncryptedData(m_ServerSocket, m_ServerEncryptor, __VA_ARGS__, "Server") #define COPY_TO_SERVER() \ @@ -99,12 +99,13 @@ CLIENTENCRYPTSEND(ToClient.data(), ToClient.size()); \ break; \ } \ - case csWaitingForEncryption: \ + /* case csWaitingForEncryption: \ { \ Log("Waiting for client encryption, queued %u bytes", ToClient.size()); \ m_ClientEncryptionBuffer.append(ToClient.data(), ToClient.size()); \ break; \ } \ + */ \ } \ DebugSleep(50); \ } @@ -276,7 +277,9 @@ cConnection::cConnection(SOCKET a_ClientSocket, cServer & a_Server) : m_ClientBuffer(1024 KiB), m_ServerBuffer(1024 KiB), m_HasClientPinged(false), - m_ProtocolState(-1) + m_ServerProtocolState(-1), + m_ClientProtocolState(-1), + m_IsServerEncrypted(false) { // Create the Logs subfolder, if not already created: #if defined(_WIN32) @@ -459,7 +462,6 @@ bool cConnection::RelayFromServer(void) { m_ServerDecryptor.ProcessData((byte *)Buffer, (byte *)Buffer, res); DataLog(Buffer, res, "Decrypted %d bytes from the SERVER", res); - m_ClientEncryptor.ProcessData((byte *)Buffer, (byte *)Buffer, res); return CLIENTSEND(Buffer, res); } } @@ -492,13 +494,10 @@ bool cConnection::RelayFromClient(void) } case csEncryptedUnderstood: { - m_ClientDecryptor.ProcessData((byte *)Buffer, (byte *)Buffer, res); - DataLog(Buffer, res, "Decrypted %d bytes from the CLIENT", res); return DecodeClientsPackets(Buffer, res); } case csEncryptedUnknown: { - m_ClientDecryptor.ProcessData((byte *)Buffer, (byte *)Buffer, res); DataLog(Buffer, res, "Decrypted %d bytes from the CLIENT", res); m_ServerEncryptor.ProcessData((byte *)Buffer, (byte *)Buffer, res); return SERVERSEND(Buffer, res); @@ -608,7 +607,7 @@ bool cConnection::DecodeClientsPackets(const char * a_Data, int a_Size) UInt32 PacketType; VERIFY(m_ClientBuffer.ReadVarInt(PacketType)); Log("Decoding client's packets, there are now %d bytes in the queue; next packet is 0x%0x, %u bytes long", m_ClientBuffer.GetReadableSpace(), PacketType, PacketLen); - switch (m_ProtocolState) + switch (m_ClientProtocolState) { case -1: { @@ -625,15 +624,26 @@ bool cConnection::DecodeClientsPackets(const char * a_Data, int a_Size) // Status query switch (PacketType) { - case 0: HANDLE_CLIENT_READ(HandleClientStatusRequest); break; - case 1: HANDLE_CLIENT_READ(HandleClientStatusPing); break; + case 0x00: HANDLE_CLIENT_READ(HandleClientStatusRequest); break; + case 0x01: HANDLE_CLIENT_READ(HandleClientStatusPing); break; } break; } case 2: { - // Login / game + // Login + switch (PacketType) + { + case 0x00: HANDLE_CLIENT_READ(HandleClientLoginStart); break; + case 0x01: HANDLE_CLIENT_READ(HandleClientLoginEncryptionKeyResponse); break; + } + break; + } + + case 3: + { + // Game: switch (PacketType) { case PACKET_BLOCK_DIG: HANDLE_CLIENT_READ(HandleClientBlockDig); break; @@ -642,7 +652,6 @@ bool cConnection::DecodeClientsPackets(const char * a_Data, int a_Size) case PACKET_CLIENT_STATUSES: HANDLE_CLIENT_READ(HandleClientClientStatuses); break; case PACKET_CREATIVE_INVENTORY_ACTION: HANDLE_CLIENT_READ(HandleClientCreativeInventoryAction); break; case PACKET_DISCONNECT: HANDLE_CLIENT_READ(HandleClientDisconnect); break; - case PACKET_ENCRYPTION_KEY_RESPONSE: HANDLE_CLIENT_READ(HandleClientEncryptionKeyResponse); break; case PACKET_ENTITY_ACTION: HANDLE_CLIENT_READ(HandleClientEntityAction); break; case PACKET_S_KEEPALIVE: HANDLE_CLIENT_READ(HandleClientKeepAlive); break; case PACKET_LOCALE_AND_VIEW: HANDLE_CLIENT_READ(HandleClientLocaleAndView); break; @@ -733,7 +742,7 @@ bool cConnection::DecodeServersPackets(const char * a_Data, int a_Size) VERIFY(m_ServerBuffer.ReadVarInt(PacketType)); Log("Decoding server's packets, there are now %d bytes in the queue; next packet is 0x%0x, %u bytes long", m_ServerBuffer.GetReadableSpace(), PacketType, PacketLen); LogFlush(); - switch (m_ProtocolState) + switch (m_ServerProtocolState) { case -1: { @@ -754,18 +763,30 @@ bool cConnection::DecodeServersPackets(const char * a_Data, int a_Size) case 2: { - // Login / game: + // Login: switch (PacketType) { - case PACKET_ATTACH_ENTITY: HANDLE_SERVER_READ(HandleServerAttachEntity); break; - case PACKET_BLOCK_ACTION: HANDLE_SERVER_READ(HandleServerBlockAction); break; - case PACKET_BLOCK_CHANGE: HANDLE_SERVER_READ(HandleServerBlockChange); break; - case PACKET_CHANGE_GAME_STATE: HANDLE_SERVER_READ(HandleServerChangeGameState); break; - case PACKET_C_CHAT_MESSAGE: HANDLE_SERVER_READ(HandleServerChatMessage); break; - case PACKET_COLLECT_PICKUP: HANDLE_SERVER_READ(HandleServerCollectPickup); break; - case PACKET_DESTROY_ENTITIES: HANDLE_SERVER_READ(HandleServerDestroyEntities); break; - case PACKET_ENCRYPTION_KEY_REQUEST: HANDLE_SERVER_READ(HandleServerEncryptionKeyRequest); break; - case PACKET_ENCRYPTION_KEY_RESPONSE: HANDLE_SERVER_READ(HandleServerEncryptionKeyResponse); break; + case 0x00: HANDLE_SERVER_READ(HandleServerLoginDisconnect); break; + case 0x01: HANDLE_SERVER_READ(HandleServerLoginEncryptionKeyRequest); break; + case 0x02: HANDLE_SERVER_READ(HandleServerLoginSuccess); break; + } + break; + } + + case 3: + { + // Game: + switch (PacketType) + { + /* + case 0x1b: HANDLE_SERVER_READ(HandleServerAttachEntity); break; + case 0x24: HANDLE_SERVER_READ(HandleServerBlockAction); break; + case 0x23: HANDLE_SERVER_READ(HandleServerBlockChange); break; + case 0x2b: HANDLE_SERVER_READ(HandleServerChangeGameState); break; + case 0x02: HANDLE_SERVER_READ(HandleServerChatMessage); break; + case 0x0d: HANDLE_SERVER_READ(HandleServerCollectPickup); break; + case 0x13: HANDLE_SERVER_READ(HandleServerDestroyEntities); break; + */ case PACKET_ENTITY: HANDLE_SERVER_READ(HandleServerEntity); break; case PACKET_ENTITY_EQUIPMENT: HANDLE_SERVER_READ(HandleServerEntityEquipment); break; case PACKET_ENTITY_HEAD_LOOK: HANDLE_SERVER_READ(HandleServerEntityHeadLook); break; @@ -852,6 +873,76 @@ bool cConnection::DecodeServersPackets(const char * a_Data, int a_Size) +/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// packet handling, client-side, initial handshake: + +bool cConnection::HandleClientHandshake(void) +{ + // Read the packet from the client: + HANDLE_CLIENT_PACKET_READ(ReadVarInt, UInt32, ProtocolVersion); + HANDLE_CLIENT_PACKET_READ(ReadVarUTF8String, AString, ServerHost); + HANDLE_CLIENT_PACKET_READ(ReadBEShort, short, ServerPort); + HANDLE_CLIENT_PACKET_READ(ReadVarInt, UInt32, NextState); + m_ClientBuffer.CommitRead(); + + Log("Received an initial handshake packet from the client:"); + Log(" ProtocolVersion = %u", ProtocolVersion); + Log(" ServerHost = \"%s\"", ServerHost.c_str()); + Log(" ServerPort = %d", ServerPort); + Log(" NextState = %u", NextState); + + // Send the same packet to the server, but with our port: + cByteBuffer Packet(512); + Packet.WriteVarInt(0); // Packet type - initial handshake + Packet.WriteVarInt(ProtocolVersion); + Packet.WriteVarUTF8String(ServerHost); + Packet.WriteBEShort(m_Server.GetConnectPort()); + Packet.WriteVarInt(NextState); + AString Pkt; + Packet.ReadAll(Pkt); + cByteBuffer ToServer(512); + ToServer.WriteVarUTF8String(Pkt); + SERVERSEND(ToServer); + + m_ClientProtocolState = (int)NextState; + m_ServerProtocolState = (int)NextState; + + return true; +} + + + + + +/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// packet handling, client-side, login: + +bool cConnection::HandleClientLoginEncryptionKeyResponse(void) +{ + Log("Client: Unexpected packet: encryption key response"); + return true; +} + + + + + +bool cConnection::HandleClientLoginStart(void) +{ + HANDLE_CLIENT_PACKET_READ(ReadVarUTF8String, AString, UserName); + Log("Received a login start packet from the client:"); + Log(" Username = \"%s\"", UserName.c_str()); + COPY_TO_SERVER(); + return true; +} + + + + + +/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// packet handling, client-side, game: + bool cConnection::HandleClientAnimation(void) { HANDLE_CLIENT_PACKET_READ(ReadBEInt, int, EntityID); @@ -972,33 +1063,6 @@ bool cConnection::HandleClientDisconnect(void) -bool cConnection::HandleClientEncryptionKeyResponse(void) -{ - HANDLE_CLIENT_PACKET_READ(ReadBEShort, short, EncKeyLength); - AString EncKey; - if (!m_ClientBuffer.ReadString(EncKey, EncKeyLength)) - { - return true; - } - HANDLE_CLIENT_PACKET_READ(ReadBEShort, short, EncNonceLength); - AString EncNonce; - if (!m_ClientBuffer.ReadString(EncNonce, EncNonceLength)) - { - return true; - } - if ((EncKeyLength > MAX_ENC_LEN) || (EncNonceLength > MAX_ENC_LEN)) - { - Log("Client: Too long encryption params"); - return true; - } - StartClientEncryption(EncKey, EncNonce); - return true; -} - - - - - bool cConnection::HandleClientEntityAction(void) { HANDLE_CLIENT_PACKET_READ(ReadBEInt, int, PlayerID); @@ -1016,43 +1080,6 @@ bool cConnection::HandleClientEntityAction(void) -bool cConnection::HandleClientHandshake(void) -{ - // Read the packet from the client: - HANDLE_CLIENT_PACKET_READ(ReadVarInt, UInt32, ProtocolVersion); - HANDLE_CLIENT_PACKET_READ(ReadVarUTF8String, AString, ServerHost); - HANDLE_CLIENT_PACKET_READ(ReadBEShort, short, ServerPort); - HANDLE_CLIENT_PACKET_READ(ReadVarInt, UInt32, NextState); - m_ClientBuffer.CommitRead(); - - Log("Received an initial handshake packet from the client:"); - Log(" ProtocolVersion = %u", ProtocolVersion); - Log(" ServerHost = \"%s\"", ServerHost.c_str()); - Log(" ServerPort = %d", ServerPort); - Log(" NextState = %u", NextState); - - // Send the same packet to the server, but with our port: - cByteBuffer Packet(512); - Packet.WriteVarInt(0); // Packet type - initial handshake - Packet.WriteVarInt(ProtocolVersion); - Packet.WriteVarUTF8String(ServerHost); - Packet.WriteBEShort(m_Server.GetConnectPort()); - Packet.WriteVarInt(NextState); - AString Pkt; - Packet.ReadAll(Pkt); - cByteBuffer ToServer(512); - ToServer.WriteVarUTF8String(Pkt); - SERVERSEND(ToServer); - - m_ProtocolState = (int)NextState; - - return true; -} - - - - - bool cConnection::HandleClientKeepAlive(void) { HANDLE_CLIENT_PACKET_READ(ReadBEInt, int, ID); @@ -1325,6 +1352,84 @@ bool cConnection::HandleClientWindowClose(void) +/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// packet handling, server-side, login: + +bool cConnection::HandleServerLoginDisconnect(void) +{ + HANDLE_SERVER_PACKET_READ(ReadVarUTF8String, AString, Reason); + Log("Received a login-disconnect packet from the server:"); + Log(" Reason = \"%s\"", Reason.c_str()); + COPY_TO_SERVER(); + return true; +} + + + + + +bool cConnection::HandleServerLoginEncryptionKeyRequest(void) +{ + // Read the packet from the server: + HANDLE_SERVER_PACKET_READ(ReadVarUTF8String, AString, ServerID); + HANDLE_SERVER_PACKET_READ(ReadBEShort, short, PublicKeyLength); + AString PublicKey; + if (!m_ServerBuffer.ReadString(PublicKey, PublicKeyLength)) + { + return false; + } + HANDLE_SERVER_PACKET_READ(ReadBEShort, short, NonceLength); + AString Nonce; + if (!m_ServerBuffer.ReadString(Nonce, NonceLength)) + { + return false; + } + Log("Got PACKET_ENCRYPTION_KEY_REQUEST from the SERVER:"); + Log(" ServerID = %s", ServerID.c_str()); + + // Reply to the server: + SendEncryptionKeyResponse(PublicKey, Nonce); + + // Do not send to client - we want the client connection open + return true; +} + + + + + +bool cConnection::HandleServerLoginSuccess(void) +{ + HANDLE_SERVER_PACKET_READ(ReadVarUTF8String, AString, UUID); + HANDLE_SERVER_PACKET_READ(ReadVarUTF8String, AString, Username); + Log("Received a login success packet from the server:"); + Log(" UUID = \"%s\"", UUID.c_str()); + Log(" Username = \"%s\"", Username.c_str()); + + Log("Server is now in protocol state Game."); + m_ServerProtocolState = 3; + + if (m_IsServerEncrypted) + { + Log("Server communication is now encrypted"); + m_ServerState = csEncryptedUnderstood; + DataLog(m_ServerEncryptionBuffer.data(), m_ServerEncryptionBuffer.size(), "Sending the queued data to server (%u bytes):", m_ServerEncryptionBuffer.size()); + SERVERENCRYPTSEND(m_ServerEncryptionBuffer.data(), m_ServerEncryptionBuffer.size()); + m_ServerEncryptionBuffer.clear(); + } + COPY_TO_CLIENT(); + Log("Client is now in protocol state Game."); + m_ClientProtocolState = 3; + return true; +} + + + + + +/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// packet handling, server-side, game: + bool cConnection::HandleServerAttachEntity(void) { HANDLE_SERVER_PACKET_READ(ReadBEInt, int, EntityID); @@ -1453,48 +1558,6 @@ bool cConnection::HandleServerDestroyEntities(void) -bool cConnection::HandleServerEncryptionKeyRequest(void) -{ - // Read the packet from the server: - HANDLE_SERVER_PACKET_READ(ReadBEUTF16String16, AString, ServerID); - HANDLE_SERVER_PACKET_READ(ReadBEShort, short, PublicKeyLength); - AString PublicKey; - if (!m_ServerBuffer.ReadString(PublicKey, PublicKeyLength)) - { - return false; - } - HANDLE_SERVER_PACKET_READ(ReadBEShort, short, NonceLength); - AString Nonce; - if (!m_ServerBuffer.ReadString(Nonce, NonceLength)) - { - return false; - } - Log("Got PACKET_ENCRYPTION_KEY_REQUEST from the SERVER:"); - Log(" ServerID = %s", ServerID.c_str()); - - // Reply to the server: - SendEncryptionKeyResponse(PublicKey, Nonce); - - // Send a 0xFD Encryption Key Request http://wiki.vg/Protocol#0xFD to the client, using our own key: - Log("Sending PACKET_ENCRYPTION_KEY_REQUEST to the CLIENT"); - AString key; - StringSink sink(key); // GCC won't allow inline instantiation in the following line, damned temporary refs - m_Server.GetPublicKey().Save(sink); - cByteBuffer ToClient(512); - ToClient.WriteByte (PACKET_ENCRYPTION_KEY_REQUEST); - ToClient.WriteBEUTF16String16(ServerID); - ToClient.WriteBEShort ((short)key.size()); - ToClient.WriteBuf (key.data(), key.size()); - ToClient.WriteBEShort (4); - ToClient.WriteBEInt (m_Nonce); // Using 'this' as the cryptographic nonce, so that we don't have to generate one each time :) - CLIENTSEND(ToClient); - return true; -} - - - - - bool cConnection::HandleServerEntity(void) { HANDLE_SERVER_PACKET_READ(ReadBEInt, int, EntityID); @@ -1779,26 +1842,6 @@ bool cConnection::HandleServerKeepAlive(void) -bool cConnection::HandleServerEncryptionKeyResponse(void) -{ - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, Lengths); - if (Lengths != 0) - { - Log("Lengths are not zero!"); - return true; - } - Log("Server communication is now encrypted"); - m_ServerState = csEncryptedUnderstood; - DataLog(m_ServerEncryptionBuffer.data(), m_ServerEncryptionBuffer.size(), "Sending the queued data to server (%u bytes):", m_ServerEncryptionBuffer.size()); - SERVERENCRYPTSEND(m_ServerEncryptionBuffer.data(), m_ServerEncryptionBuffer.size()); - m_ServerEncryptionBuffer.clear(); - return true; -} - - - - - bool cConnection::HandleServerKick(void) { HANDLE_SERVER_PACKET_READ(ReadBEUTF16String16, AString, Reason); @@ -2826,68 +2869,14 @@ void cConnection::SendEncryptionKeyResponse(const AString & a_ServerPublicKey, c // Send the packet to the server: Log("Sending PACKET_ENCRYPTION_KEY_RESPONSE to the SERVER"); cByteBuffer ToServer(1024); - ToServer.WriteByte(PACKET_ENCRYPTION_KEY_RESPONSE); + ToServer.WriteByte(0x01); // To server: Encryption key response ToServer.WriteBEShort(EncryptedLength); ToServer.WriteBuf(EncryptedSecret, EncryptedLength); ToServer.WriteBEShort(EncryptedLength); ToServer.WriteBuf(EncryptedNonce, EncryptedLength); SERVERSEND(ToServer); - m_ServerState = csWaitingForEncryption; -} - - - - - -void cConnection::StartClientEncryption(const AString & a_EncKey, const AString & a_EncNonce) -{ - // Decrypt EncNonce using privkey - RSAES::Decryptor rsaDecryptor(m_Server.GetPrivateKey()); - time_t CurTime = time(NULL); - RandomPool rng; - rng.Put((const byte *)&CurTime, sizeof(CurTime)); - byte DecryptedNonce[MAX_ENC_LEN]; - DecodingResult res = rsaDecryptor.Decrypt(rng, (const byte *)a_EncNonce.data(), a_EncNonce.size(), DecryptedNonce); - if (!res.isValidCoding || (res.messageLength != 4)) - { - Log("Client: Bad nonce length"); - return; - } - if (ntohl(*((int *)DecryptedNonce)) != m_Nonce) - { - Log("Bad nonce value"); - return; - } - - // Decrypt the symmetric encryption key using privkey: - byte SharedSecret[MAX_ENC_LEN]; - res = rsaDecryptor.Decrypt(rng, (const byte *)a_EncKey.data(), a_EncKey.size(), SharedSecret); - if (!res.isValidCoding || (res.messageLength != 16)) - { - Log("Bad key length"); - return; - } - - // Send encryption key response: - cByteBuffer ToClient(6); - ToClient.WriteByte((char)0xfc); - ToClient.WriteBEShort(0); - ToClient.WriteBEShort(0); - CLIENTSEND(ToClient); - - // Start the encryption: - m_ClientEncryptor.SetKey(SharedSecret, 16, MakeParameters(Name::IV(), ConstByteArrayParameter(SharedSecret, 16))(Name::FeedbackSize(), 1)); - m_ClientDecryptor.SetKey(SharedSecret, 16, MakeParameters(Name::IV(), ConstByteArrayParameter(SharedSecret, 16))(Name::FeedbackSize(), 1)); - Log("Client connection is now encrypted"); - m_ClientState = csEncryptedUnderstood; - - // Send the queued data: - DataLog(m_ClientEncryptionBuffer.data(), m_ClientEncryptionBuffer.size(), "Sending the queued data to client (%u bytes):", m_ClientEncryptionBuffer.size()); - CLIENTENCRYPTSEND(m_ClientEncryptionBuffer.data(), m_ClientEncryptionBuffer.size()); - m_ClientEncryptionBuffer.clear(); - - // Handle all postponed server data - DecodeServersPackets(NULL, 0); + m_ServerState = csEncryptedUnderstood; + m_IsServerEncrypted = true; } diff --git a/Tools/ProtoProxy/Connection.h b/Tools/ProtoProxy/Connection.h index d1006c95a..2dc57d645 100644 --- a/Tools/ProtoProxy/Connection.h +++ b/Tools/ProtoProxy/Connection.h @@ -71,17 +71,27 @@ protected: Decryptor m_ServerDecryptor; Encryptor m_ServerEncryptor; - Decryptor m_ClientDecryptor; - Encryptor m_ClientEncryptor; - - AString m_ClientEncryptionBuffer; // Buffer for the data to be sent to the client once encryption is established AString m_ServerEncryptionBuffer; // Buffer for the data to be sent to the server once encryption is established /// Set to true when PACKET_PING is received from the client; will cause special parsing for server kick bool m_HasClientPinged; - /// State the protocol is in (as defined by the initial handshake), -1 if no initial handshake received yet - int m_ProtocolState; + /* + The protocol states can be one of: + -1: no initial handshake received yet + 1: status + 2: login + 3: game + */ + /// State the to-server protocol is in (as defined by the initial handshake / login), -1 if no initial handshake received yet + int m_ServerProtocolState; + + /// State the to-client protocol is in (as defined by the initial handshake / login), -1 if no initial handshake received yet + int m_ClientProtocolState; + + /// True if the server connection has provided encryption keys + bool m_IsServerEncrypted; + bool ConnectToServer(void); @@ -112,7 +122,18 @@ protected: /// Decodes packets coming from the server, sends appropriate counterparts to the client; returns false if the connection is to be dropped bool DecodeServersPackets(const char * a_Data, int a_Size); - // Packet handling, client-side: + // Packet handling, client-side, initial: + bool HandleClientHandshake(void); + + // Packet handling, client-side, status: + bool HandleClientStatusPing(void); + bool HandleClientStatusRequest(void); + + // Packet handling, client-side, login: + bool HandleClientLoginEncryptionKeyResponse(void); + bool HandleClientLoginStart(void); + + // Packet handling, client-side, game: bool HandleClientAnimation(void); bool HandleClientBlockDig(void); bool HandleClientBlockPlace(void); @@ -120,9 +141,7 @@ protected: bool HandleClientClientStatuses(void); bool HandleClientCreativeInventoryAction(void); bool HandleClientDisconnect(void); - bool HandleClientEncryptionKeyResponse(void); bool HandleClientEntityAction(void); - bool HandleClientHandshake(void); bool HandleClientKeepAlive(void); bool HandleClientLocaleAndView(void); bool HandleClientPing(void); @@ -133,15 +152,18 @@ protected: bool HandleClientPlayerPositionLook(void); bool HandleClientPluginMessage(void); bool HandleClientSlotSelect(void); - bool HandleClientStatusPing(void); - bool HandleClientStatusRequest(void); bool HandleClientTabCompletion(void); bool HandleClientUpdateSign(void); bool HandleClientUseEntity(void); bool HandleClientWindowClick(void); bool HandleClientWindowClose(void); - // Packet handling, server-side: + // Packet handling, server-side, login: + bool HandleServerLoginDisconnect(void); + bool HandleServerLoginEncryptionKeyRequest(void); + bool HandleServerLoginSuccess(void); + + // Packet handling, server-side, game: bool HandleServerAttachEntity(void); bool HandleServerBlockAction(void); bool HandleServerBlockChange(void); @@ -150,8 +172,6 @@ protected: bool HandleServerCollectPickup(void); bool HandleServerCompass(void); bool HandleServerDestroyEntities(void); - bool HandleServerEncryptionKeyRequest(void); - bool HandleServerEncryptionKeyResponse(void); bool HandleServerEntity(void); bool HandleServerEntityEquipment(void); bool HandleServerEntityHeadLook(void); -- cgit v1.2.3 From 111fb24d3a4bbcd1e22feb8d92390e4eed07a225 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Tue, 29 Oct 2013 19:05:51 +0100 Subject: ProtoProxy: Updated the server-side packets to 1.7. --- Tools/ProtoProxy/Connection.h | 5 +++++ 1 file changed, 5 insertions(+) (limited to 'Tools') diff --git a/Tools/ProtoProxy/Connection.h b/Tools/ProtoProxy/Connection.h index 2dc57d645..56d443b86 100644 --- a/Tools/ProtoProxy/Connection.h +++ b/Tools/ProtoProxy/Connection.h @@ -185,6 +185,7 @@ protected: bool HandleServerEntityVelocity(void); bool HandleServerExplosion(void); bool HandleServerIncrementStatistic(void); + bool HandleServerJoinGame(void); bool HandleServerKeepAlive(void); bool HandleServerKick(void); bool HandleServerLogin(void); @@ -197,15 +198,18 @@ protected: bool HandleServerPlayerListItem(void); bool HandleServerPlayerPositionLook(void); bool HandleServerPluginMessage(void); + bool HandleServerRespawn(void); bool HandleServerSetExperience(void); bool HandleServerSetSlot(void); bool HandleServerSlotSelect(void); bool HandleServerSoundEffect(void); + bool HandleServerSpawnExperienceOrbs(void); bool HandleServerSpawnMob(void); bool HandleServerSpawnNamedEntity(void); bool HandleServerSpawnObjectVehicle(void); bool HandleServerSpawnPainting(void); bool HandleServerSpawnPickup(void); + bool HandleServerStatistics(void); bool HandleServerStatusPing(void); bool HandleServerStatusResponse(void); bool HandleServerTabCompletion(void); @@ -213,6 +217,7 @@ protected: bool HandleServerUpdateHealth(void); bool HandleServerUpdateSign(void); bool HandleServerUpdateTileEntity(void); + bool HandleServerUseBed(void); bool HandleServerWindowClose(void); bool HandleServerWindowContents(void); bool HandleServerWindowOpen(void); -- cgit v1.2.3 From db62f8bcea182908958a89b33687ca879d36816c Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Tue, 29 Oct 2013 22:06:15 +0100 Subject: ProtoProxy: Updated the server-side packets to 1.7. Forgotten a file in the previous commit. --- Tools/ProtoProxy/Connection.cpp | 410 +++++++++++++++++++++++----------------- 1 file changed, 239 insertions(+), 171 deletions(-) (limited to 'Tools') diff --git a/Tools/ProtoProxy/Connection.cpp b/Tools/ProtoProxy/Connection.cpp index 4b3442858..03a6a1863 100644 --- a/Tools/ProtoProxy/Connection.cpp +++ b/Tools/ProtoProxy/Connection.cpp @@ -646,6 +646,8 @@ bool cConnection::DecodeClientsPackets(const char * a_Data, int a_Size) // Game: switch (PacketType) { + case 0x00: HANDLE_CLIENT_READ(HandleClientKeepAlive); break; + case PACKET_BLOCK_DIG: HANDLE_CLIENT_READ(HandleClientBlockDig); break; case PACKET_BLOCK_PLACE: HANDLE_CLIENT_READ(HandleClientBlockPlace); break; case PACKET_S_CHAT_MESSAGE: HANDLE_CLIENT_READ(HandleClientChatMessage); break; @@ -653,7 +655,6 @@ bool cConnection::DecodeClientsPackets(const char * a_Data, int a_Size) case PACKET_CREATIVE_INVENTORY_ACTION: HANDLE_CLIENT_READ(HandleClientCreativeInventoryAction); break; case PACKET_DISCONNECT: HANDLE_CLIENT_READ(HandleClientDisconnect); break; case PACKET_ENTITY_ACTION: HANDLE_CLIENT_READ(HandleClientEntityAction); break; - case PACKET_S_KEEPALIVE: HANDLE_CLIENT_READ(HandleClientKeepAlive); break; case PACKET_LOCALE_AND_VIEW: HANDLE_CLIENT_READ(HandleClientLocaleAndView); break; case PACKET_PING: HANDLE_CLIENT_READ(HandleClientPing); break; case PACKET_PLAYER_ABILITIES: HANDLE_CLIENT_READ(HandleClientPlayerAbilities); break; @@ -671,7 +672,7 @@ bool cConnection::DecodeClientsPackets(const char * a_Data, int a_Size) case PACKET_WINDOW_CLOSE: HANDLE_CLIENT_READ(HandleClientWindowClose); break; } break; - } // case 2 + } // case 3 - Game default: { @@ -778,61 +779,60 @@ bool cConnection::DecodeServersPackets(const char * a_Data, int a_Size) // Game: switch (PacketType) { - /* - case 0x1b: HANDLE_SERVER_READ(HandleServerAttachEntity); break; - case 0x24: HANDLE_SERVER_READ(HandleServerBlockAction); break; - case 0x23: HANDLE_SERVER_READ(HandleServerBlockChange); break; - case 0x2b: HANDLE_SERVER_READ(HandleServerChangeGameState); break; + case 0x00: HANDLE_SERVER_READ(HandleServerKeepAlive); break; + case 0x01: HANDLE_SERVER_READ(HandleServerJoinGame); break; case 0x02: HANDLE_SERVER_READ(HandleServerChatMessage); break; + case 0x04: HANDLE_SERVER_READ(HandleServerEntityEquipment); break; + case 0x05: HANDLE_SERVER_READ(HandleServerCompass); break; + case 0x06: HANDLE_SERVER_READ(HandleServerUpdateHealth); break; + case 0x07: HANDLE_SERVER_READ(HandleServerRespawn); break; + case 0x08: HANDLE_SERVER_READ(HandleServerPlayerPositionLook); break; + case 0x09: HANDLE_SERVER_READ(HandleServerSlotSelect); break; + case 0x0a: HANDLE_SERVER_READ(HandleServerUseBed); break; + case 0x0b: HANDLE_SERVER_READ(HandleServerPlayerAnimation); break; + case 0x0c: HANDLE_SERVER_READ(HandleServerSpawnNamedEntity); break; case 0x0d: HANDLE_SERVER_READ(HandleServerCollectPickup); break; + case 0x0e: HANDLE_SERVER_READ(HandleServerSpawnObjectVehicle); break; + case 0x0f: HANDLE_SERVER_READ(HandleServerSpawnMob); break; + case 0x10: HANDLE_SERVER_READ(HandleServerSpawnPainting); break; + case 0x11: HANDLE_SERVER_READ(HandleServerSpawnExperienceOrbs); break; + case 0x12: HANDLE_SERVER_READ(HandleServerEntityVelocity); break; case 0x13: HANDLE_SERVER_READ(HandleServerDestroyEntities); break; - */ - case PACKET_ENTITY: HANDLE_SERVER_READ(HandleServerEntity); break; - case PACKET_ENTITY_EQUIPMENT: HANDLE_SERVER_READ(HandleServerEntityEquipment); break; - case PACKET_ENTITY_HEAD_LOOK: HANDLE_SERVER_READ(HandleServerEntityHeadLook); break; - case PACKET_ENTITY_LOOK: HANDLE_SERVER_READ(HandleServerEntityLook); break; - case PACKET_ENTITY_METADATA: HANDLE_SERVER_READ(HandleServerEntityMetadata); break; - case PACKET_ENTITY_PROPERTIES: HANDLE_SERVER_READ(HandleServerEntityProperties); break; - case PACKET_ENTITY_RELATIVE_MOVE: HANDLE_SERVER_READ(HandleServerEntityRelativeMove); break; - case PACKET_ENTITY_RELATIVE_MOVE_LOOK: HANDLE_SERVER_READ(HandleServerEntityRelativeMoveLook); break; - case PACKET_ENTITY_STATUS: HANDLE_SERVER_READ(HandleServerEntityStatus); break; - case PACKET_ENTITY_TELEPORT: HANDLE_SERVER_READ(HandleServerEntityTeleport); break; - case PACKET_ENTITY_VELOCITY: HANDLE_SERVER_READ(HandleServerEntityVelocity); break; - case PACKET_EXPLOSION: HANDLE_SERVER_READ(HandleServerExplosion); break; - case PACKET_INCREMENT_STATISTIC: HANDLE_SERVER_READ(HandleServerIncrementStatistic); break; - case PACKET_C_JOIN_GAME: HANDLE_SERVER_READ(HandleServerLogin); break; - case PACKET_C_KEEPALIVE: HANDLE_SERVER_READ(HandleServerKeepAlive); break; - case PACKET_KICK: HANDLE_SERVER_READ(HandleServerKick); break; - case PACKET_MAP_CHUNK: HANDLE_SERVER_READ(HandleServerMapChunk); break; - case PACKET_MAP_CHUNK_BULK: HANDLE_SERVER_READ(HandleServerMapChunkBulk); break; - case PACKET_MULTI_BLOCK_CHANGE: HANDLE_SERVER_READ(HandleServerMultiBlockChange); break; - case PACKET_NAMED_SOUND_EFFECT: HANDLE_SERVER_READ(HandleServerNamedSoundEffect); break; - case PACKET_PLAYER_ABILITIES: HANDLE_SERVER_READ(HandleServerPlayerAbilities); break; - case PACKET_PLAYER_ANIMATION: HANDLE_SERVER_READ(HandleServerPlayerAnimation); break; - case PACKET_PLAYER_LIST_ITEM: HANDLE_SERVER_READ(HandleServerPlayerListItem); break; - case PACKET_PLAYER_POSITION_LOOK: HANDLE_SERVER_READ(HandleServerPlayerPositionLook); break; - case PACKET_PLUGIN_MESSAGE: HANDLE_SERVER_READ(HandleServerPluginMessage); break; - case PACKET_SET_EXPERIENCE: HANDLE_SERVER_READ(HandleServerSetExperience); break; - case PACKET_SET_SLOT: HANDLE_SERVER_READ(HandleServerSetSlot); break; - case PACKET_SLOT_SELECT: HANDLE_SERVER_READ(HandleServerSlotSelect); break; - case PACKET_SOUND_EFFECT: HANDLE_SERVER_READ(HandleServerSoundEffect); break; - case PACKET_SPAWN_MOB: HANDLE_SERVER_READ(HandleServerSpawnMob); break; - case PACKET_SPAWN_NAMED_ENTITY: HANDLE_SERVER_READ(HandleServerSpawnNamedEntity); break; - case PACKET_SPAWN_OBJECT_VEHICLE: HANDLE_SERVER_READ(HandleServerSpawnObjectVehicle); break; - case PACKET_SPAWN_PAINTING: HANDLE_SERVER_READ(HandleServerSpawnPainting); break; - case PACKET_SPAWN_PICKUP: HANDLE_SERVER_READ(HandleServerSpawnPickup); break; - case PACKET_SPAWN_POSITION: HANDLE_SERVER_READ(HandleServerCompass); break; - case PACKET_TAB_COMPLETION: HANDLE_SERVER_READ(HandleServerTabCompletion); break; - case PACKET_TIME_UPDATE: HANDLE_SERVER_READ(HandleServerTimeUpdate); break; - case PACKET_UPDATE_HEALTH: HANDLE_SERVER_READ(HandleServerUpdateHealth); break; - case PACKET_UPDATE_SIGN: HANDLE_SERVER_READ(HandleServerUpdateSign); break; - case PACKET_UPDATE_TILE_ENTITY: HANDLE_SERVER_READ(HandleServerUpdateTileEntity); break; - case PACKET_WINDOW_CLOSE: HANDLE_SERVER_READ(HandleServerWindowClose); break; - case PACKET_WINDOW_CONTENTS: HANDLE_SERVER_READ(HandleServerWindowContents); break; - case PACKET_WINDOW_OPEN: HANDLE_SERVER_READ(HandleServerWindowOpen); break; + case 0x14: HANDLE_SERVER_READ(HandleServerEntity); break; + case 0x15: HANDLE_SERVER_READ(HandleServerEntityRelativeMove); break; + case 0x16: HANDLE_SERVER_READ(HandleServerEntityLook); break; + case 0x17: HANDLE_SERVER_READ(HandleServerEntityRelativeMoveLook); break; + case 0x18: HANDLE_SERVER_READ(HandleServerEntityTeleport); break; + case 0x19: HANDLE_SERVER_READ(HandleServerEntityHeadLook); break; + case 0x1a: HANDLE_SERVER_READ(HandleServerEntityStatus); break; + case 0x1b: HANDLE_SERVER_READ(HandleServerAttachEntity); break; + case 0x1c: HANDLE_SERVER_READ(HandleServerEntityMetadata); break; + case 0x1f: HANDLE_SERVER_READ(HandleServerSetExperience); break; + case 0x20: HANDLE_SERVER_READ(HandleServerEntityProperties); break; + case 0x21: HANDLE_SERVER_READ(HandleServerMapChunk); break; + case 0x22: HANDLE_SERVER_READ(HandleServerMultiBlockChange); break; + case 0x23: HANDLE_SERVER_READ(HandleServerBlockChange); break; + case 0x24: HANDLE_SERVER_READ(HandleServerBlockAction); break; + case 0x26: HANDLE_SERVER_READ(HandleServerMapChunkBulk); break; + case 0x27: HANDLE_SERVER_READ(HandleServerExplosion); break; + case 0x28: HANDLE_SERVER_READ(HandleServerSoundEffect); break; + case 0x29: HANDLE_SERVER_READ(HandleServerNamedSoundEffect); break; + case 0x2b: HANDLE_SERVER_READ(HandleServerChangeGameState); break; + case 0x2d: HANDLE_SERVER_READ(HandleServerWindowOpen); break; + case 0x2e: HANDLE_SERVER_READ(HandleServerWindowClose); break; + case 0x2f: HANDLE_SERVER_READ(HandleServerSetSlot); break; + case 0x30: HANDLE_SERVER_READ(HandleServerWindowContents); break; + case 0x33: HANDLE_SERVER_READ(HandleServerUpdateSign); break; + case 0x35: HANDLE_SERVER_READ(HandleServerUpdateTileEntity); break; + case 0x37: HANDLE_SERVER_READ(HandleServerStatistics); break; + case 0x38: HANDLE_SERVER_READ(HandleServerPlayerListItem); break; + case 0x39: HANDLE_SERVER_READ(HandleServerPlayerAbilities); break; + case 0x3a: HANDLE_SERVER_READ(HandleServerTabCompletion); break; + case 0x3f: HANDLE_SERVER_READ(HandleServerPluginMessage); break; + case 0x40: HANDLE_SERVER_READ(HandleServerKick); break; } // switch (PacketType) break; - } // case 2 + } // case 3 - Game // TODO: Move this elsewhere default: @@ -1006,7 +1006,7 @@ bool cConnection::HandleClientBlockPlace(void) bool cConnection::HandleClientChatMessage(void) { - HANDLE_CLIENT_PACKET_READ(ReadBEUTF16String16, AString, Message); + HANDLE_CLIENT_PACKET_READ(ReadVarUTF8String, AString, Message); Log("Received a PACKET_CHAT_MESSAGE from the client:"); Log(" Message = \"%s\"", Message.c_str()); COPY_TO_SERVER(); @@ -1052,7 +1052,7 @@ bool cConnection::HandleClientCreativeInventoryAction(void) bool cConnection::HandleClientDisconnect(void) { - HANDLE_CLIENT_PACKET_READ(ReadBEUTF16String16, AString, Reason); + HANDLE_CLIENT_PACKET_READ(ReadVarUTF8String, AString, Reason); Log("Received a PACKET_DISCONNECT from the client:"); Log(" Reason = \"%s\"", Reason.c_str()); COPY_TO_SERVER(); @@ -1094,7 +1094,7 @@ bool cConnection::HandleClientKeepAlive(void) bool cConnection::HandleClientLocaleAndView(void) { - HANDLE_CLIENT_PACKET_READ(ReadBEUTF16String16, AString, Locale); + HANDLE_CLIENT_PACKET_READ(ReadVarUTF8String, AString, Locale); HANDLE_CLIENT_PACKET_READ(ReadChar, char, ViewDistance); HANDLE_CLIENT_PACKET_READ(ReadChar, char, ChatFlags); HANDLE_CLIENT_PACKET_READ(ReadChar, char, Difficulty); @@ -1208,7 +1208,7 @@ bool cConnection::HandleClientPlayerPositionLook(void) bool cConnection::HandleClientPluginMessage(void) { - HANDLE_CLIENT_PACKET_READ(ReadBEUTF16String16, AString, ChannelName); + HANDLE_CLIENT_PACKET_READ(ReadVarUTF8String, AString, ChannelName); HANDLE_CLIENT_PACKET_READ(ReadBEShort, short, Length); AString Data; if (!m_ClientBuffer.ReadString(Data, Length)) @@ -1265,7 +1265,7 @@ bool cConnection::HandleClientStatusRequest(void) bool cConnection::HandleClientTabCompletion(void) { - HANDLE_CLIENT_PACKET_READ(ReadBEUTF16String16, AString, Query); + HANDLE_CLIENT_PACKET_READ(ReadVarUTF8String, AString, Query); Log("Received a PACKET_TAB_COMPLETION query from the client"); Log(" Query = \"%s\"", Query.c_str()); COPY_TO_SERVER(); @@ -1281,10 +1281,10 @@ bool cConnection::HandleClientUpdateSign(void) HANDLE_CLIENT_PACKET_READ(ReadBEInt, int, BlockX); HANDLE_CLIENT_PACKET_READ(ReadBEShort, short, BlockY); HANDLE_CLIENT_PACKET_READ(ReadBEInt, int, BlockZ); - HANDLE_CLIENT_PACKET_READ(ReadBEUTF16String16, AString, Line1); - HANDLE_CLIENT_PACKET_READ(ReadBEUTF16String16, AString, Line2); - HANDLE_CLIENT_PACKET_READ(ReadBEUTF16String16, AString, Line3); - HANDLE_CLIENT_PACKET_READ(ReadBEUTF16String16, AString, Line4); + HANDLE_CLIENT_PACKET_READ(ReadVarUTF8String, AString, Line1); + HANDLE_CLIENT_PACKET_READ(ReadVarUTF8String, AString, Line2); + HANDLE_CLIENT_PACKET_READ(ReadVarUTF8String, AString, Line3); + HANDLE_CLIENT_PACKET_READ(ReadVarUTF8String, AString, Line4); Log("Received a PACKET_UPDATE_SIGN from the client:"); Log(" Block = {%d, %d, %d}", BlockX, BlockY, BlockZ); Log(" Lines = \"%s\", \"%s\", \"%s\", \"%s\"", Line1.c_str(), Line2.c_str(), Line3.c_str(), Line4.c_str()); @@ -1449,16 +1449,16 @@ bool cConnection::HandleServerAttachEntity(void) bool cConnection::HandleServerBlockAction(void) { - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, BlockX); - HANDLE_SERVER_PACKET_READ(ReadBEShort, short, BlockY); - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, BlockZ); - HANDLE_SERVER_PACKET_READ(ReadByte, Byte, Byte1); - HANDLE_SERVER_PACKET_READ(ReadByte, Byte, Byte2); - HANDLE_SERVER_PACKET_READ(ReadBEShort, short, BlockID); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, BlockX); + HANDLE_SERVER_PACKET_READ(ReadBEShort, short, BlockY); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, BlockZ); + HANDLE_SERVER_PACKET_READ(ReadByte, Byte, Byte1); + HANDLE_SERVER_PACKET_READ(ReadByte, Byte, Byte2); + HANDLE_SERVER_PACKET_READ(ReadVarInt, UInt32, BlockID); Log("Received a PACKET_BLOCK_ACTION from the server:"); Log(" Pos = {%d, %d, %d}", BlockX, BlockY, BlockZ); Log(" Bytes = (%d, %d) == (0x%x, 0x%x)", Byte1, Byte2, Byte1, Byte2); - Log(" BlockID = %d", BlockID); + Log(" BlockID = %u", BlockID); COPY_TO_CLIENT(); return true; } @@ -1469,11 +1469,11 @@ bool cConnection::HandleServerBlockAction(void) bool cConnection::HandleServerBlockChange(void) { - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, BlockX); - HANDLE_SERVER_PACKET_READ(ReadByte, Byte, BlockY); - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, BlockZ); - HANDLE_SERVER_PACKET_READ(ReadBEShort, short, BlockType); - HANDLE_SERVER_PACKET_READ(ReadChar, char, BlockMeta); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, BlockX); + HANDLE_SERVER_PACKET_READ(ReadByte, Byte, BlockY); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, BlockZ); + HANDLE_SERVER_PACKET_READ(ReadVarInt, UInt32, BlockType); + HANDLE_SERVER_PACKET_READ(ReadChar, char, BlockMeta); Log("Received a PACKET_BLOCK_CHANGE from the server"); COPY_TO_CLIENT(); return true; @@ -1500,7 +1500,7 @@ bool cConnection::HandleServerChangeGameState(void) bool cConnection::HandleServerChatMessage(void) { - HANDLE_SERVER_PACKET_READ(ReadBEUTF16String16, AString, Message); + HANDLE_SERVER_PACKET_READ(ReadVarUTF8String, AString, Message); Log("Received a PACKET_CHAT_MESSAGE from the server:"); Log(" Message = \"%s\"", Message.c_str()); COPY_TO_CLIENT(); @@ -1656,20 +1656,18 @@ bool cConnection::HandleServerEntityProperties(void) for (int i = 0; i < Count; i++) { - HANDLE_SERVER_PACKET_READ(ReadBEUTF16String16, AString, Key); - HANDLE_SERVER_PACKET_READ(ReadBEDouble, double, Value); - Log(" \"%s\" = %f", Key.c_str(), Value); - } // for i - - HANDLE_SERVER_PACKET_READ(ReadBEShort, short, ListLength); - Log(" ListLength = %d", ListLength); - for (int i = 0; i < ListLength; i++) - { - HANDLE_SERVER_PACKET_READ(ReadBEInt64, Int64, UUIDHi); - HANDLE_SERVER_PACKET_READ(ReadBEInt64, Int64, UUIDLo); - HANDLE_SERVER_PACKET_READ(ReadBEDouble, double, DblVal); - HANDLE_SERVER_PACKET_READ(ReadByte, Byte, ByteVal); - Log(" [%d] = {0x%08llx%08llx, %f, %i}", i, UUIDHi, UUIDLo, DblVal, ByteVal); + HANDLE_SERVER_PACKET_READ(ReadVarUTF8String, AString, Key); + HANDLE_SERVER_PACKET_READ(ReadBEDouble, double, Value); + HANDLE_SERVER_PACKET_READ(ReadBEShort, short, ListLength); + Log(" \"%s\" = %f; %d modifiers", Key.c_str(), Value, ListLength); + for (short j = 0; j < ListLength; j++) + { + HANDLE_SERVER_PACKET_READ(ReadBEInt64, Int64, UUIDHi); + HANDLE_SERVER_PACKET_READ(ReadBEInt64, Int64, UUIDLo); + HANDLE_SERVER_PACKET_READ(ReadBEDouble, double, DblVal); + HANDLE_SERVER_PACKET_READ(ReadByte, Byte, ByteVal); + Log(" [%d] = {0x%08llx%08llx, %f, %u}", j, UUIDHi, UUIDLo, DblVal, ByteVal); + } } // for i COPY_TO_CLIENT(); return true; @@ -1734,7 +1732,7 @@ bool cConnection::HandleServerEntityStatus(void) bool cConnection::HandleServerEntityTeleport(void) { - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, EntityID); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, EntityID); HANDLE_SERVER_PACKET_READ(ReadBEInt, int, AbsX); HANDLE_SERVER_PACKET_READ(ReadBEInt, int, AbsY); HANDLE_SERVER_PACKET_READ(ReadBEInt, int, AbsZ); @@ -1742,7 +1740,7 @@ bool cConnection::HandleServerEntityTeleport(void) HANDLE_SERVER_PACKET_READ(ReadByte, Byte, Pitch); Log("Received a PACKET_ENTITY_TELEPORT from the server:"); Log(" EntityID = %d", EntityID); - Log(" Pos = (%d, %d, %d) ~ {%.02f, %.02f, %.02f}", AbsX, AbsY, AbsZ, (double)AbsX / 32, (double)AbsY / 32, (double)AbsZ / 32); + Log(" Pos = %s", PrintableAbsIntTriplet(AbsX, AbsY, AbsZ).c_str()); Log(" Yaw = %d", Yaw); Log(" Pitch = %d", Pitch); COPY_TO_CLIENT(); @@ -1772,11 +1770,11 @@ bool cConnection::HandleServerEntityVelocity(void) bool cConnection::HandleServerExplosion(void) { - HANDLE_SERVER_PACKET_READ(ReadBEDouble, double, PosX); - HANDLE_SERVER_PACKET_READ(ReadBEDouble, double, PosY); - HANDLE_SERVER_PACKET_READ(ReadBEDouble, double, PosZ); - HANDLE_SERVER_PACKET_READ(ReadBEFloat, float, Force); - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, NumRecords); + HANDLE_SERVER_PACKET_READ(ReadBEFloat, float, PosX); + HANDLE_SERVER_PACKET_READ(ReadBEFloat, float, PosY); + HANDLE_SERVER_PACKET_READ(ReadBEFloat, float, PosZ); + HANDLE_SERVER_PACKET_READ(ReadBEFloat, float, Force); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, NumRecords); struct sCoords { int x, y, z; @@ -1829,6 +1827,29 @@ bool cConnection::HandleServerIncrementStatistic(void) +bool cConnection::HandleServerJoinGame(void) +{ + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, EntityID); + HANDLE_SERVER_PACKET_READ(ReadChar, char, GameMode); + HANDLE_SERVER_PACKET_READ(ReadChar, char, Dimension); + HANDLE_SERVER_PACKET_READ(ReadChar, char, Difficulty); + HANDLE_SERVER_PACKET_READ(ReadChar, char, MaxPlayers); + HANDLE_SERVER_PACKET_READ(ReadVarUTF8String, AString, LevelType); + Log("Received a PACKET_LOGIN from the server:"); + Log(" EntityID = %d", EntityID); + Log(" GameMode = %d", GameMode); + Log(" Dimension = %d", Dimension); + Log(" Difficulty = %d", Difficulty); + Log(" MaxPlayers = %d", MaxPlayers); + Log(" LevelType = \"%s\"", LevelType.c_str()); + COPY_TO_CLIENT(); + return true; +} + + + + + bool cConnection::HandleServerKeepAlive(void) { HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PingID); @@ -1844,7 +1865,7 @@ bool cConnection::HandleServerKeepAlive(void) bool cConnection::HandleServerKick(void) { - HANDLE_SERVER_PACKET_READ(ReadBEUTF16String16, AString, Reason); + HANDLE_SERVER_PACKET_READ(ReadVarUTF8String, AString, Reason); Log("Received PACKET_KICK from the SERVER:"); if (m_HasClientPinged) { @@ -1914,31 +1935,6 @@ bool cConnection::HandleServerKick(void) -bool cConnection::HandleServerLogin(void) -{ - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, EntityID); - HANDLE_SERVER_PACKET_READ(ReadBEUTF16String16, AString, LevelType); - HANDLE_SERVER_PACKET_READ(ReadChar, char, GameMode); - HANDLE_SERVER_PACKET_READ(ReadChar, char, Dimension); - HANDLE_SERVER_PACKET_READ(ReadChar, char, Difficulty); - HANDLE_SERVER_PACKET_READ(ReadChar, char, Unused); - HANDLE_SERVER_PACKET_READ(ReadChar, char, MaxPlayers); - Log("Received a PACKET_LOGIN from the server:"); - Log(" EntityID = %d", EntityID); - Log(" LevelType = \"%s\"", LevelType.c_str()); - Log(" GameMode = %d", GameMode); - Log(" Dimension = %d", Dimension); - Log(" Difficulty = %d", Difficulty); - Log(" Unused = %d", Unused); - Log(" MaxPlayers = %d", MaxPlayers); - COPY_TO_CLIENT(); - return true; -} - - - - - bool cConnection::HandleServerMapChunk(void) { HANDLE_SERVER_PACKET_READ(ReadBEInt, int, ChunkX); @@ -2049,15 +2045,15 @@ bool cConnection::HandleServerMultiBlockChange(void) bool cConnection::HandleServerNamedSoundEffect(void) { - HANDLE_SERVER_PACKET_READ(ReadBEUTF16String16, AString, SoundName); - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosX); - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosY); - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosZ); - HANDLE_SERVER_PACKET_READ(ReadBEFloat, float, Volume); - HANDLE_SERVER_PACKET_READ(ReadByte, Byte, Pitch); + HANDLE_SERVER_PACKET_READ(ReadVarUTF8String, AString, SoundName); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosX); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosY); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosZ); + HANDLE_SERVER_PACKET_READ(ReadBEFloat, float, Volume); + HANDLE_SERVER_PACKET_READ(ReadByte, Byte, Pitch); Log("Received a PACKET_NAMED_SOUND_EFFECT from the server:"); Log(" SoundName = \"%s\"", SoundName.c_str()); - Log(" Pos = (%d, %d, %d) ~ {%d, %d, %d}", PosX, PosY, PosZ, PosX / 8, PosY / 8, PosZ / 8); + Log(" Pos = %s", PrintableAbsIntTriplet(PosX, PosY, PosZ, 8).c_str()); Log(" Volume = %f", Volume); Log(" Pitch = %d", Pitch); COPY_TO_CLIENT(); @@ -2087,10 +2083,10 @@ bool cConnection::HandleServerPlayerAbilities(void) bool cConnection::HandleServerPlayerAnimation(void) { - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PlayerID); - HANDLE_SERVER_PACKET_READ(ReadByte, Byte, AnimationID); + HANDLE_SERVER_PACKET_READ(ReadVarInt, UInt32, PlayerID); + HANDLE_SERVER_PACKET_READ(ReadByte, Byte, AnimationID); Log("Received a PACKET_PLAYER_ANIMATION from the server:"); - Log(" PlayerID: %d (0x%x)", PlayerID, PlayerID); + Log(" PlayerID: %u (0x%x)", PlayerID, PlayerID); Log(" Animation: %d", AnimationID); COPY_TO_CLIENT(); return true; @@ -2102,7 +2098,7 @@ bool cConnection::HandleServerPlayerAnimation(void) bool cConnection::HandleServerPlayerListItem(void) { - HANDLE_SERVER_PACKET_READ(ReadBEUTF16String16, AString, PlayerName); + HANDLE_SERVER_PACKET_READ(ReadVarUTF8String, AString, PlayerName); HANDLE_SERVER_PACKET_READ(ReadChar, char, IsOnline); HANDLE_SERVER_PACKET_READ(ReadBEShort, short, Ping); Log("Received a PACKET_PLAYERLIST_ITEM from the server:"); @@ -2119,7 +2115,6 @@ bool cConnection::HandleServerPlayerListItem(void) bool cConnection::HandleServerPlayerPositionLook(void) { HANDLE_SERVER_PACKET_READ(ReadBEDouble, double, PosX); - HANDLE_SERVER_PACKET_READ(ReadBEDouble, double, Stance); HANDLE_SERVER_PACKET_READ(ReadBEDouble, double, PosY); HANDLE_SERVER_PACKET_READ(ReadBEDouble, double, PosZ); HANDLE_SERVER_PACKET_READ(ReadBEFloat, float, Yaw); @@ -2139,7 +2134,7 @@ bool cConnection::HandleServerPlayerPositionLook(void) bool cConnection::HandleServerPluginMessage(void) { - HANDLE_SERVER_PACKET_READ(ReadBEUTF16String16, AString, ChannelName); + HANDLE_SERVER_PACKET_READ(ReadVarUTF8String, AString, ChannelName); HANDLE_SERVER_PACKET_READ(ReadBEShort, short, Length); AString Data; if (!m_ServerBuffer.ReadString(Data, Length)) @@ -2149,7 +2144,26 @@ bool cConnection::HandleServerPluginMessage(void) Log("Received a PACKET_PLUGIN_MESSAGE from the server"); Log(" ChannelName = \"%s\"", ChannelName.c_str()); DataLog(Data.data(), Length, " Data: %d bytes", Length); - COPY_TO_SERVER(); + COPY_TO_CLIENT(); + return true; +} + + + + + +bool cConnection::HandleServerRespawn(void) +{ + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, Dimension); + HANDLE_SERVER_PACKET_READ(ReadChar, char, Difficulty); + HANDLE_SERVER_PACKET_READ(ReadChar, char, GameMode); + HANDLE_SERVER_PACKET_READ(ReadVarUTF8String, AString, LevelType); + Log("Received a respawn packet from the server:"); + Log(" Dimension = %d", Dimension); + Log(" Difficulty = %d", Difficulty); + Log(" GameMode = %d", GameMode); + Log(" LevelType = \"%s\"", LevelType.c_str()); + COPY_TO_CLIENT(); return true; } @@ -2197,7 +2211,7 @@ bool cConnection::HandleServerSetSlot(void) bool cConnection::HandleServerSlotSelect(void) { - HANDLE_SERVER_PACKET_READ(ReadBEShort, short, SlotNum); + HANDLE_SERVER_PACKET_READ(ReadByte, Byte, SlotNum); Log("Received a PACKET_SLOT_SELECT from the server:"); Log(" SlotNum = %d", SlotNum); COPY_TO_CLIENT(); @@ -2229,6 +2243,25 @@ bool cConnection::HandleServerSoundEffect(void) +bool cConnection::HandleServerSpawnExperienceOrbs(void) +{ + HANDLE_SERVER_PACKET_READ(ReadVarInt, UInt32, EntityID); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosX); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosY); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosZ); + HANDLE_SERVER_PACKET_READ(ReadBEShort, short, Count); + Log("Received a SPAWN_EXPERIENCE_ORBS packet from the server:"); + Log(" EntityID = %u (0x%x)", EntityID, EntityID); + Log(" Pos = %s", PrintableAbsIntTriplet(PosX, PosY, PosZ).c_str()); + Log(" Count = %d", Count); + COPY_TO_CLIENT(); + return true; +} + + + + + bool cConnection::HandleServerSpawnMob(void) { HANDLE_SERVER_PACKET_READ(ReadBEInt, int, EntityID); @@ -2267,14 +2300,15 @@ bool cConnection::HandleServerSpawnMob(void) bool cConnection::HandleServerSpawnNamedEntity(void) { - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, EntityID); - HANDLE_SERVER_PACKET_READ(ReadBEUTF16String16, AString, EntityName); - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosX); - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosY); - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosZ); - HANDLE_SERVER_PACKET_READ(ReadByte, Byte, Yaw); - HANDLE_SERVER_PACKET_READ(ReadByte, Byte, Pitch); - HANDLE_SERVER_PACKET_READ(ReadBEShort, short, CurrentItem); + HANDLE_SERVER_PACKET_READ(ReadVarInt, UInt32, EntityID); + HANDLE_SERVER_PACKET_READ(ReadVarUTF8String, AString, EntityUUID); + HANDLE_SERVER_PACKET_READ(ReadVarUTF8String, AString, EntityName); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosX); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosY); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosZ); + HANDLE_SERVER_PACKET_READ(ReadByte, Byte, Yaw); + HANDLE_SERVER_PACKET_READ(ReadByte, Byte, Pitch); + HANDLE_SERVER_PACKET_READ(ReadBEShort, short, CurrentItem); AString Metadata; if (!ParseMetadata(m_ServerBuffer, Metadata)) { @@ -2283,7 +2317,8 @@ bool cConnection::HandleServerSpawnNamedEntity(void) AString HexDump; CreateHexDump(HexDump, Metadata.data(), Metadata.size(), 32); Log("Received a PACKET_SPAWN_NAMED_ENTITY from the server:"); - Log(" EntityID = %d (0x%x)", EntityID, EntityID); + Log(" EntityID = %u (0x%x)", EntityID, EntityID); + Log(" UUID = %s", EntityUUID.c_str()); Log(" Name = %s", EntityName.c_str()); Log(" Pos = %s", PrintableAbsIntTriplet(PosX, PosY, PosZ).c_str()); Log(" Rotation = ", Yaw, Pitch); @@ -2316,14 +2351,14 @@ bool cConnection::HandleServerSpawnObjectVehicle(void) DataLog(Buffer.data(), Buffer.size(), "Buffer while parsing the PACKET_SPAWN_OBJECT_VEHICLE packet (%d bytes):", Buffer.size()); #endif // _DEBUG - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, EntityID); - HANDLE_SERVER_PACKET_READ(ReadChar, char, ObjType); - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosX); - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosY); - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosZ); - HANDLE_SERVER_PACKET_READ(ReadByte, Byte, Yaw); - HANDLE_SERVER_PACKET_READ(ReadByte, Byte, Pitch); - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, DataIndicator); + HANDLE_SERVER_PACKET_READ(ReadVarInt, UInt32, EntityID); + HANDLE_SERVER_PACKET_READ(ReadByte, Byte, ObjType); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosX); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosY); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosZ); + HANDLE_SERVER_PACKET_READ(ReadByte, Byte, Pitch); + HANDLE_SERVER_PACKET_READ(ReadByte, Byte, Yaw); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, DataIndicator); AString ExtraData; short VelocityX, VelocityY, VelocityZ; if (DataIndicator != 0) @@ -2356,7 +2391,7 @@ bool cConnection::HandleServerSpawnObjectVehicle(void) */ } Log("Received a PACKET_SPAWN_OBJECT_VEHICLE from the server:"); - Log(" EntityID = %d (0x%x)", EntityID, EntityID); + Log(" EntityID = %u (0x%x)", EntityID, EntityID); Log(" ObjType = %d (0x%x)", ObjType, ObjType); Log(" Pos = %s", PrintableAbsIntTriplet(PosX, PosY, PosZ).c_str()); Log(" Rotation = ", Yaw, Pitch); @@ -2376,14 +2411,14 @@ bool cConnection::HandleServerSpawnObjectVehicle(void) bool cConnection::HandleServerSpawnPainting(void) { - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, EntityID); - HANDLE_SERVER_PACKET_READ(ReadBEUTF16String16, AString, ImageName); - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosX); - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosY); - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosZ); - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, Direction); + HANDLE_SERVER_PACKET_READ(ReadVarInt, UInt32, EntityID); + HANDLE_SERVER_PACKET_READ(ReadVarUTF8String, AString, ImageName); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosX); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosY); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosZ); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, Direction); Log("Received a PACKET_SPAWN_PAINTING from the server:"); - Log(" EntityID = %d", EntityID); + Log(" EntityID = %u", EntityID); Log(" ImageName = \"%s\"", ImageName.c_str()); Log(" Pos = %s", PrintableAbsIntTriplet(PosX, PosY, PosZ).c_str()); Log(" Direction = %d", Direction); @@ -2422,6 +2457,21 @@ bool cConnection::HandleServerSpawnPickup(void) +bool cConnection::HandleServerStatistics(void) +{ + HANDLE_SERVER_PACKET_READ(ReadVarInt, UInt32, NumEntries); + for (UInt32 i = 0; i < NumEntries; i++) + { + HANDLE_SERVER_PACKET_READ(ReadVarUTF8String, AString, StatName); + HANDLE_SERVER_PACKET_READ(ReadVarInt, UInt32, StatValue); + } + COPY_TO_CLIENT(); + return true; +} + + + + bool cConnection::HandleServerStatusPing(void) { HANDLE_SERVER_PACKET_READ(ReadBEInt64, Int64, Time); @@ -2464,7 +2514,8 @@ bool cConnection::HandleServerStatusResponse(void) bool cConnection::HandleServerTabCompletion(void) { - HANDLE_SERVER_PACKET_READ(ReadBEUTF16String16, AString, Results); + HANDLE_SERVER_PACKET_READ(ReadVarInt, UInt32, NumResults); + HANDLE_SERVER_PACKET_READ(ReadVarUTF8String, AString, Results); Log("Received a PACKET_TAB_COMPLETION from the server, results given:"); // Parse the zero-terminated list of results: @@ -2522,10 +2573,10 @@ bool cConnection::HandleServerUpdateSign(void) HANDLE_SERVER_PACKET_READ(ReadBEInt, int, BlockX); HANDLE_SERVER_PACKET_READ(ReadBEShort, short, BlockY); HANDLE_SERVER_PACKET_READ(ReadBEInt, int, BlockZ); - HANDLE_SERVER_PACKET_READ(ReadBEUTF16String16, AString, Line1); - HANDLE_SERVER_PACKET_READ(ReadBEUTF16String16, AString, Line2); - HANDLE_SERVER_PACKET_READ(ReadBEUTF16String16, AString, Line3); - HANDLE_SERVER_PACKET_READ(ReadBEUTF16String16, AString, Line4); + HANDLE_SERVER_PACKET_READ(ReadVarUTF8String, AString, Line1); + HANDLE_SERVER_PACKET_READ(ReadVarUTF8String, AString, Line2); + HANDLE_SERVER_PACKET_READ(ReadVarUTF8String, AString, Line3); + HANDLE_SERVER_PACKET_READ(ReadVarUTF8String, AString, Line4); Log("Received a PACKET_UPDATE_SIGN from the server:"); Log(" Block = {%d, %d, %d}", BlockX, BlockY, BlockZ); Log(" Lines = \"%s\", \"%s\", \"%s\", \"%s\"", Line1.c_str(), Line2.c_str(), Line3.c_str(), Line4.c_str()); @@ -2552,7 +2603,24 @@ bool cConnection::HandleServerUpdateTileEntity(void) Log("Received a PACKET_UPDATE_TILE_ENTITY from the server:"); Log(" Block = {%d, %d, %d}", BlockX, BlockY, BlockZ); Log(" Action = %d", Action); - DataLog(Data.data(), Data.size(), " Data (%d bytes)", Data.size()); + DataLog(Data.data(), Data.size(), " Data (%u bytes)", Data.size()); + COPY_TO_CLIENT(); + return true; +} + + + + + +bool cConnection::HandleServerUseBed(void) +{ + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, EntityID); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, BedX); + HANDLE_SERVER_PACKET_READ(ReadByte, Byte, BedY); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, BedZ); + Log("Received a use bed packet from the server:"); + Log(" EntityID = %d", EntityID); + Log(" Bed = {%d, %d, %d}", BedX, BedY, BedZ); COPY_TO_CLIENT(); return true; } @@ -2604,14 +2672,14 @@ bool cConnection::HandleServerWindowOpen(void) { HANDLE_SERVER_PACKET_READ(ReadChar, char, WindowID); HANDLE_SERVER_PACKET_READ(ReadChar, char, WindowType); - HANDLE_SERVER_PACKET_READ(ReadBEUTF16String16, AString, Title); + HANDLE_SERVER_PACKET_READ(ReadVarUTF8String, AString, Title); HANDLE_SERVER_PACKET_READ(ReadByte, Byte, NumSlots); HANDLE_SERVER_PACKET_READ(ReadByte, Byte, UseProvidedTitle); - int HorseInt = 0; + int HorseEntityID = 0; if (WindowType == 11) // Horse / Donkey / Mule { HANDLE_SERVER_PACKET_READ(ReadBEInt, int, intHorseInt); - HorseInt = intHorseInt; + HorseEntityID = intHorseInt; } Log("Received a PACKET_WINDOW_OPEN from the server:"); Log(" WindowID = %d", WindowID); @@ -2620,7 +2688,7 @@ bool cConnection::HandleServerWindowOpen(void) Log(" NumSlots = %d", NumSlots); if (WindowType == 11) { - Log(" HorseInt = %d (0x%08x)", HorseInt, HorseInt); + Log(" HorseEntityID = %d (0x%08x)", HorseEntityID, HorseEntityID); } COPY_TO_CLIENT(); return true; -- cgit v1.2.3 From e4906b302705796c0e2e7e7df217f67563f23572 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Tue, 29 Oct 2013 22:55:00 +0100 Subject: ProtoProxy: Working 1.7 protocol. Players can login, move around, dig blocks. --- Tools/ProtoProxy/Connection.cpp | 314 ++++++++++++++++++++-------------------- Tools/ProtoProxy/Connection.h | 4 + 2 files changed, 160 insertions(+), 158 deletions(-) (limited to 'Tools') diff --git a/Tools/ProtoProxy/Connection.cpp b/Tools/ProtoProxy/Connection.cpp index 03a6a1863..b99415900 100644 --- a/Tools/ProtoProxy/Connection.cpp +++ b/Tools/ProtoProxy/Connection.cpp @@ -112,7 +112,7 @@ #define HANDLE_CLIENT_READ(Proc) \ { \ - if (!Proc()) \ + if (!Proc) \ { \ AString Leftover; \ m_ClientBuffer.ReadAgain(Leftover); \ @@ -124,7 +124,7 @@ #define HANDLE_SERVER_READ(Proc) \ { \ - if (!Proc()) \ + if (!Proc) \ { \ m_ServerBuffer.ResetRead(); \ return true; \ @@ -604,8 +604,10 @@ bool cConnection::DecodeClientsPackets(const char * a_Data, int a_Size) // Not a complete packet yet break; } - UInt32 PacketType; + UInt32 PacketType, PacketReadSoFar; + PacketReadSoFar = m_ClientBuffer.GetReadableSpace(); VERIFY(m_ClientBuffer.ReadVarInt(PacketType)); + PacketReadSoFar -= m_ClientBuffer.GetReadableSpace(); Log("Decoding client's packets, there are now %d bytes in the queue; next packet is 0x%0x, %u bytes long", m_ClientBuffer.GetReadableSpace(), PacketType, PacketLen); switch (m_ClientProtocolState) { @@ -614,7 +616,8 @@ bool cConnection::DecodeClientsPackets(const char * a_Data, int a_Size) // No initial handshake received yet switch (PacketType) { - case 0: HANDLE_CLIENT_READ(HandleClientHandshake); break; + case 0x00: HANDLE_CLIENT_READ(HandleClientHandshake()); break; + default: HANDLE_CLIENT_READ(HandleClientUnknownPacket(PacketType, PacketLen, PacketReadSoFar)); break; } break; } // case -1 @@ -624,8 +627,9 @@ bool cConnection::DecodeClientsPackets(const char * a_Data, int a_Size) // Status query switch (PacketType) { - case 0x00: HANDLE_CLIENT_READ(HandleClientStatusRequest); break; - case 0x01: HANDLE_CLIENT_READ(HandleClientStatusPing); break; + case 0x00: HANDLE_CLIENT_READ(HandleClientStatusRequest()); break; + case 0x01: HANDLE_CLIENT_READ(HandleClientStatusPing()); break; + default: HANDLE_CLIENT_READ(HandleClientUnknownPacket(PacketType, PacketLen, PacketReadSoFar)); break; } break; } @@ -635,8 +639,9 @@ bool cConnection::DecodeClientsPackets(const char * a_Data, int a_Size) // Login switch (PacketType) { - case 0x00: HANDLE_CLIENT_READ(HandleClientLoginStart); break; - case 0x01: HANDLE_CLIENT_READ(HandleClientLoginEncryptionKeyResponse); break; + case 0x00: HANDLE_CLIENT_READ(HandleClientLoginStart()); break; + case 0x01: HANDLE_CLIENT_READ(HandleClientLoginEncryptionKeyResponse()); break; + default: HANDLE_CLIENT_READ(HandleClientUnknownPacket(PacketType, PacketLen, PacketReadSoFar)); break; } break; } @@ -646,62 +651,38 @@ bool cConnection::DecodeClientsPackets(const char * a_Data, int a_Size) // Game: switch (PacketType) { - case 0x00: HANDLE_CLIENT_READ(HandleClientKeepAlive); break; - - case PACKET_BLOCK_DIG: HANDLE_CLIENT_READ(HandleClientBlockDig); break; - case PACKET_BLOCK_PLACE: HANDLE_CLIENT_READ(HandleClientBlockPlace); break; - case PACKET_S_CHAT_MESSAGE: HANDLE_CLIENT_READ(HandleClientChatMessage); break; - case PACKET_CLIENT_STATUSES: HANDLE_CLIENT_READ(HandleClientClientStatuses); break; - case PACKET_CREATIVE_INVENTORY_ACTION: HANDLE_CLIENT_READ(HandleClientCreativeInventoryAction); break; - case PACKET_DISCONNECT: HANDLE_CLIENT_READ(HandleClientDisconnect); break; - case PACKET_ENTITY_ACTION: HANDLE_CLIENT_READ(HandleClientEntityAction); break; - case PACKET_LOCALE_AND_VIEW: HANDLE_CLIENT_READ(HandleClientLocaleAndView); break; - case PACKET_PING: HANDLE_CLIENT_READ(HandleClientPing); break; - case PACKET_PLAYER_ABILITIES: HANDLE_CLIENT_READ(HandleClientPlayerAbilities); break; - case PACKET_PLAYER_ANIMATION: HANDLE_CLIENT_READ(HandleClientAnimation); break; - case PACKET_PLAYER_LOOK: HANDLE_CLIENT_READ(HandleClientPlayerLook); break; - case PACKET_PLAYER_ON_GROUND: HANDLE_CLIENT_READ(HandleClientPlayerOnGround); break; - case PACKET_PLAYER_POSITION: HANDLE_CLIENT_READ(HandleClientPlayerPosition); break; - case PACKET_PLAYER_POSITION_LOOK: HANDLE_CLIENT_READ(HandleClientPlayerPositionLook); break; - case PACKET_PLUGIN_MESSAGE: HANDLE_CLIENT_READ(HandleClientPluginMessage); break; - case PACKET_SLOT_SELECT: HANDLE_CLIENT_READ(HandleClientSlotSelect); break; - case PACKET_TAB_COMPLETION: HANDLE_CLIENT_READ(HandleClientTabCompletion); break; - case PACKET_UPDATE_SIGN: HANDLE_CLIENT_READ(HandleClientUpdateSign); break; - case PACKET_USE_ENTITY: HANDLE_CLIENT_READ(HandleClientUseEntity); break; - case PACKET_WINDOW_CLICK: HANDLE_CLIENT_READ(HandleClientWindowClick); break; - case PACKET_WINDOW_CLOSE: HANDLE_CLIENT_READ(HandleClientWindowClose); break; + case 0x00: HANDLE_CLIENT_READ(HandleClientKeepAlive()); break; + case 0x01: HANDLE_CLIENT_READ(HandleClientChatMessage()); break; + case 0x02: HANDLE_CLIENT_READ(HandleClientUseEntity()); break; + case 0x03: HANDLE_CLIENT_READ(HandleClientPlayerOnGround()); break; + case 0x04: HANDLE_CLIENT_READ(HandleClientPlayerPosition()); break; + case 0x05: HANDLE_CLIENT_READ(HandleClientPlayerLook()); break; + case 0x06: HANDLE_CLIENT_READ(HandleClientPlayerPositionLook()); break; + case 0x07: HANDLE_CLIENT_READ(HandleClientBlockDig()); break; + case 0x08: HANDLE_CLIENT_READ(HandleClientBlockPlace()); break; + case 0x09: HANDLE_CLIENT_READ(HandleClientSlotSelect()); break; + case 0x0a: HANDLE_CLIENT_READ(HandleClientAnimation()); break; + case 0x0b: HANDLE_CLIENT_READ(HandleClientEntityAction()); break; + case 0x0d: HANDLE_CLIENT_READ(HandleClientWindowClose()); break; + case 0x0e: HANDLE_CLIENT_READ(HandleClientWindowClick()); break; + case 0x10: HANDLE_CLIENT_READ(HandleClientCreativeInventoryAction()); break; + case 0x12: HANDLE_CLIENT_READ(HandleClientUpdateSign()); break; + case 0x13: HANDLE_CLIENT_READ(HandleClientPlayerAbilities()); break; + case 0x14: HANDLE_CLIENT_READ(HandleClientTabCompletion()); break; + case 0x15: HANDLE_CLIENT_READ(HandleClientLocaleAndView()); break; + case 0x16: HANDLE_CLIENT_READ(HandleClientClientStatuses()); break; + case 0x17: HANDLE_CLIENT_READ(HandleClientPluginMessage()); break; + default: HANDLE_CLIENT_READ(HandleClientUnknownPacket(PacketType, PacketLen, PacketReadSoFar)); break; } break; } // case 3 - Game default: { - // TODO: Move this elsewhere - if (m_ClientState == csEncryptedUnderstood) - { - Log("****************** Unknown packet 0x%02x from the client while encrypted; continuing to relay blind only", PacketType); - AString Data; - m_ClientBuffer.ResetRead(); - m_ClientBuffer.ReadAll(Data); - DataLog(Data.data(), Data.size(), "Current data in the client packet queue: %d bytes", Data.size()); - m_ClientState = csEncryptedUnknown; - m_ClientBuffer.ResetRead(); - if (m_ServerState == csUnencrypted) - { - SERVERSEND(m_ClientBuffer); - } - else - { - SERVERENCRYPTSEND(m_ClientBuffer); - } - return true; - } - else - { - Log("Unknown packet 0x%02x from the client while unencrypted; aborting connection", PacketType); - return false; - } - } // default + Log("Receiving server packets while in an unknown protocol state (%d)!", m_ClientProtocolState); + HANDLE_CLIENT_READ(HandleClientUnknownPacket(PacketType, PacketLen, PacketReadSoFar)); + break; + } } // switch (m_ProtocolState) m_ClientBuffer.CommitRead(); } // while (true) @@ -739,8 +720,10 @@ bool cConnection::DecodeServersPackets(const char * a_Data, int a_Size) // Not a complete packet yet break; } - UInt32 PacketType; + UInt32 PacketType, PacketReadSoFar; + PacketReadSoFar = m_ServerBuffer.GetReadableSpace(); VERIFY(m_ServerBuffer.ReadVarInt(PacketType)); + PacketReadSoFar -= m_ServerBuffer.GetReadableSpace(); Log("Decoding server's packets, there are now %d bytes in the queue; next packet is 0x%0x, %u bytes long", m_ServerBuffer.GetReadableSpace(), PacketType, PacketLen); LogFlush(); switch (m_ServerProtocolState) @@ -748,6 +731,7 @@ bool cConnection::DecodeServersPackets(const char * a_Data, int a_Size) case -1: { Log("Receiving data from the server without an initial handshake message!"); + HANDLE_SERVER_READ(HandleServerUnknownPacket(PacketType, PacketLen, PacketReadSoFar)); break; } @@ -756,8 +740,9 @@ bool cConnection::DecodeServersPackets(const char * a_Data, int a_Size) // Status query: switch (PacketType) { - case 0: HANDLE_SERVER_READ(HandleServerStatusResponse); break; - case 1: HANDLE_SERVER_READ(HandleServerStatusPing); break; + case 0x00: HANDLE_SERVER_READ(HandleServerStatusResponse()); break; + case 0x01: HANDLE_SERVER_READ(HandleServerStatusPing()); break; + default: HANDLE_SERVER_READ(HandleServerUnknownPacket(PacketType, PacketLen, PacketReadSoFar)); break; } break; } @@ -767,9 +752,10 @@ bool cConnection::DecodeServersPackets(const char * a_Data, int a_Size) // Login: switch (PacketType) { - case 0x00: HANDLE_SERVER_READ(HandleServerLoginDisconnect); break; - case 0x01: HANDLE_SERVER_READ(HandleServerLoginEncryptionKeyRequest); break; - case 0x02: HANDLE_SERVER_READ(HandleServerLoginSuccess); break; + case 0x00: HANDLE_SERVER_READ(HandleServerLoginDisconnect()); break; + case 0x01: HANDLE_SERVER_READ(HandleServerLoginEncryptionKeyRequest()); break; + case 0x02: HANDLE_SERVER_READ(HandleServerLoginSuccess()); break; + default: HANDLE_SERVER_READ(HandleServerUnknownPacket(PacketType, PacketLen, PacketReadSoFar)); break; } break; } @@ -779,57 +765,59 @@ bool cConnection::DecodeServersPackets(const char * a_Data, int a_Size) // Game: switch (PacketType) { - case 0x00: HANDLE_SERVER_READ(HandleServerKeepAlive); break; - case 0x01: HANDLE_SERVER_READ(HandleServerJoinGame); break; - case 0x02: HANDLE_SERVER_READ(HandleServerChatMessage); break; - case 0x04: HANDLE_SERVER_READ(HandleServerEntityEquipment); break; - case 0x05: HANDLE_SERVER_READ(HandleServerCompass); break; - case 0x06: HANDLE_SERVER_READ(HandleServerUpdateHealth); break; - case 0x07: HANDLE_SERVER_READ(HandleServerRespawn); break; - case 0x08: HANDLE_SERVER_READ(HandleServerPlayerPositionLook); break; - case 0x09: HANDLE_SERVER_READ(HandleServerSlotSelect); break; - case 0x0a: HANDLE_SERVER_READ(HandleServerUseBed); break; - case 0x0b: HANDLE_SERVER_READ(HandleServerPlayerAnimation); break; - case 0x0c: HANDLE_SERVER_READ(HandleServerSpawnNamedEntity); break; - case 0x0d: HANDLE_SERVER_READ(HandleServerCollectPickup); break; - case 0x0e: HANDLE_SERVER_READ(HandleServerSpawnObjectVehicle); break; - case 0x0f: HANDLE_SERVER_READ(HandleServerSpawnMob); break; - case 0x10: HANDLE_SERVER_READ(HandleServerSpawnPainting); break; - case 0x11: HANDLE_SERVER_READ(HandleServerSpawnExperienceOrbs); break; - case 0x12: HANDLE_SERVER_READ(HandleServerEntityVelocity); break; - case 0x13: HANDLE_SERVER_READ(HandleServerDestroyEntities); break; - case 0x14: HANDLE_SERVER_READ(HandleServerEntity); break; - case 0x15: HANDLE_SERVER_READ(HandleServerEntityRelativeMove); break; - case 0x16: HANDLE_SERVER_READ(HandleServerEntityLook); break; - case 0x17: HANDLE_SERVER_READ(HandleServerEntityRelativeMoveLook); break; - case 0x18: HANDLE_SERVER_READ(HandleServerEntityTeleport); break; - case 0x19: HANDLE_SERVER_READ(HandleServerEntityHeadLook); break; - case 0x1a: HANDLE_SERVER_READ(HandleServerEntityStatus); break; - case 0x1b: HANDLE_SERVER_READ(HandleServerAttachEntity); break; - case 0x1c: HANDLE_SERVER_READ(HandleServerEntityMetadata); break; - case 0x1f: HANDLE_SERVER_READ(HandleServerSetExperience); break; - case 0x20: HANDLE_SERVER_READ(HandleServerEntityProperties); break; - case 0x21: HANDLE_SERVER_READ(HandleServerMapChunk); break; - case 0x22: HANDLE_SERVER_READ(HandleServerMultiBlockChange); break; - case 0x23: HANDLE_SERVER_READ(HandleServerBlockChange); break; - case 0x24: HANDLE_SERVER_READ(HandleServerBlockAction); break; - case 0x26: HANDLE_SERVER_READ(HandleServerMapChunkBulk); break; - case 0x27: HANDLE_SERVER_READ(HandleServerExplosion); break; - case 0x28: HANDLE_SERVER_READ(HandleServerSoundEffect); break; - case 0x29: HANDLE_SERVER_READ(HandleServerNamedSoundEffect); break; - case 0x2b: HANDLE_SERVER_READ(HandleServerChangeGameState); break; - case 0x2d: HANDLE_SERVER_READ(HandleServerWindowOpen); break; - case 0x2e: HANDLE_SERVER_READ(HandleServerWindowClose); break; - case 0x2f: HANDLE_SERVER_READ(HandleServerSetSlot); break; - case 0x30: HANDLE_SERVER_READ(HandleServerWindowContents); break; - case 0x33: HANDLE_SERVER_READ(HandleServerUpdateSign); break; - case 0x35: HANDLE_SERVER_READ(HandleServerUpdateTileEntity); break; - case 0x37: HANDLE_SERVER_READ(HandleServerStatistics); break; - case 0x38: HANDLE_SERVER_READ(HandleServerPlayerListItem); break; - case 0x39: HANDLE_SERVER_READ(HandleServerPlayerAbilities); break; - case 0x3a: HANDLE_SERVER_READ(HandleServerTabCompletion); break; - case 0x3f: HANDLE_SERVER_READ(HandleServerPluginMessage); break; - case 0x40: HANDLE_SERVER_READ(HandleServerKick); break; + case 0x00: HANDLE_SERVER_READ(HandleServerKeepAlive()); break; + case 0x01: HANDLE_SERVER_READ(HandleServerJoinGame()); break; + case 0x02: HANDLE_SERVER_READ(HandleServerChatMessage()); break; + case 0x03: HANDLE_SERVER_READ(HandleServerTimeUpdate()); break; + case 0x04: HANDLE_SERVER_READ(HandleServerEntityEquipment()); break; + case 0x05: HANDLE_SERVER_READ(HandleServerCompass()); break; + case 0x06: HANDLE_SERVER_READ(HandleServerUpdateHealth()); break; + case 0x07: HANDLE_SERVER_READ(HandleServerRespawn()); break; + case 0x08: HANDLE_SERVER_READ(HandleServerPlayerPositionLook()); break; + case 0x09: HANDLE_SERVER_READ(HandleServerSlotSelect()); break; + case 0x0a: HANDLE_SERVER_READ(HandleServerUseBed()); break; + case 0x0b: HANDLE_SERVER_READ(HandleServerPlayerAnimation()); break; + case 0x0c: HANDLE_SERVER_READ(HandleServerSpawnNamedEntity()); break; + case 0x0d: HANDLE_SERVER_READ(HandleServerCollectPickup()); break; + case 0x0e: HANDLE_SERVER_READ(HandleServerSpawnObjectVehicle()); break; + case 0x0f: HANDLE_SERVER_READ(HandleServerSpawnMob()); break; + case 0x10: HANDLE_SERVER_READ(HandleServerSpawnPainting()); break; + case 0x11: HANDLE_SERVER_READ(HandleServerSpawnExperienceOrbs()); break; + case 0x12: HANDLE_SERVER_READ(HandleServerEntityVelocity()); break; + case 0x13: HANDLE_SERVER_READ(HandleServerDestroyEntities()); break; + case 0x14: HANDLE_SERVER_READ(HandleServerEntity()); break; + case 0x15: HANDLE_SERVER_READ(HandleServerEntityRelativeMove()); break; + case 0x16: HANDLE_SERVER_READ(HandleServerEntityLook()); break; + case 0x17: HANDLE_SERVER_READ(HandleServerEntityRelativeMoveLook()); break; + case 0x18: HANDLE_SERVER_READ(HandleServerEntityTeleport()); break; + case 0x19: HANDLE_SERVER_READ(HandleServerEntityHeadLook()); break; + case 0x1a: HANDLE_SERVER_READ(HandleServerEntityStatus()); break; + case 0x1b: HANDLE_SERVER_READ(HandleServerAttachEntity()); break; + case 0x1c: HANDLE_SERVER_READ(HandleServerEntityMetadata()); break; + case 0x1f: HANDLE_SERVER_READ(HandleServerSetExperience()); break; + case 0x20: HANDLE_SERVER_READ(HandleServerEntityProperties()); break; + case 0x21: HANDLE_SERVER_READ(HandleServerMapChunk()); break; + case 0x22: HANDLE_SERVER_READ(HandleServerMultiBlockChange()); break; + case 0x23: HANDLE_SERVER_READ(HandleServerBlockChange()); break; + case 0x24: HANDLE_SERVER_READ(HandleServerBlockAction()); break; + case 0x26: HANDLE_SERVER_READ(HandleServerMapChunkBulk()); break; + case 0x27: HANDLE_SERVER_READ(HandleServerExplosion()); break; + case 0x28: HANDLE_SERVER_READ(HandleServerSoundEffect()); break; + case 0x29: HANDLE_SERVER_READ(HandleServerNamedSoundEffect()); break; + case 0x2b: HANDLE_SERVER_READ(HandleServerChangeGameState()); break; + case 0x2d: HANDLE_SERVER_READ(HandleServerWindowOpen()); break; + case 0x2e: HANDLE_SERVER_READ(HandleServerWindowClose()); break; + case 0x2f: HANDLE_SERVER_READ(HandleServerSetSlot()); break; + case 0x30: HANDLE_SERVER_READ(HandleServerWindowContents()); break; + case 0x33: HANDLE_SERVER_READ(HandleServerUpdateSign()); break; + case 0x35: HANDLE_SERVER_READ(HandleServerUpdateTileEntity()); break; + case 0x37: HANDLE_SERVER_READ(HandleServerStatistics()); break; + case 0x38: HANDLE_SERVER_READ(HandleServerPlayerListItem()); break; + case 0x39: HANDLE_SERVER_READ(HandleServerPlayerAbilities()); break; + case 0x3a: HANDLE_SERVER_READ(HandleServerTabCompletion()); break; + case 0x3f: HANDLE_SERVER_READ(HandleServerPluginMessage()); break; + case 0x40: HANDLE_SERVER_READ(HandleServerKick()); break; + default: HANDLE_SERVER_READ(HandleServerUnknownPacket(PacketType, PacketLen, PacketReadSoFar)); break; } // switch (PacketType) break; } // case 3 - Game @@ -837,30 +825,9 @@ bool cConnection::DecodeServersPackets(const char * a_Data, int a_Size) // TODO: Move this elsewhere default: { - if (m_ServerState == csEncryptedUnderstood) - { - Log("********************** Unknown packet 0x%02x from the server while encrypted; continuing to relay blind only", PacketType); - AString Data; - m_ServerBuffer.ResetRead(); - m_ServerBuffer.ReadAll(Data); - DataLog(Data.data(), Data.size(), "Current data in the server packet queue: %d bytes", Data.size()); - m_ServerState = csEncryptedUnknown; - m_ServerBuffer.ResetRead(); - if (m_ClientState == csUnencrypted) - { - CLIENTSEND(m_ServerBuffer); - } - else - { - CLIENTENCRYPTSEND(m_ServerBuffer); - } - return true; - } - else - { - Log("Unknown packet 0x%02x from the server while unencrypted; aborting connection", PacketType); - return false; - } + Log("Received a packet from the server while in an unknown state: %d", m_ServerProtocolState); + HANDLE_SERVER_READ(HandleServerUnknownPacket(PacketType, PacketLen, PacketReadSoFar)); + break; } } // switch (m_ProtocolState) @@ -1067,11 +1034,11 @@ bool cConnection::HandleClientEntityAction(void) { HANDLE_CLIENT_PACKET_READ(ReadBEInt, int, PlayerID); HANDLE_CLIENT_PACKET_READ(ReadByte, Byte, ActionType); - HANDLE_CLIENT_PACKET_READ(ReadBEInt, int, UnknownHorseVal); + HANDLE_CLIENT_PACKET_READ(ReadBEInt, int, HorseJumpBoost); Log("Received a PACKET_ENTITY_ACTION from the client:"); Log(" PlayerID = %d", PlayerID); Log(" ActionType = %d", ActionType); - Log(" UnknownHorseVal = %d (0x%08x)", UnknownHorseVal, UnknownHorseVal); + Log(" HorseJumpBoost = %d (0x%08x)", HorseJumpBoost, HorseJumpBoost); COPY_TO_SERVER(); return true; } @@ -1095,10 +1062,11 @@ bool cConnection::HandleClientKeepAlive(void) bool cConnection::HandleClientLocaleAndView(void) { HANDLE_CLIENT_PACKET_READ(ReadVarUTF8String, AString, Locale); - HANDLE_CLIENT_PACKET_READ(ReadChar, char, ViewDistance); - HANDLE_CLIENT_PACKET_READ(ReadChar, char, ChatFlags); - HANDLE_CLIENT_PACKET_READ(ReadChar, char, Difficulty); - HANDLE_CLIENT_PACKET_READ(ReadChar, char, ShowCape); + HANDLE_CLIENT_PACKET_READ(ReadChar, char, ViewDistance); + HANDLE_CLIENT_PACKET_READ(ReadChar, char, ChatFlags); + HANDLE_CLIENT_PACKET_READ(ReadChar, char, Unused); + HANDLE_CLIENT_PACKET_READ(ReadChar, char, Difficulty); + HANDLE_CLIENT_PACKET_READ(ReadChar, char, ShowCape); Log("Received a PACKET_LOCALE_AND_VIEW from the client"); COPY_TO_SERVER(); return true; @@ -1123,7 +1091,7 @@ bool cConnection::HandleClientPing(void) bool cConnection::HandleClientPlayerAbilities(void) { - HANDLE_CLIENT_PACKET_READ(ReadChar, char, Flags); + HANDLE_CLIENT_PACKET_READ(ReadChar, char, Flags); HANDLE_CLIENT_PACKET_READ(ReadBEFloat, float, FlyingSpeed); HANDLE_CLIENT_PACKET_READ(ReadBEFloat, float, WalkingSpeed); Log("Receives a PACKET_PLAYER_ABILITIES from the client:"); @@ -1154,7 +1122,7 @@ bool cConnection::HandleClientPlayerLook(void) bool cConnection::HandleClientPlayerOnGround(void) { - HANDLE_CLIENT_PACKET_READ(ReadChar, char, OnGround); + HANDLE_CLIENT_PACKET_READ(ReadChar, char, OnGround); Log("Received a PACKET_PLAYER_ON_GROUND from the client"); COPY_TO_SERVER(); return true; @@ -1167,8 +1135,8 @@ bool cConnection::HandleClientPlayerOnGround(void) bool cConnection::HandleClientPlayerPosition(void) { HANDLE_CLIENT_PACKET_READ(ReadBEDouble, double, PosX); - HANDLE_CLIENT_PACKET_READ(ReadBEDouble, double, Stance); HANDLE_CLIENT_PACKET_READ(ReadBEDouble, double, PosY); + HANDLE_CLIENT_PACKET_READ(ReadBEDouble, double, Stance); HANDLE_CLIENT_PACKET_READ(ReadBEDouble, double, PosZ); HANDLE_CLIENT_PACKET_READ(ReadChar, char, IsOnGround); Log("Received a PACKET_PLAYER_POSITION from the client"); @@ -1186,8 +1154,8 @@ bool cConnection::HandleClientPlayerPosition(void) bool cConnection::HandleClientPlayerPositionLook(void) { HANDLE_CLIENT_PACKET_READ(ReadBEDouble, double, PosX); - HANDLE_CLIENT_PACKET_READ(ReadBEDouble, double, Stance); HANDLE_CLIENT_PACKET_READ(ReadBEDouble, double, PosY); + HANDLE_CLIENT_PACKET_READ(ReadBEDouble, double, Stance); HANDLE_CLIENT_PACKET_READ(ReadBEDouble, double, PosZ); HANDLE_CLIENT_PACKET_READ(ReadBEFloat, float, Yaw); HANDLE_CLIENT_PACKET_READ(ReadBEFloat, float, Pitch); @@ -1195,7 +1163,7 @@ bool cConnection::HandleClientPlayerPositionLook(void) Log("Received a PACKET_PLAYER_POSITION_LOOK from the client"); Log(" Pos = {%.03f, %.03f, %.03f}", PosX, PosY, PosZ); Log(" Stance = %.03f", Stance); - Log(" Y, P = %.03f, %.03f", Yaw, Pitch); + Log(" Yaw, Pitch = <%.03f, %.03f>", Yaw, Pitch); Log(" IsOnGround = %s", IsOnGround ? "true" : "false"); COPY_TO_SERVER(); @@ -1278,9 +1246,9 @@ bool cConnection::HandleClientTabCompletion(void) bool cConnection::HandleClientUpdateSign(void) { - HANDLE_CLIENT_PACKET_READ(ReadBEInt, int, BlockX); - HANDLE_CLIENT_PACKET_READ(ReadBEShort, short, BlockY); - HANDLE_CLIENT_PACKET_READ(ReadBEInt, int, BlockZ); + HANDLE_CLIENT_PACKET_READ(ReadBEInt, int, BlockX); + HANDLE_CLIENT_PACKET_READ(ReadBEShort, short, BlockY); + HANDLE_CLIENT_PACKET_READ(ReadBEInt, int, BlockZ); HANDLE_CLIENT_PACKET_READ(ReadVarUTF8String, AString, Line1); HANDLE_CLIENT_PACKET_READ(ReadVarUTF8String, AString, Line2); HANDLE_CLIENT_PACKET_READ(ReadVarUTF8String, AString, Line3); @@ -1298,11 +1266,9 @@ bool cConnection::HandleClientUpdateSign(void) bool cConnection::HandleClientUseEntity(void) { - HANDLE_CLIENT_PACKET_READ(ReadBEInt, int, PlayerID); HANDLE_CLIENT_PACKET_READ(ReadBEInt, int, EntityID); HANDLE_CLIENT_PACKET_READ(ReadChar, char, MouseButton); Log("Received a PACKET_USE_ENTITY from the client:"); - Log(" PlayerID = %d", PlayerID); Log(" EntityID = %d", EntityID); Log(" MouseButton = %d", MouseButton); COPY_TO_SERVER(); @@ -1317,9 +1283,9 @@ bool cConnection::HandleClientWindowClick(void) { HANDLE_CLIENT_PACKET_READ(ReadChar, char, WindowID); HANDLE_CLIENT_PACKET_READ(ReadBEShort, short, SlotNum); - HANDLE_CLIENT_PACKET_READ(ReadChar, char, IsRightClick); + HANDLE_CLIENT_PACKET_READ(ReadChar, char, Button); HANDLE_CLIENT_PACKET_READ(ReadBEShort, short, TransactionID); - HANDLE_CLIENT_PACKET_READ(ReadChar, char, IsShiftClick); + HANDLE_CLIENT_PACKET_READ(ReadChar, char, Mode); AString Item; if (!ParseSlot(m_ClientBuffer, Item)) { @@ -1328,7 +1294,7 @@ bool cConnection::HandleClientWindowClick(void) Log("Received a PACKET_WINDOW_CLICK from the client"); Log(" WindowID = %d", WindowID); Log(" SlotNum = %d", SlotNum); - Log(" IsRclk = %d, IsShift = %d", IsRightClick, IsShiftClick); + Log(" Button = %d, Mode = %d", Button, Mode); Log(" TransactionID = 0x%x", TransactionID); Log(" ClickedItem = %s", Item.c_str()); COPY_TO_SERVER(); @@ -1352,6 +1318,22 @@ bool cConnection::HandleClientWindowClose(void) +bool cConnection::HandleClientUnknownPacket(UInt32 a_PacketType, UInt32 a_PacketLen, UInt32 a_PacketReadSoFar) +{ + AString Data; + if (!m_ClientBuffer.ReadString(Data, a_PacketLen - a_PacketReadSoFar)) + { + return false; + } + DataLog(Data.data(), Data.size(), "****************** Unknown packet 0x%x from the client; relaying and ignoring", a_PacketType); + COPY_TO_SERVER(); + return true; +} + + + + + /////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// // packet handling, server-side, login: @@ -2698,6 +2680,22 @@ bool cConnection::HandleServerWindowOpen(void) +bool cConnection::HandleServerUnknownPacket(UInt32 a_PacketType, UInt32 a_PacketLen, UInt32 a_PacketReadSoFar) +{ + AString Data; + if (!m_ServerBuffer.ReadString(Data, a_PacketLen - a_PacketReadSoFar)) + { + return false; + } + DataLog(Data.data(), Data.size(), "****************** Unknown packet 0x%x from the server; relaying and ignoring", a_PacketType); + COPY_TO_CLIENT(); + return true; +} + + + + + bool cConnection::ParseSlot(cByteBuffer & a_Buffer, AString & a_ItemDesc) { short ItemType; diff --git a/Tools/ProtoProxy/Connection.h b/Tools/ProtoProxy/Connection.h index 56d443b86..c2bce30fb 100644 --- a/Tools/ProtoProxy/Connection.h +++ b/Tools/ProtoProxy/Connection.h @@ -157,6 +157,8 @@ protected: bool HandleClientUseEntity(void); bool HandleClientWindowClick(void); bool HandleClientWindowClose(void); + + bool HandleClientUnknownPacket(UInt32 a_PacketType, UInt32 a_PacketLen, UInt32 a_PacketReadSoFar); // Packet handling, server-side, login: bool HandleServerLoginDisconnect(void); @@ -222,6 +224,8 @@ protected: bool HandleServerWindowContents(void); bool HandleServerWindowOpen(void); + bool HandleServerUnknownPacket(UInt32 a_PacketType, UInt32 a_PacketLen, UInt32 a_PacketReadSoFar); + /// Parses the slot data in a_Buffer into item description; returns true if successful, false if not enough data bool ParseSlot(cByteBuffer & a_Buffer, AString & a_ItemDesc); -- cgit v1.2.3 From 0652e7a4c88151bf1bf708ffc75a7a98d18775da Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Sat, 2 Nov 2013 17:46:37 +0100 Subject: ProtoProxy: Fixed handling of incomplete packets. --- Tools/ProtoProxy/Connection.cpp | 2 ++ 1 file changed, 2 insertions(+) (limited to 'Tools') diff --git a/Tools/ProtoProxy/Connection.cpp b/Tools/ProtoProxy/Connection.cpp index b99415900..143935fe5 100644 --- a/Tools/ProtoProxy/Connection.cpp +++ b/Tools/ProtoProxy/Connection.cpp @@ -718,6 +718,7 @@ bool cConnection::DecodeServersPackets(const char * a_Data, int a_Size) ) { // Not a complete packet yet + m_ServerBuffer.ResetRead(); break; } UInt32 PacketType, PacketReadSoFar; @@ -2683,6 +2684,7 @@ bool cConnection::HandleServerWindowOpen(void) bool cConnection::HandleServerUnknownPacket(UInt32 a_PacketType, UInt32 a_PacketLen, UInt32 a_PacketReadSoFar) { AString Data; + ASSERT(a_PacketLen >= a_PacketReadSoFar); if (!m_ServerBuffer.ReadString(Data, a_PacketLen - a_PacketReadSoFar)) { return false; -- cgit v1.2.3 From 81aa5f3419a445cb29ae727521f97a92adbe29e9 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Sat, 2 Nov 2013 20:59:29 +0100 Subject: ProtoProxy: Removed unused enums. --- Tools/ProtoProxy/Connection.cpp | 112 ++-------------------------------------- 1 file changed, 3 insertions(+), 109 deletions(-) (limited to 'Tools') diff --git a/Tools/ProtoProxy/Connection.cpp b/Tools/ProtoProxy/Connection.cpp index 143935fe5..ad5ae2930 100644 --- a/Tools/ProtoProxy/Connection.cpp +++ b/Tools/ProtoProxy/Connection.cpp @@ -143,112 +143,6 @@ typedef unsigned char Byte; -enum -{ - // client-bound packets: - PACKET_C_KEEPALIVE = 0x00, - PACKET_C_JOIN_GAME = 0x01, - PACKET_C_CHAT_MESSAGE = 0x02, - - // server-bound packets: - PACKET_S_KEEPALIVE = 0x00, // Also the initial handshake, as the very first packet - PACKET_S_CHAT_MESSAGE = 0x01, - - PACKET_TIME_UPDATE = 0x03, - PACKET_ENTITY_EQUIPMENT = 0x04, - PACKET_SPAWN_POSITION = 0x05, - PACKET_UPDATE_HEALTH = 0x06, - PACKET_USE_ENTITY = 0x07, - PACKET_PLAYER_ON_GROUND = 0x0a, - PACKET_PLAYER_POSITION = 0x0b, - PACKET_PLAYER_LOOK = 0x0c, - PACKET_PLAYER_POSITION_LOOK = 0x0d, - PACKET_BLOCK_DIG = 0x0e, - PACKET_BLOCK_PLACE = 0x0f, - PACKET_SLOT_SELECT = 0x10, - PACKET_PLAYER_ANIMATION = 0x12, - PACKET_ENTITY_ACTION = 0x13, - PACKET_SPAWN_NAMED_ENTITY = 0x14, - PACKET_SPAWN_PICKUP = 0x15, - PACKET_COLLECT_PICKUP = 0x16, - PACKET_SPAWN_OBJECT_VEHICLE = 0x17, - PACKET_SPAWN_MOB = 0x18, - PACKET_SPAWN_PAINTING = 0x19, - PACKET_SPAWN_EXPERIENCE_ORB = 0x1a, - PACKET_ENTITY_VELOCITY = 0x1c, - PACKET_DESTROY_ENTITIES = 0x1d, - PACKET_ENTITY = 0x1e, - PACKET_ENTITY_RELATIVE_MOVE = 0x1f, - PACKET_ENTITY_LOOK = 0x20, - PACKET_ENTITY_RELATIVE_MOVE_LOOK = 0x21, - PACKET_ENTITY_TELEPORT = 0x22, - PACKET_ENTITY_HEAD_LOOK = 0x23, - PACKET_ENTITY_STATUS = 0x26, - PACKET_ATTACH_ENTITY = 0x27, - PACKET_ENTITY_METADATA = 0x28, - PACKET_ENTITY_EFFECT = 0x29, - PACKET_ENTITY_EFFECT_REMOVE = 0x2a, - PACKET_SET_EXPERIENCE = 0x2b, - PACKET_ENTITY_PROPERTIES = 0x2c, - PACKET_MAP_CHUNK = 0x33, - PACKET_MULTI_BLOCK_CHANGE = 0x34, - PACKET_BLOCK_CHANGE = 0x35, - PACKET_BLOCK_ACTION = 0x36, - PACKET_MAP_CHUNK_BULK = 0x38, - PACKET_EXPLOSION = 0x3c, - PACKET_SOUND_EFFECT = 0x3d, - PACKET_NAMED_SOUND_EFFECT = 0x3e, - PACKET_CHANGE_GAME_STATE = 0x46, - PACKET_WINDOW_OPEN = 0x64, - PACKET_WINDOW_CLOSE = 0x65, - PACKET_WINDOW_CLICK = 0x66, - PACKET_SET_SLOT = 0x67, - PACKET_WINDOW_CONTENTS = 0x68, - PACKET_CREATIVE_INVENTORY_ACTION = 0x6b, - PACKET_UPDATE_SIGN = 0x82, - PACKET_UPDATE_TILE_ENTITY = 0x84, - PACKET_PLAYER_LIST_ITEM = 0xc9, - PACKET_PLAYER_ABILITIES = 0xca, - PACKET_INCREMENT_STATISTIC = 0xc8, - PACKET_TAB_COMPLETION = 0xcb, - PACKET_LOCALE_AND_VIEW = 0xcc, - PACKET_CLIENT_STATUSES = 0xcd, - PACKET_PLUGIN_MESSAGE = 0xfa, - PACKET_ENCRYPTION_KEY_RESPONSE = 0xfc, - PACKET_ENCRYPTION_KEY_REQUEST = 0xfd, - PACKET_PING = 0xfe, - PACKET_KICK = 0xff, - - // Synonyms: - PACKET_DISCONNECT = PACKET_KICK, -} ; - - - - -enum -{ - OBJECT_BOAT = 1, - OBJECT_MINECART = 10, - OBJECT_MINECART_STORAGE = 11, - OBJECT_MINECART_POWERED = 12, - OBJECT_MINECART_TNT = 13, - OBJECT_MINECART_HOPPER = 14, - OBJECT_TNT = 50, - OBJECT_ENDERCRYSTAL = 51, - OBJECT_ARROW = 60, - OBJECT_SNOWBALL = 61, - OBJECT_EGG = 62, - OBJECT_FALLING_BLOCK = 70, - OBJECT_EYE_OF_ENDER = 72, - OBJECT_DRAGON_EGG = 74, - OBJECT_FISHING_FLOAT = 90, -} ; - - - - - AString PrintableAbsIntTriplet(int a_X, int a_Y, int a_Z, double a_Divisor = 32) { return Printf("<%d, %d, %d> ~ {%.02f, %.02f, %.02f}", @@ -1468,11 +1362,11 @@ bool cConnection::HandleServerBlockChange(void) bool cConnection::HandleServerChangeGameState(void) { - HANDLE_SERVER_PACKET_READ(ReadChar, char, Reason); - HANDLE_SERVER_PACKET_READ(ReadChar, char, Data); + HANDLE_SERVER_PACKET_READ(ReadChar, char, Reason); + HANDLE_SERVER_PACKET_READ(ReadBEFloat, float, Data); Log("Received a PACKET_CHANGE_GAME_STATE from the server:"); Log(" Reason = %d", Reason); - Log(" Data = %d", Data); + Log(" Data = %f", Data); COPY_TO_CLIENT(); return true; } -- cgit v1.2.3 From cd52eeb22348bb503431f1955136f3d9fa5a2df2 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Sun, 3 Nov 2013 00:01:56 +0100 Subject: ProtoProxy: Fixed the SpawnObjectVehicle packet. --- Tools/ProtoProxy/Connection.cpp | 14 +++++++++++++- 1 file changed, 13 insertions(+), 1 deletion(-) (limited to 'Tools') diff --git a/Tools/ProtoProxy/Connection.cpp b/Tools/ProtoProxy/Connection.cpp index ad5ae2930..627b42052 100644 --- a/Tools/ProtoProxy/Connection.cpp +++ b/Tools/ProtoProxy/Connection.cpp @@ -615,6 +615,15 @@ bool cConnection::DecodeServersPackets(const char * a_Data, int a_Size) m_ServerBuffer.ResetRead(); break; } + if (PacketLen == 0) + { + m_ServerBuffer.ResetRead(); + AString All; + m_ServerBuffer.ReadAll(All); + DataLog(All.data(), All.size(), "====== Received a bad packet length? Inspect the contents below ======"); + m_ServerBuffer.CommitRead(); // Try to recover by marking everything as read + break; + } UInt32 PacketType, PacketReadSoFar; PacketReadSoFar = m_ServerBuffer.GetReadableSpace(); VERIFY(m_ServerBuffer.ReadVarInt(PacketType)); @@ -1891,6 +1900,7 @@ bool cConnection::HandleServerMapChunkBulk(void) // TODO: Save the compressed data into a file for later analysis COPY_TO_CLIENT(); + Sleep(50); return true; } @@ -2219,7 +2229,9 @@ bool cConnection::HandleServerSpawnObjectVehicle(void) m_ServerBuffer.ResetRead(); m_ServerBuffer.ReadAll(Buffer); m_ServerBuffer.ResetRead(); - m_ServerBuffer.SkipRead(1); + UInt32 PacketLen, PacketType; + m_ServerBuffer.ReadVarInt(PacketLen); + m_ServerBuffer.ReadVarInt(PacketType); if (Buffer.size() > 128) { // Only log up to 128 bytes -- cgit v1.2.3 From e7ba63b43c0408ee26ccafde9f5a2002570d4820 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Thu, 7 Nov 2013 17:13:25 +0100 Subject: ProtoProxy: Fixed SpawnMob packet. --- Tools/ProtoProxy/Connection.cpp | 25 +++++++++++++------------ 1 file changed, 13 insertions(+), 12 deletions(-) (limited to 'Tools') diff --git a/Tools/ProtoProxy/Connection.cpp b/Tools/ProtoProxy/Connection.cpp index 627b42052..9821c9056 100644 --- a/Tools/ProtoProxy/Connection.cpp +++ b/Tools/ProtoProxy/Connection.cpp @@ -2151,17 +2151,17 @@ bool cConnection::HandleServerSpawnExperienceOrbs(void) bool cConnection::HandleServerSpawnMob(void) { - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, EntityID); - HANDLE_SERVER_PACKET_READ(ReadChar, char, MobType); - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosX); - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosY); - HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosZ); - HANDLE_SERVER_PACKET_READ(ReadByte, Byte, Yaw); - HANDLE_SERVER_PACKET_READ(ReadByte, Byte, Pitch); - HANDLE_SERVER_PACKET_READ(ReadByte, Byte, HeadYaw); - HANDLE_SERVER_PACKET_READ(ReadBEShort, short, VelocityX); - HANDLE_SERVER_PACKET_READ(ReadBEShort, short, VelocityY); - HANDLE_SERVER_PACKET_READ(ReadBEShort, short, VelocityZ); + HANDLE_SERVER_PACKET_READ(ReadVarInt, UInt32, EntityID); + HANDLE_SERVER_PACKET_READ(ReadChar, char, MobType); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosX); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosY); + HANDLE_SERVER_PACKET_READ(ReadBEInt, int, PosZ); + HANDLE_SERVER_PACKET_READ(ReadByte, Byte, Yaw); + HANDLE_SERVER_PACKET_READ(ReadByte, Byte, Pitch); + HANDLE_SERVER_PACKET_READ(ReadByte, Byte, HeadYaw); + HANDLE_SERVER_PACKET_READ(ReadBEShort, short, VelocityX); + HANDLE_SERVER_PACKET_READ(ReadBEShort, short, VelocityY); + HANDLE_SERVER_PACKET_READ(ReadBEShort, short, VelocityZ); AString Metadata; if (!ParseMetadata(m_ServerBuffer, Metadata)) { @@ -2170,7 +2170,7 @@ bool cConnection::HandleServerSpawnMob(void) AString HexDump; CreateHexDump(HexDump, Metadata.data(), Metadata.size(), 32); Log("Received a PACKET_SPAWN_MOB from the server:"); - Log(" EntityID = %d", EntityID); + Log(" EntityID = %u (0x%x)", EntityID, EntityID); Log(" MobType = %d", MobType); Log(" Pos = %s", PrintableAbsIntTriplet(PosX, PosY, PosZ).c_str()); Log(" Angles = [%d, %d, %d]", Yaw, Pitch, HeadYaw); @@ -2705,6 +2705,7 @@ bool cConnection::ParseMetadata(cByteBuffer & a_Buffer, AString & a_Metadata) break; } case 6: Length = 12; break; // 3 * int + case 7: default: { ASSERT(!"Unknown metadata type"); -- cgit v1.2.3 From f0aab7c5809c627923af893ed7159596e502ea6e Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Sun, 10 Nov 2013 22:54:58 +0100 Subject: ProtoProxy: Added dblquotes. --- Tools/ProtoProxy/Connection.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'Tools') diff --git a/Tools/ProtoProxy/Connection.cpp b/Tools/ProtoProxy/Connection.cpp index 9821c9056..385caa2ce 100644 --- a/Tools/ProtoProxy/Connection.cpp +++ b/Tools/ProtoProxy/Connection.cpp @@ -2205,8 +2205,8 @@ bool cConnection::HandleServerSpawnNamedEntity(void) CreateHexDump(HexDump, Metadata.data(), Metadata.size(), 32); Log("Received a PACKET_SPAWN_NAMED_ENTITY from the server:"); Log(" EntityID = %u (0x%x)", EntityID, EntityID); - Log(" UUID = %s", EntityUUID.c_str()); - Log(" Name = %s", EntityName.c_str()); + Log(" UUID = \"%s\"", EntityUUID.c_str()); + Log(" Name = \"%s\"", EntityName.c_str()); Log(" Pos = %s", PrintableAbsIntTriplet(PosX, PosY, PosZ).c_str()); Log(" Rotation = ", Yaw, Pitch); Log(" CurrentItem = %d", CurrentItem); -- cgit v1.2.3 From dbb76ef9fefa90a1e24acc42ba0421980df89379 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Sun, 24 Nov 2013 14:35:35 +0100 Subject: RCONClient: Initial implementation. Fix #79. --- Tools/RCONClient/.gitignore | 7 + Tools/RCONClient/Globals.cpp | 10 ++ Tools/RCONClient/Globals.h | 208 +++++++++++++++++++++++ Tools/RCONClient/RCONClient.cpp | 332 +++++++++++++++++++++++++++++++++++++ Tools/RCONClient/RCONClient.sln | 20 +++ Tools/RCONClient/RCONClient.vcproj | 287 ++++++++++++++++++++++++++++++++ 6 files changed, 864 insertions(+) create mode 100644 Tools/RCONClient/.gitignore create mode 100644 Tools/RCONClient/Globals.cpp create mode 100644 Tools/RCONClient/Globals.h create mode 100644 Tools/RCONClient/RCONClient.cpp create mode 100644 Tools/RCONClient/RCONClient.sln create mode 100644 Tools/RCONClient/RCONClient.vcproj (limited to 'Tools') diff --git a/Tools/RCONClient/.gitignore b/Tools/RCONClient/.gitignore new file mode 100644 index 000000000..e124797c5 --- /dev/null +++ b/Tools/RCONClient/.gitignore @@ -0,0 +1,7 @@ +Debug/ +logs/ +Release/ +*.suo +*.user +*.ncb +*.sdf diff --git a/Tools/RCONClient/Globals.cpp b/Tools/RCONClient/Globals.cpp new file mode 100644 index 000000000..13c6ae709 --- /dev/null +++ b/Tools/RCONClient/Globals.cpp @@ -0,0 +1,10 @@ + +// Globals.cpp + +// This file is used for precompiled header generation in MSVC environments + +#include "Globals.h" + + + + diff --git a/Tools/RCONClient/Globals.h b/Tools/RCONClient/Globals.h new file mode 100644 index 000000000..a3a2f2846 --- /dev/null +++ b/Tools/RCONClient/Globals.h @@ -0,0 +1,208 @@ + +// Globals.h + +// This file gets included from every module in the project, so that global symbols may be introduced easily +// Also used for precompiled header generation in MSVC environments + + + + + +// Compiler-dependent stuff: +#if defined(_MSC_VER) + // MSVC produces warning C4481 on the override keyword usage, so disable the warning altogether + #pragma warning(disable:4481) + + // Disable some warnings that we don't care about: + #pragma warning(disable:4100) + + #define OBSOLETE __declspec(deprecated) + + // No alignment needed in MSVC + #define ALIGN_8 + #define ALIGN_16 + +#elif defined(__GNUC__) + + // TODO: Can GCC explicitly mark classes as abstract (no instances can be created)? + #define abstract + + // TODO: Can GCC mark virtual methods as overriding (forcing them to have a virtual function of the same signature in the base class) + #define override + + #define OBSOLETE __attribute__((deprecated)) + + #define ALIGN_8 __attribute__((aligned(8))) + #define ALIGN_16 __attribute__((aligned(16))) + + // Some portability macros :) + #define stricmp strcasecmp + +#else + + #error "You are using an unsupported compiler, you might need to #define some stuff here for your compiler" + + /* + // Copy and uncomment this into another #elif section based on your compiler identification + + // Explicitly mark classes as abstract (no instances can be created) + #define abstract + + // Mark virtual methods as overriding (forcing them to have a virtual function of the same signature in the base class) + #define override + + // Mark functions as obsolete, so that their usage results in a compile-time warning + #define OBSOLETE + + // Mark types / variables for alignment. Do the platforms need it? + #define ALIGN_8 + #define ALIGN_16 + */ + +#endif + + + + + +// Integral types with predefined sizes: +typedef long long Int64; +typedef int Int32; +typedef short Int16; + +typedef unsigned long long UInt64; +typedef unsigned int UInt32; +typedef unsigned short UInt16; + + + + + +// A macro to disallow the copy constructor and operator= functions +// This should be used in the private: declarations for any class that shouldn't allow copying itself +#define DISALLOW_COPY_AND_ASSIGN(TypeName) \ + TypeName(const TypeName &); \ + void operator=(const TypeName &) + +// A macro that is used to mark unused function parameters, to avoid pedantic warnings in gcc +#define UNUSED(X) (void)(X) + + + + +// OS-dependent stuff: +#ifdef _WIN32 + #define WIN32_LEAN_AND_MEAN + + #define _WIN32_WINNT 0x501 // We want to target WinXP and higher + + #include + #include + #include // IPv6 stuff + + // Windows SDK defines min and max macros, messing up with our std::min and std::max usage + #undef min + #undef max + + // Windows SDK defines GetFreeSpace as a constant, probably a Win16 API remnant + #ifdef GetFreeSpace + #undef GetFreeSpace + #endif // GetFreeSpace +#else + #include + #include // for mkdir + #include + #include + #include + #include + #include + #include + #include + #include + #include + + #include + #include + #include + #include + #include + #include +#if !defined(ANDROID_NDK) + #include +#endif +#endif + +#if !defined(ANDROID_NDK) + #define USE_SQUIRREL +#endif + +#if defined(ANDROID_NDK) + #define FILE_IO_PREFIX "/sdcard/mcserver/" +#else + #define FILE_IO_PREFIX "" +#endif + + + + + +// CRT stuff: +#include +#include +#include +#include +#include +#include + + + + + +// STL stuff: +#include +#include +#include +#include +#include +#include +#include + + + + + +// Common headers (part 1, without macros): +#include "StringUtils.h" +#include "OSSupport/CriticalSection.h" +#include "OSSupport/File.h" +#include "MCLogger.h" + + + + + +// Common definitions: + +/// Evaluates to the number of elements in an array (compile-time!) +#define ARRAYCOUNT(X) (sizeof(X) / sizeof(*(X))) + +/// Allows arithmetic expressions like "32 KiB" (but consider using parenthesis around it, "(32 KiB)" ) +#define KiB * 1024 + +/// Faster than (int)floorf((float)x / (float)div) +#define FAST_FLOOR_DIV( x, div ) ( (x) < 0 ? (((int)x / div) - 1) : ((int)x / div) ) + +// Own version of assert() that writes failed assertions to the log for review +#ifdef NDEBUG + #define ASSERT(x) ((void)0) +#else + #define ASSERT assert +#endif + +// Pretty much the same as ASSERT() but stays in Release builds +#define VERIFY( x ) ( !!(x) || ( LOGERROR("Verification failed: %s, file %s, line %i", #x, __FILE__, __LINE__ ), exit(1), 0 ) ) + + + + + diff --git a/Tools/RCONClient/RCONClient.cpp b/Tools/RCONClient/RCONClient.cpp new file mode 100644 index 000000000..288363a66 --- /dev/null +++ b/Tools/RCONClient/RCONClient.cpp @@ -0,0 +1,332 @@ + +// RCONClient.cpp + +// Implements the main app entrypoint + +#include "Globals.h" +#include "OSSupport/Socket.h" +#include "ByteBuffer.h" + + + + + +// If set to true, verbose messages are output to stderr. Use the "-v" or "--verbose" param to turn on +bool g_IsVerbose = false; + + + + + +/// This class can read and write RCON packets to / from a connected socket +class cRCONPacketizer +{ +public: + enum + { + ptCommand = 2, + ptLogin = 3, + } ; + + cRCONPacketizer(cSocket & a_Socket); + + /// Sends the packet to the socket and waits until the response is received. + /// Returns true if response successfully received, false if the client disconnected or protocol error. + /// Dumps the reply payload to stdout. + bool SendPacket(int a_PacketType, const AString & a_PacketPayload); + +protected: + /// The socket to use for reading incoming data and writing outgoing data: + cSocket & m_Socket; + + /// The RequestID of the packet that is being sent. Incremented when the reply is received + int m_RequestID; + + /// Receives the full response and dumps its payload to stdout. + /// Returns true if successful, false if the client disconnected or protocol error. + bool ReceiveResponse(void); + + /// Parses the received response packet and dumps its payload to stdout. + /// Returns true if successful, false on protocol error + /// Assumes that the packet length has already been read from the packet + /// If the packet is successfully parsed, increments m_RequestID + bool ParsePacket(cByteBuffer & a_Buffer, int a_PacketLength); +} ; + + + + + +cRCONPacketizer::cRCONPacketizer(cSocket & a_Socket) : + m_Socket(a_Socket), + m_RequestID(0) +{ +} + + + + + +bool cRCONPacketizer::SendPacket(int a_PacketType, const AString & a_PacketPayload) +{ + // Send the packet: + cByteBuffer bb(a_PacketPayload.size() + 30); + bb.WriteLEInt(m_RequestID); + bb.WriteLEInt(a_PacketType); + bb.WriteBuf(a_PacketPayload.data(), a_PacketPayload.size()); + bb.WriteBEShort(0); // Padding + AString Packet; + bb.ReadAll(Packet); + size_t Length = Packet.size(); + if (!m_Socket.Send((const char *)&Length, 4)) + { + fprintf(stderr, "Network error while sending packet: %d (%s). Aborting.", + cSocket::GetLastError(), cSocket::GetLastErrorString().c_str() + ); + return false; + } + if (!m_Socket.Send(Packet.data(), Packet.size())) + { + fprintf(stderr, "Network error while sending packet: %d (%s). Aborting.", + cSocket::GetLastError(), cSocket::GetLastErrorString().c_str() + ); + return false; + } + + return ReceiveResponse(); +} + + + + + +bool cRCONPacketizer::ReceiveResponse(void) +{ + // Receive the response: + cByteBuffer Buffer(64 KiB); + while (true) + { + char buf[1024]; + int NumReceived = m_Socket.Receive(buf, sizeof(buf), 0); + if (NumReceived == 0) + { + fprintf(stderr, "The remote end closed the connection. Aborting."); + return false; + } + if (NumReceived < 0) + { + fprintf(stderr, "Network error while receiving response: %d, %d (%s). Aborting.", + NumReceived, cSocket::GetLastError(), cSocket::GetLastErrorString().c_str() + ); + return false; + } + Buffer.Write(buf, NumReceived); + Buffer.ResetRead(); + + // Check if the buffer contains the full packet: + if (!Buffer.CanReadBytes(14)) + { + // 14 is the minimum packet size for RCON + continue; + } + int PacketSize; + VERIFY(Buffer.ReadLEInt(PacketSize)); + if (!Buffer.CanReadBytes(PacketSize)) + { + // The packet is not complete yet + continue; + } + + // Parse the packet + return ParsePacket(Buffer, PacketSize); + } +} + + + + + +bool cRCONPacketizer::ParsePacket(cByteBuffer & a_Buffer, int a_PacketLength) +{ + // Check that the request ID is equal + bool IsValid = true; + int RequestID = 0; + VERIFY(a_Buffer.ReadLEInt(RequestID)); + if (RequestID != m_RequestID) + { + if ((RequestID == -1) && (m_RequestID == 0)) + { + fprintf(stderr, "Login failed. Aborting."); + IsValid = false; + // Continue, so that the payload is printed before the program aborts. + } + else + { + fprintf(stderr, "The server returned an invalid request ID, got %d, exp. %d. Aborting.", RequestID, m_RequestID); + return false; + } + } + + // Check the packet type: + int PacketType = 0; + VERIFY(a_Buffer.ReadLEInt(PacketType)); + if (PacketType != ptCommand) + { + fprintf(stderr, "The server returned an unknown packet type: %d. Aborting.", PacketType); + IsValid = false; + // Continue, so that the payload is printed before the program aborts. + } + + AString Payload; + VERIFY(a_Buffer.ReadString(Payload, a_PacketLength - 10)); + + // Dump the payload to stdout, in a binary mode + fwrite(Payload.data(), Payload.size(), 1, stdout); + + if (IsValid) + { + m_RequestID++; + return true; + } + return false; +} + + + + + +/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// +// main: + +int RealMain(int argc, char * argv[]) +{ + new cMCLogger; // Create a new logger + + // Parse the cmdline params for server IP, port, password and the commands to send: + AString ServerAddress, Password; + int ServerPort = -1; + AStringVector Commands; + for (int i = 1; i < argc; i++) + { + if (((NoCaseCompare(argv[i], "-s") == 0) || (NoCaseCompare(argv[i], "--server") == 0)) && (i < argc - 1)) + { + ServerAddress = argv[i + 1]; + i++; + continue; + } + if (((NoCaseCompare(argv[i], "-p") == 0) || (NoCaseCompare(argv[i], "--port") == 0)) && (i < argc - 1)) + { + ServerPort = atoi(argv[i + 1]); + i++; + continue; + } + if (((NoCaseCompare(argv[i], "-w") == 0) || (NoCaseCompare(argv[i], "--password") == 0)) && (i < argc - 1)) + { + Password = argv[i + 1]; + i++; + continue; + } + if (((NoCaseCompare(argv[i], "-c") == 0) || (NoCaseCompare(argv[i], "--cmd") == 0) || (NoCaseCompare(argv[i], "--command") == 0)) && (i < argc - 1)) + { + Commands.push_back(argv[i + 1]); + i++; + continue; + } + if (((NoCaseCompare(argv[i], "-f") == 0) || (NoCaseCompare(argv[i], "--file") == 0)) && (i < argc - 1)) + { + i++; + cFile f(argv[i], cFile::fmRead); + if (!f.IsOpen()) + { + fprintf(stderr, "Cannot read commands from file \"%s\", aborting.", argv[i]); + return 2; + } + AString cmd; + f.ReadRestOfFile(cmd); + Commands.push_back(cmd); + continue; + } + if ((NoCaseCompare(argv[i], "-v") == 0) || (NoCaseCompare(argv[i], "--verbose") == 0)) + { + fprintf(stderr, "Verbose output enabled\n"); + g_IsVerbose = true; + continue; + } + fprintf(stderr, "Unknown parameter: \"%s\". Aborting.", argv[i]); + return 1; + } // for i - argv[] + + if (ServerAddress.empty() || (ServerPort < 0)) + { + fprintf(stderr, "Server address or port not set. Use the --server and --port parameters to set them. Aborting."); + return 1; + } + + // Connect: + if (cSocket::WSAStartup() != 0) + { + fprintf(stderr, "Cannot initialize network stack. Aborting\n"); + return 6; + } + if (g_IsVerbose) + { + fprintf(stderr, "Connecting to \"%s:%d\"...\n", ServerAddress.c_str(), ServerPort); + } + cSocket s = cSocket::CreateSocket(cSocket::IPv4); + if (!s.ConnectIPv4(ServerAddress, (unsigned short)ServerPort)) + { + fprintf(stderr, "Cannot connect to \"%s:%d\": %s\n", ServerAddress.c_str(), ServerPort, cSocket::GetLastErrorString().c_str()); + return 3; + } + cRCONPacketizer Packetizer(s); + + // Authenticate using the provided password: + if (!Password.empty()) + { + if (g_IsVerbose) + { + fprintf(stderr, "Sending the login packet...\n"); + } + if (!Packetizer.SendPacket(cRCONPacketizer::ptLogin, Password)) + { + // Error message has already been printed, bail out + return 4; + } + } + else + { + if (g_IsVerbose) + { + fprintf(stderr, "No password provided, not sending a login packet.\n"); + } + } + + for (AStringVector::const_iterator itr = Commands.begin(), end = Commands.end(); itr != end; ++itr) + { + if (g_IsVerbose) + { + fprintf(stderr, "Sending command \"%s\"...\n", itr->c_str()); + } + if (!Packetizer.SendPacket(cRCONPacketizer::ptCommand, *itr)) + { + return 5; + } + } + + return 0; +} + + + + + +int main(int argc, char * argv[]) +{ + // This redirection function is only so that debugging the program is easier in MSVC - when RealMain exits, it's still possible to place a breakpoint + int res = RealMain(argc, argv); + return res; +} + + + + diff --git a/Tools/RCONClient/RCONClient.sln b/Tools/RCONClient/RCONClient.sln new file mode 100644 index 000000000..0a8596e43 --- /dev/null +++ b/Tools/RCONClient/RCONClient.sln @@ -0,0 +1,20 @@ + +Microsoft Visual Studio Solution File, Format Version 10.00 +# Visual C++ Express 2008 +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "RCONClient", "RCONClient.vcproj", "{1A48B032-07D0-4DDD-8362-66C0FC7F7849}" +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|Win32 = Debug|Win32 + Release|Win32 = Release|Win32 + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {1A48B032-07D0-4DDD-8362-66C0FC7F7849}.Debug|Win32.ActiveCfg = Debug|Win32 + {1A48B032-07D0-4DDD-8362-66C0FC7F7849}.Debug|Win32.Build.0 = Debug|Win32 + {1A48B032-07D0-4DDD-8362-66C0FC7F7849}.Release|Win32.ActiveCfg = Release|Win32 + {1A48B032-07D0-4DDD-8362-66C0FC7F7849}.Release|Win32.Build.0 = Release|Win32 + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection +EndGlobal diff --git a/Tools/RCONClient/RCONClient.vcproj b/Tools/RCONClient/RCONClient.vcproj new file mode 100644 index 000000000..59d0b3b74 --- /dev/null +++ b/Tools/RCONClient/RCONClient.vcproj @@ -0,0 +1,287 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + -- cgit v1.2.3 From 274bdc40ff84af8042173d11ccd4f4db418e3033 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Sun, 24 Nov 2013 17:49:04 +0100 Subject: BiomeVisualiser: Added 1.7 biomes, recolored using AMIDST colors. --- Tools/BiomeVisualiser/BiomeColors.cpp | 114 +++++++++++++++++++++++++++ Tools/BiomeVisualiser/BiomeColors.h | 15 ++++ Tools/BiomeVisualiser/BiomeRenderer.cpp | 36 +-------- Tools/BiomeVisualiser/BiomeVisualiser.vcproj | 8 ++ 4 files changed, 141 insertions(+), 32 deletions(-) create mode 100644 Tools/BiomeVisualiser/BiomeColors.cpp create mode 100644 Tools/BiomeVisualiser/BiomeColors.h (limited to 'Tools') diff --git a/Tools/BiomeVisualiser/BiomeColors.cpp b/Tools/BiomeVisualiser/BiomeColors.cpp new file mode 100644 index 000000000..1fd0cb7a0 --- /dev/null +++ b/Tools/BiomeVisualiser/BiomeColors.cpp @@ -0,0 +1,114 @@ + +// BiomeColors.cpp + +// Implements the g_BiomeColors[] array preparation based on a stored biome-to-color map + +#include "Globals.h" +#include "BiomeColors.h" + + + + + +int g_BiomeColors[256]; + + + + + +static struct +{ + EMCSBiome Biome; + int Color; +} g_BiomeColorMap[] = +{ + { biOcean, 0x000070 }, + { biPlains, 0x8db360 }, + { biDesert, 0xfa9418 }, + { biExtremeHills, 0x606060 }, + { biForest, 0x056621 }, + { biTaiga, 0x0b6659 }, + { biSwampland, 0x2fffda }, + { biRiver, 0x3030af }, + { biHell, 0x7f0000 }, + { biSky, 0x007fff }, + { biFrozenOcean, 0xa0a0df }, + { biFrozenRiver, 0xa0a0ff }, + { biIcePlains, 0xffffff }, + { biIceMountains, 0xa0a0a0 }, + { biMushroomIsland, 0xff00ff }, + { biMushroomShore, 0xa000ff }, + { biBeach, 0xfade55 }, + { biDesertHills, 0xd25f12 }, + { biForestHills, 0x22551c }, + { biTaigaHills, 0x163933 }, + { biExtremeHillsEdge, 0x7f8f7f }, + { biJungle, 0x537b09 }, + { biJungleHills, 0x2c4205 }, + + { biJungleEdge, 0x628b17 }, + { biDeepOcean, 0x000030 }, + { biStoneBeach, 0xa2a284 }, + { biColdBeach, 0xfaf0c0 }, + { biBirchForest, 0x307444 }, + { biBirchForestHills, 0x1f5f32 }, + { biRoofedForest, 0x40511a }, + { biColdTaiga, 0x31554a }, + { biColdTaigaHills, 0x597d72 }, + { biMegaTaiga, 0x596651 }, + { biMegaTaigaHills, 0x596659 }, + { biExtremeHillsPlus, 0x507050 }, + { biSavanna, 0xbdb25f }, + { biSavannaPlateau, 0xa79d64 }, + { biMesa, 0xd94515 }, + { biMesaPlateauF, 0xb09765 }, + { biMesaPlateau, 0xca8c65 }, + + // M variants: + { biSunflowerPlains, 0xb5db88 }, + { biDesertM, 0xffbc40 }, + { biExtremeHillsM, 0x888888 }, + { biFlowerForest, 0x2d8e49 }, + { biTaigaM, 0x338e81 }, + { biSwamplandM, 0x07f9b2 }, + { biIcePlainsSpikes, 0xb4dcdc }, + { biJungleM, 0x7ba331 }, + { biJungleEdgeM, 0x628b17 }, + { biBirchForestM, 0x589c6c }, + { biBirchForestHillsM, 0x47875a }, + { biRoofedForestM, 0x687942 }, + { biColdTaigaM, 0x243f36 }, + { biMegaSpruceTaiga, 0x454f3e }, + { biMegaSpruceTaigaHills, 0x454f4e }, + { biExtremeHillsPlusM, 0x789878 }, + { biSavannaM, 0xe5da87 }, + { biSavannaPlateauM, 0xa79d74 }, + { biMesaBryce, 0xff6d3d }, + { biMesaPlateauFM, 0xd8bf8d }, + { biMesaPlateauM, 0xf2b48d }, +} ; + + + + + +static class cBiomeColorsInitializer +{ +public: + cBiomeColorsInitializer(void) + { + // Reset all colors to gray: + for (size_t i = 0; i < ARRAYCOUNT(g_BiomeColors); i++) + { + g_BiomeColors[i] = 0x7f7f7f; + } + for (size_t i = 0; i < ARRAYCOUNT(g_BiomeColorMap); i++) + { + g_BiomeColors[g_BiomeColorMap[i].Biome] = g_BiomeColorMap[i].Color; + } + } +} g_Initializer; + + + + diff --git a/Tools/BiomeVisualiser/BiomeColors.h b/Tools/BiomeVisualiser/BiomeColors.h new file mode 100644 index 000000000..0cb0f578c --- /dev/null +++ b/Tools/BiomeVisualiser/BiomeColors.h @@ -0,0 +1,15 @@ + +// BiomeColors.h + +// Declares the g_BiomeColors[] array used for biome color lookup + + + + + +extern int g_BiomeColors[256]; + + + + + diff --git a/Tools/BiomeVisualiser/BiomeRenderer.cpp b/Tools/BiomeVisualiser/BiomeRenderer.cpp index 98548179c..758eb4b48 100644 --- a/Tools/BiomeVisualiser/BiomeRenderer.cpp +++ b/Tools/BiomeVisualiser/BiomeRenderer.cpp @@ -7,6 +7,7 @@ #include "BiomeRenderer.h" #include "Pixmap.h" #include "Timer.h" +#include "BiomeColors.h" @@ -96,40 +97,11 @@ bool cBiomeRenderer::Render(cPixmap & a_Pixmap) int cBiomeRenderer::GetBiomeColor(EMCSBiome a_Biome) { - if ((a_Biome < 0) || (a_Biome > biMaxBiome)) + if ((a_Biome < 0) || (a_Biome >= ARRAYCOUNT(g_BiomeColors))) { - return 0xcfcfcf; // LtGray for unknown biomes + return 0xff0000; } - - static int BiomeColor[] = - { - // RGB: - 0x0000ff, /* Ocean */ - 0x00cf3f, /* Plains */ - 0xffff00, /* Desert */ - 0x7f7f7f, /* Extreme Hills */ - 0x00cf00, /* Forest */ - 0x007f3f, /* Taiga */ - 0x3f7f00, /* Swampland */ - 0x003fff, /* River */ - 0x7f0000, /* Hell */ - 0x007fff, /* Sky */ - 0x3f3fff, /* Frozen Ocean */ - 0x3f3fff, /* Frozen River */ - 0x7fffcf, /* Ice Plains */ - 0x3fcf7f, /* Ice Mountains */ - 0xcf00cf, /* Mushroom Island */ - 0x7f00ff, /* Mushroom Island Shore */ - 0xffff3f, /* Beach */ - 0xcfcf00, /* Desert Hills */ - 0x00cf3f, /* Forest Hills */ - 0x006f1f, /* Taiga Hills */ - 0x7f8f7f, /* Extreme Hills Edge */ - 0x004f00, /* Jungle */ - 0x003f00, /* Jungle Hills */ - } ; - - return BiomeColor[a_Biome]; + return g_BiomeColors[a_Biome]; } diff --git a/Tools/BiomeVisualiser/BiomeVisualiser.vcproj b/Tools/BiomeVisualiser/BiomeVisualiser.vcproj index 5f840129d..2616313a2 100644 --- a/Tools/BiomeVisualiser/BiomeVisualiser.vcproj +++ b/Tools/BiomeVisualiser/BiomeVisualiser.vcproj @@ -268,6 +268,10 @@ RelativePath=".\BiomeCache.h" > + + @@ -489,6 +493,10 @@ + + -- cgit v1.2.3 From 2d68969a45a1d259728bb752d95bd517cdd8a772 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Sun, 24 Nov 2013 22:10:27 +0100 Subject: AnvilStats: Fixed compilation. --- Tools/AnvilStats/Globals.h | 1 + Tools/AnvilStats/Processor.cpp | 4 ++-- 2 files changed, 3 insertions(+), 2 deletions(-) (limited to 'Tools') diff --git a/Tools/AnvilStats/Globals.h b/Tools/AnvilStats/Globals.h index db5d3c635..48e1f8492 100644 --- a/Tools/AnvilStats/Globals.h +++ b/Tools/AnvilStats/Globals.h @@ -138,6 +138,7 @@ typedef unsigned short UInt16; // CRT stuff: +#include #include #include #include diff --git a/Tools/AnvilStats/Processor.cpp b/Tools/AnvilStats/Processor.cpp index 8e1cc4c4b..4ecd685ad 100644 --- a/Tools/AnvilStats/Processor.cpp +++ b/Tools/AnvilStats/Processor.cpp @@ -554,8 +554,8 @@ void cProcessor::PopulateFileQueue(const AString & a_WorldFolder) { Path.push_back(cFile::PathSeparator); } - AStringList AllFiles = GetDirectoryContents(Path.c_str()); - for (AStringList::iterator itr = AllFiles.begin(), end = AllFiles.end(); itr != end; ++itr) + AStringVector AllFiles = cFile::GetFolderContents(Path.c_str()); + for (AStringVector::iterator itr = AllFiles.begin(), end = AllFiles.end(); itr != end; ++itr) { if (itr->rfind(".mca") != itr->length() - 4) { -- cgit v1.2.3 From 19895dc428b16445014f90c4a2f4e495bc6767d7 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Thu, 28 Nov 2013 09:52:28 +0100 Subject: ProtoProxy: Fixed after folder move. --- Tools/ProtoProxy/Connection.h | 2 +- Tools/ProtoProxy/ProtoProxy.vcproj | 62 ++++++++++++++++++++------------------ 2 files changed, 34 insertions(+), 30 deletions(-) (limited to 'Tools') diff --git a/Tools/ProtoProxy/Connection.h b/Tools/ProtoProxy/Connection.h index c2bce30fb..abb8b6cd0 100644 --- a/Tools/ProtoProxy/Connection.h +++ b/Tools/ProtoProxy/Connection.h @@ -10,7 +10,7 @@ #pragma once #include "ByteBuffer.h" -#include "../../source/OSSupport/Timer.h" +#include "OSSupport/Timer.h" diff --git a/Tools/ProtoProxy/ProtoProxy.vcproj b/Tools/ProtoProxy/ProtoProxy.vcproj index 926bbe586..0b3c77bc5 100644 --- a/Tools/ProtoProxy/ProtoProxy.vcproj +++ b/Tools/ProtoProxy/ProtoProxy.vcproj @@ -41,7 +41,7 @@ - - - - - - - - - - - - + + + + + + + + + + + + + Date: Thu, 28 Nov 2013 10:05:39 +0100 Subject: Fixed AnvilStats after folder move. --- Tools/AnvilStats/AnvilStats.vcproj | 36 ++++++++++++++++++------------------ Tools/AnvilStats/ChunkExtract.cpp | 2 +- Tools/AnvilStats/Globals.h | 16 ++++++++-------- Tools/AnvilStats/Processor.cpp | 4 ++-- Tools/AnvilStats/Statistics.cpp | 2 +- 5 files changed, 30 insertions(+), 30 deletions(-) (limited to 'Tools') diff --git a/Tools/AnvilStats/AnvilStats.vcproj b/Tools/AnvilStats/AnvilStats.vcproj index 038f32b97..c7a2e9390 100644 --- a/Tools/AnvilStats/AnvilStats.vcproj +++ b/Tools/AnvilStats/AnvilStats.vcproj @@ -41,7 +41,7 @@ diff --git a/Tools/AnvilStats/ChunkExtract.cpp b/Tools/AnvilStats/ChunkExtract.cpp index 71e804e73..96287ebef 100644 --- a/Tools/AnvilStats/ChunkExtract.cpp +++ b/Tools/AnvilStats/ChunkExtract.cpp @@ -5,7 +5,7 @@ #include "Globals.h" #include "ChunkExtract.h" -#include "../../source/OSSupport/GZipFile.h" +#include "../../src/OSSupport/GZipFile.h" diff --git a/Tools/AnvilStats/Globals.h b/Tools/AnvilStats/Globals.h index 48e1f8492..c673ecb01 100644 --- a/Tools/AnvilStats/Globals.h +++ b/Tools/AnvilStats/Globals.h @@ -163,12 +163,12 @@ typedef unsigned short UInt16; // Common headers (part 1, without macros): -#include "../../source/StringUtils.h" -#include "../../source/OSSupport/CriticalSection.h" -#include "../../source/OSSupport/Semaphore.h" -#include "../../source/OSSupport/Event.h" -#include "../../source/OSSupport/IsThread.h" -#include "../../source/OSSupport/File.h" +#include "../../src/StringUtils.h" +#include "../../src/OSSupport/CriticalSection.h" +#include "../../src/OSSupport/Semaphore.h" +#include "../../src/OSSupport/Event.h" +#include "../../src/OSSupport/IsThread.h" +#include "../../src/OSSupport/File.h" @@ -221,8 +221,8 @@ public: // Common headers (part 2, with macros): -#include "../../source/ChunkDef.h" -#include "../../source/BlockID.h" +#include "../../src/ChunkDef.h" +#include "../../src/BlockID.h" diff --git a/Tools/AnvilStats/Processor.cpp b/Tools/AnvilStats/Processor.cpp index 4ecd685ad..a16f78c18 100644 --- a/Tools/AnvilStats/Processor.cpp +++ b/Tools/AnvilStats/Processor.cpp @@ -6,8 +6,8 @@ #include "Globals.h" #include "Processor.h" #include "Callback.h" -#include "../../source/WorldStorage/FastNBT.h" -#include "zlib.h" +#include "../../src/WorldStorage/FastNBT.h" +#include "zlib/zlib.h" #include "Utils.h" diff --git a/Tools/AnvilStats/Statistics.cpp b/Tools/AnvilStats/Statistics.cpp index b5b3cb176..f7519fd37 100644 --- a/Tools/AnvilStats/Statistics.cpp +++ b/Tools/AnvilStats/Statistics.cpp @@ -5,7 +5,7 @@ #include "Globals.h" #include "Statistics.h" -#include "../../source/WorldStorage/FastNBT.h" +#include "../../src/WorldStorage/FastNBT.h" -- cgit v1.2.3 From afd94a0b11ae1e5c98efb378a14ecca140bf310b Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Thu, 28 Nov 2013 10:09:45 +0100 Subject: Fixed BiomeVisualiser after folder move. --- Tools/BiomeVisualiser/BiomeCache.h | 2 +- Tools/BiomeVisualiser/BiomeViewWnd.cpp | 2 +- Tools/BiomeVisualiser/BiomeVisualiser.vcproj | 80 +++++++++++++++------------- Tools/BiomeVisualiser/GeneratorBiomeSource.h | 2 +- 4 files changed, 47 insertions(+), 39 deletions(-) (limited to 'Tools') diff --git a/Tools/BiomeVisualiser/BiomeCache.h b/Tools/BiomeVisualiser/BiomeCache.h index bf1503d4c..da4d6c761 100644 --- a/Tools/BiomeVisualiser/BiomeCache.h +++ b/Tools/BiomeVisualiser/BiomeCache.h @@ -17,7 +17,7 @@ While the area is being filled, requests for biomes may already come, such reque #include "BiomeSource.h" -#include "../source/OSSupport/IsThread.h" +#include "../src/OSSupport/IsThread.h" diff --git a/Tools/BiomeVisualiser/BiomeViewWnd.cpp b/Tools/BiomeVisualiser/BiomeViewWnd.cpp index 7d4db58c0..0658e3810 100644 --- a/Tools/BiomeVisualiser/BiomeViewWnd.cpp +++ b/Tools/BiomeVisualiser/BiomeViewWnd.cpp @@ -7,7 +7,7 @@ #include "BiomeViewWnd.h" #include "BiomeCache.h" #include "GeneratorBiomeSource.h" -#include "../iniFile/iniFile.h" +#include "iniFile/iniFile.h" diff --git a/Tools/BiomeVisualiser/BiomeVisualiser.vcproj b/Tools/BiomeVisualiser/BiomeVisualiser.vcproj index 2616313a2..e42870b13 100644 --- a/Tools/BiomeVisualiser/BiomeVisualiser.vcproj +++ b/Tools/BiomeVisualiser/BiomeVisualiser.vcproj @@ -41,7 +41,7 @@ + + + + @@ -467,15 +475,15 @@ Name="Generating" > @@ -483,11 +491,11 @@ Name="iniFile" > diff --git a/Tools/BiomeVisualiser/GeneratorBiomeSource.h b/Tools/BiomeVisualiser/GeneratorBiomeSource.h index 0b47e5f93..751aed245 100644 --- a/Tools/BiomeVisualiser/GeneratorBiomeSource.h +++ b/Tools/BiomeVisualiser/GeneratorBiomeSource.h @@ -3,7 +3,7 @@ // Declares the cGeneratorBiomeSource that adapts a cBiomeGen into a cBiomeSource -#include "../source/Generating/BioGen.h" +#include "../src/Generating/BioGen.h" #include "BiomeSource.h" -- cgit v1.2.3 From bb37271f306507f8d0161bc655913c69412ba16a Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Thu, 28 Nov 2013 13:48:52 +0100 Subject: Fixed BlockZapper after folder move. --- Tools/BlockZapper/.gitignore | 3 +++ Tools/BlockZapper/BlockZapper.sln | 2 +- Tools/BlockZapper/BlockZapper.vcproj | 44 +++++++++++++++--------------------- Tools/BlockZapper/GNUmakefile | 28 +++++++++++------------ Tools/BlockZapper/Globals.h | 2 +- Tools/BlockZapper/Zapper.cpp | 2 +- 6 files changed, 37 insertions(+), 44 deletions(-) create mode 100644 Tools/BlockZapper/.gitignore (limited to 'Tools') diff --git a/Tools/BlockZapper/.gitignore b/Tools/BlockZapper/.gitignore new file mode 100644 index 000000000..b4e15dc3c --- /dev/null +++ b/Tools/BlockZapper/.gitignore @@ -0,0 +1,3 @@ +Debug/ +logs/ +Release/ diff --git a/Tools/BlockZapper/BlockZapper.sln b/Tools/BlockZapper/BlockZapper.sln index 9a71b9311..f65451d1b 100644 --- a/Tools/BlockZapper/BlockZapper.sln +++ b/Tools/BlockZapper/BlockZapper.sln @@ -6,7 +6,7 @@ Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "BlockZapper", "BlockZapper. {EA9D50FD-937A-4EF5-8C37-5F4175AF4FEA} = {EA9D50FD-937A-4EF5-8C37-5F4175AF4FEA} EndProjectSection EndProject -Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "zlib", "..\..\..\mc-server.clean\VC2008\zlib.vcproj", "{EA9D50FD-937A-4EF5-8C37-5F4175AF4FEA}" +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "zlib", "..\..\VC2008\zlib.vcproj", "{EA9D50FD-937A-4EF5-8C37-5F4175AF4FEA}" EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution diff --git a/Tools/BlockZapper/BlockZapper.vcproj b/Tools/BlockZapper/BlockZapper.vcproj index 2a98197eb..4fa27dd31 100644 --- a/Tools/BlockZapper/BlockZapper.vcproj +++ b/Tools/BlockZapper/BlockZapper.vcproj @@ -41,7 +41,7 @@ - - - - @@ -293,11 +285,11 @@ Name="WorldStorage" > diff --git a/Tools/BlockZapper/GNUmakefile b/Tools/BlockZapper/GNUmakefile index edd5f9009..0ef5eb3cc 100644 --- a/Tools/BlockZapper/GNUmakefile +++ b/Tools/BlockZapper/GNUmakefile @@ -100,8 +100,8 @@ endif # INCLUDE = -I.\ - -I../../source\ - -I../../zlib-1.2.7\ + -I../../src\ + -I../../lib\ @@ -114,16 +114,16 @@ INCLUDE = -I.\ SOURCES := $(shell find . '(' -name '*.cpp' -o -name '*.c' ')') SHAREDSOURCES := \ - source/Log.cpp \ - source/MCLogger.cpp \ - source/Noise.cpp \ - source/StringCompression.cpp \ - source/StringUtils.cpp \ - source/OSSupport/CriticalSection.cpp \ - source/OSSupport/File.cpp \ - source/OSSupport/IsThread.cpp \ - source/OSSupport/MakeDir.cpp \ - source/WorldStorage/FastNBT.cpp + src/Log.cpp \ + src/MCLogger.cpp \ + src/Noise.cpp \ + src/StringCompression.cpp \ + src/StringUtils.cpp \ + src/OSSupport/CriticalSection.cpp \ + src/OSSupport/File.cpp \ + src/OSSupport/IsThread.cpp \ + src/OSSupport/MakeDir.cpp \ + src/WorldStorage/FastNBT.cpp SHAREDSOURCES := $(filter-out %minigzip.c,$(SHAREDSOURCES)) @@ -142,8 +142,6 @@ BlockZapper : $(OBJECTS) $(SHAREDOBJECTS) clean : rm -rf $(BUILDDIR) BlockZapper -install : MCServer - cp MCServer MCServer @@ -175,7 +173,7 @@ $(BUILDDIR)%.o: %.cpp @sed -e 's/.*://' -e 's/\\$$//' < $(patsubst %.o,%.d,$@).tmp | fmt -1 | sed -e 's/^ *//' -e 's/$$/:/' >> $(patsubst %.o,%.d,$@) @rm -f $(patsubst %.o,%.d,$@).tmp -$(BUILDDIR)source/%.o: ../../source/%.cpp +$(BUILDDIR)src/%.o: ../../src/%.cpp @mkdir -p $(dir $@) $(CC) $(CXX_OPTIONS) -c $(INCLUDE) $< -o $@ @$(CC) $(CXX_OPTIONS) -MM $(INCLUDE) $< > $(patsubst %.o,%.d,$@) diff --git a/Tools/BlockZapper/Globals.h b/Tools/BlockZapper/Globals.h index e27315ec5..3826c72fa 100644 --- a/Tools/BlockZapper/Globals.h +++ b/Tools/BlockZapper/Globals.h @@ -7,7 +7,7 @@ -#include "../../source/Globals.h" +#include "../../src/Globals.h" diff --git a/Tools/BlockZapper/Zapper.cpp b/Tools/BlockZapper/Zapper.cpp index 702f968ab..304d49770 100644 --- a/Tools/BlockZapper/Zapper.cpp +++ b/Tools/BlockZapper/Zapper.cpp @@ -7,7 +7,7 @@ #include "WorldStorage/FastNBT.h" #include "StringCompression.h" -#include "zlib.h" +#include "zlib/zlib.h" #include "Zapper.h" -- cgit v1.2.3 From cfd9a290467e66f467e1060ab3bfc6e367c929db Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Thu, 28 Nov 2013 13:53:38 +0100 Subject: Fixed MemDumpAnalysis after foldermove. --- Tools/MemDumpAnalysis/.gitignore | 3 ++ Tools/MemDumpAnalysis/Globals.h | 8 +-- Tools/MemDumpAnalysis/MemDumpAnalysis.vcproj | 74 +++++++++++++--------------- 3 files changed, 41 insertions(+), 44 deletions(-) create mode 100644 Tools/MemDumpAnalysis/.gitignore (limited to 'Tools') diff --git a/Tools/MemDumpAnalysis/.gitignore b/Tools/MemDumpAnalysis/.gitignore new file mode 100644 index 000000000..b4e15dc3c --- /dev/null +++ b/Tools/MemDumpAnalysis/.gitignore @@ -0,0 +1,3 @@ +Debug/ +logs/ +Release/ diff --git a/Tools/MemDumpAnalysis/Globals.h b/Tools/MemDumpAnalysis/Globals.h index 92d27da2c..d5fc2abfa 100644 --- a/Tools/MemDumpAnalysis/Globals.h +++ b/Tools/MemDumpAnalysis/Globals.h @@ -9,7 +9,7 @@ #pragma once -#include "../../source/Globals.h" +#include "../../src/Globals.h" /* // System headers: @@ -23,12 +23,12 @@ #include // Common: -#include "../source/StringUtils.h" -#include "../source/OSSupport/File.h" +#include "../src/StringUtils.h" +#include "../src/OSSupport/File.h" */ // Libraries: -#include "../../expat/expat.h" +#include "expat/expat.h" diff --git a/Tools/MemDumpAnalysis/MemDumpAnalysis.vcproj b/Tools/MemDumpAnalysis/MemDumpAnalysis.vcproj index 345dfa962..8283fd531 100644 --- a/Tools/MemDumpAnalysis/MemDumpAnalysis.vcproj +++ b/Tools/MemDumpAnalysis/MemDumpAnalysis.vcproj @@ -41,6 +41,7 @@ - - - - -- cgit v1.2.3 From c90f021ed4f3f1b9f8da74aa612e0e879b6e87f7 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Thu, 28 Nov 2013 13:55:28 +0100 Subject: Fixed RCONClient after foldermove. --- Tools/RCONClient/RCONClient.vcproj | 36 ++++++++++++++++++------------------ 1 file changed, 18 insertions(+), 18 deletions(-) (limited to 'Tools') diff --git a/Tools/RCONClient/RCONClient.vcproj b/Tools/RCONClient/RCONClient.vcproj index 59d0b3b74..82b79d2a3 100644 --- a/Tools/RCONClient/RCONClient.vcproj +++ b/Tools/RCONClient/RCONClient.vcproj @@ -41,7 +41,7 @@ -- cgit v1.2.3 From 8acf0129e10f2b7ce3ec377df4b5cb95d8d93a62 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Thu, 28 Nov 2013 15:57:34 +0100 Subject: BiomeVisualiser: The biome settings are read from a file. --- Tools/BiomeVisualiser/BiomeCache.cpp | 5 ++ Tools/BiomeVisualiser/BiomeViewWnd.cpp | 83 ++++++++++++++++++++++++++++++++-- Tools/BiomeVisualiser/BiomeViewWnd.h | 19 ++++++++ 3 files changed, 102 insertions(+), 5 deletions(-) (limited to 'Tools') diff --git a/Tools/BiomeVisualiser/BiomeCache.cpp b/Tools/BiomeVisualiser/BiomeCache.cpp index b3c308422..7d9301d8f 100644 --- a/Tools/BiomeVisualiser/BiomeCache.cpp +++ b/Tools/BiomeVisualiser/BiomeCache.cpp @@ -258,6 +258,11 @@ void cBiomeCache::FilterOutItems(cItems & a_Items, int a_MinChunkX, int a_MaxChu void cBiomeCache::thrProcessQueueItem(void) { + if (m_Source == NULL) + { + return; + } + cItem * Item = NULL; { cCSLock Lock(m_CS); diff --git a/Tools/BiomeVisualiser/BiomeViewWnd.cpp b/Tools/BiomeVisualiser/BiomeViewWnd.cpp index 0658e3810..459a4323c 100644 --- a/Tools/BiomeVisualiser/BiomeViewWnd.cpp +++ b/Tools/BiomeVisualiser/BiomeViewWnd.cpp @@ -34,6 +34,8 @@ bool cBiomeViewWnd::Create(HWND a_ParentWnd, LPCTSTR a_Title) { ASSERT(m_Wnd == NULL); + InitBiomeView(); + // Create a regular STATIC window, then override its window procedure with our own. No need for obnoxious RegisterWindowClass() stuff. m_Wnd = CreateWindow("STATIC", a_Title, WS_OVERLAPPEDWINDOW | WS_VISIBLE, 0, 0, 400, 300, a_ParentWnd, NULL, GetModuleHandle(NULL), NULL); if (m_Wnd == NULL) @@ -43,11 +45,6 @@ bool cBiomeViewWnd::Create(HWND a_ParentWnd, LPCTSTR a_Title) } SetWindowLongPtr(m_Wnd, GWLP_WNDPROC, m_Thunk); - cIniFile IniFile; - cBiomeGen * BioGen = new cBioGenMultiStepMap(2); - BioGen->InitializeBiomeGen(IniFile); - m_Renderer.SetSource(new cGeneratorBiomeSource(BioGen)); - return true; } @@ -55,6 +52,82 @@ bool cBiomeViewWnd::Create(HWND a_ParentWnd, LPCTSTR a_Title) +void cBiomeViewWnd::InitBiomeView(void) +{ + cIniFile IniFile; + IniFile.ReadFile("world.ini"); + AString BiomeGenName = IniFile.GetValueSet("Generator", "BiomeGen", ""); + if (BiomeGenName.empty()) + { + LOGWARN("[Generator] BiomeGen value not set in world.ini, using \"MultiStepMap\"."); + BiomeGenName = "MultiStepMap"; + } + + int Seed = IniFile.GetValueSetI("Generator", "Seed", 0); + + bool CacheOffByDefault = false; + if (NoCaseCompare(BiomeGenName, "constant") == 0) + { + m_BiomeGen = new cBioGenConstant; + CacheOffByDefault = true; // we're generating faster than a cache would retrieve data :) + } + else if (NoCaseCompare(BiomeGenName, "checkerboard") == 0) + { + m_BiomeGen = new cBioGenCheckerboard; + CacheOffByDefault = true; // we're (probably) generating faster than a cache would retrieve data + } + else if (NoCaseCompare(BiomeGenName, "voronoi") == 0) + { + m_BiomeGen = new cBioGenVoronoi(Seed); + } + else if (NoCaseCompare(BiomeGenName, "distortedvoronoi") == 0) + { + m_BiomeGen = new cBioGenDistortedVoronoi(Seed); + } + else + { + if (NoCaseCompare(BiomeGenName, "multistepmap") != 0) + { + LOGWARNING("Unknown BiomeGen \"%s\", using \"MultiStepMap\" instead.", BiomeGenName.c_str()); + } + m_BiomeGen = new cBioGenMultiStepMap(Seed); + + /* + // Performance-testing: + LOGINFO("Measuring performance of cBioGenMultiStepMap..."); + clock_t BeginTick = clock(); + for (int x = 0; x < 5000; x++) + { + cChunkDef::BiomeMap Biomes; + m_BiomeGen->GenBiomes(x * 5, x * 5, Biomes); + } + clock_t Duration = clock() - BeginTick; + LOGINFO("cBioGenMultiStepMap for 5000 chunks took %d ticks (%.02f sec)", Duration, (double)Duration / CLOCKS_PER_SEC); + //*/ + } + + // Add a cache, if requested: + int CacheSize = IniFile.GetValueSetI("Generator", "BiomeGenCacheSize", CacheOffByDefault ? 0 : 64); + if (CacheSize > 0) + { + if (CacheSize < 4) + { + LOGWARNING("Biomegen cache size set too low, would hurt performance instead of helping. Increasing from %d to %d", + CacheSize, 4 + ); + CacheSize = 4; + } + LOGD("Using a cache for biomegen of size %d.", CacheSize); + m_BiomeGen = new cBioGenCache(m_BiomeGen, CacheSize); + } + m_BiomeGen->InitializeBiomeGen(IniFile); + m_Renderer.SetSource(new cGeneratorBiomeSource(m_BiomeGen)); + IniFile.WriteFile("world.ini"); +} + + + + LRESULT cBiomeViewWnd::WndProc(HWND a_Wnd, UINT a_Msg, WPARAM wParam, LPARAM lParam) { diff --git a/Tools/BiomeVisualiser/BiomeViewWnd.h b/Tools/BiomeVisualiser/BiomeViewWnd.h index 88e808ab3..e3f70c7e6 100644 --- a/Tools/BiomeVisualiser/BiomeViewWnd.h +++ b/Tools/BiomeVisualiser/BiomeViewWnd.h @@ -3,6 +3,12 @@ // Declares the cBiomeViewWnd class representing the window that displays biomes + + + + +#pragma once + #include "WndProcThunk.h" #include "BiomeRenderer.h" #include "BiomeCache.h" @@ -12,6 +18,13 @@ +// fwd: +class cBiomeGen; + + + + + class cBiomeViewWnd { public: @@ -26,9 +39,15 @@ protected: cBiomeRenderer m_Renderer; cPixmap m_Pixmap; + /// The generator that is to be visualised + cBiomeGen * m_BiomeGen; + bool m_IsLButtonDown; POINT m_MouseDown; + + void InitBiomeView(void); + LRESULT WndProc(HWND a_Wnd, UINT a_Msg, WPARAM wParam, LPARAM lParam); // Message handlers: -- cgit v1.2.3 From bdd86d7934e95ee1db54531b51431554d5b91796 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Thu, 28 Nov 2013 19:58:20 +0100 Subject: BiomeVisualiser: Added the TwoLevel biome generator. --- Tools/BiomeVisualiser/BiomeViewWnd.cpp | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'Tools') diff --git a/Tools/BiomeVisualiser/BiomeViewWnd.cpp b/Tools/BiomeVisualiser/BiomeViewWnd.cpp index 459a4323c..8f8849663 100644 --- a/Tools/BiomeVisualiser/BiomeViewWnd.cpp +++ b/Tools/BiomeVisualiser/BiomeViewWnd.cpp @@ -84,6 +84,10 @@ void cBiomeViewWnd::InitBiomeView(void) { m_BiomeGen = new cBioGenDistortedVoronoi(Seed); } + else if (NoCaseCompare(BiomeGenName, "twolevel") == 0) + { + m_BiomeGen = new cBioGenTwoLevel(Seed); + } else { if (NoCaseCompare(BiomeGenName, "multistepmap") != 0) -- cgit v1.2.3 From 41175b5549522482e94c91dbfcea9602acb20ee4 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Thu, 28 Nov 2013 20:19:10 +0100 Subject: BiomeVisualiser: Using the common BiomeGen creation code. --- Tools/BiomeVisualiser/BiomeViewWnd.cpp | 68 +--------------------------------- 1 file changed, 1 insertion(+), 67 deletions(-) (limited to 'Tools') diff --git a/Tools/BiomeVisualiser/BiomeViewWnd.cpp b/Tools/BiomeVisualiser/BiomeViewWnd.cpp index 8f8849663..5c1240bc7 100644 --- a/Tools/BiomeVisualiser/BiomeViewWnd.cpp +++ b/Tools/BiomeVisualiser/BiomeViewWnd.cpp @@ -56,75 +56,9 @@ void cBiomeViewWnd::InitBiomeView(void) { cIniFile IniFile; IniFile.ReadFile("world.ini"); - AString BiomeGenName = IniFile.GetValueSet("Generator", "BiomeGen", ""); - if (BiomeGenName.empty()) - { - LOGWARN("[Generator] BiomeGen value not set in world.ini, using \"MultiStepMap\"."); - BiomeGenName = "MultiStepMap"; - } - int Seed = IniFile.GetValueSetI("Generator", "Seed", 0); - bool CacheOffByDefault = false; - if (NoCaseCompare(BiomeGenName, "constant") == 0) - { - m_BiomeGen = new cBioGenConstant; - CacheOffByDefault = true; // we're generating faster than a cache would retrieve data :) - } - else if (NoCaseCompare(BiomeGenName, "checkerboard") == 0) - { - m_BiomeGen = new cBioGenCheckerboard; - CacheOffByDefault = true; // we're (probably) generating faster than a cache would retrieve data - } - else if (NoCaseCompare(BiomeGenName, "voronoi") == 0) - { - m_BiomeGen = new cBioGenVoronoi(Seed); - } - else if (NoCaseCompare(BiomeGenName, "distortedvoronoi") == 0) - { - m_BiomeGen = new cBioGenDistortedVoronoi(Seed); - } - else if (NoCaseCompare(BiomeGenName, "twolevel") == 0) - { - m_BiomeGen = new cBioGenTwoLevel(Seed); - } - else - { - if (NoCaseCompare(BiomeGenName, "multistepmap") != 0) - { - LOGWARNING("Unknown BiomeGen \"%s\", using \"MultiStepMap\" instead.", BiomeGenName.c_str()); - } - m_BiomeGen = new cBioGenMultiStepMap(Seed); - - /* - // Performance-testing: - LOGINFO("Measuring performance of cBioGenMultiStepMap..."); - clock_t BeginTick = clock(); - for (int x = 0; x < 5000; x++) - { - cChunkDef::BiomeMap Biomes; - m_BiomeGen->GenBiomes(x * 5, x * 5, Biomes); - } - clock_t Duration = clock() - BeginTick; - LOGINFO("cBioGenMultiStepMap for 5000 chunks took %d ticks (%.02f sec)", Duration, (double)Duration / CLOCKS_PER_SEC); - //*/ - } - - // Add a cache, if requested: - int CacheSize = IniFile.GetValueSetI("Generator", "BiomeGenCacheSize", CacheOffByDefault ? 0 : 64); - if (CacheSize > 0) - { - if (CacheSize < 4) - { - LOGWARNING("Biomegen cache size set too low, would hurt performance instead of helping. Increasing from %d to %d", - CacheSize, 4 - ); - CacheSize = 4; - } - LOGD("Using a cache for biomegen of size %d.", CacheSize); - m_BiomeGen = new cBioGenCache(m_BiomeGen, CacheSize); - } - m_BiomeGen->InitializeBiomeGen(IniFile); + m_BiomeGen = cBiomeGen::CreateBiomeGen(IniFile, Seed, CacheOffByDefault); m_Renderer.SetSource(new cGeneratorBiomeSource(m_BiomeGen)); IniFile.WriteFile("world.ini"); } -- cgit v1.2.3 From 1373539bceba112c6ecc2c01f9a215e40427b979 Mon Sep 17 00:00:00 2001 From: madmaxoft Date: Thu, 5 Dec 2013 12:20:37 +0100 Subject: ProtoProxy: Fixed metadata parsing. --- Tools/ProtoProxy/Connection.cpp | 36 +++++++++++++++++++++++++++--------- 1 file changed, 27 insertions(+), 9 deletions(-) (limited to 'Tools') diff --git a/Tools/ProtoProxy/Connection.cpp b/Tools/ProtoProxy/Connection.cpp index 385caa2ce..0b49859cb 100644 --- a/Tools/ProtoProxy/Connection.cpp +++ b/Tools/ProtoProxy/Connection.cpp @@ -260,6 +260,9 @@ void cConnection::Log(const char * a_Format, ...) // Log to file: cCSLock Lock(m_CSLog); fputs(FullMsg.c_str(), m_LogFile); + #ifdef _DEBUG + fflush(m_LogFile); + #endif // _DEBUG // Log to screen: // std::cout << FullMsg; @@ -2678,15 +2681,20 @@ bool cConnection::ParseMetadata(cByteBuffer & a_Buffer, AString & a_Metadata) case 1: Length = 2; break; // short case 2: Length = 4; break; // int case 3: Length = 4; break; // float - case 4: // string16 + case 4: // UTF-8 string with VarInt length { - short Len = 0; - if (!a_Buffer.ReadBEShort(Len)) + UInt32 Len; + int rs = a_Buffer.GetReadableSpace(); + if (!a_Buffer.ReadVarInt(Len)) { return false; } - short NetLen = htons(Len); - a_Metadata.append((char *)&NetLen, 2); + rs = rs - a_Buffer.GetReadableSpace(); + cByteBuffer LenBuf(8); + LenBuf.WriteVarInt(Len); + AString VarLen; + LenBuf.ReadAll(VarLen); + a_Metadata.append(VarLen); Length = Len; break; } @@ -2766,11 +2774,21 @@ void cConnection::LogMetadata(const AString & a_Metadata, size_t a_IndentCount) pos += 4; break; } - case 4: // string16 + case 4: // UTF-8 string with VarInt length { - short Length = (a_Metadata[pos + 1] << 8) | a_Metadata[pos + 2]; - Log("%sstring[%d] = \"%*s\"", Indent.c_str(), Index, Length, a_Metadata.c_str() + pos + 3); - pos += Length + 2; + cByteBuffer bb(10); + int RestLen = (int)a_Metadata.size() - pos - 1; + if (RestLen > 8) + { + RestLen = 8; + } + bb.Write(a_Metadata.data() + pos + 1, RestLen); + UInt32 Length; + int rs = bb.GetReadableSpace(); + bb.ReadVarInt(Length); + rs = rs - bb.GetReadableSpace(); + Log("%sstring[%d] = \"%*s\"", Indent.c_str(), Index, Length, a_Metadata.c_str() + pos + rs + 1); + pos += Length + rs + 2; break; } case 5: -- cgit v1.2.3