package org.hso.texturesyncclient.controller.net

import java.io.IOException
import java.net.DatagramPacket
import java.net.DatagramSocket
import java.net.InetAddress

class AutoConnect private constructor() {

    companion object {
        @Throws(IOException::class)
        fun searchServer(
            mulicastAddr: String = "ff02::dd42:c0fe",
            port: Int = 10796,
            timeoutMs: Int = 400,
            trys: Int = 10
        ): Connection? {
            val sock = DatagramSocket()
            try {
                sock.soTimeout = timeoutMs

                for (i in 0..trys) {
                    val bytes = "TextureSync".toByteArray()

                    sock.send(
                        DatagramPacket(
                            bytes,
                            0,
                            bytes.size,
                            InetAddress.getByName(mulicastAddr),
                            port
                        )
                    )

                    // Response is PortNum in BE
                    val portData = ByteArray(2)
                    val response = DatagramPacket(portData, portData.size)

                    try {
                        sock.receive(response)

                        // 2-Byte BE to Port Number
                        val serverPort = (portData[0].toInt().shl(8)).or(portData[1].toInt())

                        return Connection(response.address, serverPort)
                    } catch (e: IOException) {
                        // Timed out
                        // NOP
                    }
                }
            } catch (e: Exception) {
                throw e
            } finally {
                sock.close()
            }

            return null
        }
    }
}