暴露的 SSH 端口全天候承受撞库流量
扫描型僵尸网络遍历整个可路由的 IPv4 地址空间,对每一台在 TCP/22 上应答的主机尝试密码字典。只要 SSH 守护进程可从互联网访问,无论该主机是企业堡垒机还是一台普通 VPS,都会收到这些流量。
- 每天数千次失败认证
- 一台新主机在 TCP/22 上应答后,地址可路由仅数小时便会开始记录失败的 SSH 认证。典型的面向互联网的服务器每天在 systemd-journald 中写入数千条 Failed password 与 Invalid user 事件,而这些事件来自轮换速度远超单个管理员审查能力的地址段。
- CPU、内存与日志写入被永远无法通过认证的流量消耗
- 每一次 SSH 认证尝试都要付出一次 TCP 握手、一次 SSH 密钥交换、一次经由 /etc/pam.d/sshd 的 PAM 查找,以及一次写入 systemd-journald 的同步操作。持续的暴力破解流因此在主机上形成长期后台负载,使日志存储膨胀,并把真正的管理登录挤到 sshd 的 MaxStartups 队列之后——而攻击者无需通过任何认证即可造成上述全部后果。
- 猜中一个口令即等于完全沦陷
- 只要有一个口令正确,攻击者就获得该账户权限下的交互式 shell:勒索软件投放、数据外泄,或以主机自身地址发出的垃圾邮件。弱口令或从公开泄露库中复用的口令,在字典攻击面前数日之内即会失守,而认证日志记录这次成功尝试的方式与其他任何一行别无二致。
- pam_faillock 让攻击变成对真正管理员的锁定
- 在 /etc/pam.d/sshd 中配置的 PAM 栈使用 pam_faillock 统计连续失败次数,一旦达到 deny 阈值便锁定账户。因此,只猜中了有效用户名——始终没猜中口令——的攻击者,也可以故意触发该计数器,把真正的管理员锁在主机之外。结果是一次完全由防护机制本身造成的拒绝服务。
SSH Protector 把判定从用户态移到 netfilter 的 input 钩子
SSH Protector 守护进程按来源网络关联失败的认证事件,并提交一条 nftables 规则丢弃攻击者的整个 /24 子网。该规则一旦存在,netfilter 就在内核的 input 钩子中丢弃数据包——早于 sshd 接受连接、早于任何 PAM 查找、也早于任何日志写入。CPU 负载、日志体量以及抵达口令校验环节的尝试次数会同时下降。

