我正在尝试模仿Windows防火墙通过软件定义规则。
因此,只有由特定组启动,软件才能访问互联网。然后,我可以为每个要访问互联网的程序创建一个 .sh 文件。通过遵循此问题如何控制每个程序的互联网访问?我正在尝试阻止所有不是由特定组启动的程序访问互联网。
- 我创建了一个小组 has-internet(我没有加入这个小组):
sudo addgroup has-internet
重启电脑以确保新组已正确加载
向 iptables 添加一条规则,禁止所有不属于 has-internet 组的进程使用网络(使用 ip6tables 还可以阻止 IPv6 流量)
sudo iptables -A OUTPUT -m owner ! --gid-owner has-internet -j DROP
sudo ip6tables -A OUTPUT -m owner ! --gid-owner has-internet -j DROP
执行ping somesite.xyz
(无法连接好!:)
执行sudo ping somesite.xyz
(无法连接好!:)
执行sudo -g has-internet ping somesite.xyz
(无法连接,不好!:(
我做错了什么?请帮忙!!!
编辑
我尝试过(只是为了实验)阻止该组并且成功了......
sudo iptables -A OUTPUT -m owner --gid-owner has-internet -j DROP
执行sudo ping somesite.xyz
(可以连接)
执行sudo -g has-internet ping somesite.xyz
(无法连接)
我不明白为什么这种方式有效而反过来却无效......?
答案1
好吧,您似乎已经知道了,为了允许软件列表输出,您首先需要设置输出策略以删除所有内容:
sudo iptables -P OUTPUT DROP
然后考虑添加一条与 INPUT 表中通常存在的规则相对应的规则,也就是说,如果数据包的连接已经被跟踪并且状态为 RELATED 或 ESTABLISHED,则接受任何发送的数据包:
sudo iptables -A OUTPUT -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT
否则,将需要进一步的规则来检查每个数据包,但使用 conntrack 至少比每次检查进程所有者和组更快。
然后您可能希望允许自我通信。由于您已阻止了所有内容,因此您希望启用环回输出。
sudo iptables -o lo -j ACCEPT
之后,按照创建组所述进行操作,并创建一条规则来过滤该组的进程发送的数据包,但不是丢弃该数据包而是接受它:
sudo iptables -A OUTPUT -m owner --gid-owner has-internet -j ACCEPT
然后,您可以像往常一样为您的 iptables 规则集建立保存-恢复。至少,sudo iptables -S
可以作为临时保存,但是iptables-persistent
为了方便而建立的。
PS:如果您的系统中设置了 IPv6,请使用 执行相同的命令集ip6tables
。