/// <summary>
        /// Assert that the test client is logged in, has a PlayerCharacter and is a registered observer
        /// </summary>
        /// <param name="testClient"></param>
        /// <param name="client"></param>
        /// <returns></returns>
        public bool ValidClientState(TestClient testClient, out Client client)
        {
            if (testClient.net == null || !testClient.IsConnectedAndLoggedIn())
            {
                client = null;
                return(false);
            }
            // If do not have a PlayerCharacter, are dead etc, expect to fail
            Globals_Server.Clients.TryGetValue(testClient.playerID, out client);
            if (client == null)
            {
                Assert.AreEqual(testClient.net.GetConnectionStatusString(), "Disconnected");
                return(false);
            }

            if (client.myPlayerCharacter == null || !client.myPlayerCharacter.isAlive)
            {
                Task <string> ReplyTask = testClient.GetServerMessage();
                ReplyTask.Wait();
                string reply = ReplyTask.Result;
                Assert.AreEqual(reply, "You have no valid PlayerCharacter!");
                return(false);
            }
            if (!Globals_Game.IsObserver(client))
            {
                return(false);
            }
            return(true);
        }
示例#2
0
 public void LogInTwiceAsDifferentUsers()
 {
     // Tell the client it isn't logged in
     client.net.loggedIn = false;
     // Try to log in as anothr user
     client.LogInAndConnect(OtherUser, OtherPass, new byte[] { 1, 2, 3, 4, 5, 6, 7 });
     while (!client.IsConnectedAndLoggedIn())
     {
         Thread.Sleep(0);
     }
     Assert.IsFalse(Globals_Game.IsObserver(OtherUser));
 }
        /// <summary>Test stub for LogIn(String, String, Byte[])</summary>

        public void LogInTest(
            TestClient client,
            string user,
            string pass,
            byte[] key
            )
        {
            client.LogInAndConnect(user, pass, key);
            // If username not recognised, expect to be disconnected
            if (string.IsNullOrEmpty(user) || !Utility_Methods.CheckStringValid("combined", user) || !LogInManager.users.ContainsKey(user))
            {
                Assert.AreEqual("Disconnected", client.net.GetConnectionStatusString());
                return;
            }
            // If password is incorrect, expect an error
            Tuple <byte[], byte[]> hashNsalt = LogInManager.users[user];

            byte[] hash;
            if (pass == null)
            {
                hash = null;
            }
            else
            {
                hash = LogInManager.ComputeHash(System.Text.Encoding.UTF8.GetBytes(pass), hashNsalt.Item2);
            }
            if (hash == null || !hashNsalt.Item1.SequenceEqual(hash) || key == null || key.Length < 5)
            {
                Assert.AreEqual("Disconnected", client.net.GetConnectionStatusString());
                Assert.IsFalse(Server.ContainsConnection(user));
            }
            else
            {
                // If the login was successful, expecting a ProtoLogin followed by a ProtoClient back
                Task <ProtoMessage> getReply = client.GetReply();
                getReply.Wait();
                ProtoMessage reply = getReply.Result;
                Assert.AreEqual(reply.GetType(), typeof(ProtoLogIn));
                while (!client.IsConnectedAndLoggedIn())
                {
                    Thread.Sleep(0);
                }
                // If login was successful, the client should be in the list of registered observers
                Assert.IsTrue(Globals_Game.IsObserver(Globals_Server.Clients[user]));
                Assert.IsTrue(Server.ContainsConnection(user));
            }
        }
示例#4
0
        public void Listen()
        {
            while (server.Status == NetPeerStatus.Running && !ctSource.Token.IsCancellationRequested)
            {
                NetIncomingMessage im;
                WaitHandle.WaitAny(new WaitHandle[] { server.MessageReceivedEvent, ctSource.Token.WaitHandle });
                while ((im = server.ReadMessage()) != null && !ctSource.Token.IsCancellationRequested)
                {
                    switch (im.MessageType)
                    {
                    case NetIncomingMessageType.DebugMessage:
                    case NetIncomingMessageType.ErrorMessage:
                    case NetIncomingMessageType.WarningMessage:
                        Globals_Server.logError("Recieved warning message: " + im.ReadString());
                        break;

                    case NetIncomingMessageType.VerboseDebugMessage:
                    case NetIncomingMessageType.Data:
                    {
#if DEBUG
                        Console.WriteLine("SERVER: recieved data message");
#endif
                        if (!clientConnections.ContainsKey(im.SenderConnection))
                        {
                            //error
                            im.SenderConnection.Disconnect("Not recognised");
                            return;
                        }
                        Client c = clientConnections[im.SenderConnection];
                        if (c.alg != null)
                        {
                            im.Decrypt(c.alg);
                        }
                        ProtoMessage m = null;
                        //global::ProtoMessage.ProtoMessage y = null;
                        using (MemoryStream ms = new MemoryStream(im.Data))
                        {
                            try
                            {
                                //y = Serializer.DeserializeWithLengthPrefix<global::ProtoMessage.ProtoMessage>(ms,
                                //PrefixStyle.Fixed32);
                                m = Serializer.DeserializeWithLengthPrefix <ProtoMessage>(ms, PrefixStyle.Fixed32);
                            }
                            catch (Exception e)
                            {
                                NetOutgoingMessage errorMessage = server.CreateMessage(
                                    "Failed to deserialise message. The message may be incorrect, or the decryption may have failed.");
                                if (c.alg != null)
                                {
                                    errorMessage.Encrypt(c.alg);
                                }
                                server.SendMessage(errorMessage, im.SenderConnection,
                                                   NetDeliveryMethod.ReliableOrdered);
                                Globals_Server.logError("Failed to deserialize message for client: " + c.username);
                            }
                        }
                        if (m == null /*&& y == null*/)
                        {
                            string error = "Recieved null message from " + im.SenderEndPoint.ToString();
                            if (clientConnections.ContainsKey(im.SenderConnection))
                            {
                                error += ", recognised client " + clientConnections[im.SenderConnection];
                            }
                            else
                            {
                                error += ", unrecognised client (possible ping)";
                            }
                            error += ". Data: " + im.ReadString();
                            Globals_Server.logError(error);
                            break;
                        }

                        if (m.ActionType == Actions.LogIn)
                        {
                            ProtoLogIn login = m as ProtoLogIn;
                            if (login == null)
                            {
                                im.SenderConnection.Disconnect("Not login");
                                return;
                            }
                            lock (ServerLock)
                            {
                                if (LogInManager.VerifyUser(c.username, login.userSalt))
                                {
                                    if (LogInManager.ProcessLogIn(login, c))
                                    {
                                        string log = c.username + " logs in from " + im.SenderEndPoint.ToString();
                                        Globals_Server.logEvent(log);
                                    }
                                }
                                else
                                {
                                    ProtoMessage reply = new ProtoMessage
                                    {
                                        ActionType   = Actions.LogIn,
                                        ResponseType = DisplayMessages.LogInFail
                                    };
                                    im.SenderConnection.Disconnect("Authentication Fail");
                                }
                            }
                        }
                        // temp for testing, should validate connection first
                        else if (clientConnections.ContainsKey(im.SenderConnection))
                        {
                            if (Globals_Game.IsObserver(c))
                            {
                                ProcessMessage(m, im.SenderConnection);
                                ProtoClient clientDetails = new ProtoClient(c);
                                clientDetails.ActionType = Actions.Update;
                                SendViaProto(clientDetails, im.SenderConnection, c.alg);
                            }
                            else
                            {
                                im.SenderConnection.Disconnect("Not logged in- Disconnecting");
                            }
                        }

                        /*//IF Y ACTION
                         *  if (y.ActionType == global::ProtoMessage.Actions.LogIn)
                         *  {
                         *      global::ProtoMessage.Client forCheck = new global::ProtoMessage.Client(c.username, c.myPlayerCharacter.playerID);
                         *      global::ProtoMessage.ProtoLogIn login = y as global::ProtoMessage.ProtoLogIn;
                         *      if (login == null)
                         *      {
                         *          im.SenderConnection.Disconnect("Not login");
                         *          return;
                         *      }
                         *      lock (ServerLock)
                         *      {
                         *          if (LogInManager.VerifyUser(c.username, login.userSalt))
                         *          {
                         *              if (LogInManager.ProcessLogIn(login, forCheck, true))
                         *              {
                         *                  string log = c.username + " logs in from " + im.SenderEndPoint.ToString();
                         *                  Globals_Server.logEvent(log);
                         *              }
                         *          }
                         *          else
                         *          {
                         *              ProtoMessage reply = new ProtoMessage
                         *              {
                         *                  ActionType = Actions.LogIn,
                         *                  ResponseType = DisplayMessages.LogInFail
                         *              };
                         *              im.SenderConnection.Disconnect("Authentication Fail");
                         *          }
                         *      }
                         *  }
                         *  // temp for testing, should validate connection first
                         *  else if (clientConnections.ContainsKey(im.SenderConnection))
                         *  {
                         *      if (Globals_Game.IsObserver(c))
                         *      {
                         *          ProcessMessage(y, im.SenderConnection);
                         *          ProtoClient clientDetails = new ProtoClient(c);
                         *          clientDetails.ActionType = Actions.Update;
                         *          SendViaProto(clientDetails, im.SenderConnection, c.alg);
                         *      }
                         *      else
                         *      {
                         *          im.SenderConnection.Disconnect("Not logged in- Disconnecting");
                         *      }
                         *  }*/
                    }
                    break;

                    case NetIncomingMessageType.StatusChanged:
                        byte stat = im.ReadByte();
                        NetConnectionStatus status = NetConnectionStatus.None;
                        if (Enum.IsDefined(typeof(NetConnectionStatus), Convert.ToInt32(stat)))
                        {
                            status = (NetConnectionStatus)stat;
                        }
                        else
                        {
                            Globals_Server.logError("Failure to parse byte " + stat + " to NetConnectionStatus for endpoint " + im.ReadIPEndPoint());
                        }
                        if (status == NetConnectionStatus.Disconnected)
                        {
                            if (clientConnections.ContainsKey(im.SenderConnection))
                            {
                                Disconnect(im.SenderConnection);
                            }
                        }
                        break;

                    case NetIncomingMessageType.ConnectionApproval:
                    {
                        string senderID = im.ReadString();
                        string text     = im.ReadString();
                        Client client;
                        Globals_Server.Clients.TryGetValue(senderID, out client);
                        if (client != null)
                        {
                            ProtoLogIn logIn;
                            if (!LogInManager.AcceptConnection(client, text, out logIn))
                            {
                                im.SenderConnection.Deny();
                            }
                            else
                            {
                                NetOutgoingMessage msg = server.CreateMessage();
                                MemoryStream       ms  = new MemoryStream();
                                // Include X509 certificate as bytes for client to validate
                                Serializer.SerializeWithLengthPrefix <ProtoLogIn>(ms, logIn, PrefixStyle.Fixed32);
                                msg.Write(ms.GetBuffer());
                                clientConnections.Add(im.SenderConnection, client);
                                client.conn = im.SenderConnection;
                                im.SenderConnection.Approve(msg);
                                server.FlushSendQueue();
                                Globals_Server.logEvent("Accepted connection from " + client.username);
                            }
                        }
                        else
                        {
                            im.SenderConnection.Deny("unrecognised");
                        }
                    }

                    break;

                    case NetIncomingMessageType.ConnectionLatencyUpdated:
                        break;

                    default:
                        Globals_Server.logError("Received unrecognised incoming message type: " + im.MessageType);
                        break;
                    }
                    server.Recycle(im);
                }
            }
#if DEBUG
            Globals_Server.logEvent("Server listening thread exits");
#endif
        }
示例#5
0
        public void Listen()
        {
            while (server.Status == NetPeerStatus.Running && !ctSource.Token.IsCancellationRequested)
            {
                NetIncomingMessage im;
                WaitHandle.WaitAny(new WaitHandle[] { server.MessageReceivedEvent, ctSource.Token.WaitHandle });
                while ((im = server.ReadMessage()) != null && !ctSource.Token.IsCancellationRequested)
                {
                    if (im.SenderConnection != null)
                    {
                        Globals_Server.logEvent("Recieved: " + im.MessageType.ToString() + " | " + im.SenderConnection.RemoteEndPoint.ToString());
                    }
                    else
                    {
                        Globals_Server.logEvent("Recieved: " + im.MessageType.ToString() + " | NULL");
                    }

                    switch (im.MessageType)
                    {
                    case NetIncomingMessageType.DebugMessage:
                    case NetIncomingMessageType.ErrorMessage:
                    case NetIncomingMessageType.WarningMessage:
                        Globals_Server.logError("Recieved warning message: " + im.ReadString());
                        break;

                    case NetIncomingMessageType.VerboseDebugMessage:
                    case NetIncomingMessageType.Data:
                    {
#if DEBUG
                        //Console.WriteLine("SERVER: recieved data message");
#endif
                        if (!clientConnections.ContainsKey(im.SenderConnection))
                        {
                            //error
                            im.SenderConnection.Disconnect("Not recognised");
                            return;
                        }
                        Client c = clientConnections[im.SenderConnection];
                        if (c.alg != null)
                        {
                            im.Decrypt(c.alg);
                        }
                        ProtoMessage m = null;
                        using (MemoryStream ms = new MemoryStream(im.Data))
                        {
                            try
                            {
                                m = Serializer.DeserializeWithLengthPrefix <ProtoMessage>(ms, PrefixStyle.Fixed32);
                            }
                            catch (Exception e)
                            {
                                NetOutgoingMessage errorMessage = server.CreateMessage(
                                    "Failed to deserialise message. The message may be incorrect, or the decryption may have failed.");
                                if (c.alg != null)
                                {
                                    errorMessage.Encrypt(c.alg);
                                }
                                server.SendMessage(errorMessage, im.SenderConnection,
                                                   NetDeliveryMethod.ReliableOrdered);
                                Globals_Server.logError("Failed to deserialize message for client: " + c.username);
                            }
                        }
                        if (m == null)
                        {
                            string error = "Recieved null message from " + im.SenderEndPoint.ToString();
                            if (clientConnections.ContainsKey(im.SenderConnection))
                            {
                                error += ", recognised client " + clientConnections[im.SenderConnection];
                            }
                            else
                            {
                                error += ", unrecognised client (possible ping)";
                            }
                            error += ". Data: " + im.ReadString();
                            Globals_Server.logError(error);
                            break;
                        }

                        if (m.ActionType == Actions.LogIn)
                        {
                            ProtoLogIn login = m as ProtoLogIn;
                            if (login == null)
                            {
                                im.SenderConnection.Disconnect("Received blank login message.");
                                return;
                            }
                            lock (ServerLock)
                            {
                                if (LogInManager.VerifyUser(c.username, login.userSalt))
                                {
                                    if (LogInManager.ProcessLogIn(login, c))
                                    {
                                        string log = c.username + " logs in from " + im.SenderEndPoint.ToString();
                                        Globals_Server.logEvent(log);
                                    }
                                }
                                else
                                {
                                    ProtoMessage reply = new ProtoMessage
                                    {
                                        ActionType   = Actions.LogIn,
                                        ResponseType = DisplayMessages.LogInFail
                                    };
                                    Server.SendViaProto(reply, c.conn, c.alg);
                                    //reply = new ProtoMessage {
                                    //    ActionType = Actions.Update,
                                    //    ResponseType = DisplayMessages.Error
                                    //};
                                    //Server.SendViaProto(reply, c.conn, c.alg);
                                    im.SenderConnection.Disconnect("Authentication Fail");
                                    Globals_Server.logEvent("Wrong Password, disconnecting user.");
                                }
                            }
                        }
                        // temp for testing, should validate connection first
                        else if (clientConnections.ContainsKey(im.SenderConnection))
                        {
                            if (Globals_Game.IsObserver(c))
                            {
                                ProcessMessage(m, im.SenderConnection);
                                ProtoClient clientDetails = new ProtoClient(c);
                                clientDetails.ActionType   = Actions.Update;
                                clientDetails.ResponseType = DisplayMessages.Success;
                                SendViaProto(clientDetails, im.SenderConnection, c.alg);
                            }
                            else
                            {
                                im.SenderConnection.Disconnect("Not logged in- Disconnecting");
                            }
                        }
                    }
                    break;

                    case NetIncomingMessageType.StatusChanged:
                        byte stat = im.ReadByte();
                        NetConnectionStatus status = NetConnectionStatus.None;
                        if (Enum.IsDefined(typeof(NetConnectionStatus), Convert.ToInt32(stat)))
                        {
                            status = (NetConnectionStatus)stat;
                        }
                        else
                        {
                            Globals_Server.logError("Failure to parse byte " + stat + " to NetConnectionStatus for endpoint " + im.ReadIPEndPoint());
                        }
                        Globals_Server.logEvent("\tStatus is now: " + status);
                        if (status == NetConnectionStatus.Disconnected)
                        {
                            string reason = im.ReadString();
                            if (reason == null)
                            {
                                reason = "Unknown";
                            }
                            Globals_Server.logEvent(im.SenderConnection.RemoteEndPoint.ToString() + " has disconnected. Reason: " + reason);
                            if (clientConnections.ContainsKey(im.SenderConnection))
                            {
                                Disconnect(im.SenderConnection);
                            }
                        }
                        break;

                    case NetIncomingMessageType.ConnectionApproval:
                    {
                        string senderID = im.ReadString();
                        string text     = im.ReadString();
                        Client client;
                        Globals_Server.Clients.TryGetValue(senderID, out client);
                        if (client != null)
                        {
                            ProtoLogIn logIn;
                            //ProtoMessage logIn;
                            if (!LogInManager.AcceptConnection(client, text, out logIn))
                            {
                                im.SenderConnection.Deny("User not recognised.");
                            }
                            else
                            {
                                ProtoMessage temp = logIn;

                                NetOutgoingMessage msg = server.CreateMessage();
                                MemoryStream       ms  = new MemoryStream();
                                // Include X509 certificate as bytes for client to validate
                                //Serializer.SerializeWithLengthPrefix<ProtoLogIn>(ms, logIn, PrefixStyle.Fixed32);
                                Serializer.SerializeWithLengthPrefix <ProtoMessage>(ms, temp, PrefixStyle.Fixed32);
                                msg.Write(ms.GetBuffer());

                                clientConnections.Add(im.SenderConnection, client);
                                client.conn = im.SenderConnection;
                                im.SenderConnection.Approve(msg);
                                //server.FlushSendQueue();
                                Globals_Server.logEvent("Accepted connection from " + client.username + " | " + senderID + " | " + text);
                            }
                        }
                        else
                        {
                            im.SenderConnection.Deny("Username unrecognised.");
                        }
                        server.FlushSendQueue();
                    }

                    break;

                    case NetIncomingMessageType.ConnectionLatencyUpdated:
                        Globals_Server.logEvent("LATENCY: Still getting these.");
                        break;

                    default:
                        Globals_Server.logError("Received unrecognised incoming message type: " + im.MessageType);
                        break;
                    }
                    server.Recycle(im);
                }
            }
            Globals_Server.logEvent("Server listening thread exits.");
        }