debian下iptables管理脚本
2013-07-23 10:35:26 阿炯

本站赞助商链接,请多关照。 RedHat系列下有比较好用的iptables管理工具,可以像控制服务进程一样来对防火墙进行管理及控制,Debian默认不开启iptables,当然也没有与之相关的能直接管理的工具了。这里推荐一款工具,可以来完成这一工作,其名称为:iptables-init-debian,在MIT协议下使用。

Init script for controlling iptables as a service in a Debian box. Tested in Debian Squeeze, Wheezy and Sid.

This script relies on iptables-save and iptables-restore commands, to save and read the rules in /etc/iptables.rules. Once installed, this file must be created, by saving current rules (save command).

指令参考:
start: loads /etc/init.d/iptables.rules

stop: flushes iptables completely, and enforces ACCEPT policy

restart: convenience start & stop command

save: saves the current rules to /etc/init.d/iptables.rules

示例:
service iptables start
service iptables stop
service iptables restart
service iptables status

另外在apt源中,有一个名为'iptables-persistent'的工具,也可实现这一功能,但不怎么好用。

其它一键配置脚本
# cat iptables.sh

#!/bin/bash
ipt="/usr/sbin/iptables"

#默认策略:禁止所有进来的包、放行转发的包和所有出去的包
$ipt -P INPUT DROP
$ipt -P FORWARD ACCEPT
$ipt -P OUTPUT ACCEPT

#清空原有规则:
$ipt -F

#放行指定状态的包(必须有)否则将断开所有非指定ip远程连接
$ipt -A INPUT -m state --state RELATED,ESTABLISHED -j ACCEPT
#对中控机开放22端口,两种格式,如果未使用-m参数,第二中格式将导致无法进行远程连接
$ipt -A INPUT -s 192.168.228.129/32 -p tcp --dport 22 -j ACCEPT
#格式2:$ipt -A INPUT -s 192.168.228.129/32  -m state --state NEW -m tcp -p tcp --dport 22 -j ACCEPT

#对内网开放所有端口
$ipt -A INPUT -s 123.110.228.242/32 -p tcp --dport 0:65535 -j ACCEPT

#允许本机访问外网,不允许任何网络访问本机
#$ipt -A INPUT -p icmp --icmp-type 8 -j DROP

#放行ping命令使用的端口
$ipt -A INPUT -p icmp -j ACCEPT
$ipt -A INPUT -i lo -j ACCEPT

如果要使以上规则重启依然生效,需要将脚本的执行命令写入 /etc/rc.local 文件中:
/bin/bash /usr/local/iptables.sh

或者将以上配置放入 iptables 的配置文件:
# Firewall configuration written by system-config-firewall
# Manual customization of this file is not recommended.
*filter
# drop all input packages except rules follow
:INPUT DROP [0:0]
# allow all forward packages
:FORWARD ACCEPT [0:0]
# allow all output packages
:OUTPUT ACCEPT [0:0]

# accept state=ESTABLISHED or state=RELATED input connection
-A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT

#放行ping使用的端口
-A INPUT -p icmp -j ACCEPT
-A INPUT -i lo -j ACCEPT

#对中控机开放22端口
-A INPUT -s 192.168.28.29/32  -m state --state NEW -m tcp -p tcp --dport 22 -j ACCEPT

#对内网开放所有端口
-A INPUT -s 12.34.56.78/32 -p tcp --dport 0:65535 -j ACCEPT

#允许本机访问外网
#-A INPUT -p icmp --icmp-type 8 -j DROP

使用 iptables 对指定 ip 限速
#对外网下载限速1Mbit/s
iptables -A OUTPUT -d 0.0.0.0/0 -m limit --limit 60/s --limit-burst 30  -j ACCEPT
iptables -A OUTPUT -d 0.0.0.0/0 -j DROP

说明:iptables 是根据每秒的数据包数量来管理数据流入流出速度的,需要注意的是“--limit-burst” 决定了下载速度的大小,而 “--limit” 的值是本地每秒能产生的供应 “--limit-burst” 使用的包的数量,保证其大于等于 “--limit-burst” 就可以保证下载速度。

注意事项:
关于 iptables 的默认策略。

iptables 的默认策略(如,iptables -P INPUT DROP),只能通过 “iptables -P INPUT ACCEPT” 来清除,iptables -F 对其不生效。一定要在执行 “iptables -F” 命令之前先执行 “iptables -P INPUT ACCEPT”,否则将断开远程连接!

关于 keepalived 服务防火墙
如果配置可 keepalived 高可用服务,还需要针对该服务单独配置防火墙规则:
#放行keepalived:
-A INPUT -i em1 -d 10.0.0.0/8 -p vrrp -j ACCEPT
-A OUTPUT -o em1 -d 10.0.0.0/8 -p vrrp -j ACCEPT

扩展选项

其实匹配扩展中,还有需要加 -m 引用模块的显示扩展,默认是隐含扩展,不要使用 -m。

状态检测的包过滤:
-m state --state {NEW,ESTATBLISHED,INVALID,RELATED} 指定检测那种状态

-m multiport 指定多端口号
--sport
--dport
--ports

-m iprange 指定 IP 段
--src-range ip-ip
--dst-range ip-ip

-m connlimit 连接限定
--comlimit-above # 限定大连接个数

-m limit 现在连接速率,也就是限定匹配数据包的个数
--limit 指定速率
--limit-burst # 峰值速率,最大限定

-m string 按字符串限定
--algo bm|kmp 指定算法 bm 或 kmp
--string "STRING" 指定字符串本身

规则:放行指定端口
使用脚本设定规则:

创建脚本:
# vi /usr/local/sbin/iptables.sh

#!/bin/bash
ipt="/usr/sbin/iptables"
# 定义一个变量——iptables命令(定义变量时尽量使用绝对路径,避免环境变量的影响)
$ipt -F
# 清空原有规则
$ipt -P INPUT DROP
$ipt -P OUTPUT ACCEPT
$ipt -P FORWARD ACCEPT
# 上面三行是定义其默认策略
$ipt -A INPUT -m state --state RELATED,ESTABLISHED -j ACCEPT
# -m是指定检测状态,--state指定数据包状态(配合-m使用),该命令行的目的是使数据处理(通信)更顺畅
$ipt -A INPUT -s 192.168.8.0/24 -p tcp --dport 22 -j ACCEPT
$ipt -A INPUT -p tcp --dport 80 -j ACCEPT
$ipt -A INPUT -p tcp --dport 21 -j ACCEPT
# 上面三行命令是指定放行的包的类型  

icmp示例
iptables -I INPUT -p icmp --icmp-type 8 -j DROP

执行该脚本中的规则:
# sh /usr/local/sbin/iptables.sh

注意:脚本中指定的 IP 如果和主机 IP 不同时不要在远程端口直接运行该脚本!

icmp 协议示例
#iptables -I INPUT -p icmp --icmp-type 8 -j DROP

该规则的含义是:只允许本机访问外网,不允许外网访问本机!

iptables nat 表应用

应用 1
环境:A 机器两块网卡 ens33 (192.168.8.125)、ens37 (192.168.100.1),ens33 可以上外网,ens37 仅仅是内部网络,B 机器只有 ens37(192.168.100.100),和 A 机器 ens37 可以通信互联。

准备工作:

准备两台虚拟机
A 机器添加一块网卡 ens37,ens37 的网络连接方式选择‘LAN 区段模式’(内网交换机连接,该模式下 Windows 无法与该客户端连接),开机后并设定 IP 为 192.168.100.1

B 机器关闭原有网卡连接,新增网卡 ens37,开机后设定 IP 为 192.168.100.100(网络连接模式选择 LAN 区段,并和 A 机器中的 ens37 网卡选择相同区段)
设置 ens37 的 IP:

方法 1:
直接在命令行使用 ifconfig 命令
# ifconfig ens37 192.168.100.1/24
注:该方法只是临时设定 IP,重启后会丢失。

方法 2:复制 ens33 的配置文件,然后在配置内进行设置!

需求:

需求 1:可以让 B 机器连接外网

步骤一:A 机器打开路由转发
# echo "1" > /proc/sys/net/ipv4/ip_forward

该命令是更改内核设置,打开路由转发功能,默认值是0。

步骤二:在 A 机器的 nat 表中增加一条规则
# iptables -t nat -A POSTROUTING -s 192.168.100.0/24 -o ens33 -j MASQUERADE
# iptables -t nat -nvL
Chain PREROUTING (policy ACCEPT 0 packets, 0 bytes)
 pkts bytes target     prot opt in     out     source               destination         

Chain INPUT (policy ACCEPT 0 packets, 0 bytes)
 pkts bytes target     prot opt in     out     source               destination         

Chain OUTPUT (policy ACCEPT 0 packets, 0 bytes)
 pkts bytes target     prot opt in     out     source               destination         

Chain POSTROUTING (policy ACCEPT 0 packets, 0 bytes)
 pkts bytes target     prot opt in     out     source               destination         
    0     0 MASQUERADE  all  --  *      ens33   192.168.100.0/24     0.0.0.0/0    

说明:-o 选项后面跟设备名称,表示出口网卡,MASQUERADE 是伪装、冒充的意思。

步骤三:为 B 设置网关为 A 机器 ens37 的 IP:
# route add default gw 192.168.100.1

步骤四:配置 DNS (编辑 DNS 配置文件)
# vim /etc/resolv.conf
# Generated by NetworkManager
nameserver 19.29.29.29

然后使用 ping 命令检测,网络通畅!
注:此时 B 机器可以连通外网,但是外网机器无法访问 B 机器,A 机器的作用就类似于一个路由器!

需求 2:C 机器只能和 A 通信,让 C 机器可以直接连通 B 机器的 22 端口(端口映射)

步骤一:A 机器打开路由转发
# echo "1" > /proc/sys/net/ipv4/ip_forward

该命令是更改内核设置,打开路由转发功能,默认值是0。

步骤二:在 A 机器的 nat 表中增加 2 条规则(执行该步骤前先清除 nat 表原有规则)
规则1:
# iptables -t nat -A PREROUTING -d 192.168.8.125 -p tcp --dport 1122 -j DNAT --to 192.168.100.100:22

规则2:
# iptables -t nat -A POSTROUTING -s 192.168.100.100 -j SNAT --to 192.168.8.125

步骤三:为 B 设置网关为 A 机器 ens37 的 IP:
# route add default gw 192.168.100.1
Finish!

应用 2

iptables 限制 syn(同步)速度
原理:每 5s 内 tcp 三次握手大于 20 次的属于不正常访问。

# iptables -A INPUT -s ! 192.168.0.0/255.255.255.0 -d 192.168.8.125 -p tcp -m tcp --dport 80 -m state --state NEW -m recent --set --name httpuser --rsource  

# iptables -A INPUT -m recent --update --seconds 5 --hitcount 20 --name httpuser --rsource -j DROP
说明: 其中 192.168.0.0/255.255.255.0 为不受限制的网段,192.168.8.125 为本机 IP。
该 iptables 策略,可有效预防 syn 攻击,也可以有效防止机器人发垃圾帖。

应用 3

iptables 针对一个网段设置规则:

# iptables -I INPUT -m iprange --src-range 61.4.176.0-61.4.191.255 -j DROP

iptables 中 DNAT、SNAT 和 MASQUERADE

DNAT(Destination Network Address Translation, 目的地址转换) 通常被叫做目的映射。
SNAT(Source Network Address Translation,源地址转换)通常被叫做源映射。

iptables 中 DNAT 和 SNAT 工作原理:
在任何一个 IP 数据包中,都会有 Source IP Address 与 Destination IP Address 这两个字段,数据包所经过的路由器也是根据这两个字段是判定数据包是由什么地方发过来的,它要将数据包发到什么地方去。而 iptables 的 DNAT 与 SNAT 就是根据这个原理,对 Source IP Address 与 Destination IP Address 进行修改。

MASQUERADE(伪装)
假如当前系统用的是 ADSL/3G/4G 动态拨号方式,那么每次拨号,出口 IP 都会改变,SNAT 就会有局限性。
# iptables -t nat -A POSTROUTING -s 192.168.0.0/24 -o eth0 -j MASQUERADE

重点在 MASQUERADE 这个设定值就是将动态 IP 伪装成为 (-o) 的那块装置上的 IP,不管现在 eth0 的出口获得了怎样的动态 IP,MASQUERADE 会自动读取 eth0 设定的 IP 地址然后做 SNAT 出去,这样就实现了很好的动态 SNAT 地址转换。

iptables 规则备份和恢复
备份(另存为)
命令:iptables-save
# iptables-save > /tmp/ipt.txt

恢复
# iptables-restore < /tmp/ipt.txt


最新版本:


项目主页:https://github.com/Sirtea/iptables-init-debian