四、剖析一个完整的例子
我们假定接口ppp0通往Internet,接口eth0通往内部网络。
ppp0的IP地址是128.138.101.4,eth0的IP地址是10.1.1.1,两个接口的子网掩码都是255.255.255.0。
这个例子使用无状态包过滤机制来保护IP地址为10.1.1.2的Web服务器,这是保护Internet服务器的标准方法。
在这个例子的后面部分,我们将展示如何使用有状态的过滤机制来保护桌面用户。

在您使用iptables之前,必须启用IP forwarding(IP转发)功能,并且确保内核里已经加载了各个iptables模块。
要了解启用IP forwarding功能的更多知识,参见28.4节或者12.11.8节。
带有iptables的所有发行版本也都有能够完成启用和加载的启动脚本。

1. 第一组规则是对filter表进行初始化。
首先,冲洗掉表中所有的链,
然后将INPUT和FORWARD链的默认目标设为DROP。
和其他任何网络防火墙一样,最安全的策略就是丢弃您没有明确允许的任何包。
# iptables -F
# iptables -P INPUT DROP       // 如果是用SSH连接进行设置,不要用这条命令,会导致SSH断开;
# iptables -P FORWARD DROP

2. 规则是按照它们出现在链中的顺序来进行匹配的,所以我们将用得最多的规则放在最前面 。
FORWARD链中的前3条规则让去往10.1.1.2上网络服务的连接通过防火墙。
确切地说,我们允许SSH(端口22)、HTTP(端口80)和HTTPS(端口443)能够连到我们的Web服务器。
第一条规则允许来自可信网络的所有连接通过防火墙。
# iptables -A FORWARD -i eth0 -p ANY -j ACCEPT
# iptables -A FORWARD -d 10.1.1.2 -p tcp --dport 22  -j ACCEPT
# iptables -A FORWARD -d 10.1.1.2 -p tcp --dport 80  -j ACCEPT
# iptables -A FORWARD -d 10.1.1.2 -p tcp --dport 443 -j ACCEPT

3. 我们允许流到防火墙主机(10.1.1.1)的唯一TCP流量是SSH,它用于管理防火墙。
下面列出的第二条规则允许环回(loopback)流量,它留在防火墙主机的本地。
我们的系统管理员在他们不能ping到默认路由时会感到紧张,
所以这里的第三条规则允许从内部IP地址来的ICMP ECHO_REQUEST包。
# iptables -A INPUT -i eth0 -d 10.1.1.1  -p tcp --dport 22     -j ACCEPT
# iptables -A INPUT -i lo   -d 127.0.0.1 -p ANY                -j ACCEPT
# iptables -A INPUT -i eth0 -d 10.1.1.1  -p icmp --icmp-type 8 -j ACCEPT 

4. 为了能让任何TCP/IP主机在Internet正常工作,必须允许某些类型的ICMP包通过防火墙。
下面的8条规则就是让ICMP包既能送到防火墙主机,也能送到在它之后的网络的最小集合。
# iptables -A INPUT -p icmp --icmp-type 0 -j ACCEPT
# iptables -A INPUT -p icmp --icmp-type 3 -j ACCEPT
# iptables -A INPUT -p icmp --icmp-type 5 -j ACCEPT
# iptables -A INPUT -p icmp --icmp-type 11 -j ACCEPT
# iptables -A FORWARD -d 10.1.1.2 -p icmp --icmp-type 0 -j ACCEPT
# iptables -A FORWARD -d 10.1.1.2 -p icmp --icmp-type 3 -j ACCEPT
# iptables -A FORWARD -d 10.1.1.2 -p icmp --icmp-type 5 -j ACCEPT
# iptables -A FORWARD -d 10.1.1.2 -p icmp --icmp-type 11 -j ACCEPT

5. 接下来向NAT表的PREROUTING链加入规则。虽然NAT表的目的并不是做包过滤,
但是它的PREROUTING链对于反IP欺骗的过滤来说特别有用。
如果我们在PREROUTING链中加入DROP项,它们就不需要出现在INPUT和FORWARD链里了,
因为PREROUTING链会应用到所有进入防火墙主机的包上。
将控制项放到一个地方比重复放置它们的做法条理性要好得多。
# iptables -t nat -A PREROUTING -i ppp0 -s 10.0.0.0/8 -j DROP
# iptables -t nat -A PREROUTING -i ppp0 -s 172.16.0.0/12 -j DROP
# iptables -t nat -A PREROUTING -i ppp0 -s 192.168.0.0/16 -j DROP
# iptables -t nat -A PREROUTING -i ppp0 -s 127.0.0.0/8 -j DROP
# iptables -t nat -A PREROUTING -i ppp0 -s 224.0.0.0/8 -j DROP
 
6. 最后,我们用一条禁止所有没有得到明确许可的包的规则来结束INPUT和FORWARD链。
虽然我们在前面已经用iptables -P命令实施过这个做法,但是LOG目标(target)能让我们看到谁正在从Internet上敲我们的大门。
# iptables -A INPUT -i ppp0 -j LOG
# iptables -A FORWARD -i ppp0 -j LOG

7. 我们还可以设置IP NAT来伪装在内部网络里使用的私用地址空间。
参见12.12节了解更多有关NAT的知识。

8. Netfilter带给Linux防火墙最强大的功能之一就是有状态包过滤机制。
针对连到Internet的客户机的防火墙不是允许特定的传入服务,而是允许根据客户机的请求而传入的响应。
下面这条简单的有状态FORWARD链允许离开我们网络的所有流量通过,但只允许和我们的主机发起的连接有关的入流量通过。
# iptables -A FORWARD -i eth0 -p ANY -j ACCEPT
# iptables -A FORWARD -m state --state ESTABLISHED,RELATED -j ACCEPT

要跟踪复杂的网络会话,比如FTP和IRC,必须加载某些内核模块来启动iptables。
如果没有加载这些模块,iptables就会简单地禁止那些连接。虽然有状态包过滤器能够提高站点的安全性,
但是它们也增加了网络的复杂性。所以在防火墙上实现它之前,要确信您的确需要有状态功能。


五、调试iptables规则集
调试iptables规则集最好的办法或许就是用命令:
  iptables -L -v 

这些选项会告诉您链里面的每条规则匹配了多少个包。
我们经常在想了解有关匹配包的更多信息时,增加带有LOG目标(target)的临时iptables规则。
您可以经常通过使用像tcpdump这样的包探测器解决更棘手的问题。

六、应用实例
1. 禁止端口的实例
1). 禁止ssh 端口
只允许在192.168.62.1上使用ssh 远程登录,从其它计算机上禁止使用ssh
# iptables -A INPUT -s 192.168.62.1 -p tcp --dport 22 -j ACCEPT
# iptables -A INPUT -p tcp --dport 22 -j DROP

2). 禁止代理端口
# iptables -A INPUT -p tcp --dport 3128 -j REJECT

3). 禁止icmp 端口
除192.168.62.1外,禁止其它人ping 我的主机
# iptables -A INPUT -i eth0 -s 192.168.62.1/32 -p icmp -m icmp --icmp-type echo-request -j ACCEPT
# iptables -A INPUT -i eth0 -p icmp --icmp-type echo-request –j DROP

# iptables -A INPUT -i eth0 -s 192.168.62.1/32 -p icmp -m icmp --icmp-type 8 -j ACCEPT
# iptables -A INPUT -i eth0 -p icmp -m icmp --icmp-type 8 -j DROP
注:可以用iptables --protocol icmp --help 查看ICMP 类型

4). 禁止QQ 端口
# iptables -D FORWARD -p udp --dport 8000 -j REJECT

2. 强制访问指定的站点
要使192.168.52.0/24网络内的计算机(这此计算机的网关应设为192.168.52.10)强制访问指定的站点,
在做为防火墙的计算机(192.168.52.10)上应添加以下规则:
1). 打开ip 包转发功能
# echo 1 > /proc/sys/net/ipv4/ip_forward

2). 在NAT/防火墙计算机上的NAT 表中添加目的地址转换规则:
# iptables -t nat -I PREROUTING -i eth0 -p tcp --dport 80 -j DNAT --to-destination 202.96.134.130:80
# iptables -t nat -I PREROUTING -i eth0 -p udp --dport 80 -j DNAT --to-destination 202.96.134.130:80

3). 在NAT/防火墙计算机上的NAT 表中添加源地址转换规则:
# iptables -t nat -I POSTROUTING -o eth1 -p tcp --dport 80 -s 192.168.52.0/24 -j SNAT --to-source 202.96.134.10:20000-30000
# iptables -t nat -I POSTROUTING -o eth1 -p udp --dport 80 -s 192.168.52.0/24 -j SNAT --to-source 202.96.134.10:20000-30000

4). 测试:在内部网的任一台计算机上打开浏览器,输入任一非本网络的IP,都将指向IP 为202.96.134.130的网站.

3. 发布内部网络服务器
图4

要使因特网上的计算机访问到内部网的FTP 服务器、WEB 服务器,在做为防火墙的计算机上应
添加以下规则:
1).
# echo 1 > /proc/sys/net/ipv4/ip_forward

2). 发布内部网web 服务器
# iptables -t nat -I PREROUTING -p tcp -i eth1 -s 202.96.134.0/24 --dport 80 -j DNAT --to-destination 192.168.52.15:80
# iptables -t nat -I POSTROUTING -p tcp -i eth0 -s 192.168.52.15 --sport 80 -j SNAT --to-source 202.96.134.10:20000-30000

3). 发布内部网ftp 服务器
# iptables -t nat -I PREROUTING -p tcp -i eth1 -s 202.96.134.0/24 --dport 21 -j DNAT --to-destination 192.168.52.14:21
# iptables -t nat -I POSTROUTING -p tcp -i eth0 -s 192.168.52.14 --sport 21 -j SNAT --to-source 202.96.134.10:40000-50000

4). 注意:内部网的计算机网关要设置为防火墙的ip(192.168.52.1)
5). 测试:
     用一台IP 地址为202.96.134.0段的计算机虚拟因特网访问,
     当在其浏览器中访问http://202.96.134.10时, 实际应看到的是192.168.52.15的的web 服务;
     当访问ftp://202.96.134.10时,实际应看到的是192.168.52.14上的的ftp 服务

4. 智能DNS
图5

1).
# echo 1 > /proc/sys/net/ipv4/ip_forward

2). 在NAT 服务器上添加以下规则:
在PREROUTING 链中添加目的地址转换规则:
# iptables -t nat -I PREROUTING -i eth0 -p tcp --dpor 53 -j DNAT --to-destination 202.96.134.130
# iptables -t nat -I PREROUTING -i eth0 -p udp --dpor 53 -j DNAT --to-destination 202.96.134.130

在POSTROUTING 链中添加源地址转换规则:
# iptables -t nat -I POSTROUTING -o eth1 -s 192.168.52.0/24 -p tcp --dpor 53 -j SNAT --to-source 202.96.134.10:40000-50000
# iptables -t nat -I POSTROUTING -o eth1 -s 192.168.52.0/24 -p udp --dpor 53 -j SNAT --to-source 202.96.134.10:40000-50000

3). 测试
在内部网任一台计算机上,将DNS 设置为任意的外网IP,就可以使用DNS 
测试工具如nslookup来解析DNS 服务器202.96.134.130上的名称.

5. 端口映射
见上节透明代理设置
# iptables -t nat -A PREROUTING -i eth0 -p tcp -s 192.168.62.0/24 --dport 80 -j REDIRECT --to-ports 3128

6. 典型NAT 上网
一般做为NAT 的计算机同时也是局域网的网关,
假定该机有两块网卡eth0、eth1,
eth0连接外网,  IP 为202.96.134.134;
eth1连接局域网,IP 为192.168.62.10

1). 先在内核里打开ip 转发功能
# echo 1 > /proc/sys/net/ipv4/ip_forward

2). 使局域网用户能访问internet 所要做的nat
# iptables -t nat -A POSTROUTING -p tcp -o eth0 -j SNAT --to?202.96.134.134


如果上网的IP 是动态IP,则使用以下规则:
# iptables -t nat -A POSTROUTING -o eth0 -s 192.168.62.0/24 -j MASQUERADE

如果是通过ADSL 上网,且公网IP 是动态IP,则使用以下规则:
# iptables -t nat -A POSTROUTING -o ppp0 -s 192.168.62.0/24 -j MASQUERADE

3). 使internet 用户可以访问局域网内web 主机所要做的nat
# iptables -t nat -A PREROUTING -p tcp -d 202.96.134.134 --dport 80 -j DNAT --to-destination 192.168.62.10
注:局域网内的客户端需将默认网关、DNS 设为防火墙的IP

7. 在我们的网络机房实现NAT 共享上网
工作环境:上层代理192.168.60.6(4480),只授予教师机(192.168.62.111)使用该代理的权限
目标:不使用squid 代理上网,而是使用NAT 的方式上网
方法:
1). 确保停止教师机(192.168.62.111)的squid 或其它代理服务
2). 客户端网关、DNS 均指向192.168.62.111,浏览器代理设置为192.168.60.6(4480)。
    测试在当前情况下能否上网
3). 在教师机(192.168.62.111)上添加如下iptables 规则:
# iptables -t nat -A POSTROUTING -p tcp -d 192.168.60.6/32 --dport 4480 -j SNAT --to-source 192.168.62.111:10000-30000
解释:对于目的地为192.168.60.6、目的端口为4480的TCP 包,
      在经过防火墙路由后,将其源地址转换为192.168.62.111,端口转换为10000-30000间的某个端口。
4). 客户端测试能否上网

8. 对流媒体服务器的服务做IP 限制
1). 清空规则并放开SSH
# iptables -F
# iptables -A INPUT -s 10.1.1.11 -p tcp --dport 22 -j ACCEPT

2). 对指定IP放开,可以推送流到这台服务器, 其余的IP都禁止
A. 只对单个IP放开
# iptables -A INPUT -s 10.2.1.54 -j ACCEPT
# iptables -A INPUT -s! 10.2.1.54 -j REJECT

# iptables -A INPUT -s 10.2.1.54 -j ACCEPT
# iptables -A INPUT   -i eth0 -j REJECT

B. 对多个IP放开,即将要放开的IP插入到最后一条拒绝的规则之前
# iptables -A INPUT -s 10.2.1.54 -j ACCEPT
# iptables -A INPUT   -i eth0 -j REJECT
# iptables -I INPUT 2 -s 10.2.1.13 -j ACCEPT

3). 对指定IP段 放开,可以推送流到这台服务器,其余的IP都禁止
A. 对单个IP段放开
# iptables -I INPUT 2 -s 10.2.1.0/24 -j ACCEPT
# iptables -A INPUT   -i eth0 -j REJECT

B. 对多个IP段放开
# iptables -I INPUT 2 -s 10.2.1.0/24 -j ACCEPT
# iptables -A INPUT   -i eth0 -j REJECT
# iptables -I INPUT 2 -s 10.2.2.0/24 -j ACCEPT

其中:
10.2.1.0/24 表示: A类地址主机为8位,表示10.2.1固定,后面是可变
前面是IP地址10.2.1.0,是表示局域网地址。
后而的24是指掩码,因为IP地址和掩码用二进制表示的话都是32位的。
所以掩码的24表示那掩码前24位是1,后8位是0,转换成10进制就是表示掩码是255.255.255.0
即, 255.255.255.0=11111111.11111111.11111111.0=24个1
192.168.0.0/16 代表B类地址 主机为16,表示192.168固定,后面是可用.

4). 对指定IP拒绝,
A. 对单个IP拒绝
# iptables -A INPUT -s 10.2.1.11 -p tcp --dport 1935 -j REJECT
Logo

更多推荐