赞
踩
目录
这篇文章说一下iptables的match和target。
先说明一下实验环境。
-
- 192.168.0.0/24
- 访问用机器(Centos) --------------------- iptables设定机器(node2)
- 192.168.0.211 192.168.0.203
本节主要是为了实验匹配条件,所以匹配后的动作target,都用LOG,以后在工作中,写匹配条件,然后验证是否正确的时候也可以用先用LOG来进行测试,测试OK以后,再用-R来替换成想要的target
-p|--protocol [ALL|TCP|UDP|ICMP]
-p 是--protocol的缩写。
ALL:代表所有协议
- # 添加规则 - 记录所有的icmp协议
- root@node2:~# iptables -A INPUT -p icmp -j LOG
-
- # 查看规则
- root@node2:~# iptables -nvL INPUT
- Chain INPUT (policy ACCEPT 15 packets, 2158 bytes)
- pkts bytes target prot opt in out source destination
- 0 0 LOG icmp -- * * 0.0.0.0/0 0.0.0.0/0 LOG flags 0 level 4
-
- # 从Centos ping node2
- [root@centos ~]# ping 192.168.0.203
- PING 192.168.0.203 (192.168.0.203) 56(84) bytes of data.
- 64 bytes from 192.168.0.203: icmp_seq=1 ttl=64 time=1.47 ms
- 64 bytes from 192.168.0.203: icmp_seq=2 ttl=64 time=1.10 ms
-
- # 查看log内容可以看到来自192.168.0.211的访问
- root@node2:~# journalctl -f
- -- Logs begin at Wed 2021-12-08 09:47:03 UTC. --
- Feb 01 11:42:51 node2 kernel: IN=ens33 OUT= MAC=00:0c:29:42:c3:52:00:0c:29:07:cf:68:08:00 SRC=192.168.0.211 DST=192.168.0.203 LEN=84 TOS=0x00 PREC=0x00 TTL=64 ID=55662 DF PROTO=ICMP TYPE=8 CODE=0 ID=1337 SEQ=2
- Feb 01 11:42:52 node2 kernel: IN=ens33 OUT= MAC=00:0c:29:42:c3:52:00:0c:29:07:cf:68:08:00 SRC=192.168.0.211 DST=192.168.0.203 LEN=84 TOS=0x00 PREC=0x00 TTL=64 ID=56575 DF PROTO=ICMP TYPE=8 CODE=0 ID=1337 SEQ=3

自己ping自己的情况下,没有被记录到log中
- root@node2:~# ping node2
- PING node2(node2 (240f:73:1e6d:1:20c:29ff:fe42:c352)) 56 data bytes
- 64 bytes from node2 (240f:73:1e6d:1:20c:29ff:fe42:c352): icmp_seq=1 ttl=64 time=0.060 ms
- 64 bytes from node2 (240f:73:1e6d:1:20c:29ff:fe42:c352): icmp_seq=2 ttl=64 time=0.046 ms
- ^C
- --- node2 ping statistics ---
- 2 packets transmitted, 2 received, 0% packet loss, time 1003ms
- rtt min/avg/max/mdev = 0.046/0.053/0.060/0.007 ms
- root@node2:~# journalctl -f
-s|--src|--source [ipaddress]
ipaddress: 可以用具体的IP地址,也可以用CIDR/VLSM格式。
- # 只记录来自192.168.0.211的访问(跟协议没有关系)
- root@node2:~# iptables -A INPUT -s 192.168.0.211 -j LOG
-
-
- root@node2:~# iptables -nvL INPUT
- Chain INPUT (policy ACCEPT 9 packets, 1794 bytes)
- pkts bytes target prot opt in out source destination
- 0 0 LOG all -- * * 192.168.0.211 0.0.0.0/0 LOG flags 0 level 4
-
- # ICMP
- [root@centos ~]# ping 192.168.0.203
- PING 192.168.0.203 (192.168.0.203) 56(84) bytes of data.
- 64 bytes from 192.168.0.203: icmp_seq=1 ttl=64 time=0.587 ms
-
- root@node2:~# journalctl -f
- -- Logs begin at Wed 2021-12-08 09:47:03 UTC. --
- Feb 01 11:56:39 node2 kernel: IN=ens33 OUT= MAC=00:0c:29:42:c3:52:00:0c:29:07:cf:68:08:00 SRC=192.168.0.211 DST=192.168.0.203 LEN=84 TOS=0x00 PREC=0x00 TTL=64 ID=12713 DF PROTO=ICMP TYPE=8 CODE=0 ID=1340 SEQ=1
-
- # TCP
- [root@centos ~]# nc -v -w 2 192.168.0.203 -z 22
- Connection to 192.168.0.203 22 port [tcp/ssh] succeeded!
-
- root@node2:~# journalctl -f
- -- Logs begin at Wed 2021-12-08 09:47:03 UTC. --
- Feb 01 11:59:45 node2 multipathd[753]: sda: failed to get sgio uid: No such file or directory
- Feb 01 11:59:45 node2 kernel: IN=ens33 OUT= MAC=00:0c:29:42:c3:52:00:0c:29:07:cf:68:08:00 SRC=192.168.0.211 DST=192.168.0.203 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=20099 DF PROTO=TCP SPT=57334 DPT=22 WINDOW=29200 RES=0x00 SYN URGP=0

-d|--dst|--destination [ipaddress]
ipaddress: 可以用具体的IP地址,也可以用CIDR/VLSM格式。
- # 在filter链的OUTPUT里追加一个规则
- # 当出口是192.168.0.211的时候 记录日志
- root@node2:~# iptables -A OUTPUT -d 192.168.0.211 -j LOG
-
- root@node2:~# iptables -nvL
- Chain INPUT (policy ACCEPT 11 packets, 1910 bytes)
- pkts bytes target prot opt in out source destination
- 6 348 LOG all -- * * 192.168.0.211 0.0.0.0/0 LOG flags 0 level 4
-
- Chain FORWARD (policy ACCEPT 0 packets, 0 bytes)
- pkts bytes target prot opt in out source destination
-
- Chain OUTPUT (policy ACCEPT 7 packets, 748 bytes)
- pkts bytes target prot opt in out source destination
- 0 0 LOG all -- * * 0.0.0.0/0 192.168.0.211 LOG flags 0 level 4
-
-
- [root@centos ~]# ping 192.168.0.203
- PING 192.168.0.203 (192.168.0.203) 56(84) bytes of data.
- 64 bytes from 192.168.0.203: icmp_seq=1 ttl=64 time=0.262 ms
-
- # 可以看到有两条记录,一条是INPUT的,一条是OUTPUT的。
- # 正好对应上面的两条规则
- root@node2:~# journalctl -f
- -- Logs begin at Wed 2021-12-08 09:47:03 UTC. --
- Feb 01 12:03:55 node2 kernel: IN=ens33 OUT= MAC=00:0c:29:42:c3:52:00:0c:29:07:cf:68:08:00 SRC=192.168.0.211 DST=192.168.0.203 LEN=84 TOS=0x00 PREC=0x00 TTL=64 ID=62477 DF PROTO=ICMP TYPE=8 CODE=0 ID=1363 SEQ=1
- Feb 01 12:03:55 node2 kernel: IN= OUT=ens33 SRC=192.168.0.203 DST=192.168.0.211 LEN=84 TOS=0x00 PREC=0x00 TTL=64 ID=50252 PROTO=ICMP TYPE=0 CODE=0 ID=1363 SEQ=1

有些东西,不必特别说明,像按源地址匹配,肯定是进入本机前去过滤,按目的地址匹配,肯定是从本机出去之后过滤。下面的网卡设备也同理
-i|--in-interface [devicename]
可以用ifconfig查看网卡设备名称
- # 入口是本机回环地址的网卡的时候,记录日志
- root@node2:~# iptables -A INPUT -i lo-j LOG
-
- root@node2:~# iptables -nvL INPUT
- Chain INPUT (policy ACCEPT 13 packets, 812 bytes)
- pkts bytes target prot opt in out source destination
- 0 0 LOG all -- lo * 0.0.0.0/0 0.0.0.0/0 LOG flags 0 level 4
-
- # 自己ping 本机回环地址
- root@node2:~# ping localhost c 1
- PING localhost (127.0.0.1) 56(84) bytes of data.
- 64 bytes from localhost (127.0.0.1): icmp_seq=1 ttl=64 time=0.112 ms
-
- root@node2:~# journalctl -f
- -- Logs begin at Wed 2021-12-08 09:47:03 UTC. --
- Feb 01 12:45:05 node2 kernel: IN=lo OUT= MAC=00:00:00:00:00:00:00:00:00:00:00:00:08:00 SRC=127.0.0.1 DST=127.0.0.1 LEN=84 TOS=0x00 PREC=0x00 TTL=64 ID=13506 DF PROTO=ICMP TYPE=8 CODE=0 ID=3 SEQ=1
- Feb 01 12:45:05 node2 kernel: IN=lo OUT= MAC=00:00:00:00:00:00:00:00:00:00:00:00:08:00 SRC=127.0.0.1 DST=127.0.0.1 LEN=84 TOS=0x00 PREC=0x00 TTL=64 ID=13507 PROTO=ICMP TYPE=0 CODE=0 ID=3 SEQ=1
-

-o|--out-interface [devicename]
可以用ifconfig查看网卡设备名称
- # 出口是本机回环地址网卡的时候记录日志
- root@node2:~# iptables -A OUTPUT -o lo -j LOG
-
- root@node2:~# iptables -nvL OUTPUT
- Chain OUTPUT (policy ACCEPT 20 packets, 1592 bytes)
- pkts bytes target prot opt in out source destination
- 0 0 LOG all -- * lo 0.0.0.0/0 0.0.0.0/0 LOG flags 0 level 4
-
- # 自己ping 本机回环地址
- root@node2:~# ping localhost -c 1
- PING localhost (127.0.0.1) 56(84) bytes of data.
- 64 bytes from localhost (127.0.0.1): icmp_seq=1 ttl=64 time=0.142 ms
-
- root@node2:~# journalctl -f
- Feb 02 11:13:33 node2 kernel: IN= OUT=lo SRC=127.0.0.1 DST=127.0.0.1 LEN=84 TOS=0x00 PREC=0x00 TTL=64 ID=47683 DF PROTO=ICMP TYPE=8 CODE=0 ID=4 SEQ=1
- Feb 02 11:13:33 node2 kernel: IN= OUT=lo SRC=127.0.0.1 DST=127.0.0.1 LEN=84 TOS=0x00 PREC=0x00 TTL=64 ID=47684 PROTO=ICMP TYPE=0 CODE=0 ID=4 SEQ=1
-

因为是按端口匹配,所以只能是对OSI传输层的协议,例如TCP,UDP
-p|--protocol [TCP|UDP] --sport [portNo]
- # 来自TCP协议的80端口的访问 记录日志
- #(因为80端口是在node2机器上开放的,所以在OUTPUT链里追加规则)
- root@node2:~# iptables -A OUTPUT -p TCP --sport 80 -j LOG
-
- root@node2:~# iptables -nvL OUTPUT
- Chain OUTPUT (policy ACCEPT 42 packets, 5475 bytes)
- pkts bytes target prot opt in out source destination
- 0 1075 LOG tcp -- * * 0.0.0.0/0 0.0.0.0/0 tcp spt:80 LOG flags 0 level 4
-
- [root@centos ~]# curl 192.168.0.203
-
- # 可以看到4条记录。
- root@node2:~# journalctl -f
- Feb 02 11:28:06 node2 kernel: IN= OUT=ens33 SRC=192.168.0.203 DST=192.168.0.211 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=0 DF PROTO=TCP SPT=80 DPT=60720 WINDOW=65160 RES=0x00 ACK SYN URGP=0
- Feb 02 11:28:06 node2 kernel: IN= OUT=ens33 SRC=192.168.0.203 DST=192.168.0.211 LEN=52 TOS=0x00 PREC=0x00 TTL=64 ID=25659 DF PROTO=TCP SPT=80 DPT=60720 WINDOW=509 RES=0x00 ACK URGP=0
- Feb 02 11:28:06 node2 kernel: IN= OUT=ens33 SRC=192.168.0.203 DST=192.168.0.211 LEN=911 TOS=0x00 PREC=0x00 TTL=64 ID=25660 DF PROTO=TCP SPT=80 DPT=60720 WINDOW=509 RES=0x00 ACK PSH URGP=0
- Feb 02 11:28:06 node2 kernel: IN= OUT=ens33 SRC=192.168.0.203 DST=192.168.0.211 LEN=52 TOS=0x00 PREC=0x00 TTL=64 ID=25661 DF PROTO=TCP SPT=80 DPT=60720 WINDOW=509 RES=0x00 ACK FIN URGP=0

-p|--protocol [TCP|UDP] --dport [portNo]
- # TCP协议,目标端口是80 的 记录日志
- root@node2:~# iptables -A INPUT -p TCP --dport 80 -j LOG
-
- root@node2:~# iptables -nvL INPUT
- Chain INPUT (policy ACCEPT 34 packets, 8905 bytes)
- pkts bytes target prot opt in out source destination
- 0 0 LOG tcp -- * * 0.0.0.0/0 0.0.0.0/0 tcp dpt:80 LOG flags 0 level 4
-
- [root@centos ~]# curl 192.168.0.203
-
- root@node2:~# journalctl -f
- -- Logs begin at Wed 2021-12-08 09:47:03 UTC. --
- Feb 02 11:40:25 node2 kernel: IN=ens33 OUT= MAC=00:0c:29:42:c3:52:00:0c:29:07:cf:68:08:00 SRC=192.168.0.211 DST=192.168.0.203 LEN=60 TOS=0x00 PREC=0x00 TTL=64 ID=48899 DF PROTO=TCP SPT=60722 DPT=80 WINDOW=29200 RES=0x00 SYN URGP=0
- Feb 02 11:40:25 node2 kernel: IN=ens33 OUT= MAC=00:0c:29:42:c3:52:00:0c:29:07:cf:68:08:00 SRC=192.168.0.211 DST=192.168.0.203 LEN=52 TOS=0x00 PREC=0x00 TTL=64 ID=48900 DF PROTO=TCP SPT=60722 DPT=80 WINDOW=229 RES=0x00 ACK URGP=0
- Feb 02 11:40:25 node2 kernel: IN=ens33 OUT= MAC=00:0c:29:42:c3:52:00:0c:29:07:cf:68:08:00 SRC=192.168.0.211 DST=192.168.0.203 LEN=129 TOS=0x00 PREC=0x00 TTL=64 ID=48901 DF PROTO=TCP SPT=60722 DPT=80 WINDOW=229 RES=0x00 ACK PSH URGP=0
- Feb 02 11:40:25 node2 kernel: IN=ens33 OUT= MAC=00:0c:29:42:c3:52:00:0c:29:07:cf:68:08:00 SRC=192.168.0.211 DST=192.168.0.203 LEN=52 TOS=0x00 PREC=0x00 TTL=64 ID=48902 DF PROTO=TCP SPT=60722 DPT=80 WINDOW=242 RES=0x00 ACK URGP=0
- Feb 02 11:40:25 node2 kernel: IN=ens33 OUT= MAC=00:0c:29:42:c3:52:00:0c:29:07:cf:68:08:00 SRC=192.168.0.211 DST=192.168.0.203 LEN=52 TOS=0x00 PREC=0x00 TTL=64 ID=48903 DF PROTO=TCP SPT=60722 DPT=80 WINDOW=242 RES=0x00 ACK FIN URGP=0
- Feb 02 11:40:25 node2 kernel: IN=ens33 OUT= MAC=00:0c:29:42:c3:52:00:0c:29:07:cf:68:08:00 SRC=192.168.0.211 DST=192.168.0.203 LEN=52 TOS=0x00 PREC=0x00 TTL=64 ID=48904 DF PROTO=TCP SPT=60722 DPT=80 WINDOW=242 RES=0x00 ACK URGP=0

还有很多其它的匹配方式,可以参照match
target就是,规则匹配后进行的动作。
上面的匹配方式用的都是LOG,这里不再赘述。
匹配条件后,如果target是ACCEPT,就代表接受规则,然后当前链的后面的规则和当前链所在表的其它链的规则都会被无视。
文字表达有点不清除,看下面的例子
- # 1号规则是接受,2号规则是记录日志(来自192.168.0.211的访问)
- root@node2:~# iptables -nvL INPUT --line-numbers
- Chain INPUT (policy ACCEPT 57 packets, 4586 bytes)
- num pkts bytes target prot opt in out source destination
- 1 0 0 ACCEPT all -- * * 192.168.0.211 0.0.0.0/0
- 2 0 0 LOG all -- * * 192.168.0.211 0.0.0.0/0 LOG flags 0 level 4
-
- [root@centos ~]# ping 192.168.0.203 -c 1
- PING 192.168.0.203 (192.168.0.203) 56(84) bytes of data.
- 64 bytes from 192.168.0.203: icmp_seq=1 ttl=64 time=1.28 ms
-
- # 查看LOG记录看不到访问日志
- root@node2:~# journalctl -f
-
- # 可能有点不太清晰,这里把2号规则改成DROP
- root@node2:~# iptables -nvL INPUT --line-numbers
- Chain INPUT (policy ACCEPT 16 packets, 968 bytes)
- num pkts bytes target prot opt in out source destination
- 1 7 481 ACCEPT all -- * * 192.168.0.211 0.0.0.0/0
- 2 0 0 DROP all -- * * 192.168.0.211 0.0.0.0/0
-
- # 发现还是可以访问
- [root@centos ~]# ping 192.168.0.203 -c 1
- PING 192.168.0.203 (192.168.0.203) 56(84) bytes of data.
- 64 bytes from 192.168.0.203: icmp_seq=1 ttl=64 time=0.769 ms

匹配条件后,如果动作是DROP,就会丢弃数据包,不做任何处理。(因为不会返回信息,发送方一直是等待状态,最好不用,可以用下面的REJECT)
- # 来自192.168.0.211的访问,全部丢弃(拒绝)。
- root@node2:~# iptables -nvL INPUT --line-numbers
- Chain INPUT (policy ACCEPT 6 packets, 364 bytes)
- num pkts bytes target prot opt in out source destination
- 1 0 0 DROP all -- * * 192.168.0.211 0.0.0.0/0
-
- # 可以看到提示的是timeout,如果timeout时间设置的比较长就会产生死套接字,占用端口
- # 所以不推荐用DROP,推荐用REJECT
- [root@centos ~]# nc -v -w 2 192.168.0.203 -z 80
- nc: connect to 192.168.0.203 port 80 (tcp) failed: Connection timed out
REJECT跟DROP大致相同,匹配规则后拒绝访问,但是会给访问机器返回一条错误消息。
REJECT 目标仅在 INPUT、FORWARD 和 OUTPUT 链或其子链中有效。
- root@node2:~# iptables -nvL INPUT --line-numbers
- Chain INPUT (policy ACCEPT 8 packets, 1710 bytes)
- num pkts bytes target prot opt in out source destination
- 1 0 0 REJECT all -- * * 192.168.0.211 0.0.0.0/0 reject-with icmp-port-unreachable
-
- # 可以看到立刻返回被拒绝的错误消息
- [root@centos ~]# nc -v -w 2 192.168.0.203 -z 80
- nc: connect to 192.168.0.203 port 80 (tcp) failed: Connection refused
上面其实大家比较熟知的普通防火墙的功能了,可以拒绝某个IP的访问,也可以只接受某个IP的访问,可以用协议+IP+端口做出各种组合来设计规则。
匹配条件后,如果动作是REDIRECT ,就会根据重定向的规则转发数据包。
仅在 nat 表的 PREROUTING 和 OUTPUT 链中有效。
端口号
-j REDIRECT --to-ports 8080
端口号范围
-j REDIRECT --to-ports 8080-8090
其实这个target就是本机设置代理用的。
- root@node2:~# iptables -t nat -A PREROUTING -p tcp --dport 8090 -j REDIRECT --to-ports 80
-
- root@node2:~# iptables -t nat -nvL PREROUTING --line-numbers
- Chain PREROUTING (policy ACCEPT 1 packets, 1314 bytes)
- num pkts bytes target prot opt in out source destination
- 1 0 0 REDIRECT tcp -- * * 0.0.0.0/0 0.0.0.0/0 tcp dpt:8090 redir ports 80
-
- # 可以看到8090端口没有被启用
- root@node2:~# ss -ntl
- State Recv-Q Send-Q Local Address:Port Peer Address:Port Process
- LISTEN 0 128 127.0.0.1:6010 0.0.0.0:*
- LISTEN 0 511 0.0.0.0:80 0.0.0.0:*
- LISTEN 0 4096 127.0.0.53%lo:53 0.0.0.0:*
- LISTEN 0 128 0.0.0.0:22 0.0.0.0:*
- LISTEN 0 128 [::1]:6010 [::]:*
- LISTEN 0 511 [::]:80 [::]:*
- LISTEN 0 128 [::]:22 [::]:*
-
-
- # 依然可以访问成功
- [root@centos ~]# curl 192.168.0.203:8090
- <!DOCTYPE html>
- <html>
- <head>
- <title>Welcome to nginx!</title>
- <style>
- body {
- width: 35em;
- margin: 0 auto;
- font-family: Tahoma, Verdana, Arial, sans-serif;
- }
- </style>
- </head>
- <body>
- <h1>Welcome to nginx!</h1>
- <p>If you see this page, the nginx web server is successfully installed and
- working. Further configuration is required.</p>
-
- <p>For online documentation and support please refer to
- <a href="http://nginx.org/">nginx.org</a>.<br/>
- Commercial support is available at
- <a href="http://nginx.com/">nginx.com</a>.</p>
-
- <p><em>Thank you for using nginx.</em></p>
- </body>
- </html>
- [root@centos ~]#

- # 用链接追踪的命令可以看到端口转发的过程
- root@node2:~# conntrack -E
- [NEW] tcp 6 120 SYN_SENT src=192.168.0.211 dst=192.168.0.203 sport=34372 dport=8090 [UNREPLIED] src=192.168.0.203 dst=192.168.0.211 sport=80 dport=34372
- [UPDATE] tcp 6 60 SYN_RECV src=192.168.0.211 dst=192.168.0.203 sport=34372 dport=8090 src=192.168.0.203 dst=192.168.0.211 sport=80 dport=34372
- [UPDATE] tcp 6 432000 ESTABLISHED src=192.168.0.211 dst=192.168.0.203 sport=34372 dport=8090 src=192.168.0.203 dst=192.168.0.211 sport=80 dport=34372 [ASSURED]
- [UPDATE] tcp 6 120 FIN_WAIT src=192.168.0.211 dst=192.168.0.203 sport=34372 dport=8090 src=192.168.0.203 dst=192.168.0.211 sport=80 dport=34372 [ASSURED]
- [UPDATE] tcp 6 30 LAST_ACK src=192.168.0.211 dst=192.168.0.203 sport=34372 dport=8090 src=192.168.0.203 dst=192.168.0.211 sport=80 dport=34372 [ASSURED]
- [UPDATE] tcp 6 120 TIME_WAIT src=192.168.0.211 dst=192.168.0.203 sport=34372 dport=8090 src=192.168.0.203 dst=192.168.0.211 sport=80 dport=34372 [ASSURED]
目标网络地址转换,仅在 nat 表中的 PREROUTING 和 OUTPUT 链中有效。
-j DNAT --to-destination 192.168.0.202[:port]
这个其实就是Docker,k8s里 常用的东西。
从本机做网络地址转换,只需要在OUTPUT链做地址转换就可以
iptables -t nat -A OUTPUT \ -p tcp -d $WAN_IP --dport $PORT -j DNAT --to-destination $SV_IP
- # 从本机访问本机端口8090的数据会被转发到192.168.0.202的80端口
- root@node2:~# iptables -t nat -A OUTPUT-p tcp --dport 8090 -j DNAT --to-destination 192.168.0.202:80
-
- root@node2:~# iptables -t nat -nvL OUTPUT
- Chain OUTPUT (policy ACCEPT 0 packets, 0 bytes)
- pkts bytes target prot opt in out source destination
- 0 0 DNAT tcp -- * * 0.0.0.0/0 0.0.0.0/0 tcp dpt:8090 to:192.168.0.202:80
-
- Chain POSTROUTING (policy ACCEPT 0 packets, 0 bytes)
- pkts bytes target prot opt in out source destination
-
- # 实际上8090端口并未开放
- root@node2:~# ss -ntl
- State Recv-Q Send-Q Local Address:Port Peer Address:Port Process
- LISTEN 0 128 127.0.0.1:6010 0.0.0.0:*
- LISTEN 0 128 127.0.0.1:6011 0.0.0.0:*
- LISTEN 0 511 0.0.0.0:80 0.0.0.0:*
- LISTEN 0 4096 127.0.0.53%lo:53 0.0.0.0:*
- LISTEN 0 128 0.0.0.0:22 0.0.0.0:*
- LISTEN 0 128 [::1]:6010 [::]:*
- LISTEN 0 128 [::1]:6011 [::]:*
- LISTEN 0 511 [::]:80 [::]:*
- LISTEN 0 128 [::]:22 [::]:*
-
-
- root@node2:~# curl 192.168.0.203:8090
- <!DOCTYPE html>
- <html>
- <head>
- <title>Welcome to nginx!</title>
- <style>
- body {
- width: 35em;
- margin: 0 auto;
- font-family: Tahoma, Verdana, Arial, sans-serif;
- }
- </style>
- </head>
- <body>
- <h1>Welcome to nginx!</h1>
- <p>If you see this page, the nginx web server is successfully installed and
- working. Further configuration is required.</p>
-
- <p>For online documentation and support please refer to
- <a href="http://nginx.org/">nginx.org</a>.<br/>
- Commercial support is available at
- <a href="http://nginx.com/">nginx.com</a>.</p>
-
- <p><em>Thank you for using nginx.</em></p>
- </body>
- </html>
-

下面是地址转换的过程
- root@node2:~# conntrack -E
- [NEW] tcp 6 120 SYN_SENT src=192.168.0.203 dst=192.168.0.203 sport=48776 dport=8090 [UNREPLIED] src=192.168.0.202 dst=192.168.0.203 sport=80 dport=48776
- [UPDATE] tcp 6 60 SYN_RECV src=192.168.0.203 dst=192.168.0.203 sport=48776 dport=8090 src=192.168.0.202 dst=192.168.0.203 sport=80 dport=48776
- [UPDATE] tcp 6 432000 ESTABLISHED src=192.168.0.203 dst=192.168.0.203 sport=48776 dport=8090 src=192.168.0.202 dst=192.168.0.203 sport=80 dport=48776 [ASSURED]
- [UPDATE] tcp 6 120 FIN_WAIT src=192.168.0.203 dst=192.168.0.203 sport=48776 dport=8090 src=192.168.0.202 dst=192.168.0.203 sport=80 dport=48776 [ASSURED]
- [UPDATE] tcp 6 30 LAST_ACK src=192.168.0.203 dst=192.168.0.203 sport=48776 dport=8090 src=192.168.0.202 dst=192.168.0.203 sport=80 dport=48776 [ASSURED]
- [UPDATE] tcp 6 120 TIME_WAIT src=192.168.0.203 dst=192.168.0.203 sport=48776 dport=8090 src=192.168.0.202 dst=192.168.0.203 sport=80 dport=48776 [ASSURED]
- 192.168.0.0/24
-
- 访问用机器(Centos) ------- iptables设定机器(node2) ------- 服务器(node1)
- 192.168.0.211 192.168.0.203 192.168.0.202
在192.168.0.211机器上访问192.168.0.203的8091端口,然后转发到192.168.0.202的80端口。
这种情况下不只是需要DNAT,还需要SNAT,从192.168.0.202的80端口返回的数据包要做源地址转换。
- # 修改配置,使得当前机器可以做妆发
- root@node2:~# echo 1 > /proc/sys/net/ipv4/ip_forward
-
- # 确认修改
- root@node2:~# sysctl net.ipv4.ip_forward
- net.ipv4.ip_forward = 1
- # 目标地址转换 192.168.0.203:8091 -> 192.168.0.202:80
- root@node2:~# iptables -t nat -A PREROUTING -p tcp -d 192.168.0.203 --dport 8091 -j DNAT --to-destination 192.168.0.202:80
-
- # 源目标转换 192.168.0.202:80 -> 192.168.0.203:8091
- root@node2:~# iptables -t nat -A POSTROUTING -p tcp -d 192.168.0.202 --dport 80 -j SNAT --to-source 192.168.0.203:8091
-
- # 确认规则
- root@node2:~# iptables -t nat -nvL
- Chain PREROUTING (policy ACCEPT 5 packets, 1145 bytes)
- pkts bytes target prot opt in out source destination
- 4 240 DNAT tcp -- * * 0.0.0.0/0 192.168.0.203 tcp dpt:8091 to:192.168.0.202:80
-
- Chain INPUT (policy ACCEPT 5 packets, 1145 bytes)
- pkts bytes target prot opt in out source destination
-
- Chain OUTPUT (policy ACCEPT 0 packets, 0 bytes)
- pkts bytes target prot opt in out source destination
-
- Chain POSTROUTING (policy ACCEPT 0 packets, 0 bytes)
- pkts bytes target prot opt in out source destination
- 2 120 SNAT tcp -- * * 0.0.0.0/0 192.168.0.202 tcp dpt:80 to:192.168.0.203:8091

- # 发现访问成功
- [root@centos ~]# curl 192.168.0.203:8091
- this is node1(192.168.0.202)
因为实验环境是静态IP,如果是动态IP的话,可以不用SNAT来做源地址转换,可以跟Docker一样用MASQUERADE 来做源地址转换。使用起来更加方便。
iptables还有很多target,像RETURN经常用,还有很多不常用的可以参照target
iptables还可以用limit match来做限流(rate limit),有兴趣可以自己实验一下。
还有很多不常用的用法。有机会用到继续分享。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。