From ca705be2649a205caac2a449704b55dd029ea13b Mon Sep 17 00:00:00 2001 From: sleirsgoevy Date: Wed, 18 Oct 2023 23:32:02 +0300 Subject: Fix empty chunk serializer for protocol 47 (#5514) (Minecraft 1.8) Co-authored-by: Sergey Lisov --- CONTRIBUTORS | 1 + src/Protocol/ChunkDataSerializer.cpp | 21 +++++++++++++++++++-- 2 files changed, 20 insertions(+), 2 deletions(-) diff --git a/CONTRIBUTORS b/CONTRIBUTORS index 3657bd414..ff2f47ca3 100644 --- a/CONTRIBUTORS +++ b/CONTRIBUTORS @@ -76,6 +76,7 @@ rs2k SamJBarney Schwertspize Seadragon91 (Lukas Pioch) +sleirsgoevy (Sergey Lisov) Sofapriester Spekdrum (Pablo Beltran) SphinxC0re diff --git a/src/Protocol/ChunkDataSerializer.cpp b/src/Protocol/ChunkDataSerializer.cpp index a6620da04..cfabc6e31 100644 --- a/src/Protocol/ChunkDataSerializer.cpp +++ b/src/Protocol/ChunkDataSerializer.cpp @@ -196,12 +196,16 @@ inline void cChunkDataSerializer::Serialize47(const int a_ChunkX, const int a_Ch m_Packet.WriteBEInt32(a_ChunkX); m_Packet.WriteBEInt32(a_ChunkZ); m_Packet.WriteBool(true); // "Ground-up continuous", or rather, "biome data present" flag - m_Packet.WriteBEUInt16(Bitmask.first); + + // Minecraft 1.8 does not like completely empty packets + // Send one completely empty chunk section if this is the case + m_Packet.WriteBEUInt16(Bitmask.first ? Bitmask.first : 1); // Write the chunk size: + // Account for the single empty section if sending an empty chunk const int BiomeDataSize = cChunkDef::Width * cChunkDef::Width; const size_t ChunkSize = ( - Bitmask.second * (ChunkBlockData::SectionBlockCount * 2 + ChunkLightData::SectionLightCount * 2) + // Blocks and lighting + (Bitmask.second ? Bitmask.second : 1) * (ChunkBlockData::SectionBlockCount * 2 + ChunkLightData::SectionLightCount * 2) + // Blocks and lighting BiomeDataSize // Biome data ); m_Packet.WriteVarInt32(static_cast(ChunkSize)); @@ -250,6 +254,19 @@ inline void cChunkDataSerializer::Serialize47(const int a_ChunkX, const int a_Ch } }); + // Serialize a single empty section if sending an empty chunk + if (!Bitmask.first) + { + // Block data (all air) + for (size_t i = 0; i < ChunkBlockData::SectionBlockCount * 2; i++) + { + m_Packet.WriteBEUInt8(0); + } + // Light data (XXX: sky light is not sent if in the nether) + m_Packet.WriteBuf(ChunkLightData::SectionLightCount, ChunkLightData::DefaultSkyLightValue); + m_Packet.WriteBuf(ChunkLightData::SectionLightCount, ChunkLightData::DefaultSkyLightValue); + } + // Write the biome data: m_Packet.WriteBuf(a_BiomeMap, BiomeDataSize); } -- cgit v1.2.3