12. 动作总结

前文一直在介绍iptables的匹配条件,并没有对动作进行过总结,那么此处,我们就来总结一下iptables中的动作。

之前的举例中已经用到了一些常用动作,比如ACCEPT、DROP、REJECT等。

其实,”动作”与”匹配条件”一样,也有”基础”与”扩展”之分。

同样,使用扩展动作也需要借助扩展模块,但是,扩展动作可以直接使用,不用像使用”扩展匹配条件”那样指定特定的模块。

之前用到的ACCEPT与DROP都属于基础动作。

而REJECT则属于扩展动作。

之前举过很多例子,我们知道,使用-j可以指定动作,比如

-j ACCEPT

-j DROP

-j REJECT

其实,”动作”也有自己的选项,我们可以在使用动作时,设置对应的选项,此处以REJECT为例,展开与”动作”有关的话题。

12.1 动作REJECT

REJECT动作的常用选项为–reject-with

使用–reject-with选项,可以设置提示信息,当对方被拒绝时,会提示对方为什么被拒绝。

可用值如下

icmp-net-unreachable

icmp-host-unreachable

icmp-port-unreachable,

icmp-proto-unreachable

icmp-net-prohibited

icmp-host-pro-hibited

icmp-admin-prohibited

当不设置任何值时,默认值为icmp-port-unreachable。

我们来动手实践一下,在主机139上设置如下规则,如下图所示,当没有明确设置–reject-with的值时,默认提示信息为icmp-port-unreachable,即端口不可达之意。

img

此时在另一台主机上向主机139发起ping请求,如下图所示,提示目标端口不可达。

img

那么我们将拒绝报文的提示设置为”主机不可达”,示例如下

img

如上图所示,我们在设置拒绝的动作时,使用了–reject-with选项,将提示信息设置为icmp-host-unreachable,完成上述操作后,我们再次在在另一台主机上向主机139发起ping请求。

如下图所示。

img

可以看到,ping请求被拒绝时,提示信息已经从”目标端口不可达”变成了”目标主机不可达”。

12.2 动作LOG

在本博客中,前文并没有对LOG动作进行示例,此处我们来了解一下LOG动作。

使用LOG动作,可以将符合条件的报文的相关信息记录到日志中,但当前报文具体是被”接受”,还是被”拒绝”,都由后面的规则控制,换句话说,LOG动作只负责记录匹配到的报文的相关信息,不负责对报文的其他处理,如果想要对报文进行进一步的处理,可以在之后设置具体规则,进行进一步的处理。

示例如下,下例表示将发往22号端口的报文相关信息记录在日志中。

img

如上图所示,上述规则表示所有发往22号端口的tcp报文都符合条件,所以都会被记录到日志中,查看/var/log/messages即可看到对应报文的相关信息,但是上述规则只是用于示例,因为上例中使用的匹配条件过于宽泛,所以匹配到的报文数量将会非常之多,记录到的信息也不利于分析,所以在使用LOG动作时,匹配条件应该尽量写的精确一些,匹配到的报文数量也会大幅度的减少,这样冗余的日志信息就会变少,同时日后分析日志时,日志中的信息可用程度更高。

注:请把刚才用于示例的规则删除。

从刚才的示例中我们已经了解到,LOG动作会将报文的相关信息记录在/var/log/message文件中,当然,我们也可以将相关信息记录在指定的文件中,以防止iptables的相关信息与其他日志信息相混淆,修改/etc/rsyslog.conf文件(或者/etc/syslog.conf),在rsyslog配置文件中添加如下配置即可。

#vim /etc/rsyslog.conf

kern.warning /var/log/iptables.log

加入上述配置后,报文的相关信息将会被记录到/var/log/iptables.log文件中。

完成上述配置后,重启rsyslog服务(或者syslogd)

#service rsyslog restart

服务重启后,配置即可生效,匹配到的报文的相关信息将被记录到指定的文件中。

LOG动作也有自己的选项,常用选项如下(先列出概念,后面有示例)

–log-level选项可以指定记录日志的日志级别,可用级别有emerg,alert,crit,error,warning,notice,info,debug。

–log-prefix选项可以给记录到的相关信息添加”标签”之类的信息,以便区分各种记录到的报文信息,方便在分析时进行过滤。

注:–log-prefix对应的值不能超过29个字符。

比如,我想要将主动连接22号端口的报文的相关信息都记录到日志中,并且把这类记录命名为”want-in-from-port-22″,则可以使用如下命令

img

完成上述配置后,我在IP地址为192.168.1.98的客户端机上,尝试使用ssh工具连接上例中的主机,然后查看对应的日志文件(已经将日志文件设置为/var/log/iptables.log)

img

如上图所示,ssh连接操作的报文的相关信息已经被记录到了iptables.log日志文件中,而且这条日志中包含”标签”:want-in-from-port-22,如果有很多日志记录,我们就能通过这个”标签”进行筛选了,这样方便我们查看日志,同时,从上述记录中还能够得知报文的源IP与目标IP,源端口与目标端口等信息,从上述日志我们能够看出,192.168.1.98这个IP想要在14点11分连接到192.168.1.139(当前主机的IP)的22号端口,报文由eth4网卡进入,eth4网卡的MAC地址为00:0C:29:B7:F4:D1,客户端网卡的mac地址为F4-8E-38-82-B1-29。

除了ACCEPT、DROP、REJECT、LOG等动作,还有一些其他的常用动作,比如DNAT、SNAT等,我们会在之后的文章中对它们进行总结。

13. 动作总结二

13.1 概述

阅读这篇文章需要站在前文的基础上,如果你在阅读时遇到障碍,请参考之前的文章。

前文中,我们已经了解了如下动作

ACCEPT、DROP、REJECT、LOG

今天,我们来认识几个新动作,它们是:

SNAT、DNAT、MASQUERADE、REDIRECT

在认识它们之前,我们先来聊聊NAT,如果你对NAT的相关概念已经滚瓜烂熟,可以跳过如下场景描述。

NAT是Network Address Translation的缩写,译为”网络地址转换”,NAT说白了就是修改报文的IP地址,NAT功能通常会被集成到路由器、防火墙、或独立的NAT设备中。

为什么要修改报文的IP地址呢?我们来描述一些场景,即可知道为什么有这方面的需求了。

场景1

假设,网络内部有10台主机,它们有各自的IP地址,当网络内部的主机与其他网络中的主机通讯时,则会暴露自己的IP地址,如果我们想要隐藏这些主机的IP地址,该怎么办呢?可以这样办,如下。

当网络内部的主机向网络外部主机发送报文时,报文会经过防火墙或路由器,当报文经过防火墙或路由器时,将报文的源IP修改为防火墙或者路由器的IP地址,当其他网络中的主机收到这些报文时,显示的源IP地址则是路由器或者防火墙的,而不是那10台主机的IP地址,这样,就起到隐藏网络内部主机IP的作用,当网络内部主机的报文经过路由器时,路由器会维护一张NAT表,表中记录了报文来自于哪个内部主机的哪个进程(内部主机IP+端口),当报文经过路由器时,路由器会将报文的内部主机源IP替换为路由器的IP地址,把源端口也映射为某个端口,NAT表会把这种对应关系记录下来。

示意图如下:

img

于是,外部主机收到报文时,源IP与源端口显示的都是路由的IP与端口,当外部网络中的主机进行回应时,外部主机将响应报文发送给路由器,路由器根据刚才NAT表中的映射记录,将响应报文中的目标IP与目标端口再改为内部主机的IP与端口号,然后再将响应报文发送给内部网络中的主机。整个过程中,外部主机都不知道内部主机的IP地址,内部主机还能与外部主机通讯,于是起到了隐藏网络内主机IP的作用。

上述整个过程中,就用到了NAT功能,准确的说是用到了NAPT功能,NAPT是NAT的一种,全称为Network Address Port Translation,说白了就是映射报文IP地址的同时还会映射其端口号,就像刚才描述的过程一样。

刚才描述的过程中,”IP地址的转换”一共发生了两次。

内部网络的报文发送出去时,报文的源IP会被修改,也就是源地址转换:Source Network Address Translation,缩写为SNAT。

外部网络的报文响应时,响应报文的目标IP会再次被修改,也就是目标地址转换:Destinationnetwork address translation,缩写为DNAT。

但是,上述”整个过程”被称为SNAT,因为”整个过程”的前半段使用了SNAT,如果上述”整个过程”的前半段使用了DNAT,则整个过程被称为DNAT,也就是说,整个过程被称为SNAT还是DNAT,取决于整个过程的前半段使用了SNAT还是DNAT。

其实刚才描述的场景不仅仅能够隐藏网络内部主机的IP地址,还能够让局域网内的主机共享公网IP,让使用私网IP的主机能够访问互联网。

比如,整个公司只有一个公网IP,但是整个公司有10台电脑,我们怎样能让这10台电脑都访问互联网呢?我们可以为这10台电脑都配置上各自的私网IP,比如”192.168″这种私网IP,但是互联网是不会路由私网IP的,如果想要访问互联网,则必须使用公网IP,那么,我们就需要想办法,能让这10台主机共享公司仅有的一个公网IP,没错,这与刚才描述的场景其实完全一致,我们只要在路由器上配置公网IP,在私网主机访问公网服务时,报文经过路由器,路由器将报文中的私网IP与端口号进行修改和映射,将其映射为公网IP与端口号,这时,内网主机即可共享公网IP访问互联网上的服务了,NAT表示意图如下

img

综上所述,SNAT不仅能够隐藏网内的主机IP,还能够共享公网IP,这在IPV4地址较为紧张的今天,是非常有用的。

场景2

场景1中,我们描述的过程为SNAT的过程,虽然其过程中也牵扯到DNAT,但是由于整个过程的前半段使用了SNAT,所以整个过程称之为SNAT,那么在什么情况下,整个过程能称之为DNAT呢?

没错,当整个过程的前半段使用了DNAT时,整个过程被称为DNAT,具体场景如下。

公司有自己的局域网,网络中有两台主机作为服务器,主机1提供web服务,主机2提供数据库服务,但是这两台服务器在局域网中使用私有IP地址,只能被局域网内的主机访问,互联网无法访问到这两台服务器,整个公司只有一个可用的公网IP,怎样通过这个公网IP访问到内网中的这些服务呢?我们可以将这个公网IP配置到公司的某台主机或路由器上,然后对外宣称,这个IP地址对外提供web服务与数据库服务,于是互联网主机将请求报文发送给这公网 IP地址,也就是说,此时报文中的目标IP为公网IP,当路由器收到报文后,将报文的目标地址改为对应的私网地址,比如,如果报文的目标IP与端口号为:公网IP+3306,我们就将报文的目标地址与端口改为:主机2的私网IP+3306,同理,公网IP+80端口映射为主机1的私网IP+80端口,当私网中的主机回应对应请求报文时,再将回应报文的源地址从私网IP+端口号映射为公网IP+端口号,再由路由器或公网主机发送给互联网中的主机。

上述过程也牵扯到DNAT与SNAT,但是由于整个过程的前半段使用了DNAT,所以上述过程被称为DNAT

其实,不管是SNAT还是DNAT,都起到了隐藏内部主机IP的作用。

13.2 实验环境准备

好了,我们已经了解了SNAT与DNAT的相关概念,那么现在,我们可以动动手了,首先,准备一下实验环境

大致的实验环境是这样的,公司局域网使用的网段为10.1.0.0/16,目前公司只有一个公网IP,局域网内的主机需要共享这个IP与互联网上的主机进行通讯。

由于我们没有真正的公网IP,所以,我们使用私网IP:192.168.1.146模拟所谓的公网IP,示意图如下

img

如上述示意图所示,实验使用4台虚拟机,A、B、C、D

主机A:扮演公网主机,尝试访问公司提供的服务,IP地址为192.168.1.147

主机B:扮演了拥有NAT功能的防火墙或路由器,充当网关,并且负责NAT,公网、私网通讯的报文通过B主机时,报文会被NAT

主机C:扮演内网web服务器

主机D:扮演内网windows主机

上图中圆形所示的逻辑区域表示公司内网,网段为10.1.0.0/16,主机B、C、D都属于内网主机,主机B比较特殊,同时扮演了网关与防火墙,主机B持有公司唯一的公网IP(我们用了一个假的公网IP),局域网内主机如果想与公网主机通讯,需要共享此公网IP,由B主机进行NAT,所以,我们为主机B准备了两块网卡,公网IP与私网IP分别配置到这两块网卡中,同时,在虚拟机中设置了一个”仅主机模式”的虚拟网络,以模拟公司局域网。

聪明如你,应该已经发现了,上述实验环境与之前描述的”网络防火墙”的实验环境相差无几,只不过之前的环境并没有公网,私网的概念,而此刻,圆形逻辑区域之内为私网,圆形逻辑区域之外为公网。

环境具体准备过程如下

首先,创建一个虚拟网络,模拟公司内网。

点击vmware虚拟机的编辑菜单,打开”虚拟网络编辑器”,点击更改设置,添加”仅主机模式”的虚拟网络,下图中的VMnet6为已经添加过的虚拟网络,此处不再重复操作。

img

主机C与主机D的网关都指向主机B的私网IP,如下图所示

img

img

主机B有两块网卡,分别配置了私网IP与公网IP,私网IP为10.1.0.3,私网IP所在的网卡也存在于vmnet6中,模拟公网的IP为192.168.1.146,B主机的公网IP所在的网卡与A主机都使用桥接模式的虚拟网络,所以,B主机既能与私网主机通讯,也能与公网主机通讯。

img

由于B主机此时需要负责对报文的修改与转发,所以,需要开启B主机中的核心转发功能,Linux主机默认不会开启核心转发,这在前文中已经详细的描述过,此处不再赘述,如果你还不明白为什么,请回顾前文,使用临时生效的方法开启B主机的核心转发功能,如下图所示。

img

A主机的IP地址如下,可以与B主机进行通讯,但是不能与C、D进行通讯,因为此刻,A是公网主机,B既是公网主机又是私网主机,C、D是私网的主机,A是不可能访问到C和D的。

img

为了能够更好的区分公网服务与私网服务,我们分别在主机A与主机C上启动httpd服务,如下图所示。

img

好了,实验环境准备完毕,我们来一起动动手,实际操作一下。

13.3 动作:SNAT

在文章开头的场景中,我们已经描述过,网络内部的主机可以借助SNAT隐藏自己的IP地址,同时还能够共享合法的公网IP,让局域网内的多台主机共享公网IP访问互联网。

而此时的主机B就扮演了拥有NAT功能的设备,我们使用iptables的SNAT动作达到刚才所说的目的。

连接到B主机,添加如下规则。

img

如上图所示,上图中的规则表示将来自于10.1.0.0/16网段的报文的源地址改为公司的公网IP地址。

“-t nat”表示操作nat表,我们之前一直在灌输一个概念,就是不同的表有不同的功能,filter表的功能是过滤,nat表的功能就是地址转换,所以我们需要在nat表中定义nat规则。

“-A POSTROUTING”表示将SNAT规则添加到POSTROUTING链的末尾,在centos7中,SNAT规则只能存在于POSTROUTING链与INPUT链中,在centos6中,SNAT规则只能存在于POSTROUTING链中。

你可能会问,为什么SNAT规则必须定义在POSTROUTING链中,我们可以这样认为,POSTROUTING链是iptables中报文发出的最后一个”关卡”,我们应该在报文马上发出之前,修改报文的源地址,否则就再也没有机会修改报文的源地址了,在centos7中,SNAT规则也可以定义在INPUT链中,我们可以这样理解,发往本机的报文经过INPUT链以后报文就到达了本机,如果再不修改报文的源地址,就没有机会修改了。

“-s 10.1.0.0/16″表示报文来自于10.1.0.0/16网段,前文中一直在使用这个匹配条件,我想此处应该不用赘述了。

“-j SNAT”表示使用SNAT动作,对匹配到的报文进行处理,对匹配到的报文进行源地址转换。

“–to-source 192.168.1.146″表示将匹配到的报文的源IP修改为192.168.1.146,前文中,我们已经总结过,某些动作会有自己的选项,”–to-source”就是SNAT动作的常用选项,用于指定SNAT需要将报文的源IP修改为哪个IP地址。

好了,只要站在前文的基础上,理解上述语句应该是分分钟的事情,聪明如你应该已经学会了,那么我们来测试一下。

目前来说,我们只配置了一条SNAT规则,并没有设置任何DNAT,现在,我们从内网主机上ping外网主机,看看能不能ping通,登录内网主机C,在C主机上向A主机的外网IP发送ping请求(假外网IP),示例如下

img

如上图所示,”内网主机”已经可以依靠SNAT访问”互联网”了。

为了更加清晰的理解整个SNAT过程,在C主机上抓包看看,查看一下请求报文与响应报文的IP地址,如下,在C主机上同时打开两个命令窗口,一个命令窗口中向A主机发送ping请求,另一个窗口中,使用tcpdump命令对指定的网卡进行抓包,抓取icmp协议的包。

img

从上图可以看到,10.1.0.1发出ping包,192.168.1.147进行回应,正是A主机的IP地址(用于模拟公网IP的IP地址)

看来,只是用于配置SNAT的话,我们并不用 手动的进行DNAT设置,iptables会自动维护NAT表,并将响应报文的目标地址转换回来。

那么,我们去A主机上再次重复一遍刚才的操作,在A主机上抓包看看,如下图所示,C主机上继续向A主机的公网IP发送ping请求,在主机A的网卡上抓包看看。

img

从上图可以看出,C主机向A主机发起ping请求时得到了回应,但是在A主机上,并不知道是C主机发来的ping请求,A主机以为是B主机发来的ping请求,从抓包的信息来看,A主机以为B主机通过公网IP:192.168.1.146向自己发起了ping请求,而A主机也将响应报文回应给了B主机,所以,整个过程,A主机都不知道C主机的存在,都以为是B主机在向自己发送请求,即使不是在公网私网的场景中,我们也能够使用这种方法,隐藏网络内的主机,只不过此处,我们所描述的环境就是私网主机共享公网IP访问互联网,那么可以看到,私网中的主机已经共享了192.168.1.146这个”伪公网IP”,那么真的共享了吗?我们使用内网主机D试试,主机D是一台windows虚拟机,我们使用它向主机A发送ping请求,看看能不能ping通。如下

img

windows主机也ping通了外网主机,在A主机上抓包,看到的仍然是B主机的IP地址。

img

那么,C主机与D主机能够访问外网服务吗?我们来看看。

在C主机上访问A主机的web服务,如下图所示,访问正常。

img

同理,在windows主机中访问A主机的web服务,如下图所示,访问正常。

img

好了,源地址转换,已经完成了,我们只依靠了一条iptables规则,就能够使内网主机能够共享公网IP访问互联网了。

13.4 动作:DNAT

公司只有一个公网IP,但是公司的内网中却有很多服务器提供各种服务,我们想要通过公网访问这些服务,改怎么办呢?

没错,使用DNAT即可,我们对外宣称,公司的公网IP上既提供了web服务,也提供了windows远程桌面,不管是访问web服务还是远程桌面,只要访问这个公网IP就行了,我们利用DNAT,将公网客户端发送过来的报文的目标地址与端口号做了映射,将访问web服务的报文转发到了内网中的C主机中,将访问远程桌面的报文转发到了内网中的D主机中。

好了,理论说完了,来动手实践一下。

如果我们想要实现刚才描述的场景,则需要在B主机中进行如下配置。

img

如上图所示,我们先将nat表中的规则清空了,从头来过,清空nat表规则后,定义了一条DNAT规则。

“-t nat -I PREROUTING”表示在nat表中的PREROUTING链中配置DNAT规则,DNAT规则只配置在PREROUTING链与OUTPUT链中。

“-d 192.168.1.146 -p tcp –dport 3389″表示报文的目标地址为公司的公网IP地址,目标端口为tcp的3389号端口,而我们知道,windows远程桌面使用的默认端口号就是3389,当外部主机访问公司公网IP的3389号端口时,报文则符合匹配条件。

“-j DNAT –to-destination 10.1.0.6:3389″表示将符合条件的报文进行DNAT,也就是目标地址转换,将符合条件的报文的目标地址与目标端口修改为10.1.0.6:3389,”–to-destination”就是动作DNAT的常用选项。

那么综上所述,上图中定义的规则的含义为,当外网主机访问公司公网IP的3389时,其报文的目标地址与端口将会被映射到10.1.0.6:3389上。

好了,DNAT规则定义完了,现在能够直接使用外网主机访问私网中的服务了吗?

理论上只要完成上述DNAT配置规则即可,但是在测试时,只配置DNAT规则后,并不能正常DNAT,经过测试发现,将相应的SNAT规则同时配置后,即可正常DNAT,于是我们又配置了SNAT

示例如下。

img

注:理论上只配置DNAT规则即可,但是如果在测试时无法正常DNAT,可以尝试配置对应的SNAT,此处按照配置SNAT的流程进行。

SNAT 确保内网服务的响应数据包的源地址被修改为防火墙的外网地址,以使响应能够正确返回到发起请求的外部主机。

没错,与刚才定义SNAT时使用的规则完全一样。

好了,完成上述配置后,我们则可以通过B主机的公网IP,连接D主机(windows主机)的远程桌面了,示例如下。

找到公网中的一台windows主机,打开远程程序

img

输入公司的公网IP,点击连接按钮

注意:没有指定端口的情况下,默认使用3389端口进行连接,同时,为了确保能够连接到windows虚拟主机,请将windows虚拟主机设置为允许远程连接。

img

输入远程连接用户的密码以后,即可连接到windows主机

img

连接以后,远程连接程序显示我们连接到了公司的公网IP,但是当我们查看IP地址时,发现被远程机器的IP地址其实是公司私网中的D主机的IP地址。

上图证明,我们已经成功的通过公网IP访问到了内网中的服务。

同理,使用类似的方法,我们也能够在外网中访问到C主机提供的web服务。

示例如下。

img

如上图所示,我们将公司公网IP的801号端口映射到了公司内网中C主机的80端口,所以,当外网主机访问公司公网IP的801端口时,报文将会发送到C主机的80端口上。

这次,我们不用再次定义SNAT规则了,因为之前已经定义过SNAT规则,上次定义的SNAT规则只要定义一次就行,而DNAT规则则需要根据实际的情况去定义。

好了,完成上述DNAT映射后,我们在A主机上访问B主机的801端口试试,如下

img

可以看到,我们访问的是B主机的公网IP,但是返回结果显示的却是C主机提供的服务内容,证明DNAT已经成功。

而上述过程中,外网主机A访问的始终都是公司的公网IP,但是提供服务的却是内网主机,但是我们可以对外宣称,公网IP上提供了某些服务,快来访问吧!

我觉得我说明白了,你听明白了吗?

13.5 动作:MASQUERADE

上文中,我们已经描述了SNAT,也就是源地址转换,那么我们现在来认识一个与SNAT类似的动作:MASQUERADE

当我们拨号网上时,每次分配的IP地址往往不同,不会长期分给我们一个固定的IP地址,如果这时,我们想要让内网主机共享公网IP上网,就会很麻烦,因为每次IP地址发生变化以后,我们都要重新配置SNAT规则,这样显示不是很人性化,我们通过MASQUERADE即可解决这个问题,MASQUERADE会动态的将源地址转换为可用的IP地址,其实与SNAT实现的功能完全一致,都是修改源地址,只不过SNAT需要指明将报文的源地址改为哪个IP,而MASQUERADE则不用指定明确的IP,会动态的将报文的源地址修改为指定网卡上可用的IP地址,示例如下:

img

如上图所示,我们指定,通过外网网卡出去的报文在经过POSTROUTING链时,会自动将报文的源地址修改为外网网卡上可用的IP地址,这时,即使外网网卡中的公网IP地址发生了改变,也能够正常的、动态的将内部主机的报文的源IP映射为对应的公网IP。

可以把MASQUERADE理解为动态的、自动化的SNAT,如果没有动态SNAT的需求,没有必要使用MASQUERADE,因为SNAT更加高效。

13.6 动作:REDIRECT

使用REDIRECT动作可以在本机上进行端口映射

比如,将本机的80端口映射到本机的8080端口上

iptables -t nat -A PREROUTING -p tcp –dport 80 -j REDIRECT –to-ports 8080

经过上述规则映射后,当别的机器访问本机的80端口时,报文会被重定向到本机的8080端口上。

REDIRECT规则只能定义在PREROUTING链或者OUTPUT链中。

13.7 小结

为了方便以后回顾,我们对上述命令进行总结。

如果想要NAT功能能够正常使用,需要开启Linux主机的核心转发功能。

echo 1 > /proc/sys/net/ipv4/ip_forward

13.7.1 SNAT相关操作

配置SNAT,可以隐藏网内主机的IP地址,也可以共享公网IP,访问互联网,如果只是共享IP的话,只配置如下SNAT规则即可。

iptables -t nat -A POSTROUTING -s 10.1.0.0/16 -j SNAT --to-source 公网IP

如果公网IP是动态获取的,不是固定的,则可以使用MASQUERADE进行动态的SNAT操作,如下命令表示将10.1网段的报文的源IP修改为eth0网卡中可用的地址。

iptables -t nat -A POSTROUTING -s 10.1.0.0/16 -o eth0 -j MASQUERADE

13.7.2 DNAT相关操作

配置DNAT,可以通过公网IP访问局域网内的服务。

注:理论上来说,只要配置DNAT规则,不需要对应的SNAT规则即可达到DNAT效果。

但是在测试DNAT时,对应SNAT规则也需要配置,才能正常DNAT,可以先尝试只配置DNAT规则,如果无法正常DNAT,再尝试添加对应的SNAT规则,SNAT规则配置一条即可,DNAT规则需要根据实际情况配置不同的DNAT规则。

iptables -t nat -I PREROUTING -d 公网IP -p tcp --dport 公网端口 -j DNAT --to-destination 私网IP:端口号

iptables -t nat -I PREROUTING -d 公网IP -p tcp --dport 8080 -j DNAT --to-destination 10.1.0.1:80

iptables -t nat -A POSTROUTING -s 10.1.0.0/16 -j SNAT --to-source 公网IP

在本机进行目标端口映射时可以使用REDIRECT动作。

iptables -t nat -A PREROUTING -p tcp --dport 80 -j REDIRECT --to-ports 8080

配置完成上述规则后,其他机器访问本机的80端口时,会被映射到8080端口。

14. 总结

  1. 规则的顺序非常重要

如果报文已经被前面的规则匹配到,IPTABLES则会对报文执行对应的动作,通常是ACCEPT或者REJECT,报文被放行或拒绝以后,即使后面的规则也能匹配到刚才放行或拒绝的报文,也没有机会再对报文执行相应的动作了(前面规则的动作为LOG时除外),所以,针对相同服务的规则,更严格的规则应该放在前面。

  1. 当规则中有多个匹配条件时,条件之间默认存在”与”的关系

如果一条规则中包含了多个匹配条件,那么报文必须同时满足这个规则中的所有匹配条件,报文才能被这条规则匹配到。

  1. 在不考虑1的情况下,应该将更容易被匹配到的规则放置在前面

    比如,你写了两条规则,一条针对sshd服务,一条针对web服务。

    假设,一天之内,有20000个请求访问web服务,有200个请求访问sshd服务,

    那么,应该将针对web服务的规则放在前面,针对sshd的规则放在后面,因为访问web服务的请求频率更高。

    如果将sshd的规则放在前面,当报文是访问web服务时,sshd的规则也要白白的验证一遍,由于访问web服务的频率更高,白白耗费的资源就更多。

    如果web服务的规则放在前面,由于访问web服务的频率更高,所以无用功会比较少。

    换句话说就是,在没有顺序要求的情况下,不同类别的规则,被匹配次数多的、匹配频率高的规则应该放在前面。

  2. 当IPTABLES所在主机作为网络防火 墙时,在配置规则时,应着重考虑方向性,双向都要考虑,从外到内,从内到外。

  3. 在配置IPTABLES白名单时,往往会将链的默认策略设置为ACCEPT,通过在链的最后设置REJECT规则实现白名单机制,而不是将链的默认策略设置为DROP,如果将链的默认策略设置为DROP,当链中的规则被清空时,管理员的请求也将会被DROP掉。