返回博客

游戏服务器 DDoS 防护:为 10 分钟攻击时代准备的运维手册

发布于 2026年10月30日
游戏服务器 DDoS 防护:为 10 分钟攻击时代准备的运维手册 借助 AI 生成

概要

掌握游戏服务器 DDoS 防护:基于 Cloudflare 2026 Q3 报告,这份 10 分钟攻击时代运维手册教你快速识别 UDP flood 与 SYN 耗尽,用 nftables 和 conntrack 做内核级缓解,并分离账号平面,在 1 Gbps 以下短突发攻击中保住游戏实例不宕机。

你的匹配队列在 21:14 卡住。到 21:19 它恢复了。你查看图表,发现一个 620 Mbps 的尖峰,持续六分钟,早在警报推送到手机之前就已经消失了。你们两人团队里没有人实时看到它,你的玩家把它归类为“卡顿”。

这种攻击形态现在已是常态。Cloudflare 的 2026 年 Q3 DDoS 威胁报告显示,该季度缓解了 1820 万次网络层攻击——大约每小时 8226 次,即每 0.44 秒一次。其中,96% 在 10 分钟内结束,98% 保持在 1 Gbps 以下。超过 1 Tbps 的超大流量攻击从 Q2 的 805 次降至 Q3 的 251 次,降幅约 69%,报告将其归因于执法部门对 Aisuru、KimWolf、JackSkid 和 Mossad 物联网僵尸网络的打击。

更少的巨兽,更多的蜂群。而蜂群正是小型游戏后端最没准备好的威胁模型,因为它同时小到无法触发云服务商的缓解层级,又大到足以打满单个游戏实例。

这是一份针对这个带宽区间的运维手册。

2026 年 Q3 实际改变了什么

如果你运营游戏服务器,有三个变化值得关注。第一是持续时间。短突发、低带宽攻击同比增长 208%,这是 DDoS 出租“booter”服务的典型操作特征:廉价、可重复、成波次发射。一个晚上会迎来 40 次攻击,而不是一次。

第二是攻击向量轮换。CLDAP 反射——滥用 UDP 389 上的公共域控制器——在 H1 期间一直很活跃,但环比暴跌 99.5%,仅占攻击的 0.05%。攻击者并没有停止;他们轮换了手法。DNS 放大攻击跃升 215%,占网络层攻击的 3.43%,普通 UDP flood 从 14.06% 攀升至 31.31%。

第三是目标范围扩大。媒体行业仍然是被攻击最多的行业,但相比 Q2 份额下降了约四分之三。互联网基础设施从十名开外升至第 6 位,消费者服务和成人娱乐进入第 8 和第 9 位。游戏正处在这个面向消费者、对延迟敏感的目标集群之中。

防御者的经验教训:不要围绕上个季度的攻击向量来制定作战手册。 要围绕四个类别来构建——UDP flood、DNS 放大、反射滥用和 SYN 耗尽——并假定权重会持续变化。

游戏后端最先崩的是什么

不是所有东西同时挂掉;知道顺序能让你避免救错火。

  • 游戏端口。 权威服务器端口上的 UDP flood 会在 CPU 之前耗尽 NIC 队列。由于进程还活着,你的编排器健康检查会认为服务器“在线”,而内核中数据包正在被丢弃。
  • 会话与登录端点。 HTTP flood 打击认证服务。在突发中断线的玩家无法重新登录,而已经在游戏中的玩家也会因为重连循环失败而流失。
  • 排行榜读取。 这是大多数游戏后端中被放大最严重的读路径:一个客户端请求会扇出成一次数据库范围扫描。每秒 5000 个请求发送起来很容易,服务起来却很昂贵。
  • 遥测数据接入。 通常没有认证或限流很松,往往是最容易打的端点。
  • conntrack 表。 把它填满会拖垮主机上的所有服务,包括你的 SSH 访问;四分钟的攻击就这样变成四小时的事故。

反射攻击值得特别说明:流量来自合法的 DNS 解析器和其他第三方服务器,因此基于 IP 信誉的封禁在设计上就会失效。你正在被无辜的基础设施攻击。

检测:在图表面板之前触发的信号

你的仪表盘有延迟,内核计数器没有。最重要的前置指标是每秒包数 (pps) 与每秒比特数 (bps) 的比率。合法的 300 Mbps 游戏流量在典型载荷大小下大约是每秒 25,000-40,000 个包。一个使用 64 字节包的 300 Mbps UDP flood 则接近 500,000 pps。同样的带宽,15 倍的包数量,它会在你的带宽图看起来还算正常时杀死主机。

在被怀疑的机器上运行以下命令:

# socket and memory pressure summary
ss -s

# per-protocol counters and the ones that predict a lockup
nstat -az | grep -E 'UdpInDatagrams|UdpNoPorts|UdpInErrors|TcpExtListenDrops|TcpExtTCPReqQFullDrop'

# current conntrack table occupancy vs max
conntrack -C && sysctl net.netfilter.nf_conntrack_max

# what is actually arriving on the wire
tcpdump -nn -i eth0 'udp and not port 7777' -c 200

这样解读:

  • UdpInDatagrams 攀升,而你的游戏循环报告玩家数下降 = flood。
  • UdpNoPorts 飙升 = 扫描器正在扫你的端口范围,通常是前兆。
  • TcpExtTCPReqQFullDrop 非零 = SYN 队列溢出,意味着你已经开始丢失合法的握手请求。
  • conntrack -C 超过 nf_conntrack_max 的 70% = 离主机完全宕机只剩几分钟,而不只是游戏服务器故障。

如果你想要按端点视角而不是内核视角,UEFN 服务器崩溃诊断协议 介绍了如何区分网络层停滞和引擎层停滞,这是任何排障流程中的第一个决策。

针对那些确实穿透进来的垃圾流量,在 socket 层做 per-source token bucket 既便宜又有效。下面这个 C# 示例会在入站包到达你的模拟 tick 之前进行门控:

using System.Diagnostics;
using System.Net;

public sealed class PacketGate
{
    private readonly Dictionary<IPAddress, Bucket> _buckets = new();
    private readonly int _ratePerSecond;
    private readonly int _burst;

    // A legit client at 30 Hz sends ~30 packets/s. 120/s allows
    // headroom for retransmits without letting a flood through.
    public PacketGate(int ratePerSecond = 120, int burst = 240)
    {
        _ratePerSecond = ratePerSecond;
        _burst = burst;
    }

    public bool Allow(IPAddress source)
    {
        long now = Stopwatch.GetTimestamp();

        if (!_buckets.TryGetValue(source, out var bucket))
        {
            bucket = new Bucket { Tokens = _burst, LastRefill = now };
            _buckets[source] = bucket;
        }

        double elapsed = (now - bucket.LastRefill) / (double)Stopwatch.Frequency;
        bucket.Tokens = Math.Min(_burst, bucket.Tokens + elapsed * _ratePerSecond);
        bucket.LastRefill = now;

        if (bucket.Tokens < 1.0) return false;
        bucket.Tokens -= 1.0;
        return true;
    }

    private sealed class Bucket
    {
        public double Tokens;
        public long LastRefill;
    }
}

要清楚它做什么和不做什么。它过滤的是在你可用带宽范围内的每来源垃圾流量。一旦管道被占满,它就无能为力——那时数据包会在到达你的进程之前就被上游丢弃,无论你的代码怎么决定都一样。

应急处置手册:最初的十分钟

既然 96% 的攻击在人类来得及响应之前就结束了,这份手册的目的不是让你修复攻击,而是让你在攻击自然耗尽的过程中捕获证据并缩小爆炸半径。

T+0 到 T+2 分钟——确认,不要扩容。 忍住加实例的本能。往 flood 里扩容只会成倍增加账单和攻击面。用上面的计数器确认攻击向量,记录 pps 和带宽,并检查 conntrack 表是否正在被填满。如果是,立即进入 T+0 紧急主机保护。

T+2 到 T+5 分钟——剥离非核心负载。 关闭所有非玩法相关的东西:遥测批处理、排行榜刷新、商店轮询、社交信息流。如果你的后端支持远程配置,这只是一个开关翻转,而不是一次部署。

T+5 到 T+10 分钟——应用主机级速率限制。 内核过滤比应用层过滤便宜几个数量级:

table inet gameguard {
    set udp_flood {
        type ipv4_addr
        flags dynamic, timeout
        timeout 60s
    }

    chain input {
        type filter hook input priority filter; policy drop;

        iif lo accept
        ct state established,related accept
        tcp dport { 22, 443 } accept
        tcp dport 7777-7800 accept
        udp dport 7777-7800 accept

        # drop fragmented UDP - your game protocol should never need it
        ip frag-off & 0x1fff != 0 udp drop

        # per-source UDP cap well above a real client's send rate
        udp dport 7777-7800 update @udp_flood \
            { ip saddr limit rate over 200/second burst 400 packets } drop
    }
}

用 nft -f gameguard.nft 加载。用 nft list ruleset 和 nft list set inet gameguard udp_flood 验证。如果你搞砸了并把自己锁在外面,你就把网络事件升级成了需要物理介入的事故——先在 staging 环境测试,并把规则纳入版本控制。

T+10 分钟及以后——升级到上游。 你需要在网络边缘具备清洗或黑洞能力,而不是在主机上。大多数托管游戏服务器提供商都提供这项能力;如果你的不提供,那是一个采购问题,要在下一次攻击前解决。具体问清楚他们的 1 Gbps 以下 UDP 缓解阈值,因为大多数公开 SLA 都是为你看不到的 T 级攻击写的。

整个过程:保持带时间戳的日志。攻击开始时间、向量、峰值 pps、峰值 Gbps、你改了什么以及何时改的。事后复盘比缓解本身更有价值。

攻击向量手册:按攻击形态匹配响应

UDP flood(占攻击的 31.31%)。 随机或定向端口,迫使主机检查监听者并生成 ICMP unreachable。网络层回退架构 一文介绍了当主传输通道被猛烈攻击时,如何保持一个降级但仍可玩的模式。应对:使用 nftables 做每来源速率限制,关闭除游戏端口之外的所有 UDP 端口,并在主机上禁用 ICMP unreachable 生成。

DNS 放大攻击(3.43%,增长 215%)。 伪造源地址向开放解析器发送查询,将大量响应指向你。应对:你无法按来源封禁,因为来源是合法解析器。你只能吸收,或按响应大小和速率过滤。用 dig +short txt chaos version.bind @your.ip 确认你自己没有运行开放解析器——如果有响应,今天就关掉它。

CLDAP(降到 0.05%)。 目前安静,历史上规模巨大。提醒:CLDAP 放大攻击运行在 UDP 389 上,所以除非你需要 LDAP,否则在主机和云防火墙两层都过滤掉它。攻击者轮换回来时会回到未受保护的端口。

SYN flood。 很少靠流量,总是靠耗尽。启用 SYN cookies(sysctl -w net.ipv4.tcp_syncookies=1),调大 net.core.somaxconn,并确保 conntrack 表按照你最坏的真实场景来配置,而不是默认值。

预防:能扛过四分钟突发流量的架构

先算容量账,因为这会打消很多一厢情愿的想法。一个 64 人、100 tick 的服务器每个玩家大约产生 15-20 KB/s——也就是 1.2 MB/s,约每实例 10 Mbps。一次 400 Mbps 的攻击是该实例合法流量的 40 倍。由于 98% 的攻击低于 1 Gbps,当前分布中几乎每一次攻击都大到足以打垮单个游戏实例,同时又小到根本引不起一级清洗提供商的自动缓解。

这对你的架构产生了三个约束。

把账号平面和游戏平面分离。 如果你的登录端点、排行榜读取和玩家存档与游戏服务器运行在同一台主机上,游戏端口上的 flood 也会拖垮账号,玩家甚至看不到“马上回来”的提示页。把这些账号相关服务放在 horizOn 上——认证、Cloud Save 和排行榜都在那里托管——意味着针对游戏端口的突发流量只会降低玩法体验,而不会把每个玩家都锁在个人资料之外。

让功能裁剪成为配置变更,而不是部署。 当 flood 来袭时,你只有几秒钟。远程配置让你能立刻关掉昂贵的读路径。如果你唯一的选择是推送构建,你根本不会去用它。

让健康检查能够感知网络故障。 进程检查会在内核丢弃 90% 数据包时仍然报告“健康”。应该探测真正的玩法可达性——一个合成客户端执行真实握手并期望在 250ms 内收到响应——并让它驱动你的故障转移。

最佳实践:本周值得上线的五个改动

  1. 按包速率告警,而不仅是带宽。 把阈值设为 95 分位 pps 的 2.5 倍。仅靠带宽告警会完全漏掉短突发流量;pps 异常检测能在一台 1 Gbps 链路的主机上抓到带宽图根本不会标记的 300 Mbps flood。
  2. 刻意规划 conntrack 表大小。 根据峰值并发会话数设置 net.netfilter.nf_conntrack_max,而不是发行版默认值,并在占用率达到 70% 时告警。这一个改动就能阻止最常见的“攻击演变成事故”升级路径。
  3. 预先写好 nftables 规则集并每季度测试一次。 把它存放在仓库里,紧挨着部署配置。事件期间应用未经测试的防火墙规则,等于制造第二起事件。
  4. 向玩家发布降级模式契约。 如果缓解期间排行榜和聊天会中断十分钟,请在补丁说明和状态页中明确说明。沉默会被解读为游戏已死。如果你想要一个参考模型,被入侵后的后端架构拆解 中的韧性模式可以直接迁移到可用性事件上。
  5. 把每次攻击记录为结构化事件。 时间戳、向量、峰值 pps、峰值 Gbps、持续时长、采用的缓解措施。记录五次之后你就会看到自己的规律——大多数独立后端都是在同一个星期几、同一个小时、被同一个 booter 攻击。

核心结论

2026 年的威胁格局对只规划 T 级攻击、却忽视 400 Mbps 六分钟突发流量的团队非常不友好。巨兽攻击下降了 69%,蜂群攻击增长了 208%。你的缓解方案必须自动化、低成本、且在内核中完成,因为没有任何人能在一次警报还没读完就已结束的攻击中做出反应。

从计数器开始,而不是仪表盘。加上每来源速率限制,规划好 conntrack 表大小,把账号平面和游戏平面分离,并排练十分钟手册直到你熟到无聊。

如果这种分离中有一部分是你宁愿不碰的苦活——玩家认证、支持版本感知的 Cloud Save、排行榜、事件中可随时切换的远程配置——那正是 horizOn 处理的部分,这样你的值班时间可以花在游戏服务器上。在下一次上线窗口之前免费试用,或阅读文档。


来源:Cloudflare 2026 年 Q3 DDoS 威胁报告:更多蜂群,更少巨兽