From 089832c2fe5d6f84290508d14c480af3f5ce7d73 Mon Sep 17 00:00:00 2001 From: Daan Vanden Bosch Date: Sat, 31 Jul 2021 22:16:01 +0200 Subject: [PATCH] Simplified proxy server code. --- .../phantasmal/psoserv/messages/BbMessages.kt | 16 +++--- .../phantasmal/psoserv/messages/Messages.kt | 22 ++++++-- .../phantasmal/psoserv/messages/PcMessages.kt | 16 +++--- .../phantasmal/psoserv/servers/ProxyServer.kt | 50 ++----------------- 4 files changed, 39 insertions(+), 65 deletions(-) diff --git a/psoserv/src/main/kotlin/world/phantasmal/psoserv/messages/BbMessages.kt b/psoserv/src/main/kotlin/world/phantasmal/psoserv/messages/BbMessages.kt index 30b546e8..b54f5b76 100644 --- a/psoserv/src/main/kotlin/world/phantasmal/psoserv/messages/BbMessages.kt +++ b/psoserv/src/main/kotlin/world/phantasmal/psoserv/messages/BbMessages.kt @@ -62,13 +62,15 @@ class GuildCard( val entries: List ) -sealed class BbMessage(override val buffer: Buffer) : Message(BB_HEADER_SIZE) { +sealed class BbMessage(override val buffer: Buffer) : AbstractMessage(BB_HEADER_SIZE) { override val code: Int get() = buffer.getUShort(BB_MSG_CODE_POS).toInt() override val size: Int get() = buffer.getUShort(BB_MSG_SIZE_POS).toInt() - class InitEncryption(buffer: Buffer) : BbMessage(buffer) { - val serverKey: ByteArray get() = byteArray(INIT_MSG_SIZE, size = KEY_SIZE) - val clientKey: ByteArray get() = byteArray(INIT_MSG_SIZE + KEY_SIZE, size = KEY_SIZE) + class InitEncryption(buffer: Buffer) : BbMessage(buffer), InitEncryptionMessage { + override val serverKey: ByteArray + get() = byteArray(INIT_MSG_SIZE, size = KEY_SIZE) + override val clientKey: ByteArray + get() = byteArray(INIT_MSG_SIZE + KEY_SIZE, size = KEY_SIZE) constructor(message: String, serverKey: ByteArray, clientKey: ByteArray) : this( buf(0x0003, INIT_MSG_SIZE + 2 * KEY_SIZE) { @@ -87,14 +89,14 @@ sealed class BbMessage(override val buffer: Buffer) : Message(BB_HEADER_SIZE) { constructor() : this(buf(0x0005)) } - class Redirect(buffer: Buffer) : BbMessage(buffer) { - var ipAddress: ByteArray + class Redirect(buffer: Buffer) : BbMessage(buffer), RedirectMessage { + override var ipAddress: ByteArray get() = byteArray(0, size = 4) set(value) { require(value.size == 4) setByteArray(0, value) } - var port: Int + override var port: Int get() = uShort(4).toInt() set(value) { require(value in 0..65535) diff --git a/psoserv/src/main/kotlin/world/phantasmal/psoserv/messages/Messages.kt b/psoserv/src/main/kotlin/world/phantasmal/psoserv/messages/Messages.kt index 7a558dff..534a2456 100644 --- a/psoserv/src/main/kotlin/world/phantasmal/psoserv/messages/Messages.kt +++ b/psoserv/src/main/kotlin/world/phantasmal/psoserv/messages/Messages.kt @@ -24,12 +24,25 @@ fun messageString( data class Header(val code: Int, val size: Int) -abstract class Message(val headerSize: Int) { - abstract val buffer: Buffer - abstract val code: Int - abstract val size: Int +interface Message { + val buffer: Buffer + val code: Int + val size: Int + val headerSize: Int val bodySize: Int get() = size - headerSize +} +interface InitEncryptionMessage : Message { + val serverKey: ByteArray + val clientKey: ByteArray +} + +interface RedirectMessage : Message { + var ipAddress: ByteArray + var port: Int +} + +abstract class AbstractMessage(override val headerSize: Int) : Message { override fun toString(): String = messageString() protected fun uByte(offset: Int) = buffer.getUByte(headerSize + offset) @@ -58,5 +71,4 @@ abstract class Message(val headerSize: Int) { protected fun messageString(vararg props: Pair): String = messageString(code, size, this::class.simpleName, *props) - } diff --git a/psoserv/src/main/kotlin/world/phantasmal/psoserv/messages/PcMessages.kt b/psoserv/src/main/kotlin/world/phantasmal/psoserv/messages/PcMessages.kt index 6b143ab0..23c660e6 100644 --- a/psoserv/src/main/kotlin/world/phantasmal/psoserv/messages/PcMessages.kt +++ b/psoserv/src/main/kotlin/world/phantasmal/psoserv/messages/PcMessages.kt @@ -13,13 +13,15 @@ const val PC_HEADER_SIZE: Int = 4 const val PC_MSG_SIZE_POS: Int = 0 const val PC_MSG_CODE_POS: Int = 2 -sealed class PcMessage(override val buffer: Buffer) : Message(PC_HEADER_SIZE) { +sealed class PcMessage(override val buffer: Buffer) : AbstractMessage(PC_HEADER_SIZE) { override val code: Int get() = buffer.getUByte(PC_MSG_CODE_POS).toInt() override val size: Int get() = buffer.getUShort(PC_MSG_SIZE_POS).toInt() - class InitEncryption(buffer: Buffer) : PcMessage(buffer) { - val serverKey: ByteArray get() = byteArray(INIT_MSG_SIZE, size = KEY_SIZE) - val clientKey: ByteArray get() = byteArray(INIT_MSG_SIZE + KEY_SIZE, size = KEY_SIZE) + class InitEncryption(buffer: Buffer) : PcMessage(buffer), InitEncryptionMessage { + override val serverKey: ByteArray + get() = byteArray(INIT_MSG_SIZE, size = KEY_SIZE) + override val clientKey: ByteArray + get() = byteArray(INIT_MSG_SIZE + KEY_SIZE, size = KEY_SIZE) constructor(message: String, serverKey: ByteArray, clientKey: ByteArray) : this( buf(0x02, INIT_MSG_SIZE + 2 * KEY_SIZE) { @@ -60,14 +62,14 @@ sealed class PcMessage(override val buffer: Buffer) : Message(PC_HEADER_SIZE) { ) } - class Redirect(buffer: Buffer) : PcMessage(buffer) { - var ipAddress: ByteArray + class Redirect(buffer: Buffer) : PcMessage(buffer), RedirectMessage { + override var ipAddress: ByteArray get() = byteArray(0, size = 4) set(value) { require(value.size == 4) setByteArray(0, value) } - var port: Int + override var port: Int get() { buffer.endianness = Endianness.Big val p = uShort(4).toInt() diff --git a/psoserv/src/main/kotlin/world/phantasmal/psoserv/servers/ProxyServer.kt b/psoserv/src/main/kotlin/world/phantasmal/psoserv/servers/ProxyServer.kt index 4ff56df9..9442a7a0 100644 --- a/psoserv/src/main/kotlin/world/phantasmal/psoserv/servers/ProxyServer.kt +++ b/psoserv/src/main/kotlin/world/phantasmal/psoserv/servers/ProxyServer.kt @@ -4,10 +4,7 @@ import mu.KotlinLogging import world.phantasmal.core.disposable.TrackedDisposable import world.phantasmal.psolib.buffer.Buffer import world.phantasmal.psoserv.encryption.Cipher -import world.phantasmal.psoserv.messages.BbMessage -import world.phantasmal.psoserv.messages.Header -import world.phantasmal.psoserv.messages.Message -import world.phantasmal.psoserv.messages.PcMessage +import world.phantasmal.psoserv.messages.* import java.net.* class ProxyServer( @@ -119,7 +116,7 @@ class ProxyServer( override fun processMessage(message: Message): ProcessResult { when (message) { - is PcMessage.InitEncryption -> if (decryptCipher == null) { + is InitEncryptionMessage -> if (decryptCipher == null) { decryptCipher = createCipher(message.serverKey) encryptCipher = createCipher(message.serverKey) @@ -135,7 +132,7 @@ class ProxyServer( clientSocket, this, clientDecryptCipher, - clientEncryptCipher + clientEncryptCipher, ) this.clientHandler = clientListener val thread = Thread(clientListener::listen) @@ -143,46 +140,7 @@ class ProxyServer( thread.start() } - is BbMessage.InitEncryption -> if (decryptCipher == null) { - decryptCipher = createCipher(message.serverKey) - encryptCipher = createCipher(message.serverKey) - - val clientDecryptCipher = createCipher(message.clientKey) - val clientEncryptCipher = createCipher(message.clientKey) - - logger.info { - "Encryption initialized, start listening to client." - } - - // Start listening to client on another thread. - val clientListener = ClientHandler( - clientSocket, - this, - clientDecryptCipher, - clientEncryptCipher - ) - this.clientHandler = clientListener - val thread = Thread(clientListener::listen) - thread.name = "${ProxyServer::class.simpleName} client" - thread.start() - } - - is PcMessage.Redirect -> { - val oldAddress = InetAddress.getByAddress(message.ipAddress) - - redirectMap[Pair(oldAddress, message.port)]?.let { (newAddress, newPort) -> - logger.debug { - "Rewriting redirect from $oldAddress:${message.port} to $newAddress:$newPort." - } - - message.ipAddress = newAddress.address - message.port = newPort - - return ProcessResult.Changed - } - } - - is BbMessage.Redirect -> { + is RedirectMessage -> { val oldAddress = InetAddress.getByAddress(message.ipAddress) redirectMap[Pair(oldAddress, message.port)]?.let { (newAddress, newPort) ->