private void ConnectionMessageLogin(object sender, ProtocolMessageEventArgs <LoginMessage> e) { var connection = (ClientConnection)sender; // check client version if (e.Message.Version != ServerConnection.ProtocolVersion) { logger.Error("Protocol version mismatch Client: {0} Server: {1}", e.Message.Version, ServerConnection.ProtocolVersion); var error = new ErrorMessage { ErrorCode = ErrorCodes.VersionMismatch, Data = ServerConnection.ProtocolVersion, Message = string.Format("Wrong client version ({0}) expected {1}", e.Message.Version, ServerConnection.ProtocolVersion) }; connection.Send(error); connection.Disconnect(); return; } if (string.IsNullOrEmpty(e.Message.Login) || string.IsNullOrEmpty(e.Message.Password)) { logger.Error("Invalid login or password"); var error = new ErrorMessage { ErrorCode = ErrorCodes.LoginPasswordIncorrect, Message = "Invalid login or password" }; connection.Send(error); connection.Disconnect(); return; } // checking login and password LoginData loginData; var login = e.Message.Login.ToLower(); if (_server.UsersStorage.Login(login, e.Message.Password, out loginData)) { TimeSpan banTimeLeft; if (_server.UsersStorage.IsBanned(login, out banTimeLeft)) { var error = new ErrorMessage { ErrorCode = ErrorCodes.LoginPasswordIncorrect, Message = "You are banned. Time left: " + banTimeLeft }; connection.Send(error); logger.Error("User banned {0} ({1})", e.Message.Login, connection.Id); connection.Disconnect(); return; } var oldConnection = _server.ConnectionManager.Find(c => c.UserId == loginData.UserId); if (oldConnection != null) { logger.Info("Disconnecting previous instance"); oldConnection.Send(new ErrorMessage { ErrorCode = ErrorCodes.AnotherInstanceLogged, Message = "Another instance of you connected. You will be disconnected." }); oldConnection.Disconnect(); } connection.Authorized = true; connection.UserId = loginData.UserId; connection.UserRole = loginData.Role; connection.Login = login; connection.DisplayName = e.Message.DisplayName; ServerPlayerCharacterEntity playerEntity; #region Getting player entity if (loginData.State == null) { logger.Info("No state. Creating new entity and the state for " + e.Message.DisplayName); // create new message playerEntity = GetNewPlayerEntity(connection, DynamicIdHelper.GetNextUniqueId()); var state = new UserState { EntityId = playerEntity.DynamicEntity.DynamicId }; _server.UsersStorage.SetData(login, state.Save()); } else { var state = UserState.Load(loginData.State); // load new player entity playerEntity = new ServerPlayerCharacterEntity(connection, new PlayerCharacter(), _server); var bytes = _server.EntityStorage.LoadEntityBytes(state.EntityId); if (bytes == null) { logger.Warn("{0} entity is absent, creating new one... Id={1}", e.Message.DisplayName, state.EntityId); playerEntity = GetNewPlayerEntity(connection, state.EntityId); } else { using (var ms = new MemoryStream(bytes)) { playerEntity.DynamicEntity = Serializer.Deserialize <PlayerCharacter>(ms); } } } playerEntity.PlayerCharacter.IsReadOnly = loginData.Role == UserRole.Guest; playerEntity.PlayerCharacter.CanFly = loginData.Role == UserRole.Administrator; //Check playerEntity.DynamicEntity Initialisation var player = playerEntity.DynamicEntity as PlayerCharacter; if (player != null) { if (player.Health.MaxValue == 0 || player.Health.EntityOwnerId == 0) { player.Health.MaxValue = 100; player.Health.CurrentValue = 100; player.HealthState = DynamicEntityHealthState.Normal; player.DisplacementMode = EntityDisplacementModes.Walking; logger.Info("PlayerCharacter was missing Health initialization + health state. EntityId : {0}", player.DynamicId); } if (player.Stamina.MaxValue == 0 || player.Stamina.EntityOwnerId == 0) { player.Stamina.MaxValue = 100; player.Stamina.CurrentValue = 100; logger.Info("PlayerCharacter was missing Stamina initialization. EntityId : {0}", player.DynamicId); } if (player.Oxygen.MaxValue == 0 || player.Oxygen.EntityOwnerId == 0) { player.Oxygen.MaxValue = 100; player.Oxygen.CurrentValue = 100; logger.Info("PlayerCharacter was missing Oxygen initialization. EntityId : {0}", player.DynamicId); } } #endregion _server.EntityFactory.PrepareEntity(playerEntity.DynamicEntity); connection.ServerEntity = playerEntity; connection.Send(new LoginResultMessage { Logged = true }); logger.Info("{1} {0} logged as {3} EntityId = {2} ", e.Message.Login, connection.Id, connection.ServerEntity.DynamicEntity.DynamicId, e.Message.DisplayName); var gameInfo = new GameInformationMessage { ChunkSize = AbstractChunk.ChunkSize, MaxViewRange = 32, WorldParameter = _server.LandscapeManager.WorldGenerator.WorldParameters, GlobalState = _server.GlobalStateManager.GlobalState, AreaSize = MapArea.AreaSize }; connection.Send(gameInfo); connection.Send(new EntityInMessage { Entity = playerEntity.DynamicEntity, Link = playerEntity.DynamicEntity.GetLink() }); connection.Send(new DateTimeMessage { DateTime = _server.Clock.Now, TimeFactor = _server.Clock.TimeFactor }); OnPlayerAuthorized(new ConnectionEventArgs { Connection = connection }); } else { var error = new ErrorMessage { ErrorCode = ErrorCodes.LoginPasswordIncorrect, Message = "Wrong login/password combination" }; logger.Error("Incorrect login information {0} ({1})", e.Message.Login, connection.Id); connection.Send(error, new LoginResultMessage { Logged = false }); connection.Disconnect(); } }