internal static PlayerInfoRecord Read(BinaryReader r)
            {
                var record = new PlayerInfoRecord();

                record.maxSequences = r.ReadByte();
                r.Skip(1);
                record.channelMask = r.ReadUInt16();
                record.heapSize    = r.ReadUInt32();
                return(record);
            }
        private void parseInfo(Stream stream)
        {
            using (var r = new BinaryReader(stream)) {
                var sig = r.Read4C();
                if (sig != "INFO")
                {
                    throw new InvalidDataException("INFO signature is wrong");
                }
                var internalSize = r.ReadUInt32();
                if (internalSize != stream.Length)
                {
                    throw new InvalidDataException("INFO block size is wrong!");
                }

                const int subsectionCount     = 8;
                var       subSectionPositions = r.ReadUInt32Array(subsectionCount);

                List <UInt32> ReadInfoRecordPtrTable(int subsectionIndex)
                {
                    stream.Position = subSectionPositions[subsectionIndex];
                    var recordCount = r.ReadUInt32();

                    return(r.ReadUInt32Array((int)recordCount));
                }

                using (var subReader = new BinaryReader(new SubStream(stream, 0))) {
                    List <uint> recordPositions = ReadInfoRecordPtrTable(0);
                    sequenceInfo = new List <SequenceInfoRecord>(recordPositions.Count);
                    foreach (var position in recordPositions)
                    {
                        if (position == 0)
                        {
                            sequenceInfo.Add(null);
                            continue;
                        }
                        subReader.BaseStream.Position = position;
                        var record = SequenceInfoRecord.Read(subReader);
                        sequenceInfo.Add(record);
                    }
                }

                using (var subReader = new BinaryReader(new SubStream(stream, 0))) {
                    List <uint> recordPositions = ReadInfoRecordPtrTable(2);
                    bankInfo = new List <BankInfoRecord>(recordPositions.Count);
                    foreach (var position in recordPositions)
                    {
                        if (position == 0)
                        {
                            bankInfo.Add(null);
                            continue;
                        }
                        subReader.BaseStream.Position = position;
                        var record = BankInfoRecord.Read(subReader);
                        bankInfo.Add(record);
                    }
                }

                using (var subReader = new BinaryReader(new SubStream(stream, 0))) {
                    List <uint> recordPositions = ReadInfoRecordPtrTable(3);
                    waveArchiveInfo = new List <WaveArchiveInfoRecord>(recordPositions.Count);
                    foreach (var position in recordPositions)
                    {
                        if (position == 0)
                        {
                            waveArchiveInfo.Add(null);
                            continue;
                        }
                        subReader.BaseStream.Position = position;
                        WaveArchiveInfoRecord record = WaveArchiveInfoRecord.Read(subReader);
                        waveArchiveInfo.Add(record);
                    }
                }

                using (var subReader = new BinaryReader(new SubStream(stream, 0))) {
                    List <uint> recordPositions = ReadInfoRecordPtrTable(4);
                    playerInfo = new List <PlayerInfoRecord>(recordPositions.Count);
                    foreach (var position in recordPositions)
                    {
                        if (position == 0)
                        {
                            playerInfo.Add(null);
                            continue;
                        }
                        subReader.BaseStream.Position = position;
                        PlayerInfoRecord record = PlayerInfoRecord.Read(subReader);
                        playerInfo.Add(record);
                    }
                }

                using (var subReader = new BinaryReader(new SubStream(stream, 0))) {
                    List <uint> recordPositions = ReadInfoRecordPtrTable(5);
                    groupInfo = new List <GroupInfoRecord>(recordPositions.Count);
                    foreach (var position in recordPositions)
                    {
                        if (position == 0)
                        {
                            groupInfo.Add(null);
                            continue;
                        }
                        subReader.BaseStream.Position = position;
                        GroupInfoRecord record = GroupInfoRecord.Read(subReader);
                        groupInfo.Add(record);
                    }
                }

                using (var subReader = new BinaryReader(new SubStream(stream, 0))) {
                    List <uint> recordPositions = ReadInfoRecordPtrTable(7);
                    streamInfo = new List <StreamInfoRecord>(recordPositions.Count);
                    foreach (var position in recordPositions)
                    {
                        if (position == 0)
                        {
                            streamInfo.Add(null);
                            continue;
                        }
                        subReader.BaseStream.Position = position;
                        StreamInfoRecord record = StreamInfoRecord.Read(subReader);
                        streamInfo.Add(record);
                    }
                }
            }
        }
        /// <summary>
        /// Main Telegram Sync Task
        /// <para>Current playerlist is requested from the server and added to the database</para>
        /// </summary>
        /// <returns></returns>
        static async Task Run()
        {
            ServerHelper serverHelper = new ServerHelper();

            Config.LogSync("CSGO Telegram Sync Online...");

            while (true)
            {
                try
                {
                    Config.LogSync("*** START playerlist cache refresh run ***");
                    DateTime StartTime = DateTime.Now;

                    List <PlayerInfo> playerList = serverHelper.GetPlayersForced(ForceRetries);

                    if (playerList.Count > 0)
                    {
                        using (var mc = new CSGODataContext())
                        {
                            List <PlayerInfoRecord> currentPlayerRecords = mc.PlayerInfos.ToList();
                            mc.PlayerInfos.RemoveRange(currentPlayerRecords);
                            mc.SaveChanges();

                            foreach (PlayerInfo currentPlayer in playerList)
                            {
                                if (currentPlayer.Name.Length > 0)
                                {
                                    PlayerInfoRecord tempPlayerRecord = new PlayerInfoRecord {
                                        Name = currentPlayer.Name, Date = DateTime.Now, Time = currentPlayer.Time
                                    };
                                    mc.PlayerInfos.Add(tempPlayerRecord);
                                }
                            }

                            mc.SaveChanges();

                            Config.LogSync($"{playerList.Count} players added to database");
                            Config.LogSync("*** END playerlist cache refresh run ***");
                        }
                    }

                    DateTime EndTime = DateTime.Now;

                    TimeSpan span        = EndTime - StartTime;
                    int      timeRunning = (int)span.TotalMilliseconds;

                    int newDelay = 0;
                    if (timeRunning > RefreshDelay)
                    {
                        newDelay = 1000;
                    }
                    else
                    {
                        newDelay = RefreshDelay - timeRunning;
                    }

                    Config.LogSync($"*** SLEEP {newDelay} milliseconds ***");
                    await Task.Delay(newDelay);
                }
                catch (Exception ex)
                {
                    Config.LogSync("FATAL ERROR!");
                    Config.LogSync($"Error Message: {ex.Message}");
                    Restart();
                }
            }
        }