iptables/netfilter
netfilter
:在Linux内核中的一个软件框架,用于管理网络数据包。不仅具有网络地址转换(NAT
)的功能,也具备数据包内容修改、以及数据包过滤等防火墙功能。利用运作于用户空间的应用软件,如iptable等,来控制Netfilter,系统管理者可以管理通过Linux操作系统的各种网络数据包
iptables
:一个运行在用户空间的应用软件,通过控制Linux内核netfilter
模块,来管理网络数据包的流动与转送。在大部分的Linux系统上面,iptables是使用/usr/sbin/iptables
来操作,文件则放置在手册页Man
底下,可以通过man iptables
(Centos 7中还需要使用man iptables-extensions
) 指令获取。通常iptables都需要内核层级的模块来配合运作,iptables是主要在内核层级里面iptables API运作功能的模块。因相关动作上的需要,iptables的操作需要用到超级用户的权限。
传说中的四表五链
一、RAW
功能:关闭在nat表启用的连接追踪机制
包含的链:
PREROUTING
、OUTPUT
caution:此表一般不用,不建议在此表中添加规则
二、mangle
功能:主要用来管理mangle包,可以使用mangle匹配来该表报的TOS等特性。
以下是managle表中仅有的几种操作:
TOS
TTL
MARK
包含的链:
PREROUING
、INPUT
、OUTPUT
、FORWARD
、PREROUTING
caution:强烈建议你不要在这个表里做任何过滤,不管是DANT,SNAT或者MASQUERADE。
三、nat
功能:此表仅用于NAT(网络地址转换),也就是转换包的源或者目标地址。
DNAT
SNAT
MASQUERADE
包含的链:
PREROUING
、[INPUT]
、OUTPUT
、FORWARD
、PREROUTING
(INPUT链在nat表中目前只在Centos 7上有)DNAT:操作主要用在当你有一个合法的IP地址,要把对防火墙的访问重定向到其他的服务器上面(比如DMZ),主要用于改变目标地址。
SNAT:该变包的原地址,这在极大程度上就可以隐藏内网或者DMZ,也可以是内网用户连接到互联网,通过一个IP地址。
MASQUERADE:其作用和SNAT的作用完全一样,只是计算机的符合稍微多一点,其主要作用 是使用在外网IP为动态IP时,比如PPP、PPPOE等拨号获得的地址,MASQUERADE可以探测外网地址,并转发。
四、filter
功能:用来过滤数据包,可以根据控制语句对数据包进行一系列动作,例如ACCEPT、DROP等,几乎所有的target都可以在这使用。
包含的链:
INPUT
、OUTPUT
、FORWARD
五链
REROUTING:路由前访问控制,一般做外访内控制
INPUT:进入的包
FORWARD:转发
OUTPUT:出去的包
POSTROUTING:路由后
防火墙过滤规则
报文流向:表优先级为RAW-->MANGLE-->NAT-->FILTER
流入本机:PREROUTING--> INPUT --> 用户空间进程
流出本机:用户空间进程 --> OUTPUT --> POSTROUTING
转发:PREROUTING --> FORWARD --> POSTROUTING
iptables命令使用及规则
一、常用子命令
命令格式:iptables [-t table] SUBCOMMAND chain [matches...] [target]
1
2
|
-t table:
raw、mangle、nat、[filter]
|
链管理:
Command | -N,--new-chain |
Example | iptables -N mychain |
Explanation | 新增一条自定义链 |
Command | -X, --delete-chain |
Example | iptables -X mychain |
Explanation | 删除自定义的链,保证链中规则为空才能删除 |
Command | -P,--policy |
Example | iptables -P INPUT DROP |
Explanation | 设置链的默认策略,常用策略有:ACCEPT,DROP,REJECT |
Command | -E,--rename-chain |
Example | iptables -E mychain youchain |
Explanation | 重命名自定义链,链的引用计数需为0 |
规则管理:
Command | -A, --append |
Example | iptables -A INPUT ... |
Explanation | 在所选择的链末添加规则。当源地址或目的地址是以名字而 不是ip地址的形式出现时,若这些名字可以被解析为多个地址,则这条规则会和所有可用的地址结合。 |
Command | -D, --delete |
Example | iptables -D INPUT --dport 80 -j DROP或iptables -D INPUT 1 |
Explanation | 从所选链中删除规则。有两种方法指定要删除的规则:一是 把规则完完整整地写出来,再就是指定规则在所选链中的序号(每条链的规则都各自从1被编号)。 |
Command | -R, --replace |
Example | iptables -R INPUT 1 -s 192.168.0.1 -j DROP |
Explanation | 在所选中的链里指定的行上(每条链的规则都各自从1被编 号)替换规则。它主要的用处是试验不同的规则。当源地址或目的地址是以名字而不是ip地址的形式出现 时,若这些名字可以被解析为多个地址,则这条command会失败。 |
Command | -I, --insert |
Example | iptables -I INPUT 1 --dport 80 -j ACCEPT |
Explanation | 根据给出的规则序号向所选链中插入规则。如果序号为1, 规则会被插入链的头部,其实默认序号就是1。 |
Command | -F, --flush |
Example | iptables -F INPUT |
Explanation | 清空所选的链。如果没有指定链,则清空指定表中的所有 链。如果什么都没有指定,就清空默认表所有的链。当然,也可以一条一条地删,但用这个command会快些。 |
Command | -Z, --zero |
Example | iptables -Z INPUT |
Explanation | 把指定链(如未指定,则认为是所有链)的所有计数器归零。 |
查看:
Command | -L, --list |
Example | iptables -L |
Explanation | 显示所选链的所有规则。如果没有指定链,则显示指定表中 的所有链。如果什么都没有指定,就显示默认表所有的链。精确输出受其它参数影响,如-n和-v等参数,下面会介绍。 |
Command | -n |
Example | iptables -nL |
Explanation | 以数字形式显示 |
Command | -v |
Example | iptables -nvL |
Explanation | 显示详细信息,可使用-vv,-vvv查看更详细的信息 |
Command | -x |
Example | iptables -nxL |
Explanation | 显示计数器的精确值而非单位换算后的结果 |
Command | --line-numbers |
Example | iptables --line-numbers |
Explanation | 显示所有规则的编号 |
二、通用匹配条件
Command | [!] -s, --source address[/mask][,...] |
Example | iptables -A INPUT -s 192.168.1.1 |
Explanation | 匹配IP原地址: 1、单个ip地址 2、网段地址 3、取反地址,在地址前面加“!”号 4、缺省是任意地址 |
Command | [!] -d, --destination address[/mask][,...] |
Example | iptables -A INPUT -d 192.168.1.1 |
Explanation | 匹配IP目标地址,与原地址一样 |
Command | [!] -i, --in-interface name |
Example | iptables -A INPUT -i eno16777736 |
Explanation | 限制报文流入接口,只能用于PREROUTING,INPUT及FORWARD |
Command | [!] -o, --out-interface name |
Example | iptables -A INPUT -o eno16777736 |
Explanation | 限制报文流出的接口,只能用于OUTPUT,FORWARD及POSTROUTING |
三、扩展匹配条件
隐式扩展:
tcp: 隐含指明了“-m tcp”,有专用选项
Command | [!] --source-port,--sport port[:port] |
Example | iptables -A INPUT -p tcp --sport 22 -j ACCEPT |
Explanation | 基于TCP包的源端口来匹配包,端口的指定形式如下: 1、不指定此项,则暗示所有端口。 2、使用的端口名字必须是在/etc/service中定义的端口 3、可以使用连续的端口,如:--sport 22:25,表示从22号端口到25号端口 4、--sport :80 表示0到80 5、--sport 22: 表示22到65535 |
Command | [!] --destination-port,--dport port[:port] |
Example | iptables -D INPUT --dport 80 -j ACCEPT |
Explanation | 匹配报文中的tcp首部的目标端口;可以是端口范围,使用方式与--sport大同小异 |
Command | [!] --tcp-flags mask comp |
Example | iptables -A INPUT --tcp-flags syn,fin,ack,rst syn |
Explanation | 检查报文中mask指明的tcp标志位,而要这些标志位comp中必须为1 例子中表示tcp三次握手中的第一次回话,用于控制tcp连接 |
Command | [!] --syn |
Example | iptables -A INPUT --syn |
Explanation | --syn相当于“--tcp-flags syn,fin,ack,rst syn”;tcp三次握手的第一次 |
udp:隐含指明了“-m udp”,有专用选
Command | [!] --source-port,--sport port[:port] |
Example | iptables -A INPUT -p tcp --sport 22 -j ACCEPT |
Explanation | 基于TCP包的源端口来匹配包,端口的指定形式如下: 1、不指定此项,则暗示所有端口。 2、使用的端口名字必须是在/etc/service中定义的端口 3、可以使用连续的端口,如:--sport 22:25,表示从22号端口到25号端口 4、--sport :80 表示0到80 5、--sport 22: 表示22到65535 |
Command | [!] --destination-port,--dport port[:port] |
Example | iptables -D INPUT --dport 80 -j ACCEPT |
Explanation | 匹配报文中的tcp首部的目标端口;可以是端口范围,使用方式与--sport大同小异 |
Command | [!] --tcp-flags mask comp |
Example | iptables -A INPUT --tcp-flags syn,fin,ack,rst syn |
Explanation | 检查报文中mask指明的tcp标志位,而要这些标志位comp中必须为1 例子中表示tcp三次握手中的第一次回话,用于控制tcp连接 |
Command | [!] --syn |
Example | iptables -A INPUT --syn |
Explanation | --syn相当于“--tcp-flags syn,fin,ack,rst syn”;tcp三次握手的第一次 |
icmp:隐含指明了“-m icmp”,有专用选项
Command | [!] --icmp-type {type[/code]|typename} |
Example | iptables -A INPUT -p icmp --icmp-type 8 |
Explanation | icmp-type常用类型: 0:icmp response 8:icmp request 其他类型可通过goole |
显示扩展
Command | multiport [!] --source-ports,--sports port[,port|,port:port]... [!] --destination-ports,--dports port[,port|,port:port]... [!] --ports port[,port|,port:port]... |
Example | 1、iptables -I INPUT -s 0/0 -d 172.18.100.6 -p tcp -m multiport --dports 22,80 -j ACCEPT 2、iptables -I OUTPUT -d 0/0 -s 172.18.100.6 -p tcp -m multiport --sports 22,80 -j ACCEPT |
Explanation | 多端口匹配,以离散方式定义多端口匹配,最多可以指定15个端口 |
Command | iprange [!] --src-range from[-to]:源地址范围 [!] --dst-range from[-to]:目标地址范围 |
Example | iptables -A INPUT -p tcp --dport 22 -m iprange --src-range 172.18.4.5-172.18.4.20 -j ACCEPT |
Explanation | 指明一段连续的ip地址范围做为源地址或目标地址匹配 |
Command | string --algo {bm|kmp}:算法 [!] --string pattern:给定要检查的字符串模式; [!] --hex-string pattern:给定要检查的字符串模式;16禁止编码方式(提高性能,但文本必须为16禁止编码) |
Example | iptables -I OUTPUT -s 172.18.100.6 -d 0/0 -p tcp --sport 80 -m string --algo bm --string "old" -j REJECT |
Explanation | 对报文中的应用层数据做字符串匹配检测 |
Command | time --datestart YYYY[-MM[-DD[Thh[:mm[:ss]]]]]:起始日期时间; --datestop YYYY[-MM[-DD[Thh[:mm[:ss]]]]]:结束日期时间; --timestart hh:mm[:ss]:起始时间; --timestop hh:mm[:ss]:结束时间; [!] --monthdays day[,day...]:匹配一个月中的哪些天; [!] --weekdays day[,day...]:匹配一个周中的哪些天; |
Example | iptables -R INPUT 4 -d 172.18.100.6 -p tcp --dport 23 -m iprange --src-range 172.18.100.1-172.18.100.100 -m time --timestart 09:00:00 --timestop 16:00:00 --weekdays 1,2,3,4,5 -j ACCEPT |
Explanation | 根据收到报文的时间/日期与指定的时间/日期范围进行匹配 |
Command | connlimit --connlimit-upto n:连接数量小于等于n则匹配; --connlimit-above n:连接数量大于n则匹配 |
Example | iptables -A INPUT -s 0/0 -d 172.18.100.6 -p tcp --dport 23 -m connlimit --connlimit-upto 2 -j ACCEPT |
Explanation | 根据每客户端主机做并发连接数限制,即每客户端最多可同时发起的连接数量 |
Command | limit --limit rate[/second|/minute|/hour|/day] --limit-burst number 限制特定包瞬间传入的峰值,一次同时涌入的包是否超过此值,如果超过就丢弃 |
Example | iptables -R INPUT 3 -d 172.18.100.6 -p icmp --icmp-type 8 -m limit --limit 20/minute --limit-burst 3 -j ACCEPT |
Explanation | 基于令牌桶算法对报文的速率做匹配 |
Command | state [!] --state state INVALID:无法识别的连接; ESTABLISHED:连接追踪模板当中存在记录的连接; NEW:连接追踪模板当中不存的连接请求; RELATED:相关联的连接; 例如:ftp(数据连接需要依赖命令连接) UNTRACKED:未追踪的连接 |
Example | iptables -A INPUT -m state --state RELATED,ESTABLISHED |
Explanation | 指定要匹配包的的状态,当前有4种状态可用:INVALID,ESTABLISHED,NEW和RELATED。 INVALID意味着这个包没有已知的流或连接与之关 联,也可能是它包含的数据或包头有问题。ESTABLISHED意思是包是完全有效的,而 且属于一个已建立的连接,这个连接的两端都已经有数据发送。NEW表示包将要或已 经开始建立一个新的连接,或者是这个包和一个还没有在两端都有数据发送的连接有关。RELATED说明包正在建立一个新的连接,这个连接是和一个已建立的连接相关的。比 如,FTP data transfer,ICMP error 和一个TCP或UDP连接相关。注意NEW状态并不在试图建立新连接的TCP包里寻找SYN标 记,因此它不应该不加修改地用在只有一个防火墙或在不同的防火墙之间没有启用负载平衡的地方。 |
四、处理动作
1、ACCEPT target
这个target没有任何选项和参数,使用也很简单,指定-j ACCEPT即可。一旦包 满足了指定的匹配条件,就会被ACCEPT,并且不会再去匹配当前链中的其他规则或同一个表内的其他规则, 但它还要通过其他表中的链,而且在那儿可能会被DROP也说不准 |
2、DROP target
顾名思义,如果包符合条件,这个target就会把它丢掉,也就是说包的生命到此结束,不会再向前走一 步,效果就是包被阻塞了。在某些情况下,这个target会引起意外的结果,因为它不会向发送者返回任何信 息,也不会向路由器返回信息,这就可能会使连接的另一方的sockets因苦等回音而亡:) 解决这个问题的较 好的办法是使用REJECT target,(译者注:因为它在丢弃包的同时还会向发送者返 回一个错误信息,这样另一方就能正常结束),尤其是在阻止端口扫描工具获得更多的信息时,可以隐蔽被 过滤掉的端口等等(译者注:因为扫描工具扫描一个端口时,如果没有返回信息,一般会认为端口未打开或 被防火墙等设备过滤掉了)。还要注意如果包在子链中被DROP了,那么它在主链里也不会再继续前进,不管 是在当前的表还是在其他表里。总之,包死翘翘了。 |
3、DNAT target
Option | --to-destination |
Example | iptables -t nat -A PREROUTING -p tcp -d 15.45.23.67 --dport 80 -j DNAT --to-destination 192.168.1.1-192.168.1.10 |
Explanation | 目标地址转换,上述例子表示,所有发往地址15.45.23.67的包都转发到一段LAN使用的私有地址中,即192.168.1.1到 192.168.1.10。 |
4、RETURN
如果当前CHIAN是别的CHAIN调用的子CHIAN,那么返回到调用点下一条规则处开始执行,
如果当前CHIAN不是子CHAIN,那么就以默认策略执行.
1. 从一个CHAIN里可以jump到另一个CHAIN, jump到的那个CHAIN是子CHAIN.
2. 从子CHAIN return后,回到触发jump的那条规则,从那条规则的下一条继续匹配.
3. 如果return不是在子CHAIN里,而是在main CHAIN,那么就以默认规则进行.
1
2
3
|
The RETURN target will cause the current packet to stop traveling through the chain where it hit the rule.
If it is the subchain of another chain, the packet will
continue
to travel through the superior chains as
if
nothing had happened
If the chain is the main chain,
for
example the INPUT chain, the packet will have the default policy taken on it. The default policy is normally
set
to ACCEPT, DROP or similar.
|
5、LOG target
Option | --log-level level emerg, alert, crit, error, warning, notice, info or debug --log-prefix prefix |
Example | iptables -I FORWARD 2 -s 10.0.1.0/24 -p tcp -m multiport --dports 80,21,22,23 -m state --state NEW -j LOG --log-prefix "(new connctions)" |
Explanation | 记录日志,可以通过状态机制记录,默认记录在:/var/log/message |
6、REDIRECT target
Option | --to-ports port[-port] |
Example | iptables -t nat -A PREROUTING -d 172.18.100.67 -p tcp --dport 80 -j REDIRECT --to-ports 8080 |
Explanation | 端口重定向,将客户端访问的端口重定向至其他端口,可以有效隐藏真实端口 |
7、DNAT target
Option | --to-destination [ipaddr[-ipaddr]][:port[-port]] |
Example | iptables -t nat -A PREROUTING -d 172.18.4.71 -p tcp --dport 80 -j DNAT --to-destination 10.0.0.10:8080 |
Explanation | 修改IP报文中的目标IP地址 让本地网络中服务器使用统一的地址向外提供服务(发布服务),但隐藏了自己的真实地址; 请求:由外网主机发起,修改其目标地址,由管理员定义; 响应:修改源地址,但由nat自动根据会话表中的追踪机制实现对应修改; |
8、SNAT taget
Option | --to-source [ipaddr[-ipaddr]] |
Example | iptables -t nat -A POSTROUTING -j SNAT --to-source 172.18.4.1 |
Explanation | 修改IP报文中的源IP地址; 让本地网络中的主机可使用统一地址与外部主机通信,从而实现地址伪装; 请求:由内网主机发起,修改源IP,如果修改则由管理员定义; 响应:修改目标IP,由nat自动根据会话表中追踪机制实现相应修改; |
9、MASQUERADE target
Option | MASQUERADE |
Example | iptables -t nat -A POSTROUTING -j MASQUERADE |
Explanation | 可以自动探测外网IP地址,用于在公网地址不固定的场景,例如:ppoe拨号 |
练习
由于场景不同,可能对于防火墙的使用方式也不同,所以就此没有具体的实验步骤,不过有些重点还是说一下,一般做控制时 INPUT链的默认规则应为DROP,如果想限制严格也可以将OUTPUT设置为DROP,在使用FORWARD链时,应该修改内核参数,已支持转发功能。
常用场景:
主机防火墙
网络防火墙
端口映射
就此提出几个练习,
1、限制本地主机的web服务器在周一不允许访问;新请求的速率不能超过100个每秒;web服务器包含了admin字符串的页面不允许访问;web服务器仅允许响应报文离开本机;
2、在工作时间,即周一到周五的8:30-18:00,开放本机的ftp服务给172.18.0.0网络中的主机访问;数据下载请求的次数每分钟不得超过5个;
3、开放本机的ssh服务给172.18.x.1-172.18.x.100中的主机,x为你的学号,新请求建立的速率一分钟不得超过2个;仅允许响应报文通过其服务端口离开本机;
4、拒绝TCP标志位全部为1及全部为0的报文访问本机;
5、允许本机ping别的主机;但不开放别的主机ping本机;
6、修改所有内网主机访问互联网时都是用外网接口IP,两种方式
7、修改所有访问外网地址端口为80的都修改为内网提供web服务的8080端口,新请求建立的速率一分钟不得超过5个,访问字符串不可以包含'sex'并记录日志,且开头为 "weblog"