仅使用 iptables 在成功连接时取消阻止 SSH

仅使用 iptables 在成功连接时取消阻止 SSH

我目前在 Linux 路由器上有这些 iptables 规则,用于阻止重复的 SSH 连接:

-A wan_ingress -p tcp --dport 22 -m state --state NEW -m recent --name sshthrottle --set -m comment --comment "Tag incoming SSH requests"
-A wan_ingress -m state --state NEW -m recent --name sshthrottle --rcheck --seconds 300 --reap --hitcount 3 -j logdrop -m comment --comment "Log and drop packets"
-A logdrop -j LOG --log-prefix "sshthrottle:drop "
-A logdrop -j DROP

但问题是它也会阻止重复成功的连接,如果我在五分钟内成功连接和断开三次,我也会被阻止。不过只有五分钟,所以直到现在我才忍受。

由于 SSH 暴力破解程序会自动限制自身,我现在想将超时时间从五分钟延长到一天,但这意味着我每天只能进行有限次数的 SSH,否则也会被阻止。

所以我想知道最好的方法是添加一个额外的 iptables 规则,该规则表示如果 SSH 连接成功,则从用于计算连接尝试次数的列表中删除该 IP。

我认为它会使用类似--state ESTABLISHED第二个数据包计数器来确认 SSH 会话已实际建立(以避免将长时间不成功的登录尝试计为已建立的连接),但是我不太确定如何将该规则应用到触发从原始列表中删除该 IP。

答案1

我总是将 ssh 配置为先敲高端口,断开连接,登录到端口 22,然后检查高端口是否在最后一分钟内被 IP 敲过。扔掉所有没有先敲响的东西

答案2

这是一种似乎有效的方法。我添加了这些规则现有的,以便只有在连接尚未被阻止时才能到达:

-A wan_ingress -p tcp --dport 22 -m state --state ESTABLISHED -m recent \
    --name unblock --set -m comment --comment "Tag successful SSH connections"

-A wan_ingress -p tcp --dport 22 -m state --state ESTABLISHED -m recent \
    --name unblock --rcheck --seconds 10 --reap --hitcount 50 -j unblock \
    -m comment --comment "Remove the IP from the sshthrottle list after successful login"

-A unblock -m recent --name sshthrottle --remove -j LOG --log-prefix "unblock "

这是通过计算通过已建立的 SSH 连接发送的数据包数量来实现的。如果在 10 秒窗口内发送了至少 50 个数据包,则会跳转到表unblock,从标记列表中删除该 IP 并记录该事实。连接建立后,--state NEW原始规则上的条件将确保 IP 不会重新添加到标记列表中。

无论有多少数据包通过已建立的连接,这都只会记录一条消息,因为仅当 IP 存在于标记列表中时才会记录该消息。如果不存在,则不会打印任何日志消息。一旦建立连接,它就不会存在,以--state NEW确保仅将新连接添加到列表中。

50 个数据包可能需要调整。它似乎对我有用,因为快速的 SSH 连接在达到 50 个数据包之前就被阻止了。登录成功时,还没有达到50个数据包,所以不做任何操作就登录和退出,仍然可能会导致被阻止。按十几次回车键或ls登录后运行足以命中 50 个数据包并将该 IP 从标记的 IP 列表中删除。

答案3

这是显而易见的:只允许使用 ssh-key 登录,完全禁止密码登录。无需在这里摸索防火墙。

为什么你要给暴力破解者哪怕是统计上微不足道的机会去意外猜出正确的 24 个字符的密码呢?

如果您在连接失败后仍然想阻止:这正是fail2ban 的用途。

再说一次,没有任何理由让防火墙参与其中,除非你真的真的想自找麻烦,但没有任何额外的好处。

相关内容