From e71bac2028eb1e676604d3c3b2badd840e7c9b59 Mon Sep 17 00:00:00 2001 From: Andrew Steinborn Date: Mon, 24 Dec 2018 05:25:58 -0500 Subject: [PATCH] Fix ProtocolUtil#readString() to respect Unicode. This brings Velocity's to conformance to what Mojang does in PacketDataSerializer. --- .../com/velocitypowered/proxy/protocol/ProtocolUtils.java | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/proxy/src/main/java/com/velocitypowered/proxy/protocol/ProtocolUtils.java b/proxy/src/main/java/com/velocitypowered/proxy/protocol/ProtocolUtils.java index 08bd58ca5..89d88de73 100644 --- a/proxy/src/main/java/com/velocitypowered/proxy/protocol/ProtocolUtils.java +++ b/proxy/src/main/java/com/velocitypowered/proxy/protocol/ProtocolUtils.java @@ -51,12 +51,18 @@ public enum ProtocolUtils { public static String readString(ByteBuf buf, int cap) { int length = readVarInt(buf); - checkArgument(length <= cap, "Bad string size (got %s, maximum is %s)", length, cap); + checkArgument(length >= 0, "Got a negative-length string (%s)", length); + // `cap` is interpreted as a UTF-8 character length, hence the multiplication by 4 - this covers + // the full Unicode plane - a 4 byte character (surrogate) is the maximum. We do a later sanity + // check to make sure our optimistic guess was good enough. + checkArgument(length <= cap * 4, "Bad string size (got %s, maximum is %s)", length, cap); checkState(buf.isReadable(length), "Trying to read a string that is too long (wanted %s, only have %s)", length, buf.readableBytes()); String str = buf.toString(buf.readerIndex(), length, StandardCharsets.UTF_8); buf.skipBytes(length); + checkState(str.length() <= cap, "Got a too-long string (got %s, max %s)", + str.length(), cap); return str; }