Ejemplo n.º 1
0
        async Task PunishGrid(MyCubeGrid grid)
        {
            var blocks = grid.GetFatBlocks();

            for (var i = 0; i < blocks.Count; i++)
            {
                // move to the next frame so we won't lag the server
                if (i % ProcessedBlockCountPerFrame == 0)
                {
                    await VRageUtils.MoveToGameLoop();
                }

                var block = blocks[i];
                if (block == null)
                {
                    continue;
                }

                switch (_config.PunishType)
                {
                case PunishType.Shutdown:
                {
                    DisableFunctionalBlock(block);
                    break;
                }

                case PunishType.Damage:
                {
                    DamageBlock(block);
                    break;
                }
                }
            }
        }
Ejemplo n.º 2
0
        async Task BroadcastLaggyGrids(CancellationToken cancellationToken)
        {
            if (_config.PunishType != PunishType.Broadcast)
            {
                _entityGpsBroadcaster.ClearGpss();
                return;
            }

            var allGpsSources = new Dictionary <long, GridGpsSource>();

            foreach (var(player, rank) in _players.Entities.GetLaggiestEntities(true).Indexed())
            {
                var playerId = player.Id;
                if (!_grids.TryGetLaggiestGridOwnedBy(playerId, out var laggiestGrid))
                {
                    continue;
                }

                var gpsSource = new GridGpsSource(laggiestGrid.Id, player.LagNormal, player.PinRemainingTime, rank);
                allGpsSources[gpsSource.GridId] = gpsSource;
            }

            foreach (var(grid, rank) in _grids.Entities.GetLaggiestEntities(true).Indexed())
            {
                var gpsSource = new GridGpsSource(grid.Id, grid.LagNormal, grid.PinRemainingTime, rank);
                allGpsSources[gpsSource.GridId] = gpsSource;
            }

            await VRageUtils.MoveToGameLoop(cancellationToken);

            _entityGpsBroadcaster.ReplaceGpss(allGpsSources.Values);
            await VRageUtils.MoveToThreadPool(cancellationToken);

            Log.Trace("broadcast done");
        }
Ejemplo n.º 3
0
        public async Task Main(CancellationToken canceller)
        {
            Log.Info("started main");

            await VRageUtils.MoveToGameLoop(canceller);

            _entityGpsBroadcaster.ClearGpss();
            await VRageUtils.MoveToThreadPool(canceller);

            _questTracker.Clear();

            // Wait for some time during the session startup
            await TaskUtils.Delay(() => _config.FirstIdleTime.Seconds(), 1.Seconds(), canceller);

            IsIdle = false;

            Log.Info("started collector loop");

            // MAIN LOOP
            while (!canceller.IsCancellationRequested)
            {
                if (!_config.IsEnabled)
                {
                    _grids.Clear();
                    _players.Clear();
                    _questTracker.Clear();
                    _punishExecutor.Clear();
                    _punishChatFeed.Clear();

                    await VRageUtils.MoveToGameLoop(canceller);

                    _entityGpsBroadcaster.ClearGpss();

                    await Task.Delay(1.Seconds(), canceller);

                    return;
                }

                using var _ = CustomProfiling.Profile("AutoModerator.Main");

                await Profile(canceller);

                FixExemptBlockTypeCollection();
                Warn();
                AnnouncePunishments();
                await Punish(canceller);
                await AnnounceDeletedGrids(canceller);

                Log.Debug("interval done");
            }
        }
Ejemplo n.º 4
0
        public async Task Update(IReadOnlyDictionary <long, PunishSource> lags)
        {
            // move to the game loop so we can synchronously operate on blocks
            await VRageUtils.MoveToGameLoop();

            foreach (var(gridId, lag) in lags)
            {
                if (!lag.IsPinned)
                {
                    continue;
                }

                if (!VRageUtils.TryGetCubeGridById(gridId, out var grid))
                {
                    Log.Warn($"grid not found for grid id: {gridId}");
                    continue;
                }

                if (!_punishedIds.Contains(gridId))
                {
                    _punishedIds.Add(gridId);
                    Log.Info($"Punished: \"{grid.DisplayName}\" type: {_config.PunishType}");
                }

                await PunishGrid(grid);

                Log.Debug($"block punish: \"{grid.Name}\" <{lag.GridId}> {_config.PunishType}");

                // move to the next frame so we won't lag the server
                await VRageUtils.MoveToGameLoop();
            }

            foreach (var existingId in _punishedIds)
            {
                if (!lags.ContainsKey(existingId))
                {
                    var name = VRageUtils.TryGetCubeGridById(existingId, out var g) ? $"\"{g.DisplayName}\"" : $"<{existingId}>";
                    Log.Info($"Done punishment: {name}");
                }
            }

            _punishedIds.ExceptWith(lags.Keys);

            // back to some worker thread
            await TaskUtils.MoveToThreadPool();
        }
Ejemplo n.º 5
0
        async Task AnnounceDeletedGrids(CancellationToken canceller)
        {
            // stop tracking deleted grids & report cheating
            // we're doing this right here to get the max chance of grabbing the owner name
            var lostGrids = new List <TrackedEntity>();

            await VRageUtils.MoveToGameLoop(canceller);

            foreach (var(_, trackedGrid) in _grids.Entities)
            {
                if (!MyEntities.TryGetEntityById(trackedGrid.Id, out _))
                {
                    lostGrids.Add(trackedGrid);
                }
            }

            await TaskUtils.MoveToThreadPool(canceller);

            foreach (var lostGrid in lostGrids)
            {
                _grids.StopTracking(lostGrid.Id);

                // high-profile grid deleted
                if (lostGrid.LagNormal >= _config.QuestLagNormal)
                {
                    var gridName  = lostGrid.Name;
                    var ownerName = lostGrid.OwnerName;
                    Log.Warn($"Laggy grid deleted by player: {gridName}: {ownerName}");

                    if (_config.EnablePunishChatFeed)
                    {
                        _chatManager.SendMessage(_config.PunishReportChatName, 0, $"Laggy grid deleted by player: {gridName}: {ownerName}");
                    }
                }
            }

            Log.Trace("announcing deleted entities done");
        }