Netfilter/Iptables(以下简称Iptables)是unix/linux自带的一款优秀且开放源代码的完全自由的基于包过滤的防火墙工具,它的功能十分强大,使用非常灵活,可以对流入和流出服务器的数据包进行很精细的控制。
iptables是linux2.4及2.6内核中集成的服务。 iptables主要工作在OSI七层的二、三、四层,如果重新编译内核,iptables也可以支持7层控制]
#学好iptables的基础: 1、OSI7层模型以及不同层对应哪些协议? 2、TCP/IP三次握手,四次断开的过程,TCP HEADER,状态转换 3、常用的服务端口要非常清楚了解。 4、常用服务协议原理http协议,icmp协议。 #企业中安全配置原则: 1、尽可能不给服务器配置外网IP,可以通过代理转发或者通过防火墙映射。 2、并发不是特别大情况有外网IP,可以开启防火墙服务。 3、大并发的情况,不能开iptables,影响性能,利用硬件防火墙提升架构安全。Copy to clipboardErrorCopied
#容器:装东西的器皿,docker容器技术,将镜像装在了一个系统中,这个系统就称为容器 iptables称为一个容器---装着防火墙的表 防火墙的表又是一个容器---装着防火墙的链 防火墙的链也是一个容器---装着防火墙的规则 iptables---表---链---规则 规则:防火墙一条一条安全策略 #防火墙匹配规则流程: 1. 防火墙是层层过滤的,实际是按照配置规则的顺序从上到下,从前到后进行过滤的。 2. 如果匹配上规则,即明确表示是阻止还是通过,数据包就不再向下匹配新的规则。 3. 如果规则中没有明确表明是阻止还是通过的,也就是没有匹配规则,向下进行匹配,直到匹配默认规则得到明确的阻止还是通过。 4. 防火墙的默认规则是所有规则执行完才执行的。Copy to clipboardErrorCopied
#应用场景 1.主机安全 2.内部共享上网 3.端口或IP映射 #iptables工作流程 1.匹配规则是从上往下的依次执行的 2.只要匹配上规则,就不会再往下执行 3.如果都没有匹配到规则,就执行默认的规则 4.防火墙默认规则最后执行,默认允许所有 #注意:匹配越多的规则越往前放
iptables 是集成在 Linux 内核中的包过滤防火墙系统,使用 iptables 可以添加、删除具体的过滤规则,iptables 默认维护着 4 个表和 5 个链,所有的防火墙策略规则都被分别写入这些表与链中
#"四表"是指iptables 的功能: 默认的 iptables规则表有filter表(过滤规则表)、nat 表(地址转换规则表)、mangle(修改数据标记位规则表)、raw(跟踪数据表规则表) filter 表:控制数据包是否允许进出及转发,可以控制的链路有 INPUT、FORWARD 和 OUTPUT。 nat 表:控制数据包中地址转换,可以控制的链路有 PREROUTING、INPUT、OUTPUT 和 POSTROUTING。 mangle:修改数据包中的原数据,可以控制的链路有 PREROUTING、INPUT、OUTPUT、FORWARD 和 POSTROUTING。 raw:控制 nat 表中连接追踪机制的启用状况,可以控制的链路有 PREROUTING、OUTPUT。 #"五链"是指内核中控制网络的 NetFilter 定义的 5 个规则链,每个规则表中包含多个数据链: INPUT(入站数据过滤)、OUTPUT(出站数据过滤)、FORWARD(转发数据过滤)、PREROUTING(路由前过滤)和POSTROUTING(路由后过滤),防火墙规则需要写入到这些具体的数据链中,可以看出,如果是外部主机发送数据包给防火墙本机,数据将会经过 PREROUTING 链与 INPUT 链;如果是防火墙本机发送数据包到外部主机,数据将会经过 OUTPUT 链与 POSTROUTING 链;如果防火墙作为路由负责转发数据,则数据将经过 PREROUTING 链、FORWARD 链以及 POSTROUTING 链
Linux 防火墙的过滤框架
#四表: 1.Filter表 2.NAT表 3.Managle表 4.Raw表 #五链: 1.INPUT 2.FORWARD 3.OUTPUT 4.PREROUTING 5.POSTRUTING
1、#Filter:实现防火墙安全过滤功能 INPUT 对于指定到本地套接字的包,即到达本地防火墙服务器的数据包 外面---->(门)房子iptables FORWARD 路由穿过的数据包,即经过本地防火墙服务器的数据包 外面-----(前门)房子(后门)---房子 OUTPUT 本地创建的数据包 外面<-----(门)房子iptables 2、#NAT:实现将数据包中IP地址或者端口信息,内网到外网进行改写/外网到内网进行改写 PREROUTING 一进来就对数据包进行改变 在路由之前,进行数据包IP地址或端口信息的转换 OUTPUT 本地创建的数据包在路由之前进行改变 本地防火墙要出去的流量进行相应转换(了解) POSTROUTING 在数据包即将出去时改变数据包信息 在路由之后,进行数据包IP地址或端口信息的转换 SNAT 和 DNAT 是 iptables 中使用 NAT 规则相关的的两个重要概念。如上图所示,如果内网主机访问外网而经过路由时,源IP会发生改变,这种变更行为就是SNAT;反之,当外网的数据经过路由发往内网主机时,数据包中的目的IP (路由器上的公网IP) 将修改为内网IP,这种变更行为就是DNAT #注: 在nat server 中,先更改配置文件,/etc/sysctl.conf 中改为 net.ipv4.ip_forward = 1 修改完成后,命令行sysctl -p 让其全部执行生效 3、#Managle:对数据进行标记 4、#Raw:将数据包一些标记信息进行拆解Copy to clipboardErrorCopied
[root@web02 ~]# yum install -y iptables-services
[root@m01 ~]# modprobe ip_tables [root@m01 ~]# modprobe iptable_filter [root@m01 ~]# modprobe iptable_nat [root@m01 ~]# modprobe ip_conntrack [root@m01 ~]# modprobe ip_conntrack_ftp [root@m01 ~]# modprobe ip_nat_ftp [root@m01 ~]# modprobe ipt_state #查看加载的模块 [root@m01 ~]# lsmod | egrep 'filter|nat|ipt'
[root@web02 ~]# systemctl stop firewalld [root@web02 ~]# systemctl disable firewalld Removed symlink /etc/systemd/system/multi-user.target.wants/firewalld.service. Removed symlink /etc/systemd/system/dbus-org.fedoraproject.FirewallD1.service. [root@web02 ~]# systemctl start iptables.service
-A --- 表示将规则添加到指定链上 -I --- 表示将规则插入到指定链上 -D --- 表示将规则从指定链上删除 -R --- 表示将规则信息进行修改 -p --- 指定相应服务协议信息(tcp udp icmp all) --dport --- 表示指定目标端口信息 --sport --- 表示指定源端口号信息 -j --- 指定对相应匹配规则执行什么操作(ACCEPT DROP REJECT REDIRECT) ACCEPT 允许通过 DROP 直接拒绝 REJECT 委婉拒绝 REDIRECT 重定向 -s --- 指定匹配的源地址网段信息,或者匹配的主机信息 -d --- 指定匹配的目标地址网段信息,或者匹配的主机信息 -i --- 指定匹配的进入流量接口信息 只能配置在INPUT链上 -o --- 指定匹配的发出流量接口信息 只能配置在OUTPUT链上 -m --- 指定应用扩展模块参数 multiport --- 可以匹配多个不连续端口信息 Copy to clipboardErrorCopied
iptables -F --- 清除防火墙默认规则 iptables -X --- 清除防火墙自定义链 iptables -Z --- 清除防火墙技术器信息Copy to clipboardErrorCopied
iptables -L --- -L 以列表形式显示所有规则信息 iptables -L -n --- -n 以数字形式显示IP地址或端口信息,不要转换为字符串显示 iptables -t nat -L -n --- -t 表示指定查看或者配置相应的表 iptables -L -n -v --- -v 表示显示详细规则信息,包含匹配计数器数值信息 iptables -L -n --line-number --- --line-number 显示规则序号信息Copy to clipboardErrorCopied
iptables -t filter -A INPUT -p tcp --dport 22 -j DROP --- -A 表示添加规则到相应链上,默认表示添加规则到结尾 iptables -t filter -D INPUT -p tcp --dport 22 -j DROP --- -D 表示删除规则从相应链上。 iptables -t filter -D INPUT 规则序号 iptables -t filter -I INPUT -p tcp --dport 22 -j DROP --- -I 表示插入规则到相应链上,默认表示插入规则到首部 iptables -t filter -I INPUT 3 -p tcp --dport 22 -j DROP --- 指定规则插入位置 iptables -t filter -R INPUT 6 -p tcp --dport 8080 -j DROP --- -R 指定将配置好的规则信息进行替换Copy to clipboardErrorCopied
iptables -t filter -A INPUT -s 10.0.0.0/24 -p tcp --dport 22 -j DROP iptables -t filter -A INPUT -s 10.0.0.9 -p tcp --dport 22 -j DROP iptables -t filter -A INPUT -i eth0 -s 10.0.0.9 -p tcp --dport 22 -j DROP Copy to clipboardErrorCopied
10.0.0.1 10.0.0.253 10.0.0.9(只允许) iptables -t filter -A INPUT -s 10.0.0.9 -p tcp --dport 22 -j ACCEPT iptables -t filter -A INPUT -s 10.0.0.0/24 -p tcp --dport 22 -j DROP iptables -t filter -A INPUT ! -s 10.0.0.9 -p tcp --dport 22 -j ACCEPT 通过利用 !进行规则取反,进行策略控制Copy to clipboardErrorCopied
iptables -A INPUT -s 10.0.0.9 -p tcp --dport 22:80 -j DROP --- 匹配连续的端口号访问 iptables -A INPUT -s 10.0.0.9 -m multiport -p tcp --dport 22,24,25 -j DROP --- 匹配不连续的端口号访问 Copy to clipboardErrorCopied
#实现ping功能测试链路是否正常,基于icmp协议实现的 icmp协议有多种类型: icmp-type 8:请求类型 icmp-type 0:回复类型 #实践01:实现禁止主机访问防火墙服务器(禁ping) iptables -A INPUT -p icmp --icmp-type 8 -j DROP iptables -A OUTPUT -p icmp --icmp-type 0 -j DROP #实践02:实现禁止防火墙访问主机服务器(禁ping) iptables -A OUTPUT -p icmp --icmp-type 8 -j DROP iptables -A INPUT -p icmp --icmp-type 0 -j DROP #实践03:所有icmp类型都禁止 iptables -A INPUT -p icmp -m icmp --icmp-type any -j DROP iptables -A OUTPUT -p icmp -m icmp --icmp-type any -j DROP #实践04:实现防火墙状态机制控制 NEW: 发送数据包里面控制字段为syn=1,发送第一次握手的数据包 ESTABLISHED: 请求数据包发出之后,响应回来的数据包称为回复的包 RELATED: 基于一个连接,然后建立新的连接 INVALID: 无效的的数据包,数据包结构不符合正常要求的 iptables -A INPUT -m state --state NEW,ESTABLISHED,RELATED -j ACCEPT Copy to clipboardErrorCopied
# 将38080端口转发至本机的80端口 [root@web01 ~]# iptables -t nat -A PREROUTING -p tcp --dport 38080 -j REDIRECT --to-port 80 [root@web01 ~]# iptables -t nat -A OUTPUT -p tcp --dport 80 -j DNAT --to-destination 172.16.1.8
[root@web02 ~]# iptables -nvL #查看防火墙状态 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
[root@web02 ~]# iptables -nL -t nat #查看防火墙规则,指定表 Chain PREROUTING (policy ACCEPT) target prot opt source destination Chain INPUT (policy ACCEPT) target prot opt source destination Chain OUTPUT (policy ACCEPT) target prot opt source destination Chain POSTROUTING (policy ACCEPT) target prot opt source destination [root@web02 ~]#
#删除链中所有的规则 [root@web02 ~]# iptables -F #删除用户定义的链 [root@web02 ~]# iptables -X #规则计数器清零 [root@web02 ~]# iptables -Z
[root@web02 ~]# iptables -t filter -A INPUT -p tcp --dport 22 -j DROP iptables #命令 -t #指定表 filter #表名字 -A #添加规则至链的最后 INPUT #链名字 -p #指定协议 tcp #tcp协议 --dport #指定端口 -j #指定动作 DROP #丢弃
[root@web02 ~]# iptables -nL --line-numbers Chain INPUT (policy ACCEPT) num target prot opt source destination 1 ACCEPT tcp -- 0.0.0.0/0 0.0.0.0/0 tcp dpt:22 2 DROP tcp -- 0.0.0.0/0 0.0.0.0/0 tcp dpt:3306 Chain FORWARD (policy ACCEPT) num target prot opt source destination Chain OUTPUT (policy ACCEPT) num target prot opt source destination [root@web02 ~]# [root@web02 ~]# iptables -D INPUT 2
[root@web02 ~]# iptables -t filter -A INPUT -p tcp --dport 3306 -j DROP
#配置访问抛弃 [root@web02 ~]# iptables -t filter -A INPUT -p tcp -s 10.0.0.7 -i eth0 -j DROP -s 指定源地址 -i 指定网卡 #测试访问 [root@web01 ~]# curl 10.0.0.8 curl: (7) Failed connect to 10.0.0.8:80; Connection timed out #配置访问拒绝 [root@web02 ~]# iptables -t filter -A INPUT -p tcp -s 10.0.0.9 -i eth0 -j REJECT #访问测试 [root@web03 ~]# curl 10.0.0.8 curl: (7) Failed connect to 10.0.0.8:80; Connection refused
[root@web02 ~]# iptables -t filter -A INPUT -p tcp -s 10.0.0.0/24 -i eth0 -j DROP
[root@web02 ~]# iptables -t filter -A INPUT -p tcp ! -s 10.0.0.1 -i eth0 -j DROP
#拒绝多个端口访问,可以使用逗号隔开 [root@web02 ~]# iptables -t filter -A INPUT -p tcp -m multiport --dport 21,22,23,24 -j DROP -m #指定扩展项 multiport #多端口匹配 #写端口范围可以使用 : 在端口之间 [root@web02 ~]# iptables -t filter -A INPUT -p tcp --dport 22:100 -j DROP
1)#考虑防火墙开在哪台机器上 2)#该机器部署了什么服务 nginx keepalived 3)#服务开启的是什么端口 80 443 22 4)#默认规则为所有都拒绝
#允许访问80和443 iptables -I INPUT -p tcp -m multiport --dport 80,443 -j ACCEPT -I 添加规则至前面 #只允许跳板机连接22端口 iptables -A INPUT -p tcp -s 172.16.1.61 --dport 22 -j ACCEPT #禁止ping iptables -A INPUT -p icmp --icmp-type 8 ! -s 172.16.1.61 -j DROP #允许访问外网 iptables -A INPUT -i eth0 -j ACCEPT #默认拒绝所有 iptables -P INPUT DROP -P #更改policy默认策略
重要问题(实战坑)
#根据以上配置方法,最后一步设置了默认拒绝所有规则,那么跳板机连接主机后,千万不要进行清理防火墙的操作,否则就什么都连接不上了,因为清理防火墙规则不会清理'iptables -P INPUT DROP'这一条规则,那么防火墙默认规则就变成所有都dorp了 #解决方法: 需要到虚拟机或者物理机上操作 1.iptables -P INPUT ACCEPT 2.systemctl restart iptables 3.重启物理机(有风险) #避免方法: 1)将 iptables -P INPUT ACCEPT 加到定时任务(测试阶段可用该方法) * * * * * /usr/sbin/iptables -P INPUT ACCEPT 2)其他环境测试,测试没有问题后,复制所有规则到环境执行 3)配置前,先保存之前的防火墙规则,根据以前的规则修改 [root@web01 ~]# iptables-save > iptables_m01_20200116 修改后导入规则 [root@web01 ~]# iptables-restore < iptables_m01_20200116
iptables -F iptables -X iptables -Z iptables -A INPUT -p tcp -m multiport --dport 80,443 -j ACCEPT iptables -A INPUT -p tcp --dport 22 -j ACCEPT iptables -A INPUT -s 10.0.1.0/24 -j ACCEPT iptables -A INPUT -s 172.16.1.0/24 -j ACCEPT iptables -A INPUT -i lo -j ACCEPT iptables -P INPUT DROP iptables -P FORWARD DROP iptables -P OUTPUT ACCEPT iptables -nL
#把规则写入iptables配置文件 [root@m01 ~]# vim /etc/sysconfig/iptables # sample configuration for iptables service # you can edit this manually or use system-config-firewall # please do not ask us to add additional ports/services to this default configuration *filter :INPUT ACCEPT [0:0] :FORWARD ACCEPT [0:0] :OUTPUT ACCEPT [0:0] -A INPUT -m state --state RELATED,ESTABLISHED -j ACCEPT -A INPUT -p icmp -j ACCEPT -A INPUT -i lo -j ACCEPT -A INPUT -p tcp -m state --state NEW -m tcp --dport 22 -j ACCEPT -A INPUT -j REJECT --reject-with icmp-host-prohibited -A FORWARD -j REJECT --reject-with icmp-host-prohibited COMMIT #保存已经配置的规则 [root@m01 ~]# service iptables save iptables: Saving firewall rules to /etc/sysconfig/iptables:[ OK ]
echo 'net.ipv4.ip_forward = 1' >> /etc/sysctl.conf sysctl -p iptables -A FORWARD -i eth1 -s 172.16.1.0/24 -j ACCEPT iptables -A FORWARD -o eth0 -s 172.16.1.0/24 -j ACCEPT iptables -A FORWARD -i eth0 -d 172.16.1.0/24 -j ACCEPT iptables -A FORWARD -o eth1 -d 172.16.1.0/24 -j ACCEPT iptables -t nat -A POSTROUTING -s 172.16.1.0/24 -j SNAT --to-source 10.0.0.61 -j 指定动作 SNAT 源地址转换 --to-source 源地址转换指向
[root@web01 ~]# cat /etc/sysconfig/network-scripts/ifcfg-eth1 GATEWAY=172.16.1.61 DNS1=223.5.5.5 [root@web01 ~]# ifdown eth1 && ifup eth1
[root@m01 ~]# iptables -t nat -A PREROUTING -d 10.0.0.61 -p tcp --dport 5555 -j DNAT --to-destination 172.16.1.7:22 [root@m01 ~]# iptables -t nat -A POSTROUTING -s 172.16.1.0/24 -j SNAT --to-source 10.0.0.61 -d 指定目的ip DNAT 目标地址转换 --to-destination 目标地址转换指向
[root@m01 ~]# iptables -t nat -A PREROUTING -d 10.0.1.61 -j DNAT --to-destination 172.16.1.7 iptables -A FORWARD -i eth1 -s 172.16.1.0/24 -j ACCEPT iptables -A FORWARD -o eth0 -s 172.16.1.0/24 -j ACCEPT iptables -A FORWARD -i eth0 -d 172.16.1.0/24 -j ACCEPT iptables -A FORWARD -o eth1 -d 172.16.1.0/24 -j ACCEPT iptables -t nat -A POSTROUTING -s 172.16.1.0/24 -j SNAT --to-source 10.0.0.61
1、详述iptales工作流程以及规则过滤顺序? 2、iptables有几个表以及每个表有几个链? #四表五链 3、iptables的几个表以及每个表对应链的作用,对应企业应用场景? 4、画图讲解iptables包过滤经过不同表和链简易流程图并阐述。 5、请写出查看iptables当前所有规则的命令。 6、禁止来自10.0.0.188 ip地址访问80端口的请求 7、如何使在命令行执行的iptables规则永久生效? #(service iptables save) 8、实现把访问10.0.0.3:80的请求转到172.16.1.17:80 #(iptables -t nat -A OUTPUT -p tcp --dport 80 -j DNAT --to-destination 172.16.1.8) 9、实现172.16.1.0/24段所有主机通过124.32.54.26外网IP共享上网 10、写一个防火墙配置脚本,只允许远程主机访问本机的80端口 #iptables -t filter -A INPUT -p tcp --dport 22 -j ACCEPT #iptables -t filter -A INPUT -j DROP 11、写一个脚本解决DOS攻击生产案例 #!/bin/bash #步骤: # 写一个脚本解决DOS攻击生产案例 # 过滤出IP及IP重复次数 # grep -oE "([0-9]{1,3}\.){3}[0-9]{1,3}" /var/log/nginx/access.log # awk '{print $1}' /var/log/nginx/access.log # awk '{print $1}' /var/log/nginx/access.log | uniq -c | sort -n # 每一分钟怎么做? # 将统计结果超过100的,屏蔽掉 DIR="/var/log/nginx/access.log" IPS_DIR="/var/log/nginx/IPS.txt" DATE=`date +%F_%H_%M` BACKUP_DIR="/var/log/nginx/backup" NEW_FILE_NAME=$BACKUP_DIR/$DATE.txt if [ ! -d $BACKUP_DIR ];then mkdir -pv $BACKUP_DIR fi cp -r $DIR $NEW_FILE_NAME >$DIR awk '{print $1}' $NEW_FILE_NAME | sort | uniq -c | sort -n > ${IPS_DIR} while read line do COUNT=`echo $line | awk '{print $1}'` IP=`echo $line | awk '{print $2}'` if [ $COUNT -gt 100 ];then /usr/sbin/iptables -t filter -A INPUT -s $IP -p tcp -j DROP fi done < ${IPS_DIR}
/nginx/access.log | uniq -c | sort -n
DIR="/var/log/nginx/access.log"
IPS_DIR="/var/log/nginx/IPS.txt"
DATE=date +%F_%H_%M
BACKUP_DIR="/var/log/nginx/backup"
NEW_FILE_NAME=
B
A
C
K
U
P
D
I
R
/
BACKUP_DIR/
BACKUPDIR/DATE.txt
if [ ! -d $BACKUP_DIR ];then
mkdir -pv $BACKUP_DIR
fi
cp -r $DIR $NEW_FILE_NAME
$DIR
awk ‘{print $1}’ $NEW_FILE_NAME | sort | uniq -c | sort -n > ${IPS_DIR}
while read line
do
COUNT=`echo $line | awk '{print $1}'`
IP=echo $line | awk '{print $2}'
if [ $COUNT -gt 100 ];then
/usr/sbin/iptables -t filter -A INPUT -s $IP -p tcp -j DROP
fi
done < ${IPS_DIR}