diff --git a/build.gradle b/build.gradle index 452ad0e84..4ec1ae4ce 100644 --- a/build.gradle +++ b/build.gradle @@ -86,8 +86,6 @@ dependencies { api 'io.netty:netty-codec:4.1.51.Final' implementation 'io.netty:netty-transport-native-epoll:4.1.51.Final:linux-x86_64' - api 'com.github.jhg023:Pbbl:1.0.2' - // https://mvnrepository.com/artifact/it.unimi.dsi/fastutil api 'it.unimi.dsi:fastutil:8.4.1' diff --git a/src/main/java/net/minestom/server/network/packet/server/play/ChunkDataPacket.java b/src/main/java/net/minestom/server/network/packet/server/play/ChunkDataPacket.java index 545a54dd4..f6270ebb3 100644 --- a/src/main/java/net/minestom/server/network/packet/server/play/ChunkDataPacket.java +++ b/src/main/java/net/minestom/server/network/packet/server/play/ChunkDataPacket.java @@ -1,5 +1,7 @@ package net.minestom.server.network.packet.server.play; +import io.netty.buffer.ByteBuf; +import io.netty.buffer.Unpooled; import it.unimi.dsi.fastutil.ints.Int2ObjectMap; import net.minestom.server.MinecraftServer; import net.minestom.server.data.Data; @@ -11,8 +13,6 @@ import net.minestom.server.network.packet.server.ServerPacketIdentifier; import net.minestom.server.utils.BlockPosition; import net.minestom.server.utils.Utils; import net.minestom.server.utils.binary.BinaryWriter; -import net.minestom.server.utils.buffer.BufferUtils; -import net.minestom.server.utils.buffer.BufferWrapper; import net.minestom.server.utils.chunk.ChunkUtils; import net.minestom.server.world.biomes.Biome; import org.jglrxavpok.hephaistos.nbt.NBTCompound; @@ -47,7 +47,7 @@ public class ChunkDataPacket implements ServerPacket { writer.writeBoolean(fullChunk); int mask = 0; - BufferWrapper blocks = BufferUtils.getBuffer(MAX_BUFFER_SIZE); + ByteBuf blocks = Unpooled.buffer(MAX_BUFFER_SIZE); for (byte i = 0; i < CHUNK_SECTION_COUNT; i++) { if (fullChunk || (sections.length == CHUNK_SECTION_COUNT && sections[i] != 0)) { short[] section = getSection(i); @@ -91,8 +91,8 @@ public class ChunkDataPacket implements ServerPacket { } // Data - writer.writeVarInt(blocks.getSize()); - writer.writeBufferAndFree(blocks); + writer.writeVarInt(blocks.writerIndex()); + writer.getBuffer().writeBytes(blocks); // Block entities writer.writeVarInt(blockEntities.size()); diff --git a/src/main/java/net/minestom/server/utils/PacketUtils.java b/src/main/java/net/minestom/server/utils/PacketUtils.java index 3c261fa22..3581db3bd 100644 --- a/src/main/java/net/minestom/server/utils/PacketUtils.java +++ b/src/main/java/net/minestom/server/utils/PacketUtils.java @@ -21,11 +21,10 @@ public final class PacketUtils { * @param packet the packet to write into {@code buf} */ public static void writePacket(ByteBuf buf, ServerPacket packet) { - BinaryWriter writer = new BinaryWriter(); - Utils.writeVarIntBuf(buf, packet.getId()); - packet.write(writer); - buf.writeBytes(writer.toByteArray()); + final ByteBuf packetBuffer = getPacketBuffer(packet); + + writePacket(buf, packetBuffer, packet.getId()); } /** @@ -35,11 +34,40 @@ public final class PacketUtils { * @return a {@link ByteBuf} containing {@code packet} */ public static ByteBuf writePacket(ServerPacket packet) { - ByteBuf buffer = Unpooled.buffer(); + final ByteBuf packetBuffer = getPacketBuffer(packet); - writePacket(buffer, packet); + // Add 5 for the packet id and for the packet size + final int size = packetBuffer.writerIndex() + 5 + 5; + ByteBuf buffer = Unpooled.buffer(size); + + writePacket(buffer, packetBuffer, packet.getId()); return buffer; } + /** + * Write a packet buffer into {@code buf} + * + * @param buf the buffer which will receive the packet id/data + * @param packetBuffer the buffer containing the raw packet data + * @param packetId the packet id + */ + private static void writePacket(ByteBuf buf, ByteBuf packetBuffer, int packetId) { + Utils.writeVarIntBuf(buf, packetId); + buf.writeBytes(packetBuffer); + } + + /** + * Get the buffer representing the raw packet data + * + * @param packet the packet to write + * @return the {@link ByteBuf} containing the raw packet data + */ + private static ByteBuf getPacketBuffer(ServerPacket packet) { + BinaryWriter writer = new BinaryWriter(); + packet.write(writer); + + return writer.getBuffer(); + } + } diff --git a/src/main/java/net/minestom/server/utils/Utils.java b/src/main/java/net/minestom/server/utils/Utils.java index bac4cf108..4b351e276 100644 --- a/src/main/java/net/minestom/server/utils/Utils.java +++ b/src/main/java/net/minestom/server/utils/Utils.java @@ -3,7 +3,6 @@ package net.minestom.server.utils; import io.netty.buffer.ByteBuf; import net.minestom.server.instance.Chunk; import net.minestom.server.utils.binary.BinaryWriter; -import net.minestom.server.utils.buffer.BufferWrapper; public final class Utils { @@ -30,17 +29,6 @@ public final class Utils { } while (value != 0); } - public static void writeVarIntBuffer(BufferWrapper buffer, int value) { - do { - byte temp = (byte) (value & 0b01111111); - value >>>= 7; - if (value != 0) { - temp |= 0b10000000; - } - buffer.putByte(temp); - } while (value != 0); - } - public static void writeVarInt(BinaryWriter writer, int value) { do { byte temp = (byte) (value & 0b01111111); @@ -103,14 +91,14 @@ public final class Utils { 70409299, 70409299, 0, 69273666, 69273666, 0, 68174084, 68174084, 0, Integer.MIN_VALUE, 0, 5}; - public static void writeBlocks(BufferWrapper buffer, short[] blocksId, int bitsPerEntry) { + public static void writeBlocks(ByteBuf buffer, short[] blocksId, int bitsPerEntry) { short count = 0; for (short id : blocksId) if (id != 0) count++; - buffer.putShort(count); - buffer.putByte((byte) bitsPerEntry); + buffer.writeShort(count); + buffer.writeByte((byte) bitsPerEntry); int[] blocksData = new int[Chunk.CHUNK_SIZE_X * Chunk.CHUNK_SECTION_SIZE * Chunk.CHUNK_SIZE_Z]; for (int y = 0; y < Chunk.CHUNK_SECTION_SIZE; y++) { for (int x = 0; x < Chunk.CHUNK_SIZE_X; x++) { @@ -121,28 +109,28 @@ public final class Utils { } } } - long[] data = encodeBlocks(blocksData, bitsPerEntry); - buffer.putVarInt(data.length); + final long[] data = encodeBlocks(blocksData, bitsPerEntry); + writeVarIntBuf(buffer, data.length); for (int i = 0; i < data.length; i++) { - buffer.putLong(data[i]); + buffer.writeLong(data[i]); } } public static long[] encodeBlocks(int[] blocks, int bitsPerEntry) { - long maxEntryValue = (1L << bitsPerEntry) - 1; - char valuesPerLong = (char) (64 / bitsPerEntry); - int magicIndex = 3 * (valuesPerLong - 1); - long divideMul = Integer.toUnsignedLong(MAGIC[magicIndex]); - long divideAdd = Integer.toUnsignedLong(MAGIC[magicIndex + 1]); - int divideShift = MAGIC[magicIndex + 2]; - int size = (blocks.length + valuesPerLong - 1) / valuesPerLong; + final long maxEntryValue = (1L << bitsPerEntry) - 1; + final char valuesPerLong = (char) (64 / bitsPerEntry); + final int magicIndex = 3 * (valuesPerLong - 1); + final long divideMul = Integer.toUnsignedLong(MAGIC[magicIndex]); + final long divideAdd = Integer.toUnsignedLong(MAGIC[magicIndex + 1]); + final int divideShift = MAGIC[magicIndex + 2]; + final int size = (blocks.length + valuesPerLong - 1) / valuesPerLong; long[] data = new long[size]; for (int i = 0; i < blocks.length; i++) { - long value = blocks[i]; - int cellIndex = (int) (i * divideMul + divideAdd >> 32L >> divideShift); - int bitIndex = (i - cellIndex * valuesPerLong) * bitsPerEntry; + final long value = blocks[i]; + final int cellIndex = (int) (i * divideMul + divideAdd >> 32L >> divideShift); + final int bitIndex = (i - cellIndex * valuesPerLong) * bitsPerEntry; data[cellIndex] = data[cellIndex] & ~(maxEntryValue << bitIndex) | (value & maxEntryValue) << bitIndex; } diff --git a/src/main/java/net/minestom/server/utils/binary/BinaryWriter.java b/src/main/java/net/minestom/server/utils/binary/BinaryWriter.java index c1ca6fc72..157e45e36 100644 --- a/src/main/java/net/minestom/server/utils/binary/BinaryWriter.java +++ b/src/main/java/net/minestom/server/utils/binary/BinaryWriter.java @@ -7,13 +7,11 @@ import net.minestom.server.utils.BlockPosition; import net.minestom.server.utils.NBTUtils; import net.minestom.server.utils.SerializerUtils; import net.minestom.server.utils.Utils; -import net.minestom.server.utils.buffer.BufferWrapper; import org.jglrxavpok.hephaistos.nbt.NBT; import org.jglrxavpok.hephaistos.nbt.NBTWriter; import java.io.IOException; import java.io.OutputStream; -import java.nio.ByteBuffer; import java.nio.charset.StandardCharsets; import java.util.UUID; import java.util.function.Consumer; @@ -210,15 +208,6 @@ public class BinaryWriter extends OutputStream { consumer.accept(this); } - public void writeBufferAndFree(BufferWrapper buffer) { - ByteBuffer byteBuffer = buffer.getByteBuffer(); - final int size = buffer.getSize(); - byte[] cache = new byte[size]; - byteBuffer.position(0).get(cache, 0, size); - writeBytes(cache); - buffer.free(); - } - /** * Write an {@link UUID} * It is done by writing both long, the most & least significant bits @@ -263,6 +252,15 @@ public class BinaryWriter extends OutputStream { return bytes; } + /** + * Get the raw buffer used by this binary writer + * + * @return the raw buffer + */ + public ByteBuf getBuffer() { + return buffer; + } + @Override public void write(int b) { writeByte((byte) b); diff --git a/src/main/java/net/minestom/server/utils/buffer/BufferUtils.java b/src/main/java/net/minestom/server/utils/buffer/BufferUtils.java deleted file mode 100644 index e4c1eb826..000000000 --- a/src/main/java/net/minestom/server/utils/buffer/BufferUtils.java +++ /dev/null @@ -1,22 +0,0 @@ -package net.minestom.server.utils.buffer; - -import com.github.pbbl.heap.ByteBufferPool; - -import java.nio.ByteBuffer; - -public final class BufferUtils { - - private static final ByteBufferPool pool = new ByteBufferPool(); - - private BufferUtils() { - - } - - public static BufferWrapper getBuffer(int size) { - return new BufferWrapper(pool.take(size)); - } - - protected static void giveBuffer(ByteBuffer byteBuffer) { - pool.give(byteBuffer); - } -} diff --git a/src/main/java/net/minestom/server/utils/buffer/BufferWrapper.java b/src/main/java/net/minestom/server/utils/buffer/BufferWrapper.java deleted file mode 100644 index d4d000f12..000000000 --- a/src/main/java/net/minestom/server/utils/buffer/BufferWrapper.java +++ /dev/null @@ -1,57 +0,0 @@ -package net.minestom.server.utils.buffer; - -import net.minestom.server.utils.Utils; - -import java.nio.ByteBuffer; - -public class BufferWrapper { - - private final ByteBuffer byteBuffer; - private int size; - - protected BufferWrapper(ByteBuffer byteBuffer) { - this.byteBuffer = byteBuffer; - } - - public void putByte(byte b) { - this.byteBuffer.put(b); - size += Byte.BYTES; - } - - public void putShort(short s) { - this.byteBuffer.putShort(s); - size += Short.BYTES; - } - - public void putInt(int n) { - this.byteBuffer.putInt(n); - size += Integer.BYTES; - } - - public void putLong(long l) { - this.byteBuffer.putLong(l); - size += Long.BYTES; - } - - public void putVarInt(int n) { - Utils.writeVarIntBuffer(this, n); - size += Utils.getVarIntSize(n); - } - - public void putBytes(byte[] bytes) { - this.byteBuffer.put(bytes); - size += Byte.BYTES * bytes.length; - } - - public void free() { - BufferUtils.giveBuffer(getByteBuffer()); - } - - public int getSize() { - return size; - } - - public ByteBuffer getByteBuffer() { - return byteBuffer; - } -}