From d68ebd1eaf51132d73f121991dc66e5c937b05df Mon Sep 17 00:00:00 2001 From: md_5 Date: Sun, 17 Sep 2023 08:01:45 +1000 Subject: [PATCH] Minecraft 1.20.2-rc1 support --- api/pom.xml | 2 +- chat/pom.xml | 2 +- config/pom.xml | 4 +- pom.xml | 2 +- .../protocol/AbstractPacketHandler.java | 15 ++ .../md_5/bungee/protocol/DefinedPacket.java | 34 +++- .../bungee/protocol/MinecraftDecoder.java | 2 + .../bungee/protocol/MinecraftEncoder.java | 2 + .../net/md_5/bungee/protocol/Protocol.java | 150 ++++++++++++++---- .../bungee/protocol/ProtocolConstants.java | 3 +- .../protocol/packet/FinishConfiguration.java | 37 +++++ .../md_5/bungee/protocol/packet/Login.java | 74 +++++++-- .../protocol/packet/LoginAcknowledged.java | 37 +++++ .../bungee/protocol/packet/LoginRequest.java | 14 +- .../md_5/bungee/protocol/packet/Respawn.java | 24 ++- .../protocol/packet/ScoreboardDisplay.java | 23 ++- .../protocol/packet/StartConfiguration.java | 37 +++++ proxy/pom.xml | 2 +- .../java/net/md_5/bungee/ServerConnector.java | 58 +++++-- .../java/net/md_5/bungee/UserConnection.java | 1 + .../bungee/connection/DownstreamBridge.java | 17 +- .../bungee/connection/InitialHandler.java | 58 ++++--- .../bungee/connection/UpstreamBridge.java | 19 ++- .../net/md_5/bungee/entitymap/EntityMap.java | 2 + .../bungee/entitymap/EntityMap_1_16_2.java | 1 + .../net/md_5/bungee/netty/ChannelWrapper.java | 44 ++++- .../net/md_5/bungee/netty/HandlerBoss.java | 12 +- 27 files changed, 574 insertions(+), 102 deletions(-) create mode 100644 protocol/src/main/java/net/md_5/bungee/protocol/packet/FinishConfiguration.java create mode 100644 protocol/src/main/java/net/md_5/bungee/protocol/packet/LoginAcknowledged.java create mode 100644 protocol/src/main/java/net/md_5/bungee/protocol/packet/StartConfiguration.java diff --git a/api/pom.xml b/api/pom.xml index 1f03f987..30739518 100644 --- a/api/pom.xml +++ b/api/pom.xml @@ -72,7 +72,7 @@ org.yaml snakeyaml - 2.0 + 2.2 compile diff --git a/chat/pom.xml b/chat/pom.xml index c04033b5..87c2beb1 100644 --- a/chat/pom.xml +++ b/chat/pom.xml @@ -22,7 +22,7 @@ com.google.code.gson gson - 2.10 + 2.10.1 compile diff --git a/config/pom.xml b/config/pom.xml index d5151371..06d2e13b 100644 --- a/config/pom.xml +++ b/config/pom.xml @@ -22,14 +22,14 @@ com.google.code.gson gson - 2.10 + 2.10.1 compile true org.yaml snakeyaml - 2.0 + 2.2 compile true diff --git a/pom.xml b/pom.xml index fce42064..6537974d 100644 --- a/pom.xml +++ b/pom.xml @@ -99,7 +99,7 @@ com.google.guava guava - 31.1-jre + 32.1.2-jre compile diff --git a/protocol/src/main/java/net/md_5/bungee/protocol/AbstractPacketHandler.java b/protocol/src/main/java/net/md_5/bungee/protocol/AbstractPacketHandler.java index 88865b85..0f8f5885 100644 --- a/protocol/src/main/java/net/md_5/bungee/protocol/AbstractPacketHandler.java +++ b/protocol/src/main/java/net/md_5/bungee/protocol/AbstractPacketHandler.java @@ -11,6 +11,7 @@ import net.md_5.bungee.protocol.packet.Commands; import net.md_5.bungee.protocol.packet.EncryptionRequest; import net.md_5.bungee.protocol.packet.EncryptionResponse; import net.md_5.bungee.protocol.packet.EntityStatus; +import net.md_5.bungee.protocol.packet.FinishConfiguration; import net.md_5.bungee.protocol.packet.GameState; import net.md_5.bungee.protocol.packet.Handshake; import net.md_5.bungee.protocol.packet.KeepAlive; @@ -18,6 +19,7 @@ import net.md_5.bungee.protocol.packet.Kick; import net.md_5.bungee.protocol.packet.LegacyHandshake; import net.md_5.bungee.protocol.packet.LegacyPing; import net.md_5.bungee.protocol.packet.Login; +import net.md_5.bungee.protocol.packet.LoginAcknowledged; import net.md_5.bungee.protocol.packet.LoginPayloadRequest; import net.md_5.bungee.protocol.packet.LoginPayloadResponse; import net.md_5.bungee.protocol.packet.LoginRequest; @@ -34,6 +36,7 @@ import net.md_5.bungee.protocol.packet.ScoreboardObjective; import net.md_5.bungee.protocol.packet.ScoreboardScore; import net.md_5.bungee.protocol.packet.ServerData; import net.md_5.bungee.protocol.packet.SetCompression; +import net.md_5.bungee.protocol.packet.StartConfiguration; import net.md_5.bungee.protocol.packet.StatusRequest; import net.md_5.bungee.protocol.packet.StatusResponse; import net.md_5.bungee.protocol.packet.Subtitle; @@ -223,4 +226,16 @@ public abstract class AbstractPacketHandler public void handle(ServerData serverData) throws Exception { } + + public void handle(LoginAcknowledged loginAcknowledged) throws Exception + { + } + + public void handle(StartConfiguration startConfiguration) throws Exception + { + } + + public void handle(FinishConfiguration finishConfiguration) throws Exception + { + } } diff --git a/protocol/src/main/java/net/md_5/bungee/protocol/DefinedPacket.java b/protocol/src/main/java/net/md_5/bungee/protocol/DefinedPacket.java index 111802f7..c1017e60 100644 --- a/protocol/src/main/java/net/md_5/bungee/protocol/DefinedPacket.java +++ b/protocol/src/main/java/net/md_5/bungee/protocol/DefinedPacket.java @@ -15,7 +15,9 @@ import java.util.EnumSet; import java.util.List; import java.util.UUID; import lombok.RequiredArgsConstructor; +import se.llbit.nbt.ErrorTag; import se.llbit.nbt.NamedTag; +import se.llbit.nbt.SpecificTag; import se.llbit.nbt.Tag; @RequiredArgsConstructor @@ -293,14 +295,35 @@ public abstract class DefinedPacket return null; } - public static Tag readTag(ByteBuf input) + public static Tag readTag(ByteBuf input, int protocolVersion) { - Tag tag = NamedTag.read( new DataInputStream( new ByteBufInputStream( input ) ) ); + DataInputStream in = new DataInputStream( new ByteBufInputStream( input ) ); + Tag tag; + if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_20_2 ) + { + try + { + byte type = in.readByte(); + if ( type == 0 ) + { + return Tag.END; + } else + { + tag = SpecificTag.read( type, in ); + } + } catch ( IOException ex ) + { + tag = new ErrorTag( "IOException while reading tag type:\n" + ex.getMessage() ); + } + } else + { + tag = NamedTag.read( in ); + } Preconditions.checkArgument( !tag.isError(), "Error reading tag: %s", tag.error() ); return tag; } - public static void writeTag(Tag tag, ByteBuf output) + public static void writeTag(Tag tag, ByteBuf output, int protocolVersion) { try { @@ -378,6 +401,11 @@ public abstract class DefinedPacket write( buf ); } + public Protocol nextProtocol() + { + return null; + } + public abstract void handle(AbstractPacketHandler handler) throws Exception; @Override diff --git a/protocol/src/main/java/net/md_5/bungee/protocol/MinecraftDecoder.java b/protocol/src/main/java/net/md_5/bungee/protocol/MinecraftDecoder.java index 773e954c..1bc50e8c 100644 --- a/protocol/src/main/java/net/md_5/bungee/protocol/MinecraftDecoder.java +++ b/protocol/src/main/java/net/md_5/bungee/protocol/MinecraftDecoder.java @@ -5,12 +5,14 @@ import io.netty.channel.ChannelHandlerContext; import io.netty.handler.codec.MessageToMessageDecoder; import java.util.List; import lombok.AllArgsConstructor; +import lombok.Getter; import lombok.Setter; @AllArgsConstructor public class MinecraftDecoder extends MessageToMessageDecoder { + @Getter @Setter private Protocol protocol; private final boolean server; diff --git a/protocol/src/main/java/net/md_5/bungee/protocol/MinecraftEncoder.java b/protocol/src/main/java/net/md_5/bungee/protocol/MinecraftEncoder.java index d4b03843..5d0ca482 100644 --- a/protocol/src/main/java/net/md_5/bungee/protocol/MinecraftEncoder.java +++ b/protocol/src/main/java/net/md_5/bungee/protocol/MinecraftEncoder.java @@ -4,12 +4,14 @@ import io.netty.buffer.ByteBuf; import io.netty.channel.ChannelHandlerContext; import io.netty.handler.codec.MessageToByteEncoder; import lombok.AllArgsConstructor; +import lombok.Getter; import lombok.Setter; @AllArgsConstructor public class MinecraftEncoder extends MessageToByteEncoder { + @Getter @Setter private Protocol protocol; private boolean server; diff --git a/protocol/src/main/java/net/md_5/bungee/protocol/Protocol.java b/protocol/src/main/java/net/md_5/bungee/protocol/Protocol.java index 746defae..285e591e 100644 --- a/protocol/src/main/java/net/md_5/bungee/protocol/Protocol.java +++ b/protocol/src/main/java/net/md_5/bungee/protocol/Protocol.java @@ -19,11 +19,13 @@ import net.md_5.bungee.protocol.packet.Commands; import net.md_5.bungee.protocol.packet.EncryptionRequest; import net.md_5.bungee.protocol.packet.EncryptionResponse; import net.md_5.bungee.protocol.packet.EntityStatus; +import net.md_5.bungee.protocol.packet.FinishConfiguration; import net.md_5.bungee.protocol.packet.GameState; import net.md_5.bungee.protocol.packet.Handshake; import net.md_5.bungee.protocol.packet.KeepAlive; import net.md_5.bungee.protocol.packet.Kick; import net.md_5.bungee.protocol.packet.Login; +import net.md_5.bungee.protocol.packet.LoginAcknowledged; import net.md_5.bungee.protocol.packet.LoginPayloadRequest; import net.md_5.bungee.protocol.packet.LoginPayloadResponse; import net.md_5.bungee.protocol.packet.LoginRequest; @@ -40,6 +42,7 @@ import net.md_5.bungee.protocol.packet.ScoreboardObjective; import net.md_5.bungee.protocol.packet.ScoreboardScore; import net.md_5.bungee.protocol.packet.ServerData; import net.md_5.bungee.protocol.packet.SetCompression; +import net.md_5.bungee.protocol.packet.StartConfiguration; import net.md_5.bungee.protocol.packet.StatusRequest; import net.md_5.bungee.protocol.packet.StatusResponse; import net.md_5.bungee.protocol.packet.Subtitle; @@ -85,7 +88,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_19, 0x1E ), map( ProtocolConstants.MINECRAFT_1_19_1, 0x20 ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x1F ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x23 ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x23 ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x24 ) ); TO_CLIENT.registerPacket( Login.class, @@ -100,7 +104,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_19, 0x23 ), map( ProtocolConstants.MINECRAFT_1_19_1, 0x25 ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x24 ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x28 ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x28 ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x29 ) ); TO_CLIENT.registerPacket( Chat.class, Chat::new, @@ -128,7 +133,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_19, 0x3B ), map( ProtocolConstants.MINECRAFT_1_19_1, 0x3E ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x3D ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x41 ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x41 ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x43 ) ); TO_CLIENT.registerPacket( BossBar.class, @@ -138,7 +144,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_16, 0x0C ), map( ProtocolConstants.MINECRAFT_1_17, 0x0D ), map( ProtocolConstants.MINECRAFT_1_19, 0x0A ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0xB ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x0B ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x0A ) ); TO_CLIENT.registerPacket( PlayerListItem.class, // PlayerInfo @@ -168,7 +175,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_17, 0x11 ), map( ProtocolConstants.MINECRAFT_1_19, 0x0E ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x0D ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0xF ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x0F ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x10 ) ); TO_CLIENT.registerPacket( ScoreboardObjective.class, @@ -183,7 +191,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_17, 0x53 ), map( ProtocolConstants.MINECRAFT_1_19_1, 0x56 ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x54 ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x58 ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x58 ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x5A ) ); TO_CLIENT.registerPacket( ScoreboardScore.class, @@ -198,7 +207,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_17, 0x56 ), map( ProtocolConstants.MINECRAFT_1_19_1, 0x59 ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x57 ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x5B ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x5B ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x5D ) ); TO_CLIENT.registerPacket( ScoreboardDisplay.class, @@ -213,7 +223,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_17, 0x4C ), map( ProtocolConstants.MINECRAFT_1_19_1, 0x4F ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x4D ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x51 ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x51 ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x53 ) ); TO_CLIENT.registerPacket( Team.class, @@ -228,7 +239,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_17, 0x55 ), map( ProtocolConstants.MINECRAFT_1_19_1, 0x58 ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x56 ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x5A ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x5A ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x5C ) ); TO_CLIENT.registerPacket( PluginMessage.class, @@ -244,7 +256,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_19, 0x15 ), map( ProtocolConstants.MINECRAFT_1_19_1, 0x16 ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x15 ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x17 ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x17 ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x18 ) ); TO_CLIENT.registerPacket( Kick.class, @@ -260,7 +273,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_19, 0x17 ), map( ProtocolConstants.MINECRAFT_1_19_1, 0x19 ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x17 ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x1A ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x1A ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x1B ) ); TO_CLIENT.registerPacket( Title.class, @@ -276,7 +290,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_18, 0x5A ), map( ProtocolConstants.MINECRAFT_1_19_1, 0x5D ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x5B ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x5F ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x5F ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x61 ) ); TO_CLIENT.registerPacket( ClearTitles.class, @@ -284,7 +299,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_17, 0x10 ), map( ProtocolConstants.MINECRAFT_1_19, 0x0D ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x0C ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0xE ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x0E ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x0F ) ); TO_CLIENT.registerPacket( Subtitle.class, @@ -293,7 +309,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_18, 0x58 ), map( ProtocolConstants.MINECRAFT_1_19_1, 0x5B ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x59 ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x5D ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x5D ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x5F ) ); TO_CLIENT.registerPacket( TitleTimes.class, @@ -302,7 +319,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_18, 0x5B ), map( ProtocolConstants.MINECRAFT_1_19_1, 0x5E ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x5C ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x60 ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x60 ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x62 ) ); TO_CLIENT.registerPacket( SystemChat.class, @@ -310,7 +328,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_19, 0x5F ), map( ProtocolConstants.MINECRAFT_1_19_1, 0x62 ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x60 ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x64 ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x64 ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x67 ) ); TO_CLIENT.registerPacket( PlayerListHeaderFooter.class, @@ -329,7 +348,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_19, 0x60 ), map( ProtocolConstants.MINECRAFT_1_19_1, 0x63 ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x61 ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x65 ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x65 ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x68 ) ); TO_CLIENT.registerPacket( EntityStatus.class, @@ -345,7 +365,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_19, 0x18 ), map( ProtocolConstants.MINECRAFT_1_19_1, 0x1A ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x19 ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x1C ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x1C ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x1D ) ); TO_CLIENT.registerPacket( Commands.class, @@ -357,7 +378,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_17, 0x12 ), map( ProtocolConstants.MINECRAFT_1_19, 0x0F ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x0E ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x10 ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x10 ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x11 ) ); TO_CLIENT.registerPacket( GameState.class, @@ -369,7 +391,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_19, 0x1B ), map( ProtocolConstants.MINECRAFT_1_19_1, 0x1D ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x1C ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x1F ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x1F ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x20 ) ); TO_CLIENT.registerPacket( ViewDistance.class, @@ -381,7 +404,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_19, 0x49 ), map( ProtocolConstants.MINECRAFT_1_19_1, 0x4C ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x4B ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x4F ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x4F ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x51 ) ); TO_CLIENT.registerPacket( ServerData.class, @@ -389,19 +413,27 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_19, 0x3F ), map( ProtocolConstants.MINECRAFT_1_19_1, 0x42 ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x41 ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x45 ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x45 ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x47 ) ); TO_CLIENT.registerPacket( PlayerListItemRemove.class, PlayerListItemRemove::new, map( ProtocolConstants.MINECRAFT_1_19_3, 0x35 ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x39 ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x39 ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x3B ) ); TO_CLIENT.registerPacket( PlayerListItemUpdate.class, PlayerListItemUpdate::new, map( ProtocolConstants.MINECRAFT_1_19_3, 0x36 ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x3A ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x3A ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x3C ) + ); + TO_CLIENT.registerPacket( + StartConfiguration.class, + StartConfiguration::new, + map( ProtocolConstants.MINECRAFT_1_20_2, 0x65 ) ); TO_SERVER.registerPacket( @@ -418,7 +450,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_19, 0x11 ), map( ProtocolConstants.MINECRAFT_1_19_1, 0x12 ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x11 ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x12 ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x12 ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x14 ) ); TO_SERVER.registerPacket( Chat.class, Chat::new, @@ -453,7 +486,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_19, 0x08 ), map( ProtocolConstants.MINECRAFT_1_19_1, 0x09 ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x08 ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x09 ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x09 ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x0A ) ); TO_SERVER.registerPacket( ClientSettings.class, @@ -466,7 +500,8 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_19, 0x07 ), map( ProtocolConstants.MINECRAFT_1_19_1, 0x08 ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x07 ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x08 ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x08 ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x09 ) ); TO_SERVER.registerPacket( PluginMessage.class, @@ -481,7 +516,13 @@ public enum Protocol map( ProtocolConstants.MINECRAFT_1_19, 0x0C ), map( ProtocolConstants.MINECRAFT_1_19_1, 0x0D ), map( ProtocolConstants.MINECRAFT_1_19_3, 0x0C ), - map( ProtocolConstants.MINECRAFT_1_19_4, 0x0D ) + map( ProtocolConstants.MINECRAFT_1_19_4, 0x0D ), + map( ProtocolConstants.MINECRAFT_1_20_2, 0x0F ) + ); + TO_SERVER.registerPacket( + StartConfiguration.class, + StartConfiguration::new, + map( ProtocolConstants.MINECRAFT_1_20_2, 0x0B ) ); } }, @@ -559,6 +600,59 @@ public enum Protocol LoginPayloadResponse::new, map( ProtocolConstants.MINECRAFT_1_13, 0x02 ) ); + TO_SERVER.registerPacket( + LoginAcknowledged.class, + LoginAcknowledged::new, + map( ProtocolConstants.MINECRAFT_1_20_2, 0x03 ) + ); + } + }, + // 3 + CONFIGURATION + { + + { + TO_CLIENT.registerPacket( + PluginMessage.class, + PluginMessage::new, + map( ProtocolConstants.MINECRAFT_1_20_2, 0x00 ) + ); + TO_CLIENT.registerPacket( + Kick.class, + Kick::new, + map( ProtocolConstants.MINECRAFT_1_20_2, 0x01 ) + ); + TO_CLIENT.registerPacket( + FinishConfiguration.class, + FinishConfiguration::new, + map( ProtocolConstants.MINECRAFT_1_20_2, 0x02 ) + ); + TO_CLIENT.registerPacket( + KeepAlive.class, + KeepAlive::new, + map( ProtocolConstants.MINECRAFT_1_20_2, 0x03 ) + ); + + TO_SERVER.registerPacket( + ClientSettings.class, + ClientSettings::new, + map( ProtocolConstants.MINECRAFT_1_20_2, 0x00 ) + ); + TO_SERVER.registerPacket( + PluginMessage.class, + PluginMessage::new, + map( ProtocolConstants.MINECRAFT_1_20_2, 0x01 ) + ); + TO_SERVER.registerPacket( + FinishConfiguration.class, + FinishConfiguration::new, + map( ProtocolConstants.MINECRAFT_1_20_2, 0x02 ) + ); + TO_SERVER.registerPacket( + KeepAlive.class, + KeepAlive::new, + map( ProtocolConstants.MINECRAFT_1_20_2, 0x03 ) + ); } }; /*========================================================================*/ diff --git a/protocol/src/main/java/net/md_5/bungee/protocol/ProtocolConstants.java b/protocol/src/main/java/net/md_5/bungee/protocol/ProtocolConstants.java index 8b27abff..46311941 100644 --- a/protocol/src/main/java/net/md_5/bungee/protocol/ProtocolConstants.java +++ b/protocol/src/main/java/net/md_5/bungee/protocol/ProtocolConstants.java @@ -43,6 +43,7 @@ public class ProtocolConstants public static final int MINECRAFT_1_19_3 = 761; public static final int MINECRAFT_1_19_4 = 762; public static final int MINECRAFT_1_20 = 763; + public static final int MINECRAFT_1_20_2 = 1073741976; public static final List SUPPORTED_VERSIONS; public static final List SUPPORTED_VERSION_IDS; @@ -105,7 +106,7 @@ public class ProtocolConstants if ( SNAPSHOT_SUPPORT ) { // supportedVersions.add( "1.20.x" ); - // supportedVersionIds.add( ProtocolConstants.MINECRAFT_1_20 ); + supportedVersionIds.add( ProtocolConstants.MINECRAFT_1_20_2 ); } SUPPORTED_VERSIONS = supportedVersions.build(); diff --git a/protocol/src/main/java/net/md_5/bungee/protocol/packet/FinishConfiguration.java b/protocol/src/main/java/net/md_5/bungee/protocol/packet/FinishConfiguration.java new file mode 100644 index 00000000..51dee077 --- /dev/null +++ b/protocol/src/main/java/net/md_5/bungee/protocol/packet/FinishConfiguration.java @@ -0,0 +1,37 @@ +package net.md_5.bungee.protocol.packet; + +import io.netty.buffer.ByteBuf; +import lombok.Data; +import lombok.EqualsAndHashCode; +import net.md_5.bungee.protocol.AbstractPacketHandler; +import net.md_5.bungee.protocol.DefinedPacket; +import net.md_5.bungee.protocol.Protocol; +import net.md_5.bungee.protocol.ProtocolConstants; + +@Data +@EqualsAndHashCode(callSuper = false) +public class FinishConfiguration extends DefinedPacket +{ + + @Override + public void read(ByteBuf buf, ProtocolConstants.Direction direction, int protocolVersion) + { + } + + @Override + public void write(ByteBuf buf, ProtocolConstants.Direction direction, int protocolVersion) + { + } + + @Override + public Protocol nextProtocol() + { + return Protocol.GAME; + } + + @Override + public void handle(AbstractPacketHandler handler) throws Exception + { + handler.handle( this ); + } +} diff --git a/protocol/src/main/java/net/md_5/bungee/protocol/packet/Login.java b/protocol/src/main/java/net/md_5/bungee/protocol/packet/Login.java index 6c750743..f110c655 100644 --- a/protocol/src/main/java/net/md_5/bungee/protocol/packet/Login.java +++ b/protocol/src/main/java/net/md_5/bungee/protocol/packet/Login.java @@ -36,6 +36,7 @@ public class Login extends DefinedPacket private int simulationDistance; private boolean reducedDebugInfo; private boolean normalRespawn; + private boolean limitedCrafting; private boolean debug; private boolean flat; private Location deathLocation; @@ -49,10 +50,16 @@ public class Login extends DefinedPacket { hardcore = buf.readBoolean(); } - gameMode = buf.readUnsignedByte(); + if ( protocolVersion < ProtocolConstants.MINECRAFT_1_20_2 ) + { + gameMode = buf.readUnsignedByte(); + } if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_16 ) { - previousGameMode = buf.readUnsignedByte(); + if ( protocolVersion < ProtocolConstants.MINECRAFT_1_20_2 ) + { + previousGameMode = buf.readUnsignedByte(); + } worldNames = new HashSet<>(); int worldCount = readVarInt( buf ); @@ -61,19 +68,25 @@ public class Login extends DefinedPacket worldNames.add( readString( buf ) ); } - dimensions = readTag( buf ); + if ( protocolVersion < ProtocolConstants.MINECRAFT_1_20_2 ) + { + dimensions = readTag( buf, protocolVersion ); + } } if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_16 ) { if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_16_2 && protocolVersion < ProtocolConstants.MINECRAFT_1_19 ) { - dimension = readTag( buf ); - } else + dimension = readTag( buf, protocolVersion ); + } else if ( protocolVersion < ProtocolConstants.MINECRAFT_1_20_2 ) { dimension = readString( buf ); } - worldName = readString( buf ); + if ( protocolVersion < ProtocolConstants.MINECRAFT_1_20_2 ) + { + worldName = readString( buf ); + } } else if ( protocolVersion > ProtocolConstants.MINECRAFT_1_9 ) { dimension = buf.readInt(); @@ -81,7 +94,7 @@ public class Login extends DefinedPacket { dimension = (int) buf.readByte(); } - if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_15 ) + if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_15 && protocolVersion < ProtocolConstants.MINECRAFT_1_20_2 ) { seed = buf.readLong(); } @@ -116,6 +129,15 @@ public class Login extends DefinedPacket { normalRespawn = buf.readBoolean(); } + if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_20_2 ) + { + limitedCrafting = buf.readBoolean(); + dimension = readString( buf ); + worldName = readString( buf ); + seed = buf.readLong(); + gameMode = buf.readUnsignedByte(); + previousGameMode = buf.readByte(); + } if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_16 ) { debug = buf.readBoolean(); @@ -142,10 +164,16 @@ public class Login extends DefinedPacket { buf.writeBoolean( hardcore ); } - buf.writeByte( gameMode ); + if ( protocolVersion < ProtocolConstants.MINECRAFT_1_20_2 ) + { + buf.writeByte( gameMode ); + } if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_16 ) { - buf.writeByte( previousGameMode ); + if ( protocolVersion < ProtocolConstants.MINECRAFT_1_20_2 ) + { + buf.writeByte( previousGameMode ); + } writeVarInt( worldNames.size(), buf ); for ( String world : worldNames ) @@ -153,19 +181,25 @@ public class Login extends DefinedPacket writeString( world, buf ); } - writeTag( dimensions, buf ); + if ( protocolVersion < ProtocolConstants.MINECRAFT_1_20_2 ) + { + writeTag( dimensions, buf, protocolVersion ); + } } if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_16 ) { if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_16_2 && protocolVersion < ProtocolConstants.MINECRAFT_1_19 ) { - writeTag( (Tag) dimension, buf ); - } else + writeTag( (Tag) dimension, buf, protocolVersion ); + } else if ( protocolVersion < ProtocolConstants.MINECRAFT_1_20_2 ) { writeString( (String) dimension, buf ); } - writeString( worldName, buf ); + if ( protocolVersion < ProtocolConstants.MINECRAFT_1_20_2 ) + { + writeString( worldName, buf ); + } } else if ( protocolVersion > ProtocolConstants.MINECRAFT_1_9 ) { buf.writeInt( (Integer) dimension ); @@ -175,7 +209,10 @@ public class Login extends DefinedPacket } if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_15 ) { - buf.writeLong( seed ); + if ( protocolVersion < ProtocolConstants.MINECRAFT_1_20_2 ) + { + buf.writeLong( seed ); + } } if ( protocolVersion < ProtocolConstants.MINECRAFT_1_14 ) { @@ -208,6 +245,15 @@ public class Login extends DefinedPacket { buf.writeBoolean( normalRespawn ); } + if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_20_2 ) + { + buf.writeBoolean( limitedCrafting ); + writeString( (String) dimension, buf ); + writeString( worldName, buf ); + buf.writeLong( seed ); + buf.writeByte( gameMode ); + buf.writeByte( previousGameMode ); + } if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_16 ) { buf.writeBoolean( debug ); diff --git a/protocol/src/main/java/net/md_5/bungee/protocol/packet/LoginAcknowledged.java b/protocol/src/main/java/net/md_5/bungee/protocol/packet/LoginAcknowledged.java new file mode 100644 index 00000000..1df2915d --- /dev/null +++ b/protocol/src/main/java/net/md_5/bungee/protocol/packet/LoginAcknowledged.java @@ -0,0 +1,37 @@ +package net.md_5.bungee.protocol.packet; + +import io.netty.buffer.ByteBuf; +import lombok.Data; +import lombok.EqualsAndHashCode; +import net.md_5.bungee.protocol.AbstractPacketHandler; +import net.md_5.bungee.protocol.DefinedPacket; +import net.md_5.bungee.protocol.Protocol; +import net.md_5.bungee.protocol.ProtocolConstants; + +@Data +@EqualsAndHashCode(callSuper = false) +public class LoginAcknowledged extends DefinedPacket +{ + + @Override + public void read(ByteBuf buf, ProtocolConstants.Direction direction, int protocolVersion) + { + } + + @Override + public void write(ByteBuf buf, ProtocolConstants.Direction direction, int protocolVersion) + { + } + + @Override + public Protocol nextProtocol() + { + return Protocol.CONFIGURATION; + } + + @Override + public void handle(AbstractPacketHandler handler) throws Exception + { + handler.handle( this ); + } +} diff --git a/protocol/src/main/java/net/md_5/bungee/protocol/packet/LoginRequest.java b/protocol/src/main/java/net/md_5/bungee/protocol/packet/LoginRequest.java index 5186a6a8..e62a3a03 100644 --- a/protocol/src/main/java/net/md_5/bungee/protocol/packet/LoginRequest.java +++ b/protocol/src/main/java/net/md_5/bungee/protocol/packet/LoginRequest.java @@ -32,7 +32,7 @@ public class LoginRequest extends DefinedPacket } if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_19_1 ) { - if ( buf.readBoolean() ) + if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_20_2 || buf.readBoolean() ) { uuid = readUUID( buf ); } @@ -49,13 +49,19 @@ public class LoginRequest extends DefinedPacket } if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_19_1 ) { - if ( uuid != null ) + if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_20_2 ) { - buf.writeBoolean( true ); writeUUID( uuid, buf ); } else { - buf.writeBoolean( false ); + if ( uuid != null ) + { + buf.writeBoolean( true ); + writeUUID( uuid, buf ); + } else + { + buf.writeBoolean( false ); + } } } } diff --git a/protocol/src/main/java/net/md_5/bungee/protocol/packet/Respawn.java b/protocol/src/main/java/net/md_5/bungee/protocol/packet/Respawn.java index 4f633e98..e6b1b0c9 100644 --- a/protocol/src/main/java/net/md_5/bungee/protocol/packet/Respawn.java +++ b/protocol/src/main/java/net/md_5/bungee/protocol/packet/Respawn.java @@ -27,7 +27,7 @@ public class Respawn extends DefinedPacket private String levelType; private boolean debug; private boolean flat; - private boolean copyMeta; + private byte copyMeta; private Location deathLocation; private int portalCooldown; @@ -38,7 +38,7 @@ public class Respawn extends DefinedPacket { if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_16_2 && protocolVersion < ProtocolConstants.MINECRAFT_1_19 ) { - dimension = readTag( buf ); + dimension = readTag( buf, protocolVersion ); } else { dimension = readString( buf ); @@ -62,7 +62,10 @@ public class Respawn extends DefinedPacket previousGameMode = buf.readUnsignedByte(); debug = buf.readBoolean(); flat = buf.readBoolean(); - copyMeta = buf.readBoolean(); + if ( protocolVersion < ProtocolConstants.MINECRAFT_1_20_2 ) + { + copyMeta = buf.readByte(); + } } else { levelType = readString( buf ); @@ -78,6 +81,10 @@ public class Respawn extends DefinedPacket { portalCooldown = readVarInt( buf ); } + if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_20_2 ) + { + copyMeta = buf.readByte(); + } } @Override @@ -87,7 +94,7 @@ public class Respawn extends DefinedPacket { if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_16_2 && protocolVersion < ProtocolConstants.MINECRAFT_1_19 ) { - writeTag( (Tag) dimension, buf ); + writeTag( (Tag) dimension, buf, protocolVersion ); } else { writeString( (String) dimension, buf ); @@ -111,7 +118,10 @@ public class Respawn extends DefinedPacket buf.writeByte( previousGameMode ); buf.writeBoolean( debug ); buf.writeBoolean( flat ); - buf.writeBoolean( copyMeta ); + if ( protocolVersion < ProtocolConstants.MINECRAFT_1_20_2 ) + { + buf.writeByte( copyMeta ); + } } else { writeString( levelType, buf ); @@ -132,6 +142,10 @@ public class Respawn extends DefinedPacket { writeVarInt( portalCooldown, buf ); } + if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_20_2 ) + { + buf.writeByte( copyMeta ); + } } @Override diff --git a/protocol/src/main/java/net/md_5/bungee/protocol/packet/ScoreboardDisplay.java b/protocol/src/main/java/net/md_5/bungee/protocol/packet/ScoreboardDisplay.java index b8f30276..cdaabb75 100644 --- a/protocol/src/main/java/net/md_5/bungee/protocol/packet/ScoreboardDisplay.java +++ b/protocol/src/main/java/net/md_5/bungee/protocol/packet/ScoreboardDisplay.java @@ -7,6 +7,7 @@ import lombok.EqualsAndHashCode; import lombok.NoArgsConstructor; import net.md_5.bungee.protocol.AbstractPacketHandler; import net.md_5.bungee.protocol.DefinedPacket; +import net.md_5.bungee.protocol.ProtocolConstants; @Data @NoArgsConstructor @@ -18,20 +19,32 @@ public class ScoreboardDisplay extends DefinedPacket /** * 0 = list, 1 = side, 2 = below. */ - private byte position; + private int position; private String name; @Override - public void read(ByteBuf buf) + public void read(ByteBuf buf, ProtocolConstants.Direction direction, int protocolVersion) { - position = buf.readByte(); + if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_20_2 ) + { + position = readVarInt( buf ); + } else + { + position = buf.readByte(); + } name = readString( buf ); } @Override - public void write(ByteBuf buf) + public void write(ByteBuf buf, ProtocolConstants.Direction direction, int protocolVersion) { - buf.writeByte( position ); + if ( protocolVersion >= ProtocolConstants.MINECRAFT_1_20_2 ) + { + writeVarInt( position, buf ); + } else + { + buf.writeByte( position ); + } writeString( name, buf ); } diff --git a/protocol/src/main/java/net/md_5/bungee/protocol/packet/StartConfiguration.java b/protocol/src/main/java/net/md_5/bungee/protocol/packet/StartConfiguration.java new file mode 100644 index 00000000..cebbd394 --- /dev/null +++ b/protocol/src/main/java/net/md_5/bungee/protocol/packet/StartConfiguration.java @@ -0,0 +1,37 @@ +package net.md_5.bungee.protocol.packet; + +import io.netty.buffer.ByteBuf; +import lombok.Data; +import lombok.EqualsAndHashCode; +import net.md_5.bungee.protocol.AbstractPacketHandler; +import net.md_5.bungee.protocol.DefinedPacket; +import net.md_5.bungee.protocol.Protocol; +import net.md_5.bungee.protocol.ProtocolConstants; + +@Data +@EqualsAndHashCode(callSuper = false) +public class StartConfiguration extends DefinedPacket +{ + + @Override + public void read(ByteBuf buf, ProtocolConstants.Direction direction, int protocolVersion) + { + } + + @Override + public void write(ByteBuf buf, ProtocolConstants.Direction direction, int protocolVersion) + { + } + + @Override + public Protocol nextProtocol() + { + return Protocol.CONFIGURATION; + } + + @Override + public void handle(AbstractPacketHandler handler) throws Exception + { + handler.handle( this ); + } +} diff --git a/proxy/pom.xml b/proxy/pom.xml index 7af26db1..335ee3d5 100644 --- a/proxy/pom.xml +++ b/proxy/pom.xml @@ -96,7 +96,7 @@ com.mysql mysql-connector-j - 8.0.33 + 8.1.0 runtime diff --git a/proxy/src/main/java/net/md_5/bungee/ServerConnector.java b/proxy/src/main/java/net/md_5/bungee/ServerConnector.java index a99d9914..7ef4ee91 100644 --- a/proxy/src/main/java/net/md_5/bungee/ServerConnector.java +++ b/proxy/src/main/java/net/md_5/bungee/ServerConnector.java @@ -43,6 +43,7 @@ import net.md_5.bungee.protocol.packet.GameState; import net.md_5.bungee.protocol.packet.Handshake; import net.md_5.bungee.protocol.packet.Kick; import net.md_5.bungee.protocol.packet.Login; +import net.md_5.bungee.protocol.packet.LoginAcknowledged; import net.md_5.bungee.protocol.packet.LoginPayloadRequest; import net.md_5.bungee.protocol.packet.LoginPayloadResponse; import net.md_5.bungee.protocol.packet.LoginRequest; @@ -52,6 +53,7 @@ import net.md_5.bungee.protocol.packet.Respawn; import net.md_5.bungee.protocol.packet.ScoreboardObjective; import net.md_5.bungee.protocol.packet.ScoreboardScore; import net.md_5.bungee.protocol.packet.SetCompression; +import net.md_5.bungee.protocol.packet.StartConfiguration; import net.md_5.bungee.protocol.packet.ViewDistance; import net.md_5.bungee.util.AddressUtil; import net.md_5.bungee.util.BufUtil; @@ -145,8 +147,15 @@ public class ServerConnector extends PacketHandler public void handle(LoginSuccess loginSuccess) throws Exception { Preconditions.checkState( thisState == State.LOGIN_SUCCESS, "Not expecting LOGIN_SUCCESS" ); - ch.setProtocol( Protocol.GAME ); - thisState = State.LOGIN; + if ( user.getPendingConnection().getVersion() >= ProtocolConstants.MINECRAFT_1_20_2 ) + { + ServerConnection server = new ServerConnection( ch, target ); + cutThrough( server ); + } else + { + ch.setProtocol( Protocol.GAME ); + thisState = State.LOGIN; + } // Only reset the Forge client when: // 1) The user is switching servers (so has a current server) @@ -182,6 +191,12 @@ public class ServerConnector extends PacketHandler Preconditions.checkState( thisState == State.LOGIN, "Not expecting LOGIN" ); ServerConnection server = new ServerConnection( ch, target ); + handleLogin( bungee, ch, user, target, handshakeHandler, server, login ); + cutThrough( server ); + } + + public static void handleLogin(ProxyServer bungee, ChannelWrapper ch, UserConnection user, BungeeServerInfo target, ForgeServerHandler handshakeHandler, ServerConnection server, Login login) throws Exception + { ServerConnectedEvent event = new ServerConnectedEvent( user, server ); bungee.getPluginManager().callEvent( event ); @@ -225,14 +240,13 @@ public class ServerConnector extends PacketHandler // Set tab list size, TODO: what shall we do about packet mutability Login modLogin = new Login( login.getEntityId(), login.isHardcore(), login.getGameMode(), login.getPreviousGameMode(), login.getWorldNames(), login.getDimensions(), login.getDimension(), login.getWorldName(), login.getSeed(), login.getDifficulty(), - (byte) user.getPendingConnection().getListener().getTabListSize(), login.getLevelType(), login.getViewDistance(), login.getSimulationDistance(), login.isReducedDebugInfo(), login.isNormalRespawn(), login.isDebug(), login.isFlat(), login.getDeathLocation(), + (byte) user.getPendingConnection().getListener().getTabListSize(), login.getLevelType(), login.getViewDistance(), login.getSimulationDistance(), login.isReducedDebugInfo(), login.isNormalRespawn(), login.isLimitedCrafting(), login.isDebug(), login.isFlat(), login.getDeathLocation(), login.getPortalCooldown() ); user.unsafe().sendPacket( modLogin ); - if ( user.getServer() != null ) + if ( user.getDimension() != null ) { - user.getServer().setObsolete( true ); user.getTabListHandler().onServerChange(); user.getServerSentScoreboard().clear(); @@ -244,14 +258,15 @@ public class ServerConnector extends PacketHandler } user.getSentBossBars().clear(); - user.unsafe().sendPacket( new Respawn( login.getDimension(), login.getWorldName(), login.getSeed(), login.getDifficulty(), login.getGameMode(), login.getPreviousGameMode(), login.getLevelType(), login.isDebug(), login.isFlat(), false, login.getDeathLocation(), + user.unsafe().sendPacket( new Respawn( login.getDimension(), login.getWorldName(), login.getSeed(), login.getDifficulty(), login.getGameMode(), login.getPreviousGameMode(), login.getLevelType(), login.isDebug(), login.isFlat(), (byte) 0, login.getDeathLocation(), login.getPortalCooldown() ) ); - user.getServer().disconnect( "Quitting" ); } else { + user.unsafe().sendPacket( BungeeCord.getInstance().registerChannels( user.getPendingConnection().getVersion() ) ); + ByteBuf brand = ByteBufAllocator.DEFAULT.heapBuffer(); DefinedPacket.writeString( bungee.getName() + " (" + bungee.getVersion() + ")", brand ); - user.unsafe().sendPacket( new PluginMessage( user.getPendingConnection().getVersion() >= ProtocolConstants.MINECRAFT_1_13 ? "minecraft:brand" : "MC|Brand", DefinedPacket.toArray( brand ), handshakeHandler.isServerForge() ) ); + user.unsafe().sendPacket( new PluginMessage( user.getPendingConnection().getVersion() >= ProtocolConstants.MINECRAFT_1_13 ? "minecraft:brand" : "MC|Brand", DefinedPacket.toArray( brand ), handshakeHandler != null && handshakeHandler.isServerForge() ) ); brand.release(); } @@ -295,19 +310,40 @@ public class ServerConnector extends PacketHandler if ( login.getDimension() == user.getDimension() ) { user.unsafe().sendPacket( new Respawn( (Integer) login.getDimension() >= 0 ? -1 : 0, login.getWorldName(), login.getSeed(), login.getDifficulty(), login.getGameMode(), login.getPreviousGameMode(), login.getLevelType(), login.isDebug(), login.isFlat(), - false, login.getDeathLocation(), login.getPortalCooldown() ) ); + (byte) 0, login.getDeathLocation(), login.getPortalCooldown() ) ); } user.setServerEntityId( login.getEntityId() ); user.unsafe().sendPacket( new Respawn( login.getDimension(), login.getWorldName(), login.getSeed(), login.getDifficulty(), login.getGameMode(), login.getPreviousGameMode(), login.getLevelType(), login.isDebug(), login.isFlat(), - false, login.getDeathLocation(), login.getPortalCooldown() ) ); + (byte) 0, login.getDeathLocation(), login.getPortalCooldown() ) ); if ( user.getPendingConnection().getVersion() >= ProtocolConstants.MINECRAFT_1_14 ) { user.unsafe().sendPacket( new ViewDistance( login.getViewDistance() ) ); } user.setDimension( login.getDimension() ); + } + } - // Remove from old servers + private void cutThrough(ServerConnection server) + { + if ( user.getPendingConnection().getVersion() >= ProtocolConstants.MINECRAFT_1_20_2 ) + { + if ( user.getServer() != null ) + { + // Begin config mode + user.unsafe().sendPacket( new StartConfiguration() ); + } else + { + ch.setDecodeProtocol( Protocol.CONFIGURATION ); + ch.write( new LoginAcknowledged() ); + ch.setEncodeProtocol( Protocol.CONFIGURATION ); + } + } + + // Remove from old servers + if ( user.getServer() != null ) + { + user.getServer().setObsolete( true ); user.getServer().disconnect( "Quitting" ); } diff --git a/proxy/src/main/java/net/md_5/bungee/UserConnection.java b/proxy/src/main/java/net/md_5/bungee/UserConnection.java index 67a4269a..9d2df335 100644 --- a/proxy/src/main/java/net/md_5/bungee/UserConnection.java +++ b/proxy/src/main/java/net/md_5/bungee/UserConnection.java @@ -72,6 +72,7 @@ public final class UserConnection implements ProxiedPlayer /*========================================================================*/ @NonNull private final ProxyServer bungee; + @Getter @NonNull private final ChannelWrapper ch; @Getter diff --git a/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java b/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java index 528d53ac..117ebb76 100644 --- a/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java +++ b/proxy/src/main/java/net/md_5/bungee/connection/DownstreamBridge.java @@ -26,6 +26,7 @@ import java.util.stream.Collectors; import lombok.RequiredArgsConstructor; import net.md_5.bungee.ServerConnection; import net.md_5.bungee.ServerConnection.KeepAliveData; +import net.md_5.bungee.ServerConnector; import net.md_5.bungee.UserConnection; import net.md_5.bungee.Util; import net.md_5.bungee.api.ProxyServer; @@ -51,11 +52,13 @@ import net.md_5.bungee.netty.ChannelWrapper; import net.md_5.bungee.netty.PacketHandler; import net.md_5.bungee.protocol.DefinedPacket; import net.md_5.bungee.protocol.PacketWrapper; +import net.md_5.bungee.protocol.Protocol; import net.md_5.bungee.protocol.ProtocolConstants; import net.md_5.bungee.protocol.packet.BossBar; import net.md_5.bungee.protocol.packet.Commands; import net.md_5.bungee.protocol.packet.KeepAlive; import net.md_5.bungee.protocol.packet.Kick; +import net.md_5.bungee.protocol.packet.Login; import net.md_5.bungee.protocol.packet.PlayerListItem; import net.md_5.bungee.protocol.packet.PlayerListItemRemove; import net.md_5.bungee.protocol.packet.PlayerListItemUpdate; @@ -83,6 +86,7 @@ public class DownstreamBridge extends PacketHandler private final ProxyServer bungee; private final UserConnection con; private final ServerConnection server; + private boolean receivedLogin; @Override public void exception(Throwable t) throws Exception @@ -134,7 +138,7 @@ public class DownstreamBridge extends PacketHandler public void handle(PacketWrapper packet) throws Exception { EntityMap rewrite = con.getEntityRewrite(); - if ( rewrite != null ) + if ( rewrite != null && con.getCh().getEncodeProtocol() == Protocol.GAME ) { rewrite.rewriteClientbound( packet.buf, con.getServerEntityId(), con.getClientEntityId(), con.getPendingConnection().getVersion() ); } @@ -756,6 +760,17 @@ public class DownstreamBridge extends PacketHandler throw CancelSendSignal.INSTANCE; } + @Override + public void handle(Login login) throws Exception + { + Preconditions.checkState( !receivedLogin, "Not expecting login" ); + + receivedLogin = true; + ServerConnector.handleLogin( bungee, server.getCh(), con, server.getInfo(), null, server, login ); + + throw CancelSendSignal.INSTANCE; + } + @Override public String toString() { diff --git a/proxy/src/main/java/net/md_5/bungee/connection/InitialHandler.java b/proxy/src/main/java/net/md_5/bungee/connection/InitialHandler.java index 536e65e7..e542c1be 100644 --- a/proxy/src/main/java/net/md_5/bungee/connection/InitialHandler.java +++ b/proxy/src/main/java/net/md_5/bungee/connection/InitialHandler.java @@ -59,6 +59,7 @@ import net.md_5.bungee.protocol.packet.Handshake; import net.md_5.bungee.protocol.packet.Kick; import net.md_5.bungee.protocol.packet.LegacyHandshake; import net.md_5.bungee.protocol.packet.LegacyPing; +import net.md_5.bungee.protocol.packet.LoginAcknowledged; import net.md_5.bungee.protocol.packet.LoginPayloadResponse; import net.md_5.bungee.protocol.packet.LoginRequest; import net.md_5.bungee.protocol.packet.LoginSuccess; @@ -111,6 +112,7 @@ public class InitialHandler extends PacketHandler implements PendingConnection private boolean legacy; @Getter private String extraDataInHandshake = ""; + private UserConnection userCon; @Override public boolean shouldHandle(PacketWrapper packet) throws Exception @@ -121,12 +123,12 @@ public class InitialHandler extends PacketHandler implements PendingConnection private enum State { - HANDSHAKE, STATUS, PING, USERNAME, ENCRYPT, FINISHING; + HANDSHAKE, STATUS, PING, USERNAME, ENCRYPT, FINISHING, CONFIGURING; } private boolean canSendKickMessage() { - return thisState == State.USERNAME || thisState == State.ENCRYPT || thisState == State.FINISHING; + return thisState == State.USERNAME || thisState == State.ENCRYPT || thisState == State.FINISHING || thisState == State.CONFIGURING; } @Override @@ -593,29 +595,18 @@ public class InitialHandler extends PacketHandler implements PendingConnection { if ( !ch.isClosing() ) { - UserConnection userCon = new UserConnection( bungee, ch, getName(), InitialHandler.this ); + userCon = new UserConnection( bungee, ch, getName(), InitialHandler.this ); userCon.setCompressionThreshold( BungeeCord.getInstance().config.getCompressionThreshold() ); - userCon.init(); unsafe.sendPacket( new LoginSuccess( getUniqueId(), getName(), ( loginProfile == null ) ? null : loginProfile.getProperties() ) ); - ch.setProtocol( Protocol.GAME ); - - ch.getHandle().pipeline().get( HandlerBoss.class ).setHandler( new UpstreamBridge( bungee, userCon ) ); - bungee.getPluginManager().callEvent( new PostLoginEvent( userCon ) ); - ServerInfo server; - if ( bungee.getReconnectHandler() != null ) + if ( getVersion() >= ProtocolConstants.MINECRAFT_1_20_2 ) { - server = bungee.getReconnectHandler().getServer( userCon ); + thisState = State.CONFIGURING; } else { - server = AbstractReconnectHandler.getForcedHost( InitialHandler.this ); + ch.setProtocol( Protocol.GAME ); + finish2(); } - if ( server == null ) - { - server = bungee.getServerInfo( listener.getDefaultServer() ); - } - - userCon.connect( server, null, true, ServerConnectEvent.Reason.JOIN_PROXY ); } } } ); @@ -626,6 +617,37 @@ public class InitialHandler extends PacketHandler implements PendingConnection bungee.getPluginManager().callEvent( new LoginEvent( InitialHandler.this, complete ) ); } + @Override + public void handle(LoginAcknowledged loginAcknowledged) throws Exception + { + Preconditions.checkState( thisState == State.CONFIGURING, "Not expecting CONFIGURING" ); + + finish2(); + ch.setEncodeProtocol( Protocol.CONFIGURATION ); + } + + private void finish2() + { + userCon.init(); + + ch.getHandle().pipeline().get( HandlerBoss.class ).setHandler( new UpstreamBridge( bungee, userCon ) ); + bungee.getPluginManager().callEvent( new PostLoginEvent( userCon ) ); + ServerInfo server; + if ( bungee.getReconnectHandler() != null ) + { + server = bungee.getReconnectHandler().getServer( userCon ); + } else + { + server = AbstractReconnectHandler.getForcedHost( InitialHandler.this ); + } + if ( server == null ) + { + server = bungee.getServerInfo( listener.getDefaultServer() ); + } + + userCon.connect( server, null, true, ServerConnectEvent.Reason.JOIN_PROXY ); + } + @Override public void handle(LoginPayloadResponse response) throws Exception { diff --git a/proxy/src/main/java/net/md_5/bungee/connection/UpstreamBridge.java b/proxy/src/main/java/net/md_5/bungee/connection/UpstreamBridge.java index a3536903..d288b6f2 100644 --- a/proxy/src/main/java/net/md_5/bungee/connection/UpstreamBridge.java +++ b/proxy/src/main/java/net/md_5/bungee/connection/UpstreamBridge.java @@ -25,15 +25,18 @@ import net.md_5.bungee.forge.ForgeConstants; import net.md_5.bungee.netty.ChannelWrapper; import net.md_5.bungee.netty.PacketHandler; import net.md_5.bungee.protocol.PacketWrapper; +import net.md_5.bungee.protocol.Protocol; import net.md_5.bungee.protocol.ProtocolConstants; import net.md_5.bungee.protocol.packet.Chat; import net.md_5.bungee.protocol.packet.ClientChat; import net.md_5.bungee.protocol.packet.ClientCommand; import net.md_5.bungee.protocol.packet.ClientSettings; import net.md_5.bungee.protocol.packet.KeepAlive; +import net.md_5.bungee.protocol.packet.LoginAcknowledged; import net.md_5.bungee.protocol.packet.PlayerListItem; import net.md_5.bungee.protocol.packet.PlayerListItemRemove; import net.md_5.bungee.protocol.packet.PluginMessage; +import net.md_5.bungee.protocol.packet.StartConfiguration; import net.md_5.bungee.protocol.packet.TabCompleteRequest; import net.md_5.bungee.protocol.packet.TabCompleteResponse; import net.md_5.bungee.util.AllowedCharacters; @@ -51,7 +54,6 @@ public class UpstreamBridge extends PacketHandler BungeeCord.getInstance().addConnection( con ); con.getTabListHandler().onConnect(); - con.unsafe().sendPacket( BungeeCord.getInstance().registerChannels( con.getPendingConnection().getVersion() ) ); } @Override @@ -134,7 +136,7 @@ public class UpstreamBridge extends PacketHandler if ( con.getServer() != null ) { EntityMap rewrite = con.getEntityRewrite(); - if ( rewrite != null ) + if ( rewrite != null && con.getServer().getCh().getEncodeProtocol() == Protocol.GAME ) { rewrite.rewriteServerbound( packet.buf, con.getClientEntityId(), con.getServerEntityId(), con.getPendingConnection().getVersion() ); } @@ -319,6 +321,19 @@ public class UpstreamBridge extends PacketHandler con.getPendingConnection().relayMessage( pluginMessage ); } + @Override + public void handle(StartConfiguration startConfiguration) throws Exception + { + ChannelWrapper ch = con.getServer().getCh(); + if ( ch.getDecodeProtocol() == Protocol.LOGIN ) + { + ch.setDecodeProtocol( Protocol.CONFIGURATION ); + ch.write( new LoginAcknowledged() ); + ch.setEncodeProtocol( Protocol.CONFIGURATION ); + throw CancelSendSignal.INSTANCE; + } + } + @Override public String toString() { diff --git a/proxy/src/main/java/net/md_5/bungee/entitymap/EntityMap.java b/proxy/src/main/java/net/md_5/bungee/entitymap/EntityMap.java index 5440f4b5..30cc36a4 100644 --- a/proxy/src/main/java/net/md_5/bungee/entitymap/EntityMap.java +++ b/proxy/src/main/java/net/md_5/bungee/entitymap/EntityMap.java @@ -82,6 +82,8 @@ public abstract class EntityMap case ProtocolConstants.MINECRAFT_1_19_4: case ProtocolConstants.MINECRAFT_1_20: return EntityMap_1_16_2.INSTANCE_1_19_4; + case ProtocolConstants.MINECRAFT_1_20_2: + return EntityMap_1_16_2.INSTANCE_1_20_2; } throw new RuntimeException( "Version " + version + " has no entity map" ); } diff --git a/proxy/src/main/java/net/md_5/bungee/entitymap/EntityMap_1_16_2.java b/proxy/src/main/java/net/md_5/bungee/entitymap/EntityMap_1_16_2.java index e5e784a0..5815ebf9 100644 --- a/proxy/src/main/java/net/md_5/bungee/entitymap/EntityMap_1_16_2.java +++ b/proxy/src/main/java/net/md_5/bungee/entitymap/EntityMap_1_16_2.java @@ -20,6 +20,7 @@ class EntityMap_1_16_2 extends EntityMap static final EntityMap_1_16_2 INSTANCE_1_19 = new EntityMap_1_16_2( 0x02, 0x2F ); static final EntityMap_1_16_2 INSTANCE_1_19_1 = new EntityMap_1_16_2( 0x02, 0x30 ); static final EntityMap_1_16_2 INSTANCE_1_19_4 = new EntityMap_1_16_2( 0x03, 0x30 ); + static final EntityMap_1_16_2 INSTANCE_1_20_2 = new EntityMap_1_16_2( -1, 0x33 ); // private final int spawnPlayerId; private final int spectateId; diff --git a/proxy/src/main/java/net/md_5/bungee/netty/ChannelWrapper.java b/proxy/src/main/java/net/md_5/bungee/netty/ChannelWrapper.java index 6e4529e9..915f8a7b 100644 --- a/proxy/src/main/java/net/md_5/bungee/netty/ChannelWrapper.java +++ b/proxy/src/main/java/net/md_5/bungee/netty/ChannelWrapper.java @@ -11,6 +11,7 @@ import lombok.Getter; import lombok.Setter; import net.md_5.bungee.compress.PacketCompressor; import net.md_5.bungee.compress.PacketDecompressor; +import net.md_5.bungee.protocol.DefinedPacket; import net.md_5.bungee.protocol.MinecraftDecoder; import net.md_5.bungee.protocol.MinecraftEncoder; import net.md_5.bungee.protocol.PacketWrapper; @@ -35,12 +36,33 @@ public class ChannelWrapper this.remoteAddress = ( this.ch.remoteAddress() == null ) ? this.ch.parent().localAddress() : this.ch.remoteAddress(); } - public void setProtocol(Protocol protocol) + public Protocol getDecodeProtocol() + { + return ch.pipeline().get( MinecraftDecoder.class ).getProtocol(); + } + + public void setDecodeProtocol(Protocol protocol) { ch.pipeline().get( MinecraftDecoder.class ).setProtocol( protocol ); + } + + public Protocol getEncodeProtocol() + { + return ch.pipeline().get( MinecraftEncoder.class ).getProtocol(); + + } + + public void setEncodeProtocol(Protocol protocol) + { ch.pipeline().get( MinecraftEncoder.class ).setProtocol( protocol ); } + public void setProtocol(Protocol protocol) + { + setDecodeProtocol( protocol ); + setEncodeProtocol( protocol ); + } + public void setVersion(int protocol) { ch.pipeline().get( MinecraftDecoder.class ).setProtocolVersion( protocol ); @@ -51,13 +73,29 @@ public class ChannelWrapper { if ( !closed ) { + DefinedPacket defined = null; if ( packet instanceof PacketWrapper ) { - ( (PacketWrapper) packet ).setReleased( true ); - ch.writeAndFlush( ( (PacketWrapper) packet ).buf, ch.voidPromise() ); + PacketWrapper wrapper = (PacketWrapper) packet; + wrapper.setReleased( true ); + ch.writeAndFlush( wrapper.buf, ch.voidPromise() ); + defined = wrapper.packet; } else { ch.writeAndFlush( packet, ch.voidPromise() ); + if ( packet instanceof DefinedPacket ) + { + defined = (DefinedPacket) packet; + } + } + + if ( defined != null ) + { + Protocol nextProtocol = defined.nextProtocol(); + if ( nextProtocol != null ) + { + setEncodeProtocol( nextProtocol ); + } } } } diff --git a/proxy/src/main/java/net/md_5/bungee/netty/HandlerBoss.java b/proxy/src/main/java/net/md_5/bungee/netty/HandlerBoss.java index 33494237..fd840d28 100644 --- a/proxy/src/main/java/net/md_5/bungee/netty/HandlerBoss.java +++ b/proxy/src/main/java/net/md_5/bungee/netty/HandlerBoss.java @@ -17,6 +17,7 @@ import net.md_5.bungee.connection.PingHandler; import net.md_5.bungee.protocol.BadPacketException; import net.md_5.bungee.protocol.OverflowPacketException; import net.md_5.bungee.protocol.PacketWrapper; +import net.md_5.bungee.protocol.Protocol; import net.md_5.bungee.util.QuietException; /** @@ -101,9 +102,18 @@ public class HandlerBoss extends ChannelInboundHandlerAdapter return; } + PacketWrapper packet = (PacketWrapper) msg; + if ( packet.packet != null ) + { + Protocol nextProtocol = packet.packet.nextProtocol(); + if ( nextProtocol != null ) + { + channel.setDecodeProtocol( nextProtocol ); + } + } + if ( handler != null ) { - PacketWrapper packet = (PacketWrapper) msg; boolean sendPacket = handler.shouldHandle( packet ); try {