/// <summary> /// Client wanted to transfer to a city server. /// </summary> public static void HandleCityTokenRequest(NetworkClient Client, ProcessedPacket P) { string AccountName = P.ReadString(); string CityGUID = P.ReadString(); string CharGUID = P.ReadString(); if (AccountName == string.Empty || CityGUID == string.Empty || CharGUID == string.Empty) { return; } Guid Token = Guid.NewGuid(); CityInfo CServer = NetworkFacade.CServerListener.GetCityServer(CityGUID); using (var db = DataAccess.Get()) { Account Acc = db.Accounts.GetByUsername(AccountName); PacketStream CServerPacket = new PacketStream(0x01, 0); CServerPacket.WriteHeader(); ushort PacketLength = (ushort)(PacketHeaders.UNENCRYPTED + 1 + 4 + (Client.RemoteIP.Length + 1) + 4 + (CharGUID.ToString().Length + 1) + (Token.ToString().Length + 1)); CServerPacket.WriteUInt16(PacketLength); CServerPacket.WriteByte(0); //CharacterCreate = false. CServerPacket.WriteInt32(Acc.AccountID); CServerPacket.WriteString(Client.RemoteIP); CServerPacket.WriteInt32(Client.RemotePort); CServerPacket.WriteString(CharGUID.ToString()); CServerPacket.WriteString(Token.ToString("")); CServer.Client.Send(CServerPacket.ToArray()); } }
public override void RemoveClient(NetworkClient Client) { CityInfo Info = CityServers.FirstOrDefault(x => x.Client == Client); if (CityServers.TryTake(out Info)) { lock (NetworkFacade.ClientListener.Clients) { PacketStream ClientPacket = new PacketStream((byte)PacketType.CITY_SERVER_OFFLINE, 0); ClientPacket.WriteString(Info.Name); ClientPacket.WriteString(Info.Description); ClientPacket.WriteString(Info.IP); ClientPacket.WriteInt32(Info.Port); ClientPacket.WriteByte((byte)Info.Status); ClientPacket.WriteUInt64(Info.Thumbnail); ClientPacket.WriteString(Info.UUID); ClientPacket.WriteUInt64(Info.Map); foreach (NetworkClient Receiver in NetworkFacade.ClientListener.Clients) { Receiver.SendEncrypted((byte)PacketType.CITY_SERVER_OFFLINE, ClientPacket.ToArray()); } } Debug.WriteLine("Removed CityServer!"); } }
/// <summary> /// A cityserver logged in! /// </summary> public static void HandleCityServerLogin(NetworkClient Client, ProcessedPacket P) { Logger.LogInfo("CityServer logged in!\r\n"); string Name = P.ReadString(); string Description = P.ReadString(); string IP = P.ReadString(); int Port = P.ReadInt32(); CityInfoStatus Status = (CityInfoStatus)P.ReadByte(); ulong Thumbnail = P.ReadUInt64(); string UUID = P.ReadString(); ulong Map = P.ReadUInt64(); CityInfo Info = new CityInfo(true); Info.Name = Name; Info.Description = Description; Info.IP = IP; Info.Port = Port; Info.Status = Status; Info.Thumbnail = Thumbnail; Info.UUID = UUID; Info.Map = Map; Info.Client = Client; Info.Online = true; NetworkFacade.CServerListener.CityServers.Add(Info); NetworkFacade.CServerListener.PotentialLogins.TryTake(out Client); NetworkClient[] Clients = new NetworkClient[NetworkFacade.ClientListener.Clients.Count]; NetworkFacade.ClientListener.Clients.CopyTo(Clients, 0); PacketStream ClientPacket = new PacketStream((byte)PacketType.NEW_CITY_SERVER, 0); ClientPacket.WriteString(Name); ClientPacket.WriteString(Description); ClientPacket.WriteString(IP); ClientPacket.WriteInt32(Port); ClientPacket.WriteByte((byte)Status); ClientPacket.WriteUInt64(Thumbnail); ClientPacket.WriteString(UUID); ClientPacket.WriteUInt64(Map); foreach (NetworkClient Receiver in Clients) { Receiver.SendEncrypted((byte)PacketType.NEW_CITY_SERVER, ClientPacket.ToArray()); } }
/// <summary> /// Client requested information about a city. /// </summary> public static void HandleCityInfoRequest(NetworkClient Client, ProcessedPacket P) { //This packet only contains a dummy byte, don't bother reading it. PacketStream Packet = new PacketStream((byte)PacketType.CITY_LIST, 0); Packet.WriteByte((byte)NetworkFacade.CServerListener.CityServers.Count); if (NetworkFacade.CServerListener.CityServers.Count > 0) { lock (NetworkFacade.CServerListener.CityServers) { foreach (CityInfo CInfo in NetworkFacade.CServerListener.CityServers) { Packet.WriteString(CInfo.Name); Packet.WriteString(CInfo.Description); Packet.WriteString(CInfo.IP); Packet.WriteInt32(CInfo.Port); //Hack (?) to ensure status is written correctly. switch (CInfo.Status) { case CityInfoStatus.Ok: Packet.WriteByte(1); break; case CityInfoStatus.Busy: Packet.WriteByte(2); break; case CityInfoStatus.Full: Packet.WriteByte(3); break; case CityInfoStatus.Reserved: Packet.WriteByte(4); break; } Packet.WriteUInt64(CInfo.Thumbnail); Packet.WriteString(CInfo.UUID); Packet.WriteUInt64(CInfo.Map); } } } Client.SendEncrypted((byte)PacketType.CITY_LIST, Packet.ToArray()); }
/// <summary> /// Client wanted to retire a character. /// </summary> public static void HandleCharacterRetirement(NetworkClient Client, ProcessedPacket P) { PacketStream Packet; string AccountName = P.ReadString(); string GUID = P.ReadString(); if (AccountName == string.Empty || GUID == string.Empty) { return; } using (var db = DataAccess.Get()) { Account Acc = db.Accounts.GetByUsername(AccountName); IQueryable <Character> Query = db.Characters.GetForAccount(Acc.AccountID); //F**K, I hate LINQ. Guid CharGUID = new Guid(GUID); Character Char = Query.Where(x => x.GUID == CharGUID).SingleOrDefault(); if (Char != null) { db.Characters.RetireCharacter(Char); } else { return; } //This actually updates the record, not sure how. Acc.NumCharacters--; if (Char != null) { CityInfo CInfo = NetworkFacade.CServerListener.GetCityServer(Char.City); //Just in case... if (CInfo != null) { Packet = new PacketStream(0x02, 0); Packet.WriteHeader(); ushort PacketLength = (ushort)(PacketHeaders.UNENCRYPTED + 4 + GUID.Length + 1); Packet.WriteUInt16(PacketLength); Packet.WriteInt32(Acc.AccountID); Packet.WriteString(GUID); CInfo.Client.Send(Packet.ToArray()); } } } Packet = new PacketStream((byte)PacketType.RETIRE_CHARACTER_STATUS, 0); Packet.WriteString(GUID); Client.SendEncrypted((byte)PacketType.RETIRE_CHARACTER_STATUS, Packet.ToArray()); }
public static void HandlePlayerOnlineResponse(NetworkClient Client, ProcessedPacket P) { byte Result = (byte)P.ReadByte(); string Token = P.ReadString(); //NOTE: Might have to find another way to identify a client, since two people // can be on the same account from the same IP. string RemoteIP = P.ReadString(); int RemotePort = P.ReadInt32(); PacketStream Packet; NetworkClient FoundClient; switch (Result) { case 0x01: Packet = new PacketStream((byte)PacketType.REQUEST_CITY_TOKEN, 0); Packet.WriteString(Token); FoundClient = NetworkFacade.ClientListener.GetClient(RemoteIP, RemotePort); if (FoundClient != null) { FoundClient.SendEncrypted((byte)PacketType.REQUEST_CITY_TOKEN, Packet.ToArray()); } break; case 0x02: //Write player was already online packet! Packet = new PacketStream((byte)PacketType.PLAYER_ALREADY_ONLINE, 0); Packet.WriteByte(0x00); //Dummy FoundClient = NetworkFacade.ClientListener.GetClient(RemoteIP, RemotePort); if (FoundClient != null) { FoundClient.SendEncrypted((byte)PacketType.PLAYER_ALREADY_ONLINE, Packet.ToArray()); } break; } }
/// <summary> /// Client created a character! /// </summary> public static void HandleCharacterCreate(NetworkClient Client, ProcessedPacket P) { Logger.LogInfo("Received CharacterCreate!"); string AccountName = SanitizeAccount(P.ReadString()); //Need to be variable length, because the success packet contains a token. PacketStream CCStatusPacket = new PacketStream((byte)PacketType.CHARACTER_CREATION_STATUS, 0); using (var db = DataAccess.Get()) { Account Acc = db.Accounts.GetByUsername(AccountName); if (Acc.NumCharacters >= 3) { CCStatusPacket.WriteByte((int)LoginDataModel.Entities.CharacterCreationStatus.ExceededCharacterLimit); Client.SendEncrypted(CCStatusPacket.PacketID, CCStatusPacket.ToArray()); return; } //TODO: Send GUID to client... var Char = new Character(); string LastCached = P.ReadString(); if (LastCached == string.Empty) { //TODO: Proper error... CCStatusPacket.WriteByte((int)LoginDataModel.Entities.CharacterCreationStatus.NameAlreadyExisted); Client.SendEncrypted(CCStatusPacket.PacketID, CCStatusPacket.ToArray()); return; } Char.LastCached = ProtoHelpers.ParseDateTime(LastCached); Char.Name = P.ReadString(); Char.Sex = P.ReadString(); Char.Description = P.ReadString(); Char.GUID = Guid.NewGuid(); Char.HeadOutfitID = (long)P.ReadUInt64(); Char.BodyOutfitID = (long)P.ReadUInt64(); Char.AccountID = Acc.AccountID; Char.AppearanceType = P.ReadByte(); Char.CityName = P.ReadString(); Char.CityThumb = (long)P.ReadUInt64(); Char.City = P.ReadString(); Char.CityMap = (long)P.ReadUInt64(); Char.CityIp = P.ReadString(); Char.CityPort = P.ReadInt32(); Char.Money = NetworkFacade.INITIAL_MONEY; //These are going into DB, so be nazi. Sieg heil! if (Char.Name == string.Empty || Char.Sex == string.Empty || Char.Description == string.Empty) { CCStatusPacket.WriteByte((int)LoginDataModel.Entities.CharacterCreationStatus.NameAlreadyExisted); Client.SendEncrypted(CCStatusPacket.PacketID, CCStatusPacket.ToArray()); return; } var status = db.Characters.CreateCharacter(Char); switch (status) { case LoginDataModel.Entities.CharacterCreationStatus.NameAlreadyExisted: CCStatusPacket.WriteByte((int)LoginDataModel.Entities.CharacterCreationStatus.NameAlreadyExisted); Client.SendEncrypted(CCStatusPacket.PacketID, CCStatusPacket.ToArray()); break; case LoginDataModel.Entities.CharacterCreationStatus.NameTooLong: CCStatusPacket.WriteByte((int)LoginDataModel.Entities.CharacterCreationStatus.NameTooLong); Client.SendEncrypted(CCStatusPacket.PacketID, CCStatusPacket.ToArray()); break; case LoginDataModel.Entities.CharacterCreationStatus.Success: Guid Token = Guid.NewGuid(); //This actually updates the record, not sure how. Acc.NumCharacters++; //THIS NEEDS TO HAPPEN FIRST FOR CITY SERVER AUTHENTICATION TO WORK! CityInfo CServer = NetworkFacade.CServerListener.GetCityServer(Char.City); //Just in case... if (CServer != null) { PacketStream CServerPacket = new PacketStream(0x01, 0); CServerPacket.WriteHeader(); ushort PacketLength = (ushort)(PacketHeaders.UNENCRYPTED + 1 + 4 + (Client.RemoteIP.Length + 1) + 4 + (Char.GUID.ToString().Length + 1) + (Token.ToString().Length + 1)); CServerPacket.WriteUInt16(PacketLength); CServerPacket.WriteByte(1); //CharacterCreate = true CServerPacket.WriteInt32(Acc.AccountID); CServerPacket.WriteString(Client.RemoteIP); CServerPacket.WriteInt32(Client.RemotePort); CServerPacket.WriteString(Char.GUID.ToString()); CServerPacket.WriteString(Token.ToString("")); CServer.Client.Send(CServerPacket.ToArray()); } CCStatusPacket.WriteByte((int)LoginDataModel.Entities.CharacterCreationStatus.Success); CCStatusPacket.WriteString(Char.GUID.ToString()); CCStatusPacket.WriteString(Token.ToString()); Client.SendEncrypted(CCStatusPacket.PacketID, CCStatusPacket.ToArray()); break; } } }