public async Task WaitForData()
        {
            var mainPageViewModel = MainPageViewModel.GetInstance();

            using (var dr = new DataReader(ServerProxy.TcpSocket.InputStream))
            {
                while (mainPageViewModel.ConnectionStatus)
                {
                    var stringHeader = await dr.LoadAsync(4);

                    if (stringHeader == 0)
                    {
                        mainPageViewModel.ConnectionStatus = false;
                        return;
                    }

                    int messageLength = dr.ReadInt32();
                    uint numBytes = await dr.LoadAsync((uint)messageLength);

                    var packetBaseBuffer = new byte[numBytes];

                    dr.ReadBytes(packetBaseBuffer);

                    var packetBase = new PacketBase();

                    using (var stream = new MemoryStream(packetBaseBuffer))
                    {
                        try
                        {
                            var reader = new BinaryReader(stream);

                            packetBase.Read(reader);
                        }
                        catch (Exception e)
                        {
#if DEBUG
                            throw;
#endif
                        }
                    }


                    var incomingMessage = IncomingMessageFactory.GetMessage(
                        packetBase.Data as PacketV1);

                    incomingMessage.HandleMessage();
                }
            }
        }
        public void Initialize()
        {
            _testGameMoveDataPoint = new GameMoveDataPoint { MoveType = MoveType.Dump, Player = "NewPlayer", TimeOfMove = 5 };

            _playerGameStats = new PlayerGameStats
                {
                    AvgTimeBetweenDumps = 10,
                    AvgTimeBetweenPeels = 5,
                    IsWinner = true,
                    NumberOfDumps = 3,
                    NumberOfPeels = 0,
                    PerformedFirstPeel = false,
                    RawGameData = new List<GameMoveDataPoint>() {_testGameMoveDataPoint, _testGameMoveDataPoint, _testGameMoveDataPoint}
                };

            _gameData = new GameData {GameDuration = 10, GameHost = "GameHost", GameStartTime = DateTime.Now, Winner = "NewPlayer"};
            _gameData.GameMoves.Add(_testGameMoveDataPoint);
            _gameData.GameMoves.Add(_testGameMoveDataPoint);
            _gameData.PlayerDictionary.Add("NewPlayer", _playerGameStats);
            _gameData.PlayerDictionary.Add("NewPlayer2", _playerGameStats);

            _gameDataList = new GameDataList();
            _gameDataList._GameData.Add(_gameData);
            _gameDataList._GameData.Add(_gameData);

            _stringPacketV1 = new PacketV1
                {
                    PacketType = PacketType.c_QueryIfAliasAvailable,
                    Data = "Mobius",
                    Recipients = null,
                    Sender = "*****@*****.**"
                };

            _IBinarySerializablePacketV1 = new PacketV1
            {
                PacketType = PacketType.c_UploadGameData,
                Data = _gameData,
                Recipients = null,
                Sender = "*****@*****.**"
            };

            _packetBase = new PacketBase
                {
                    PacketVersion = PacketVersion.Version1,
                    Data = _stringPacketV1
                };
        }
        public static void SendMessage(Client recipient, PacketType packetType, object data)
        {
            if (recipient == null)
            {
                return;
            }

            #if DEBUG
            //
            // If we're debugging, make sure that the data type matches that required by the packetType, or else throw an exception.
            //

            var type = DataPacket.PacketTypeMap[packetType];

            if (type != null)
            {
                var testObject = Convert.ChangeType(data, type);
            }
            else
            {
                if (data != null)
                {
                    throw new ArgumentException("Data from this packet type was expected to be null, but wasn't.");
                }
            }
            #endif

            // ToDo: Don't hardcode Packet Version 1 here.  Instead, add a packet version property to Client, and switch on that.
            var packetBase = new PacketBase {PacketVersion = PacketVersion.Version1};

            var packetV1 = new PacketV1
            {
                PacketType = packetType,
                Data = data,
                Sender = ServerName
            };

            packetV1.Recipients.Add(recipient.UserInfo.EmailAddress);

            packetBase.Data = packetV1;

            dynamic baseBuffer;

            using (var stream = new MemoryStream())
            {
                var binaryWriter = new BinaryWriter(stream);

                packetBase.Write(binaryWriter);

                baseBuffer = stream.ToArray();
            }

            var messageSize = baseBuffer.Length;

            byte[] bytes = BitConverter.GetBytes(messageSize);

            if (BitConverter.IsLittleEndian)
            {
                Array.Reverse(bytes);
            }

            var offset = 0;

            var messageBuffer = new byte[sizeof(uint) + messageSize];

            bytes.CopyTo(messageBuffer, offset);

            offset += sizeof(uint);

            baseBuffer.CopyTo(messageBuffer, offset);

            recipient.Send(messageBuffer);
        }
        private async Task SendMessage(PacketType packetType, IEnumerable<Friend> recipientList, object data)
        {
            var mainPageViewModel = MainPageViewModel.GetInstance();

            if ((ServerProxy.TcpSocket == null) || mainPageViewModel.ConnectionStatus == false)
            {
                return;
            }

#if DEBUG
            //
            // If we're debugging, make sure that the data type matches that required by the packetType, or else throw an exception.
            //

            var type = DataPacket.PacketTypeMap[packetType];

            if (type != null)
            {
                var testObject = Convert.ChangeType(data, type);
            }
            else
            {
                if (data != null)
                {
                    throw new ArgumentException("Data from this packet type was expected to be null, but wasn't.");
                }
            }
#endif

            using (var dataWriter = new DataWriter(ServerProxy.TcpSocket.OutputStream))
            {
                byte[] msgSizeBuffer;
                dynamic baseBuffer = null;

                if (PacketType.c_HeartBeat == packetType)
                {
                    // Message Size is specified by the size of an int.
                    msgSizeBuffer = new byte[] {0, 0, 0, 0};
                }
                else
                {
                    var packetBase = new PacketBase {PacketVersion = PacketVersion.Version1};

                    var packetV1 = new PacketV1
                        {
                            PacketType = packetType,
                            Data = data,
                            Sender = Settings.EmailAddress
                        };

                    foreach (var b in recipientList)
                    {
                        packetV1.Recipients.Add(b.EmailAddress);
                    }

                    packetBase.Data = packetV1;

                    using (var stream = new MemoryStream())
                    {
                        var binaryWriter = new BinaryWriter(stream);

                        packetBase.Write(binaryWriter);

                        baseBuffer = stream.ToArray();
                    }


                    var messageSize = baseBuffer.Length;

                    msgSizeBuffer = BitConverter.GetBytes(messageSize);

                    if (!BitConverter.IsLittleEndian)
                    {
                        Array.Reverse(msgSizeBuffer);
                    }
                }


                //
                // 1. Write the message size
                // 2. Write the object buffer (unless it's a heartbeat)
                //

                dataWriter.WriteBytes(msgSizeBuffer);

                if (baseBuffer != null)
                {
                    dataWriter.WriteBytes(baseBuffer);
                }

                await dataWriter.StoreAsync();

                dataWriter.DetachStream();
            }
        }
        public static PacketHandler GetPacketHandler(PacketBase packetBase)
        {
            PacketHandler packetHandler = null;

            var packet = packetBase.Data as PacketV1;

            if (null == packet)
            {
                return null;
            }

            switch (packet.PacketType)
            {
                case PacketType.c_LogIn:
                case PacketType.c_LogOut:
                case PacketType.c_JoinRoom:
                case PacketType.c_LeaveRoom:
                case PacketType.c_InitiateGame:
                case PacketType.c_Chat:
                case PacketType.c_ReadyForGameStart:
                    packetHandler = new RoomPacketHandler(
                            packet.PacketType,
                            packet.Sender,
                            packet.Recipients,
                            packet.Data);
                    break;

                case PacketType.c_Dump:
                case PacketType.c_Peel:
                case PacketType.c_Victory:
                    packetHandler = new GamePacketHandler(
                            packet.PacketType,
                            packet.Sender,
                            packet.Recipients,
                            packet.Data);
                    break;

                case PacketType.c_AcceptFriendRequest:
                case PacketType.c_RejectFriendRequest:
                case PacketType.c_SendFriendRequest:
                case PacketType.c_RemoveFriend:
                case PacketType.c_FindBuddyFromGlobalList:
                case PacketType.c_QueryIfAliasAvailable:
                case PacketType.c_UploadGameData:
                    packetHandler = new DataBasePacketHandler(
                            packet.PacketType,
                            packet.Sender,
                            packet.Recipients,
                            packet.Data);
                    break;

                case PacketType.c_StartingMatchmaking:
                case PacketType.c_StoppingMatchmaking:
                    packetHandler = new MatchmakingPacketHandler(
                            packet.PacketType,
                            packet.Sender,
                            packet.Recipients,
                            packet.Data);
                    break;

                default:
                    Trace.WriteLine(string.Format("[PacketHandlerFactory] - " +
                            "Invalid packet type from client PacketType = {0}",
                            packet.PacketType.ToString()));
                    break;
            }

            return packetHandler;
        }
        public void HandleMessage(ref Client client, byte[] msgBytes)
        {
            var packetBase = new PacketBase();

            using (var stream = new MemoryStream(msgBytes))
            {
                try
                {
                    var reader = new BinaryReader(stream);

                    packetBase.Read(reader);
                }
                catch (Exception e)
                {
            #if DEBUG
                    throw;
            #else
                    Trace.WriteLine(string.Format("[IncomingMessageHandler.HandleMessage] - " +
                            "Invalid packet from client! Deserialization failed: {0}, Trace: {1}",
                            e.Message,
                            e.StackTrace));
            #endif
                }
            }

            var handler = PacketHandlerFactory.GetPacketHandler(packetBase);

            if (handler != null)
            {
                handler.DoActions(ref client);
            }
        }