iptables部署
1、iptables简介
Netfilter/Iptables(以下简称Iptables)是unix/linux自带的一款优秀且开放源代码的安全*的**基于包过滤的防火墙工具**,它的功能十分强大,使用非常灵活,可以对流入和流出服务器的数据包进行很精细的控制。特别是它可以在一台非常低的硬件配置下跑的非常好 Iptables是Linux2.4及2.6内核中集成的服务。其功能与安全性比其**ipfwadm,ipchains**强大的多,iptables主要工作在OSI七层的二、三、四层,如果重新编译内核,iptables也可以支持**7层控制**(squid代理+iptables)
iptables的术语:
容器:包含和被包含的关系
iptables是表的容器
iptables包含表 (4张表)表是链的容器,每个表都包含若干个链
链是规则的容器,真正过滤规则是属于链里面的
级别的形象比喻
iptables国家
表省
链 市
规则 县
iptables工作流程
1.防火墙是一层层过滤的。实际是按照配置规则的顺序从上到下,从前到后进行过滤的。
2.如果匹配上规则,即明确表是阻止还是通过,此时数据包就不在向下匹配新规则了。
3.如果所有规则中没有明确是阻止还是通过这个数据包,也就是么有匹配上新规则,向下进行匹配,直到匹配默认规则得到明确的组织还是通过
4.防火墙的默认规则是对应链的所有规则执行完才会执行的。
iptables表(tables)和链(chains)
Filter表
是真正的防火墙功能 INPUT
进服务器 OUTPUT出服务器 FORWARD 流经服务器 Nat
表 负责数据包改写 网关共享上网、IP和端口映射
OUTPUT
PREROUTING
POSTROUTING
Mangle表 路由标记 用的不多
####所有链全有
RAW 表 用处很少和Mangle一样
我们可以通过man iptables 来获取
iptables表和链工作流程图
提示: iptables主要由2个作用,第一是防火墙
,第二是路由
。
NAT功能:
企业案例:1)局域网上网共享(路由和网关)NAT POSTROUTING
2)外部IP和端口映射为内部IP和端口(DMZ功能),NAT PREROUTING
Filter功能,即防火墙FILTER INPUT FORWARD
企业案例:主要应用于服务器防火墙
2、配置iptables防火墙
CENTOS系统默认已经安装了iptables,产看iptables的规则用如下命令:
iptables -L -n Chain INPUT (policy ACCEPT) target prot opt source destination Chain FORWARD (policy ACCEPT) target prot opt source destination Chain OUTPUT (policy ACCEPT) target prot opt source destination
表示针对input,forward,output链 ACCEPT是默认规则,默认是运行通过的。如果没有指定表,默认就是filter表。如果要查看nat表的规则用:iptables -L -n -t nat
查看iptables默认加载的内核模块
[root@lnmp01 ~]# lsmod|grep ^ip iptable_filter 2793 0 ip_tables 17831 1 iptable_filter ipv6 334932 280
加载如下模块到linux内核
modprobe ip_tables modprobe iptable_filter modprobe iptable_nat modprobe ip_conntrack_ftp modprobe ip_nat_ftp modprobe ip_conntrack modprobe ipt_state
然后再用lsmod|egrep ^ip命令来查看加载的iptalbes的模块
[root@lnmp01 ~]# lsmod|egrep ^ip iptable_nat 6051 0 iptable_filter 2793 0 ip_tables 17831 2 iptable_nat,iptable_filter ipv6 334932 280
这样就可以看到nat模块也加载到内核了。
清空所有规则,只留下默认规则
iptables -F iptables -X iptables -Z
说明:
iptables -F //清除所有规则,不会处理默认的规则。
iptables -X //删除用户自定义的链。
iptables -Z //链的记数器清零。
书写一个规则,禁用80端口的防火墙配置命令:
iptables -t filter -A INPUT -p tcp --dport 80 -j DROP #或者用下面命令,不写fileter,因为默认的表就是filter iptables -A INPUT -p tcp --dport 80 -j DROP
-A
添加规则到指定链的结尾,最后一条 -I
添加规则到指定链的开头,第一条 -t
指定表,也可以不指定默认是filter -p
指定协议(all.tcp,udp.icmp)默认all --dport
指定端口 -j
处理的行为
ACCPET接收、DROP丢弃、REJECT拒绝
最好使用ACCPET
和DROP
,因为拒绝会返回给用户信息。
清除规则可以使用iptables -F
,还可以使用iptables -D INPUT 1
-D
指定删除的链 --line-number
显示序列号 iptables -L -n --line-numbe
r
[root@lnmp01 ~]# iptables -L -n --line-number Chain INPUT (policy ACCEPT) num target prot opt source destination Chain FORWARD (policy ACCEPT) num target prot opt source destination Chain OUTPUT (policy ACCEPT) num target prot opt source destination
添加的规则可以对链使用-A和-I参数-A表示(add或append),-I表示(insert插入)。如果想在一些规则中插入一条规则的话,就只能用-I参数了,如下:
iptables -t filter -A INPUT -p tcp --dport 80 -j DROP iptables -t filter -A INPUT -p tcp --dport 81 -j DROP iptables -t filter -A INPUT -p tcp --dport 82 -j DROP iptables -t filter -A INPUT -p tcp --dport 83 -j DROP iptables -t filter -I INPUT 2 -p tcp --dport 84 -j DROP [root@lnmp01 ~]# iptables -L -n --line-number Chain INPUT (policy ACCEPT) num target prot opt source destination 1 DROP tcp -- 0.0.0.0/0 0.0.0.0/0 tcp dpt:80 2 DROP tcp -- 0.0.0.0/0 0.0.0.0/0 tcp dpt:84 3 DROP tcp -- 0.0.0.0/0 0.0.0.0/0 tcp dpt:81 4 DROP tcp -- 0.0.0.0/0 0.0.0.0/0 tcp dpt:82 5 DROP tcp -- 0.0.0.0/0 0.0.0.0/0 tcp dpt:83
可以看到添加的规则iptables -t filter -I INPUT 2 -p tcp --dport 84 -j DROP用了-I的参数,此规则备插入到了第一条规则和第三条规则之间了。
那么如何对某个规则删除呢,可以使用如下方式来删除
1. iptables -D INPUT -p tcp –dport 8080 -j DROP
2. iptables -F 删所有规则
3. /etc/init.d/iptables restart (用iptables命令行配置的命令都是临时生效)
4. iptables -D INPUT 规则序号
不仅可以对端口配置规则,还可以对网段配置规则
iptables -A INPUT -s 10.0.0.0/24 -j DROP
-s
指定源地址 ,还可以使用不是这个网段的进行操作
iptables -A INPUT ! -s 10.0.0.0/24 -j DROP
控制22端口 eth0网卡进来的数据
iptables -A INPUT -p tcp --dport 22 -i eth0 ! -s 10.0.0.0/24 -j DROP iptables -A INPUT -p tcp --dport 22 -i eth0 ! -s 192.168.1.1 -j DROP
还可以配置端口范围规则
iptables -A INPUT -p tcp --sport 22:80 iptables -A INPUT -p tcp --dport 21,22,23 -j DROP---->错误语法 iptables -I INPUT -p tcp -m multiport --dport 22,23,24,25 -j DROP iptables -I INPUT -p tcp -m multiport ! --dport 22,23,24,25 -j DROP iptables -I INPUT -p tcp --dport 3306:8809 -j ACCEPT iptables -I INPUT -p tcp --dport 18:80 -j DROP <----最佳方法
匹配ICMP
类型,icmp中有很多类型,其中8
代表ping
iptables -A INPUT -p icmp --icmp-type 8 -j DROP
如果有ftp服务的话,就要用到-m state --state参数来配置规则了
iptables -A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT iptables -A OUTPUT -m state --state ESTABLISHED,RELATED -j ACCEPT
参数-m state --state说明:
-m state --state NEW:已经或启动新的连接 ESTABLISHED:已建立的连接 RELATED:正在启动的新连接 INVALID:非法或无法识别的 FTP服务是特殊的,需要配状态连接
限制指定时间包的允许通过数量及并发数,用参数
-m limit --limit n/{second/minute/hour}和
--limit-burst [n],前一个n表示指定时间内的请求速率
“n”
为速率,后面为时间分别为:秒、分、时,后一个n表示在同一时间内允许通过的请求
“n”
为数字,不指定默认为5
配置示例如下:
iptables -I INPUT -s 10.0.1.0/24 -p icmp --icmp-type 8 -m limit --limit 5/min --limit-burst 2 -j ACCEPT
又比如用limit参数来自定义链处理syn攻击
iptables -N syn-flood iptables -A INPUT -i eth0 -syn -j syn-flood iptables -A syn-flood -m limit -limit 5000/s -limit-burst 200 -j RETURN iptables -A syn-flood -j DROP
3、生产环境配置主机防火墙的两种模式
1. 允许所有程序,对操作伤害的进行拒绝操纵 应用场景:企业配置上网网关路由
2. 拒绝所有操作,允许指定的操作 应用场景:服务器主机防火墙
配置一个企业防火墙的步骤如下:
#清空防火墙规则,并设置一些必要的规则 iptables -F iptables -X iptables -Z iptables -A INPUT -p tcp --dport 52113 -s 10.0.0.0/24 -j ACCEPT iptables -A INPUT -i lo -j ACCEPT iptables -A OUTPUT -o lo -j ACCEPT #设置默认规则 iptables -P INPUT DROP iptables -P OUTPUT ACCEPT iptables -P FORWARD DROP #允许合法的进入,比如企业内网络,其他idc机房的网络 iptables -A INPUT -s 124.43.62.96/27 -p all -j ACCEP iptables -A INPUT -s 192.168.1.0/24 -p all -j ACCEPT iptables -A INPUT -s 10.0.0.0/24 -p all -j ACCEPT iptables -A INPUT -s 203.83.24.0/24 -p all -j ACCEPT iptables -A INPUT -s 201.82.34.0/24 -p all -j ACCEPT #提供必要的外部服务 iptables -A INPUT -p tcp --dport 80 -j ACCEPT iptables -A INPUT -p icmp --icmp-type 8 -j ACCEPT #允许关联的状态包 ftp协议 iptables -A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT iptables -A OUTPUT -m state --state ESTABLISHED,RELATED -j ACCEPT
然后用nmap 扫描的主机ip -p 1-65535来查看被扫描主机开放的端口有哪些。
配置好规则后只是当前环境下生效,如果防火墙重启或清除规则命令的话,这些配置的规则就会失效,所以要对配置的规则进行保存处理
命令行执行/etc/init.d/iptables save 配置会自动保存到/etc/sysconfig/iptables文件中。生产环境中如果有个规则要修改的话,可以直接修改/etc/sysconfig/iptables这个文件中的规则即可
案例一:自动封IP:分析web或应用日志或者网络连接状态封掉垃圾IP
#!/bin/sh /bin/netstat -na|grep ESTABLISHED|awk \'{print $5}\'|awk -F: \'print $1\'|sort|uniq -c|sort -rn|head -10|grep -v -E \'192.168|127.0\'|awk \'if ($2!=null && $1>100) {print $2}\'>/home/shell/dropip for i in $(cat /home/shell/dropip) do /sbin/iptables -I INPUT -s $i -j DROP echo "$i is killed at `date`">>/var/log/ddos done
案例二:写一个脚本解决DOS攻击生产案例
提示:根据web日志或者或者网络连接数,监控当某个IP并发连接数或者短时内PV达到100,即调用防火墙命令封掉对应的IP,监控频率每隔3分钟。防火墙命令为:iptables -I INPUT -s 10.0.1.10 -j DROP
本脚本使用测试文件进行编写
#!/bin/sh # [ -f /etc/init.d/functions ] && . /etc/init.d/functions IP_file="/server/scripts/ddos.txt" IP_filter_command="iptables -I INPUT -j DROP -s" IP_recover_command="iptables -D INPUT -j DROP -s" function IP_check(){ grep "EST" ${IP_file}|awk -F "[ |:]+" \'{print $6}\'|sort |uniq -c|sort -rn -k1 > /server/scripts/ip.txt } function IP_filter(){ exec < /server/scripts/ip.txt while read line do IP_count=`echo $line|awk \'{print $1}\'` IP=`echo $line|awk \'{print $2}\'` IP_fil=`iptables -L -n|grep "\b${IP}\b"|wc -l` if [ ${IP_count} -gt 25 -a ${IP_fil} -eq 0 ];then ${IP_filter_command} ${IP} echo "${IP}" >> /server/scripts/ip_filtered.txt action "Filter ${IP}" /bin/true fi done } function IP_recover(){ exec < /server/scripts/ip.txt while read line do IP_count=`echo $line|awk \'{print $1}\'` IP=`echo $line|awk \'{print $2}\'` IP_fil=`iptables -L -n|grep "\b${IP}\b"|wc -l` if [ ${IP_count} -le 25 -a ${IP_fil} -eq 1 ];then ${IP_recover_command} ${IP} echo "${IP}" >> /server/scripts/ip_filtered.txt action "Recover ${IP}" /bin/true fi done } function main(){ case "$1" in filter) IP_check echo "$(date +%F-%H:%M:%S) filtered by $(whoami)" >> /server/scripts/ip_filtered.txt IP_filter ;; recover) IP_check echo "$(date +%F-%H:%M:%S) recovered by $(whoami)" >> /server/scripts/ip_filtered.txt IP_recover ;; *) echo "USAGE:$0 {filter|recover}" exit 1 esac } main $*
4、配置iptables的nat
nat表设置
局域网共享的两条命令方法:
方法1:适合于有固定外网地址的:
iptables -t nat -A POSTROUTING -s 192.168.1.0/24 -o eth0 -j SNAT --to-source 10.0.0.7
(1)-s 192.168.1.0/24 办公室或IDC内网网段。
(2)-o eth0 为网关的外网卡接口。
(3)-j SNAT --to-source 10.0.0.19 是网关外网卡IP地址。
方法2:适合变化外网地址(ADSL):
iptables -t nat -A POSTROUTING -s 192.168.1.0/24 -j MASQUERADE
要使局域网能够共享上网的话,或者说使用nat表做地址转换的话,必要要开启内核转发功能
vim /etc/sysctl.conf net.ipv4.ip_forward = 1 sysctl -p
开启了内核转发功能,别忘了要保证farward也是要被允许的。即:
保证iptables FORWARD要ACCEPT
iptables -P FORWARD ACCEPT
如果客户机需要上网的话,还需要配置默认路由和DNS
#客户机的默认路由配置,指向nat网关的主机地址。例如: route add default gw 172.16.1.5 #对客户机的网卡的dns设置如下: DNS1=202.96.209.5 DNS2=202.96.209.6
配置好默认路由后用route -n来检查本地的路由表
案例:实现把访问nat网关的地址10.0.0.5:80的请求转到web服务的主机地址172.16.1.8:80
iptables -t nat -A PREROUTING -d 10.0.0.5 -p tcp --dport 80 -j DNAT --to-destination 172.16.1.8:80
5、iptables常用企业案例
1、Linux主机防火墙(表:FILTER
控制链:INPUT
)
2、局域网机器共享上网(表:NAT
控制链:POSTROUTING
)
iptables -t nat -A POSTROUTING -s 192.168.1.0/24 -o eth0 -j SNAT --to-source 10.0.0.7
3、外部地址和端口,映射为内部地址和端口(表:NAT
控制的链:PREROUTING
)
iptables -t nat -A PREROUTING -d 10.0.0.7 -p tcp --dport 80 -j DNAT --to-destination 192.168.1.8:9000
iptables 生产应用场景
1)局域网共享
上网(适合做企业内部局域网上网网关,以及IDC机房内网的上网网关[nat POSTROUTING]
)
2)服务器防火墙
功能(适合IDC机房具有外网IP的服务器)(主要是filter INPUT
的控制)
3)把外部IP及端口映射
到局域网内部(可以一对一IP映射,也可以针对某一个端口映射)也可能是IDC把网站的外网VIP及网站端口映射到负载均衡器上(硬件防火墙
)。(nat PREROUTING
)
4)办公路由器+网关功能
(zebra路由+iptables过滤及NAT+squid正向透明代理)80+ntop/iftop/iptraf流量查看+tc/cbq流量控制限速
5)邮件的网关
iptables防火墙的应用
1)主机防火墙
2)网关的应用(IP映射,端口映射
)
3)过滤信息,监控限制流量及员工上网行为
(squid(正向代理缓存加过滤)+ntop(图形流量监控)+通常(流量限制)+iptraf/iftop(流量查看))
如果IPTABLES
的服务器升级内核可以实现类似squid
的过滤功能
4)网关装杀毒软件监听9999端口,(网关杀毒
)
5)结合zebra
配置企业级路由器
问题:如果局域网上网人数太多,那么局域网的ip地址nat地址转换成外网的一个ip的话,可能外网一些web服务会认为这种方式访问是一种恶意攻击,解决办法就是将局域网划分为多个vlan,然后将每个vlan映射到不同的外网ip地址上,这样就保证了多人ip地址nat转换成外网ip不会太多,外网的web也就不认为这是一种恶意攻击而被禁掉。映射多个外网ip示例如下:
iptables -t nat -A POSTROUTING -s 10.0.0.1/255.255.255.0 -o eth0 -j SNAT --to-source 124.42.60.11-124.42.60.16 iptables -t nat -A POSTROUTING -s 172.16.1.0/255.255.255.0 -o eth0 -j SNAT --to-source 124.42.60.103-124.42.60.106
拍错:dmesg里面显示ip_conntrack: table full, dropping packet.
的错误提示.如何解决
这个错误问题为内核需要对防火墙优化,优化参数如下:
net.nf_conntrack_max = 25000000 net.netfilter.nf_conntrack_max = 25000000 net.netfilter.nf_conntrack_tcp_timeout_established = 180 net.netfilter.nf_conntrack_tcp_timeout_time_wait = 120 net.netfilter.nf_conntrack_tcp_timeout_close_wait = 60 net.netfilter.nf_conntrack_tcp_timeout_fin_wait = 120
调整内核参数/etc/sysctl.conf
后,需执行/sbin/sysctl -p
使得修改生效。
强调:如果并发比较大,或者日PV多的情况下,开启防火墙要注意,很可能导致网站访问缓慢
大并发(并发1万,PV日3000万)要么购买硬件防火墙,要么不开iptables防火墙
zebra路由软件部署
zebra部署在linux系统,可以让linux系统作为路由器转发数据包,等同于路由器的作用。
1、下载zebra软件,进行编译安装
wget http://ftp.twaren.net/Unix/NonGNU/quagga/quagga-0.99.20.tar.gz
安装说明:http://www.routingloops.co.uk/cisco/how-to-install-quagga-on-centos-6-5/
编译安装如下:
cd /home/goser/tools tar xf quagga-0.99.20.tar.gz cd quagga-0.99.20 ./configure make && make install
2、生成zebra配置文件
cp /usr/local/etc/zebra.conf.sample /usr/local/etc/zebra.conf
可以查看到zebra的登录秘钥,默认的秘钥为zebra,当然也可以对此默认的秘钥做修改
cat /usr/local/etc/zebra.conf ! -*- zebra -*- ! ! zebra sample configuration file ! ! $Id: zebra.conf.sample,v 1.1 2002/12/13 20:15:30 paul Exp $ ! hostname Router password zebra enable password zebra ! ! Interface\'s description. ! !interface lo ! description test of desc. ! !interface sit0 ! multicast ! ! Static default route sample. ! !ip route 0.0.0.0/0 203.181.89.241 ! !log file zebra.log
3、运行zebra服务
/usr/local/sbin/zebra -d -u root privs_init: could not lookup group quagga
这个提示为:需要quagga做才能运行zebra服务。所以先创建quagga用户组,再运行zebra服务
groupadd quagga /usr/local/sbin/zebra -d -u root
查看zebra服务启动所占用的端口号为2601
netstat -lntup|grep zebra tcp 0 0 0.0.0.0:2601 0.0.0.0:* LISTEN 35351/zebra tcp 0 0 :::2601 :::* LISTEN 35351/zebra
4、通过telnet连接2601端口进入zebra环境,来配置路由即可
telnet localhost 2601 Trying ::1... Connected to localhost. Escape character is \'^]\'. Hello, this is Quagga (version 0.99.20). Copyright 1996-2005 Kunihiro Ishiguro, et al. User Access Verification Password: Router> enable Password: Router# configure terminal Router(config)#
当然也可以通过telnet localhost zebra进入zebra环境。
5、进入zebra环境,配置如下:
#Linux上配置zebra路由: client(config)#int eth0 client(config-if)#ip add 10.1.34.81 255.255.255.0 client(config-if)#int eth1 client(config-if)#ip add 110.233.24.96 255.255.255.224 client(config)#ip route 0.0.0.0 0.0.0.0 10.1.32.1 client(config)#ip route 110.233.24.96/27 eth1