From f00b9b73ead178340c3b023b131da2a179683876 Mon Sep 17 00:00:00 2001 From: Andrew Steinborn Date: Fri, 23 Apr 2021 19:16:47 -0400 Subject: [PATCH] Make ServerboundHandshakePacket immutable --- .../proxy/connection/InboundConnection.java | 2 +- .../backend/VelocityServerConnection.java | 43 ++++++++--------- .../connection/client/ConnectedPlayer.java | 5 +- .../client/HandshakeSessionHandler.java | 2 +- .../client/InitialInboundConnection.java | 2 +- .../client/LoginSessionHandler.java | 4 +- .../client/StatusSessionHandler.java | 2 +- .../ServerboundHandshakePacket.java | 46 ++++--------------- .../proxy/server/PingSessionHandler.java | 21 +++++---- 9 files changed, 52 insertions(+), 75 deletions(-) diff --git a/api/src/main/java/com/velocitypowered/api/proxy/connection/InboundConnection.java b/api/src/main/java/com/velocitypowered/api/proxy/connection/InboundConnection.java index 4652899f1..c03adb9a8 100644 --- a/api/src/main/java/com/velocitypowered/api/proxy/connection/InboundConnection.java +++ b/api/src/main/java/com/velocitypowered/api/proxy/connection/InboundConnection.java @@ -29,7 +29,7 @@ public interface InboundConnection { * * @return the hostname from the client */ - Optional connectedHost(); + Optional connectedHostname(); /** * Determine whether or not the player remains online. diff --git a/proxy/src/main/java/com/velocitypowered/proxy/connection/backend/VelocityServerConnection.java b/proxy/src/main/java/com/velocitypowered/proxy/connection/backend/VelocityServerConnection.java index 197272884..23b3a4411 100644 --- a/proxy/src/main/java/com/velocitypowered/proxy/connection/backend/VelocityServerConnection.java +++ b/proxy/src/main/java/com/velocitypowered/proxy/connection/backend/VelocityServerConnection.java @@ -118,8 +118,8 @@ public class VelocityServerConnection implements MinecraftConnectionAssociation, return result; } - private String getHandshakeRemoteAddress() { - return proxyPlayer.connectedHost().map(InetSocketAddress::getHostString).orElse(""); + private String playerConnectedHostname() { + return proxyPlayer.connectedHostname().map(InetSocketAddress::getHostString).orElse(""); } private String createLegacyForwardingAddress(UnaryOperator> propertiesTransform) { @@ -128,10 +128,10 @@ public class VelocityServerConnection implements MinecraftConnectionAssociation, // UUID (undashed), and if you are in online-mode, their login properties (from Mojang). SocketAddress playerRemoteAddress = proxyPlayer.remoteAddress(); if (!(playerRemoteAddress instanceof InetSocketAddress)) { - return getHandshakeRemoteAddress(); + return playerConnectedHostname(); } StringBuilder data = new StringBuilder() - .append(getHandshakeRemoteAddress()) + .append(playerConnectedHostname()) .append('\0') .append(((InetSocketAddress) proxyPlayer.remoteAddress()).getHostString()) .append('\0') @@ -162,24 +162,12 @@ public class VelocityServerConnection implements MinecraftConnectionAssociation, // Initiate the handshake. ProtocolVersion protocolVersion = proxyPlayer.getConnection().getProtocolVersion(); - ServerboundHandshakePacket handshake = new ServerboundHandshakePacket(); - handshake.setNextStatus(StateRegistry.LOGIN_ID); - handshake.setProtocolVersion(protocolVersion); - if (forwardingMode == PlayerInfoForwarding.LEGACY) { - handshake.setServerAddress(createLegacyForwardingAddress()); - } else if (forwardingMode == PlayerInfoForwarding.BUNGEEGUARD) { - byte[] secret = server.configuration().getForwardingSecret(); - handshake.setServerAddress(createBungeeGuardForwardingAddress(secret)); - } else if (proxyPlayer.getConnection().getType() == ConnectionTypes.LEGACY_FORGE) { - handshake.setServerAddress(getHandshakeRemoteAddress() + HANDSHAKE_HOSTNAME_TOKEN); - } else { - handshake.setServerAddress(getHandshakeRemoteAddress()); - } - + String address = getHandshakeAddressField(forwardingMode); SocketAddress destinationAddr = registeredServer.serverInfo().address(); - if (destinationAddr instanceof InetSocketAddress) { - handshake.setPort(((InetSocketAddress) destinationAddr).getPort()); - } + int port = destinationAddr instanceof InetSocketAddress + ? ((InetSocketAddress) destinationAddr).getPort() : 0; + ServerboundHandshakePacket handshake = new ServerboundHandshakePacket(protocolVersion, + address, port, StateRegistry.LOGIN_ID); mc.delayedWrite(handshake); mc.setProtocolVersion(protocolVersion); @@ -188,6 +176,19 @@ public class VelocityServerConnection implements MinecraftConnectionAssociation, mc.flush(); } + private String getHandshakeAddressField(PlayerInfoForwarding forwardingMode) { + if (forwardingMode == PlayerInfoForwarding.LEGACY) { + return createLegacyForwardingAddress(); + } else if (forwardingMode == PlayerInfoForwarding.BUNGEEGUARD) { + byte[] secret = server.configuration().getForwardingSecret(); + return createBungeeGuardForwardingAddress(secret); + } else if (proxyPlayer.getConnection().getType() == ConnectionTypes.LEGACY_FORGE) { + return playerConnectedHostname() + HANDSHAKE_HOSTNAME_TOKEN; + } else { + return playerConnectedHostname(); + } + } + public @Nullable MinecraftConnection getConnection() { return connection; } diff --git a/proxy/src/main/java/com/velocitypowered/proxy/connection/client/ConnectedPlayer.java b/proxy/src/main/java/com/velocitypowered/proxy/connection/client/ConnectedPlayer.java index d05f20954..9abe2e542 100644 --- a/proxy/src/main/java/com/velocitypowered/proxy/connection/client/ConnectedPlayer.java +++ b/proxy/src/main/java/com/velocitypowered/proxy/connection/client/ConnectedPlayer.java @@ -50,7 +50,6 @@ import com.velocitypowered.api.proxy.server.RegisteredServer; import com.velocitypowered.api.util.GameProfile; import com.velocitypowered.api.util.ModInfo; import com.velocitypowered.proxy.VelocityServer; -import com.velocitypowered.proxy.config.VelocityConfiguration; import com.velocitypowered.proxy.connection.MinecraftConnection; import com.velocitypowered.proxy.connection.MinecraftConnectionAssociation; import com.velocitypowered.proxy.connection.backend.VelocityServerConnection; @@ -238,7 +237,7 @@ public class ConnectedPlayer implements MinecraftConnectionAssociation, Player { } @Override - public Optional connectedHost() { + public Optional connectedHostname() { return Optional.ofNullable(virtualHost); } @@ -616,7 +615,7 @@ public class ConnectedPlayer implements MinecraftConnectionAssociation, Player { */ private Optional getNextServerToTry(@Nullable RegisteredServer current) { if (serversToTry == null) { - String virtualHostStr = connectedHost().map(InetSocketAddress::getHostString) + String virtualHostStr = connectedHostname().map(InetSocketAddress::getHostString) .orElse("") .toLowerCase(Locale.ROOT); serversToTry = server.configuration().getForcedHosts().getOrDefault(virtualHostStr, diff --git a/proxy/src/main/java/com/velocitypowered/proxy/connection/client/HandshakeSessionHandler.java b/proxy/src/main/java/com/velocitypowered/proxy/connection/client/HandshakeSessionHandler.java index 8d9fbf669..c1f6b9b2b 100644 --- a/proxy/src/main/java/com/velocitypowered/proxy/connection/client/HandshakeSessionHandler.java +++ b/proxy/src/main/java/com/velocitypowered/proxy/connection/client/HandshakeSessionHandler.java @@ -213,7 +213,7 @@ public class HandshakeSessionHandler implements MinecraftSessionHandler { } @Override - public Optional connectedHost() { + public Optional connectedHostname() { return Optional.ofNullable(ping.getVhost()); } diff --git a/proxy/src/main/java/com/velocitypowered/proxy/connection/client/InitialInboundConnection.java b/proxy/src/main/java/com/velocitypowered/proxy/connection/client/InitialInboundConnection.java index 49571ec9f..a2a383489 100644 --- a/proxy/src/main/java/com/velocitypowered/proxy/connection/client/InitialInboundConnection.java +++ b/proxy/src/main/java/com/velocitypowered/proxy/connection/client/InitialInboundConnection.java @@ -54,7 +54,7 @@ public final class InitialInboundConnection implements InboundConnection, } @Override - public Optional connectedHost() { + public Optional connectedHostname() { return Optional.of(InetSocketAddress.createUnresolved(cleanedAddress, handshake.getPort())); } diff --git a/proxy/src/main/java/com/velocitypowered/proxy/connection/client/LoginSessionHandler.java b/proxy/src/main/java/com/velocitypowered/proxy/connection/client/LoginSessionHandler.java index 4acde610d..085dec7ee 100644 --- a/proxy/src/main/java/com/velocitypowered/proxy/connection/client/LoginSessionHandler.java +++ b/proxy/src/main/java/com/velocitypowered/proxy/connection/client/LoginSessionHandler.java @@ -58,7 +58,6 @@ import java.security.GeneralSecurityException; import java.security.KeyPair; import java.security.MessageDigest; import java.util.Arrays; -import java.util.Locale; import java.util.Optional; import java.util.UUID; import java.util.concurrent.CompletableFuture; @@ -66,7 +65,6 @@ import java.util.concurrent.ExecutionException; import java.util.concurrent.ThreadLocalRandom; import net.kyori.adventure.text.Component; import net.kyori.adventure.text.format.NamedTextColor; -import net.kyori.adventure.translation.GlobalTranslator; import org.apache.logging.log4j.LogManager; import org.apache.logging.log4j.Logger; import org.asynchttpclient.ListenableFuture; @@ -240,7 +238,7 @@ public class LoginSessionHandler implements MinecraftSessionHandler { // Initiate a regular connection and move over to it. ConnectedPlayer player = new ConnectedPlayer(server, profileEvent.gameProfile(), - mcConnection, inbound.connectedHost().orElse(null), onlineMode); + mcConnection, inbound.connectedHostname().orElse(null), onlineMode); this.connectedPlayer = player; if (!server.canRegisterConnection(player)) { player.disconnect0(Component.translatable("velocity.error.already-connected-proxy", diff --git a/proxy/src/main/java/com/velocitypowered/proxy/connection/client/StatusSessionHandler.java b/proxy/src/main/java/com/velocitypowered/proxy/connection/client/StatusSessionHandler.java index 70fac7f61..36010d7a0 100644 --- a/proxy/src/main/java/com/velocitypowered/proxy/connection/client/StatusSessionHandler.java +++ b/proxy/src/main/java/com/velocitypowered/proxy/connection/client/StatusSessionHandler.java @@ -168,7 +168,7 @@ public class StatusSessionHandler implements MinecraftSessionHandler { if (passthrough == PingPassthroughMode.DISABLED) { return CompletableFuture.completedFuture(constructLocalPing(shownVersion)); } else { - String virtualHostStr = inbound.connectedHost().map(InetSocketAddress::getHostString) + String virtualHostStr = inbound.connectedHostname().map(InetSocketAddress::getHostString) .map(str -> str.toLowerCase(Locale.ROOT)) .orElse(""); List serversToTry = server.configuration().getForcedHosts().getOrDefault( diff --git a/proxy/src/main/java/com/velocitypowered/proxy/network/packet/serverbound/ServerboundHandshakePacket.java b/proxy/src/main/java/com/velocitypowered/proxy/network/packet/serverbound/ServerboundHandshakePacket.java index 3fc140266..17beb7a88 100644 --- a/proxy/src/main/java/com/velocitypowered/proxy/network/packet/serverbound/ServerboundHandshakePacket.java +++ b/proxy/src/main/java/com/velocitypowered/proxy/network/packet/serverbound/ServerboundHandshakePacket.java @@ -35,15 +35,17 @@ public class ServerboundHandshakePacket implements Packet { final int nextStatus = ProtocolUtils.readVarInt(buf); return new ServerboundHandshakePacket(protocolVersion, hostname, port, nextStatus); }; - public static final PacketWriter ENCODER = PacketWriter.deprecatedEncode(); + public static final PacketWriter ENCODER = (out, packet, version) -> { + ProtocolUtils.writeVarInt(out, packet.protocolVersion.protocol()); + ProtocolUtils.writeString(out, packet.serverAddress); + out.writeShort(packet.port); + ProtocolUtils.writeVarInt(out, packet.nextStatus); + }; - private ProtocolVersion protocolVersion; - private String serverAddress = ""; - private int port; - private int nextStatus; - - public ServerboundHandshakePacket() { - } + private final ProtocolVersion protocolVersion; + private final String serverAddress; + private final int port; + private final int nextStatus; public ServerboundHandshakePacket(final ProtocolVersion protocolVersion, final String hostname, final int port, final int nextStatus) { this.protocolVersion = protocolVersion; @@ -52,14 +54,6 @@ public class ServerboundHandshakePacket implements Packet { this.nextStatus = nextStatus; } - @Override - public void encode(ByteBuf buf, ProtocolVersion ignored) { - ProtocolUtils.writeVarInt(buf, this.protocolVersion.protocol()); - ProtocolUtils.writeString(buf, this.serverAddress); - buf.writeShort(this.port); - ProtocolUtils.writeVarInt(buf, this.nextStatus); - } - @Override public boolean handle(PacketHandler handler) { return handler.handle(this); @@ -69,38 +63,18 @@ public class ServerboundHandshakePacket implements Packet { return protocolVersion; } - @Deprecated - public void setProtocolVersion(ProtocolVersion protocolVersion) { - this.protocolVersion = protocolVersion; - } - public String getServerAddress() { return serverAddress; } - @Deprecated - public void setServerAddress(String serverAddress) { - this.serverAddress = serverAddress; - } - public int getPort() { return port; } - @Deprecated - public void setPort(int port) { - this.port = port; - } - public int getNextStatus() { return nextStatus; } - @Deprecated - public void setNextStatus(int nextStatus) { - this.nextStatus = nextStatus; - } - @Override public String toString() { return MoreObjects.toStringHelper(this) diff --git a/proxy/src/main/java/com/velocitypowered/proxy/server/PingSessionHandler.java b/proxy/src/main/java/com/velocitypowered/proxy/server/PingSessionHandler.java index c290fc587..63e2447d2 100644 --- a/proxy/src/main/java/com/velocitypowered/proxy/server/PingSessionHandler.java +++ b/proxy/src/main/java/com/velocitypowered/proxy/server/PingSessionHandler.java @@ -50,20 +50,25 @@ public class PingSessionHandler implements MinecraftSessionHandler { @Override public void activated() { - ServerboundHandshakePacket handshake = new ServerboundHandshakePacket(); - handshake.setNextStatus(StateRegistry.STATUS_ID); - SocketAddress address = server.serverInfo().address(); + String hostname; + int port; if (address instanceof InetSocketAddress) { InetSocketAddress socketAddr = (InetSocketAddress) address; - handshake.setServerAddress(socketAddr.getHostString()); - handshake.setPort(socketAddr.getPort()); + hostname = socketAddr.getHostString(); + port = socketAddr.getPort(); } else { // Just fake it - handshake.setServerAddress("127.0.0.1"); + hostname = "127.0.0.1"; + port = 25565; } - handshake.setProtocolVersion(version); - connection.delayedWrite(handshake); + + connection.delayedWrite(new ServerboundHandshakePacket( + version, + hostname, + port, + StateRegistry.STATUS_ID + )); connection.setState(StateRegistry.STATUS); connection.delayedWrite(ServerboundStatusRequestPacket.INSTANCE);