简介

网络中的防火墙,是一种将内部和外部网络分开的方法,是一种隔离技术。防火墙在内网与外网通信时进行访问控制,依据所设置的规则对数据包作出判断,最大限度地阻止网络中不法分子破坏企业网络,从而加强了企业网络安全。

防火墙的分类

硬件防火墙,如思科的ASA防火墙,H3C的Secpath防火墙等
软件防火墙,如iptables、firewalld等

Linux包过滤防火墙简介

1、Linux操作系统中默认内置一个软件防火墙,即iptables防火墙
2、netfilter位于Linux内核中的包过滤功能体系,又称为模块,并且自动加载,是内核很小的一部分称为Linux防火墙的“内核态”,注意,真正生效的是内核态。
3、iptables位于/sbin/iptables,用来管理防火墙规则的工具称为Linux防火墙的“用户态”。仅仅是管理工具,真正起作用的是内核态。
纯干货详解iptables工作原理以及使用方法

iptables规则链

规则的作用:对数据包进行过滤或处理
链的作用:容纳各种防火墙规则,相当于容器
链的分类依据:处理数据包的不同时机
系统默认自带的5种规则链:
INPUT:处理入站数据包
OUTPUT:处理出站数据包
FORWARD:处理转发数据包
POSTROUTING:在进行路由选择后处理数据包(出站过滤)
PREROUTING:在进行路由选择前处理数据包(入站过滤)
注意:POSTROUTING、PREROUTING在做NAT时所使用

iptables规则表

表的作用:容纳各种规则链
表的划分依据:防火墙规则的作用相似,以功能进行划分
默认包括4个规则表:
raw表:确定是否对该数据包进行状态跟踪
mangle:为数据包设置标记,标记之后可以分流、限流
nat表:修改数据包中的源、目标IP地址或端口
filter表:确定是否放行该数据包,即过滤
注意:最终规则是存到链里面,最小的容器是链表里面会存放链,链是一条又一条的规则,一条一条的存

五链四表图

纯干货详解iptables工作原理以及使用方法
raw表:包含了PREROUTING和OUTPUT。注意只能在这两个时机进行跟踪。
mangle表:包含了PREROUTING、INPUT、FORWARD、OUTPUT、POSTROUTING。注意在这5个时机做标记。
nat表:包含了PREROUTING、OUTPUT、POSTROUTING。注意在这3个时机进行ip或端口修改。
filter表:包含了INPUT、FORWARD、OUTPUT。注意在这3个时机进行过滤数据。

iptables匹配流程

规则表之间的顺序:raw→mangle→nat→filter,即先做状态跟踪→在做标记→在做修改源目IP或端口→在做是否过滤

规则链之间的顺序:

入站:PREROUTING→INPUT 路由前发现是自己的,直接进站
出站:OUTPUT→POSTROUTING
转发:PREOUTING→FORWARD→POSTROUTING
注意:PREROUTING和POSTROUTING是最外围,规则链是靠时机分的,分为了入站,出站,转发三个时机

规则链内的匹配顺序:

按顺序依次检查,匹配即停止(LOG策略外)
若找不到相匹配规则,按该链的默认策略处理

匹配流程示意图

纯干货详解iptables工作原理以及使用方法

主机型防火墙:

1、入站:数据包发来,路由前,先做跟踪,再做标记,修改,查看路由,如果是发往本机的直接往上走,进站前标记,然后出站过滤
2、出站:出站和路由后,指的是最上面的路由选择,本机选择之后先经过跟踪→标记→修改→是否过滤,出站之后是mangle表的路由后→nat表的路由后

网络型防火墙:

3、转发:数据进来以后,经过路由前raw、mangle、nat,路由前完成之后进行选择,发现此数据是需要发到别的地方,非本地,通过forward,经过mangle的forward,filter的forward,还要经过路由后标记、修改IP及端口,结束

iptables命令语法

  • 语法构成
    iptables [-I 链名] [-t 表名] [-p 条件] [-j 控制类型]
  • 参数详解
    -A:在链的末尾追加一条规则
    -I:在链的开头(或指定序号)插入一条规则
    -L:列出所有的规则条目
    -n:以数字形式显示规则信息(协议解释成数字)
    -v:以更详细的方式显示规则信息
    --line-numbers:查看规则时,显示规则的序号
    -D:删除链内指定序号(或内容)的一条规则
    -F:清空所有的规则
    -P:为指定的链设置默认规则(一条没有匹配上,按照默认规则走)
  • 注意事项
    不指定表名时,默认指filter表
    不指定链名时,默认指定表内的所有链
    除非设置链的默认策略,否则必须指定匹配条件
    选项、链名、控制类型使用大写字母,其余均为小写
  • 数据包的常见控制类型
    ACCEPT:允许通过
    DROP:直接丢弃,不给出任何回应
    REJECT:拒绝通过,必要时会给出提示
    LOG:记录日志信息,然后传给下一跳规则继续匹配

规则的匹配类型

1、通用匹配(可直接使用,不依赖于其他条件或扩展)

常见的通用匹配条件
协议匹配:-p 协议名
地址匹配:-s 源地址、-d 目的地址
接口匹配:-i 入站网卡、-o 出站网卡

2、隐含匹配(要求以特定的协议匹配作为前提)

常见的通用匹配条件
端口匹配:--sport源端口、--dport目的端口
TCP标记匹配:--tcp-flags 检查范围 被设置的标记
ICMP类型匹配:--icmp-type ICMP类型

3、显式匹配(要求以"-m扩展模块”的形式明确指出类型)

常见的通用匹配条件
多端口匹配:-m multiport --sports 源端口列表;-m multiport --dports 目的端口列表
IP范围匹配:-m iprange-src-range IP范围
MAC地址匹配:-m mac --mac-source MAC地址
状态匹配:-m state --state 连接状态

实验环境

  • 系统环境:centos6.5
  • 内网IP:192.168.100.77/24
  • 公网IP:172.16.16.101/24
  • 网关防火墙:
    公网网网卡:eth0:172.16.16.254
    内网网卡:eth1:192.168.100.254

实验论证

准备工作

1、清空防火墙规则、关闭Selinux

[root@Init5 ~]# vim /etc/sysconfig/selinux
纯干货详解iptables工作原理以及使用方法

[root@Init5 ~]# reboot #重启

[root@Init5 ~]# /etc/init.d/iptables stop #清空防火墙规则

2、查看网卡信息

[root@Init5 ~]# vim /etc/sysconfig/network-scripts/ifcfg-eth0 #查看网关防火墙公网网卡信息
纯干货详解iptables工作原理以及使用方法

[root@Init5 ~]# vim /etc/sysconfig/network-scripts/ifcfg-eth1 #查看网关防火墙内网网卡信息
纯干货详解iptables工作原理以及使用方法

[root@client ~]# vim /etc/sysconfig/network-scripts/ifcfg-eth0 #查看公网网卡信息

纯干货详解iptables工作原理以及使用方法

[root@redhat6 ~]# vim /etc/sysconfig/network-scripts/ifcfg-eth0 #查看内网网卡信息
纯干货详解iptables工作原理以及使用方法

3、开启网关防火墙路由功能

[root@Init5 ~]# vim /etc/sysctl.conf #配置一些系统信息以及内核参数

纯干货详解iptables工作原理以及使用方法

[root@Init5 ~]# sysctl -p #重新加载配置文件

4、测试互联互通

[root@client ~]# ping -c 3 172.16.16.254 #公网服务器ping公网网关
[root@client ~]# ping -c 3 192.168.100.77 #公网服务器ping内网服务器

纯干货详解iptables工作原理以及使用方法

一、iptables语法详解

1、内网ICMP设置DROP,网关防火墙ping是什么效果?

[root@redhat6 ~]# iptables -I INPUT -p ICMP -j DROP #拒绝其他主机ping通此主机
[root@Init5 ~]# ping 192.168.100.77

纯干货详解iptables工作原理以及使用方法

[root@Init5 ~]# /etc/init.d/iptables stop #网关防火墙清空iptables规则

2、内网ICMP设置REJECT,网关防火墙ping是什么效果?

[root@redhat6 ~]# iptables -I INPUT -p ICMP -j REJECT #内网设置REJECT
[root@Init5 ~]# ping -c 4 192.168.100.77

纯干货详解iptables工作原理以及使用方法

[root@Init5 ~]# /etc/init.d/iptables stop #网关防火墙清空iptables规则

3、内网ICMP设置LOG,内网网关ping是什么效果?

[root@redhat6 ~]# iptables -I INPUT -j LOG #内网设置LOG
[root@redhat6 ~]# tail -f /var/log/messages #监视日志文件
[root@Init5 ~]# ping -c 4 192.168.100.77 #网关服务器ping内网

此时切换内网,查看监视日志
纯干货详解iptables工作原理以及使用方法

[root@Init5 ~]# /etc/init.d/iptables stop #网关防火墙清空iptables规则

4、设置默认规则

[root@redhat6 ~]# iptables -I INPUT -p tcp --dport 22 -j ACCEPT #为了连接Xshell远程连接,将22端口设置为允许
[root@redhat6 ~]# iptables -P INPUT DROP #默认除了22端口,其余走默认,全部禁掉,根据业务需要,再将允许的端口添加

5、添加iptables新规则

[root@redhat6 ~]# iptables -I INPUT -p tcp --dport 80 -j ACCEPT #在第一行插入此规则
[root@redhat6 ~]# iptables -L -n --line-numbers

纯干货详解iptables工作原理以及使用方法

[root@redhat6 ~]# iptables -A INPUT -p tcp --dport 21 -j DROP #在行尾追加此规则
纯干货详解iptables工作原理以及使用方法

6、查看防火墙规则

[root@redhat6 ~]# iptables -L
纯干货详解iptables工作原理以及使用方法

[root@redhat6 ~]# iptables -L -n
纯干货详解iptables工作原理以及使用方法

[root@redhat6 ~]# iptables -L -n --line-numbers
纯干货详解iptables工作原理以及使用方法

7、删除、清空规则

[root@redhat6 ~]# iptables -D INPUT -p tcp --dport 21 -j DROP #指定防火墙内容规则进行删除
[root@redhat6 ~]# iptables -D INPUT 1 #指定序列进行删除
[root@redhat6 ~]# iptables -P INPUT ACCEPT #注意一下哈,我之前设了一个默认是拒绝所有入站,现在改掉,否则演示清空规则的时候,使用xshell连接,会直接被踢掉
[root@redhat6 ~]# iptables -F #不加-t,默认过滤,相当与-t filter,也就是INPUT OUTPUT FWORD都清空

#继续添加一些新规则

[root@redhat6 ~]# iptables -I OUTPUT -p icmp -j DROP
[root@redhat6 ~]# iptables -I INPUT -p icmp -j DROP
[root@redhat6 ~]# iptables -n -L --line-numbers

纯干货详解iptables工作原理以及使用方法

[root@redhat6 ~]# iptables -F OUTPUT #清除所有出站
[root@redhat6 ~]# iptables -n -L --line-numbers

纯干货详解iptables工作原理以及使用方法

二、通用匹配

1、协议匹配:-p 协议名

[root@redhat6 ~]# /etc/init.d/iptables stop #实验之前清空防火墙

①.内网设置

[root@redhat6 ~]# iptables -I INPUT -p tcp --dport 22 -j ACCEPT #允许我连接Xshell
[root@redhat6 ~]# iptables -P INPUT DROP #进站默认一律丢弃
[root@redhat6 ~]# iptables -P FORWARD DROP #通过此主机进行数据转发,又不是网关防火墙先丢弃

[root@redhat6 ~]# /etc/init.d/httpd start #开启Web服务

[root@redhat6 ~]# iptables -I INPUT -p tcp --dport 80 -j ACCEPT #虽然之前进站默认设置的是丢弃,但是此时添加这条语句也是可以访问Web服务器,用什么开启什么就可以了

②.网关设置

[root@redhat6 ~]# iptables -I INPUT -p tcp --dport 22 -j ACCEPT #先保证Xshell可以使用
[root@redhat6 ~]# iptables -P INPUT DROP #目前为止除了22端口,其余进站全禁掉

③.公网访问内网

[root@client ~]# elinks 192.168.100.77

纯干货详解iptables工作原理以及使用方法

④.网关添加新规则

[root@Init5 ~]# iptables -P FORWARD DROP #将数据转发默认全部丢弃掉

⑤.公网再次访问内网

[root@client ~]# elinks 192.168.100.77
纯干货详解iptables工作原理以及使用方法

2、地址匹配:-s 源地址、-d 目的地址

①.网关设置

[root@Init5 ~]# iptables -I FORWARD -d 192.168.100.77 -p tcp -j ACCEPT #要注意,即使添加了此项,外网主机依然无法访问,此时只允许了去访问了,并没有允许数据包回来
[root@Init5 ~]# iptables -I FORWARD -s 192.168.100.77 -p tcp -j ACCEPT #添加此项允许数据包回来

②.公网再次访问内网

[root@client ~]# elinks 192.168.100.77
纯干货详解iptables工作原理以及使用方法

3、接口匹配:-i 入站网卡、-o 出站网卡

①.网关设置

[root@Init5 ~]# iptables -t nat -A PREROUTING -i eth0 -d 172.16.16.254 -p tcp --dport 80 -j DNAT --to-destination 192.168.100.77
#这里做了一个DNAT地址转换,下一个帖子会详细介绍,是将公网网关172.16.16.254/24转换成192.168.100.77/24内网IP地址访问

[root@Init5 ~]# iptables -I FORWARD -i eth0 -p tcp --dport 80 -j ACCEPT #这里设置了允许入站网卡eth0转发tcp协议80端口的服务。此时是允许访问内网主机
[root@Init5 ~]# iptables -I FORWARD -i eth0 -p tcp --dport 80 -j DROP #将丢弃80服务的规则放在第一条

②.公网访问内网

[root@client ~]# elinks 172.16.16.254
纯干货详解iptables工作原理以及使用方法

③.网关设置

[root@Init5 ~]# iptables -D FORWARD -i eth0 -p tcp --dport 80 -j DROP #清除丢弃访问80服务的规则

④.公网访问内网

[root@client ~]# elinks 172.16.16.254
纯干货详解iptables工作原理以及使用方法

⑤.网关设置

[root@Init5 ~]# iptables -I FORWARD -s 192.168.100.0/24 -p tcp --sport 80 -j DROP
[root@Init5 ~]# iptables -I FORWARD -o eth0 -s 192.168.100.0/24 -p tcp --sport 80 -j DROP
#注意一下,在转发过程中,源地址是192.168.100.0/24网段,源端口是80的,全部禁掉

⑥.公网再次访问内网

[root@client ~]# elinks 172.16.16.254 #无法访问

三、隐含匹配

1、端口匹配:--sport源端口、--dport目的端口

[root@Init5 ~]# /etc/init.d/iptables stop #实验之前清空防火墙

①.网关设置(基本上DNS上在网关型防火墙设置如下)

[root@Init5 ~]# iptables -I FORWARD -s 192.168.1.0/24 -p udp --dport 53 -j ACCEPT
[root@Init5 ~]# iptables -I FORWARD -d 192.168.1.0/24 -p udp --sport 53 -j ACCEPT
[root@Init5 ~]# iptables -I FORWARD -d 192.168.1.0/24 -p tcp --sport 53 -j ACCEPT
[root@Init5 ~]# iptables -I FORWARD -s 192.168.1.0/24 -p tcp --dport 53 -j ACCEPT

②.内网(主机型)

[root@redhat6 ~]# iptables -A INPUT -p tcp --dport 20:21 -j ACCEPT #冒号代表连续的端口
[root@redhat6 ~]# iptables -A INPUT -p tcp --dport 24500:24600 -j ACCEPT

2、TCP标记匹配:--tcp-flags 检查范围 被设置的标记

写法1:

[root@redhat6 ~]# iptables -I INPUT -i eth0 -p tcp --tcp-flags SYN,RST,ACK SYN -j DROP #SYN被标记,直接丢弃

写法2:

[root@redhat6 ~]# iptables -I INPUT -i eth0 -p tcp ! --tcp-flags SYN,RST,ACK SYN -j ACCEPT #!代表逻辑非

此时查看Xshell
纯干货详解iptables工作原理以及使用方法

3、 ICMP类型匹配:--icmp-type ICMP类型

"8"作用:对应ICMP请求,禁止其他机子ping本机

①.内网设置

[root@redhat6 ~]# /etc/init.d/iptables stop #实验之前清空防火墙
[root@redhat6 ~]# iptables -A INPUT -p icmp --icmp-type 8 -j DROP #8代表禁止其他机子ping本机
[root@redhat6 ~]# ping -c 4 172.16.16.101

纯干货详解iptables工作原理以及使用方法

②.公网ping内网

[root@client ~]# ping -c 4 192.168.100.77
纯干货详解iptables工作原理以及使用方法

"0"作用:对应ICMP回显应答(ping应答)

①.内网设置

[root@redhat6 ~]# iptables -I INPUT -p tcp --dport 22 -j ACCEPT
[root@redhat6 ~]# iptables -P INPUT DROP #进站时机设置默认丢弃
[root@redhat6 ~]# ping 192.168.100.254 #此时自己的网关也无法ping通

[root@redhat6 ~]# iptables -I INPUT -p icmp --icmp-type 0 -j ACCEPT #回显应答(ping应答)

[root@redhat6 ~]# ping 192.168.100.254

纯干货详解iptables工作原理以及使用方法

"3"作用:对应ICMP目标不可达

①.内网

[root@redhat6 ~]# iptables -I INPUT -p icmp --icmp-type 3 -j ACCEPT
[root@redhat6 ~]# ping 192.168.100.254 #网关能ping通

②.网关防火墙

[root@Init5 ~]# iptables -I INPUT -p icmp --icmp-type 3 -j REJECT
[root@Init5 ~]# iptables -I INPUT -p icmp -j REJECT

③.内网

[root@redhat6 ~]# ping 192.168.100.254

纯干货详解iptables工作原理以及使用方法

[root@redhat6 ~]# iptables -I INPUT -p icmp --icmp-type 3 -j DROP
[root@redhat6 ~]# ping -c 3 192.168.100.254

纯干货详解iptables工作原理以及使用方法

四、显示匹配

1、 多端口匹配:-m multiport --sports 源端口列表;-m multiport --dports 目的端口列表

[root@redhat6 ~]# /etc/init.d/iptables stop #实验之前清空防火墙
[root@Init5 ~]# /etc/init.d/iptables stop
[root@redhat6 ~]# iptables -I INPUT -p tcp -m multiport --dports 20,25,80,443,100,53 -j ACCEPT

纯干货详解iptables工作原理以及使用方法

2、IP范围匹配:-m iprange-src-range IP范围

①.网关设置

[root@Init5 ~]# iptables -A INPUT -p icmp -m iprange --src-range 192.168.100.50-192.168.100.200 -j DROP #丢弃掉"192.168.1.50-192.168.1.200"网段,不允许ping

②.内网测试

[root@redhat6 ~]# ping -c4 192.168.100.254
纯干货详解iptables工作原理以及使用方法

3、MAC地址匹配:-m mac --mac-source MAC地址(注意!!!!!!经过一个路由MAC地址就变了)

①.网关设置

[root@Init5 ~]# iptables -D INPUT -p icmp -m iprange --src-range 192.168.100.50-192.168.100.200 -j DROP #清除规则
[root@Init5 ~]# iptables -A INPUT -m mac --mac-source 00:0C:29:03:B1:BA -j DROP

②.内网测试

[root@redhat6 ~]# ping -c4 192.168.100.254
纯干货详解iptables工作原理以及使用方法

4、 状态匹配:-m state --state 连接状态

常见的连接状态包括

NEW:与任何连接无关的(客户端发送请求给服务器端,服务器端还没有进行处理)
ESTABLISHED:响应请求或已建立连接的
RELATED:与已有连接有相关性的,如FTP数据连接(客户端访问服务器端FTP,21端口已经连接,当20端口要建立的时候,就属于RELATED)

三台机子全部清掉防火墙

[root@Init5 ~]# /etc/init.d/iptables stop

①.内网设置

[root@redhat6 ~]# iptables -I INPUT -p tcp --dport 22 -j ACCEPT
[root@redhat6 ~]# iptables -P INPUT DROP #此时只有22端口可以进去,除此之外啥都不行

[root@redhat6 ~]# ping 192.168.100.254 #ping网关不通

[root@redhat6 ~]# iptables -A INPUT -m state --state ESTABLISHED -j ACCEPT

[root@redhat6 ~]# ping 192.168.100.254 #可以ping通

[root@raid ~]# iptables -A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT #设置与ftp相关连

[root@raid ~]# iptables -I INPUT -p tcp -m state --state NEW --dport 80 -j ACCEPT #与任何连接无关