Example #1
0
        public override void Start(object config)
        {
            UnetConfig unetConfig = null;

            if (config is UnetConfig)
            {
                unetConfig = (UnetConfig)config;
            }
            else if (config is JObject)
            {
                unetConfig = ((JObject)config).ToObject <UnetConfig>();
            }

            Program.DEFAULT_CHANNEL_BYTE = unetConfig.ConnectionConfig.AddChannel(QosType.ReliableSequenced);

            unetManager = new NetLibraryManager(unetConfig.GlobalConfig);

            hostId = unetManager.AddHost(new HostTopology(unetConfig.ConnectionConfig, unetConfig.MaxConnections), Program.Config.ListenPort, null);
        }
Example #2
0
        static void Start(RelayConfig rConfig)
        {
            RelayConfig.CurrentConfig = rConfig;
            Console.WriteLine("================================");
            Console.WriteLine("[INFO] Starting relay...");
            unet = new NetLibraryManager(rConfig.globalConfig);

            messageBuffer = new byte[RelayConfig.CurrentConfig.bufferSize];
            HostTopology hostTopology = new HostTopology(RelayConfig.CurrentConfig.connectionConfig, RelayConfig.CurrentConfig.maxConnections);

            unet.AddHost(hostTopology, RelayConfig.CurrentConfig.relayPort, null);
            Console.WriteLine("[INFO] Relay started!");
            Console.WriteLine("[INFO] Press [Q] to quit the application");
            while ((!Console.KeyAvailable || Console.ReadKey(true).Key != ConsoleKey.Q))
            {
                NetworkEventType @event = unet.Receive(out int hostId, out int connectionId, out int channelId, messageBuffer, RelayConfig.CurrentConfig.bufferSize, out int receivedSize, out byte errorByte);
                NetworkError     error  = (NetworkError)errorByte;

                if (error != NetworkError.Ok)
                {
                    ConsoleColor previousColor = Console.ForegroundColor;
                    Console.ForegroundColor = ConsoleColor.Red;
                    Console.WriteLine("[ERROR] Relay encountered UNET transport error \"" + error.ToString() + "\" during a \"" + @event.ToString() + "\" event.");
                    Console.ForegroundColor = previousColor;
                }

                switch (@event)
                {
                case NetworkEventType.DataEvent:
                {
                    MessageType mType = (MessageType)messageBuffer[receivedSize - 1];
                    switch (mType)
                    {
                    case MessageType.StartServer:
                    {
                        //Check if they are already connected or perhaps are already hosting, if so return
                        Client client;
                        Room   room = new Room(client = new Client()
                                {
                                    connectionId = (ushort)connectionId,
                                    hostId       = (byte)hostId,
                                    isServer     = true,
                                    connectTick  = DateTime.UtcNow.Ticks
                                });
                        rooms.Add(room);
                        unet.GetConnectionInfo(hostId, connectionId, out string address, out int port, out byte byteError);
                        if (RelayConfig.CurrentConfig.enableRuntimeMetaLogging)
                        {
                            Console.WriteLine("[INFO] Server started from address " + address);
                        }
                        addressToRoom.Add(address + ":" + port, room);
                    }
                    break;

                    case MessageType.ConnectToServer:
                    {
                        //Check if they are already connected or perhaps are already hosting; if so, return
                        byte   addressLength  = (byte)(receivedSize - 1);             //messageBuffer[1]; // address length + ip type
                        string addressAndPort = Encoding.ASCII.GetString(messageBuffer, 0, addressLength);
                        addressAndPort = addressAndPort.AsIPv6CompatString();
                        if (RelayConfig.CurrentConfig.enableRuntimeMetaLogging)
                        {
                            Console.WriteLine("[INFO] Connection requested to address " + addressAndPort);
                        }
                        if (addressToRoom.ContainsKey(addressAndPort))
                        {
                            if (RelayConfig.CurrentConfig.enableRuntimeMetaLogging)
                            {
                                Console.WriteLine("[INFO] Connection approved");
                            }
                            Room   room   = addressToRoom[addressAndPort];
                            Client client = new Client()
                            {
                                connectionId = (ushort)connectionId,
                                hostId       = (byte)hostId,
                                isServer     = false,
                                connectTick  = DateTime.UtcNow.Ticks
                            };
                            room.HandleClientConnect(client);
                        }
                    }
                    break;

                    case MessageType.Data:
                    {
                        foreach (var room in rooms)
                        {
                            if (room.HasPeer((ushort)connectionId, out bool isServer))
                            {
                                // Found a matching client in room
                                if (isServer)
                                {
                                    ushort destination = (ushort)(messageBuffer[receivedSize - 3] | (messageBuffer[receivedSize - 2] << 8));
                                    //Safety check. Make sure who they want to send to ACTUALLY belongs to their room
                                    if (room.HasPeer(destination, out isServer) && !isServer)
                                    {
                                        // TODO: Use unsafe to make messageBuffer look smaller
                                        //ReverseOffset(messageBuffer, 2, receivedSize);
                                        messageBuffer[receivedSize - 3] = (byte)MessageType.Data;                          // [data, data, data, dest1, dest2, mtype_r, none, none, none] => [{data, data, data, mtype_s}, dest2, mtype_r, none, none, none]
                                        room.Send(hostId, destination, connectionId, channelId, messageBuffer, receivedSize - 2, out errorByte);
                                    }
                                }
                                else
                                {
                                    // Read client message
                                    //ForwardOffset(messageBuffer, 2, receivedSize);
                                    messageBuffer.ToBytes((ushort)connectionId, receivedSize - 1);            // Put connection id at the end of the recieved message (because optimization)
                                    messageBuffer[receivedSize + 1] = (byte)MessageType.Data;                 // Set message type
                                    room.Send(hostId, room.ServerID, connectionId, channelId, messageBuffer, receivedSize + 2, out errorByte);
                                }
                            }
                        }
                    }
                    break;

                    case MessageType.ClientDisconnect:
                    {
                        ushort cid = messageBuffer.FromBytes(1);
                        if (RelayConfig.CurrentConfig.enableRuntimeMetaLogging)
                        {
                            Console.WriteLine("[INFO] Client disconnect request");
                        }
                        foreach (Room room in rooms)
                        {
                            if (room.HandleClientDisconnect((ushort)cid, true))
                            {
                                --connectedPeers;
                                break;
                            }
                        }
                    }
                    break;
                    }
                }
                break;

                case NetworkEventType.DisconnectEvent:
                {
                    if (RelayConfig.CurrentConfig.enableRuntimeMetaLogging)
                    {
                        Console.WriteLine("[INFO] Peer disconnected");
                    }
                    foreach (Room room in rooms)
                    {
                        if (room.HandleClientDisconnect((ushort)connectionId))
                        {
                            --connectedPeers;
                            break;
                        }
                    }
                }
                break;

                case NetworkEventType.Nothing:
                    Thread.Sleep(1);
                    break;

                case NetworkEventType.ConnectEvent:
                {
                    connectedPeers++;
                }
                break;
                }
                if (lastConnectedClients != connectedPeers && (DateTime.UtcNow.Ticks - lastPrintedConnectedClientsTick) > 30 * TimeSpan.TicksPerSecond)
                {
                    lastPrintedConnectedClientsTick = DateTime.UtcNow.Ticks;
                    lastConnectedClients            = connectedPeers;
                    PrintStatusUpdate();
                }
            }
            Console.WriteLine("[INFO] Relay shutting down...");
        }