|  | 
 
| -- 
 dns 视图(dns view)
 Berkeley Internet Name Domain (BIND)  --伯克利网络名字域
 bind 9 版本加入了视图功能   view
 
 CDN 内容分发网络  (content  distributed network)
 
 将网站源服务器中的内容存储到分布于各地的CDN网络节点上,通过智能网络流量分配控制系统,
 将终端用户的访问请求自动指向健康可用且距离本地最近的CDN专用服务器上,以提高用户访问
 的响应速度和服务的可用性,改善互联网上的服务质量。
 
 bind+squid  实现基本CDN
 
 分布式缓存服务器  + 智能DNS(DNS view)
 www.abc.com  --》
 内蒙用户
 新疆用户  北京
 
 成都 武汉   上海
 
 
 广州
 (网站源在深圳)
 
 IP库如何获得?
 IANA(互联网数字分配机构,internet assigned numbers authority)
 ARIN (American registry for internet numbers)
 北美,南美
 RIPE
 欧洲,中东,北非
 APNIC
 亚洲,大洋洲
 
 www.apnic.net
 这个网站上有一个叫whois数据库,可以查询所有的公网IP现在被分配到哪
 
 
 参考网址:
 http://bbs.chinaunix.net/thread-577601-1-1.html
 
 --使用下面的脚本,就会在当前运行的目录下产生chinanet(电信),unicom(网通),others(其它)这三个IP库文件
 # vim ripe.sh
 #!/bin/sh
 mkdir /root/apnic -p
 FILE=/root/apnic/ip_apnic
 wget http://ftp.apnic.net/apnic/stats/apnic/delegated-apnic-latest -O $FILE
 grep 'apnic|CN|ipv4|' $FILE | cut -f 4,5 -d'|'|sed -e 's/|/ /g' | while read ip cnt
 do
 echo $ip
  cnt mask=$(cat << EOF | bc | tail -1
 pow=32;
 define log2(x) {
 if (x<=1) return (pow);
 pow--;
 return(log2(x/2));
 }
 log2($cnt)
 EOF)
 echo $ip/$mask>> cn.net
 if whois [url=mailto
  ip@whois.apnic.net]$ip@whois.apnic.net[/url] | grep -i ".*chinanet.*\|.*telecom.*">/dev/null;then echo $ip/$mask >> chinanet
 elif whois [url=mailto
  ip@whois.apnic.net]$ip@whois.apnic.net[/url] | grep -i ".*unicom.*">/dev/null;then echo $ip/$mask >> unicom
 else
 echo $ip/$mask >> others
 fi
 done
 
 --注意:上面的脚本在rhel5里能执行,因为rhel5默认会安装jwhois这个包(这个包自带whois命令,不要用我们编译出来的whois3命令,在查询时会卡住)
 
 如果上面的脚本要在rhel6里执行的话,则yum install jwhois  -y
 然后把脚本里mask变量里的$()这个执行符号改成 ` `这个执行符号
 
 ===============================================================
 
 实践:上面我做的IP库是电信与网通的IP库
 
 如果我现在是按地域来划分的,假设我划分成(北京,成都,上海,深圳,武汉)这五个CDN节点,请尝试把他们的IP库给做出来
 (地域的划分情况随你自己,比如湖南离武汉和深圳都比较近,你要划分到哪一个区域自己定)
 
 北京
 
 成都 武汉   上海
 
 
 广州
 (网站源在深圳)
 
 #!/bin/sh
 mkdir /root/apnic -p
 touch /root/apnic/ip_apnic
 FILE=/root/apnic/ip_apnic
 rm -f $FILE
 wget http://ftp.apnic.net/apnic/stats/apnic/delegated-apnic-latest -O $FILE
 grep 'apnic|CN|ipv4|' $FILE | cut -f 4,5 -d'|'|sed -e 's/|/ /g' | while read ip cnt
 do
 echo $ip
  cnt mask=`cat << EOF | bc | tail -1
 pow=32;
 define log2(x) {
 if (x<=1) return (pow);
 pow--;
 return(log2(x/2));
 }
 log2($cnt)
 EOF`
 echo $ip/$mask>> cn.net
 if whois [url=mailto
  ip@whois.apnic.net]$ip@whois.apnic.net[/url] |grep descr:|head -1| grep -i ".*xinjiang.*\|.*tibet.*\|.*qinghai.*\|.*gansu.*\|.*yunnan.*\|.*sichuan.*">/dev/null;then echo $ip/$mask >> chengdu
 elif whois [url=mailto
  ip@whois.apnic.net]$ip@whois.apnic.net[/url] |grep descr:|head -1| grep -i ".*neimeng.*\|.*ningxia.*\|.*shanxi.*\|.*hebei.*\|.*beijing.*\|.*tianjin.*\|.*shandong.*\|.*liaoning.*\|.*jilin.*\|.*heilongjiang.*">/dev/null;then echo $ip/$mask >> beijing
 elif whois [url=mailto
  ip@whois.apnic.net]$ip@whois.apnic.net[/url] |grep descr:|head -1| grep -i ".*shannxi.*\|.*shaanxi.*\|.*henan.*\|.*chongqing.*\|.*hubei.*\|.*hunan.*\|.*jiangxi.*">/dev/null;then echo $ip/$mask >> wuhan
 elif whois [url=mailto
  ip@whois.apnic.net]$ip@whois.apnic.net[/url] |grep descr:|head -1|grep -i ".*guangxi.*\|.*guangdong.*\|.*hainan.*\|.*fujian.*\|.*hk.*\|.*macau.*">/dev/null;then echo $ip/$mask >> shenzhen
 elif whois [url=mailto
  ip@whois.apnic.net]$ip@whois.apnic.net[/url] |grep descr:|head -1| grep -i ".*anhui.*\|.*zhejiang.*\|.*jiangsu.*\|.*shanghai.*">/dev/null;then echo $ip/$mask >> shanghai
 else
 echo $ip/$mask >> others
 fi
 done
 
 --注意:上面的脚本产生的结果大部分应该是没问题的,但也有一些会存在分配的问题,改脚本或者是单独处理肯定是可以解决的;这里只是提供一个思路,不要把这个脚本直接用到真实环境
 
 =====================================================================
 
 DNS view
 根据你访问过来的IP对应ACL列表来判断,从而解析到不同的服务器主机
 在CDN中应用很多,也是解决目前区域间带宽小和延迟大的问题的一种方法。
 
 DNS 视图
 view优点:
 优化访问速度
 成本低,无需额外设备
 配置灵活简单
 负载均衡
 
 视图的在DNS里的配置原理:
 每一个view由match-clients来匹配网段,如:
 match-clients {10.1.1.0/24;20.1.1.0/24}
 --表示只有10.1.1和20.1.1网段可以访问此view
 --那么因为定义的网段可能有很多,所以使用了acl,定义方法如下
 acl "internalnet" {10.1.1.0/24;20.1.1.0/24;30.1.1.0/24}
 view "internel" {
 match-clients { "internalnet"; };
 };
 
 --或者使用include 来定义一个文件,在文件里写多网段IP
 vim /var/named/internalnet    --在此文件里写IP库
 include "internalnet";  --把此IP库文件给装载进来
 view "internel" {
 match-clients { internalnet;}   --这里不是include的文件名,而是这个文件里定义的acl名
 };
 
 第一步:定义ACL文件  (用来放网段的文件,IP库)
 # yum install bind* -y
 
 [root@li ~]# vim /var/named/dianxin  --电信IP库
 acl dx {
 10.1.1.153;
 10.1.1.101; --IP写法
 200.11.22.0/24; --网段写法
 };
 
 [root@li ~]# vim /var/named/wangtong  --网通IP库
 acl wt {
 10.1.1.73;
 10.1.1.174;
 100.10.20.0/24;
 };
 
 第二步:配置named.conf
 
 [root@li ~]# vim /etc/named.conf
 
 options {
 listen-on port 53 { any; }; --改为any
 listen-on-v6 port 53 { ::1; };
 directory  "/var/named";
 dump-file  "/var/named/data/cache_dump.db";
 statistics-file "/var/named/data/named_stats.txt";
 memstatistics-file "/var/named/data/named_mem_stats.txt";
 allow-query     { any; }; --改为any
 recursion yes;
 dnssec-enable yes;
 dnssec-validation yes;
 dnssec-lookaside auto;
 bindkeys-file "/etc/named.iscdlv.key";
 managed-keys-directory "/var/named/dynamic";
 };
 logging {
 channel default_debug {
 file "data/named.run";
 severity dynamic;
 };
 };
 #zone "." IN {
 # type hint;
 # file "named.ca";
 #};
 #include "/etc/named.rfc1912.zones"; --这里把上面的根域和子配置文件里所有域都注释掉;因为配置了视图,那么所有的域都得要配置才行,所以这里就直接注释不用
 include "/etc/named.root.key";
 --下面的就是在主配置文件上新加的
 
 include "dianxin";
 include "wangtong";
 
 view "v1" {   --视图名,随便取
 match-clients {dx;}; --dx为acl名,而不是IP库文件名
 zone "cluster.com" IN {
 type master;
 file "data/dx.cluster.com.zone";
 };
 };
 view "v2" {
 match-clients {wt;};
 zone "cluster.com" IN {
 type master;
 file "data/wt.cluster.com.zone";
 };
 };
 
 view "v3" {
 match-clients {any;};  --any代表所有,这里一定要放在最后,匹配完了dx,wt,最后的所有都为others
 zone "cluster.com" IN {
 type master;
 file "data/others.cluster.com.zone";
 };
 };
 
 第三步:配置named.conf里定义的三个zone文件
 # vim /var/named/data/dx.cluster.com.zone
 $TTL 86400
 @       IN      SOA     dx.     root.   (
 2011102401
 120
 60
 30
 86400 )
 IN      NS      10.1.1.35.
 www     IN      A       1.1.1.1  --此为www.cluster.com域名的电信线路的IP,或者是在电信机房的服务器的IP
 
 # vim /var/named/data/wt.cluster.com.zone
 $TTL 86400
 @       IN      SOA     wt.     root.   (
 2011102401
 120
 60
 30
 86400 )
 IN      NS      10.1.1.35.
 www     IN      A       2.2.2.2  --网通线路的
 
 # vim /var/named/others.cluster.com.zone
 $TTL 86400
 @       IN      SOA     others.     root.   (
 2011102401
 120
 60
 30
 86400 )
 IN      NS      10.1.1.35.
 www     IN      A       3.3.3.3 --除了电信和网通外的用户指向的服务器IP,如果你只有电信和网通两个线路,可以随意指向其中一个。但这里是实验,我假设有三个线路,所以这里指向第三个IP 3.3.3.3
 
 第四步: 重启服务
 /etc/init.d/named restart
 
 问题:上面做的是单机单域,多地域多运营商都要区分如何做?
 
 也就是IP库文件要分得更细,
 比如广东附近几个省的电信的IP段要单独一个IP库
 广东附近几个省的网通的IP段要单独一个IP库
 其它的类似
 
 课外扩展:
 上网查查类似dnspod这种智能DNS服务运营商
 
 ====================================================================
 
 http://www.netfilter.org/
 netfilter / iptables   --iptables 的全名  2.4版本内核后都集成有这个组件
 
 1,包过滤防火墙
 在网络层对数据包进行选择,主要是对数据包的所使用的协议,端口,源地址和目标地址等参数来进行过滤
 实现四层的包过滤(OSI七层)
 
 2,状态检测
 TCP有三次握手的阶段,常用的WEB,文件下载,发送和接收邮件等等都是TCP
 状态检测防火墙除了包过滤防火墙所考查的参数之外,还要关心数据包连接的状态
 3,代理网关  squid
 把内网和外网是完全隔离的,内网和外网不能进行直接的TCP通讯,必须通过代理网关的处理
 .exe .jpg
 可以实现七层的包过滤
 
 iptables  基本概念
 
 四张表:    表里有链  (chain )
 filter:  用来进行包过滤:  INPUT  OUTPUT FORWARD
 nat:   用来网络地址转换:   network  address translation ,允许一个内网地址块,通过NAT转换成公网IP,实现对公网的访问,解决IP地址不足
 PREROUTING   POSTROUTING OUTPUT
 mangle :用来对数据包标志
 PREROUTING INPUT OUTPUT  FORWARD  POSTROUTING
 
 raw:对原始数据包的处理
 PREROUTING OUTPUT
 
 
 Incoming                 /     \         Outgoing
 -->[Routing ]--->|FORWARD|------->
 [Decision]     \_____/        ^
 |                        |
 |                       ____
 ___                     /    \
 /   \                  |OUTPUT|
 |INPUT|                  \____/
 \___/                      ^
 |                        |
 ----> Local Process ----
 
 
 iptables
 -A  增加一条规则,后接链名,默认是加到规则的最后面
 -D  删除
 -L  列出规则
 -n   以数值显示
 -I   在最前面插入规则
 -v   显示统计数据,与-L一起用,看到的信息更多
 
 -F  清空规则
 -z   清空计数器
 -x   清空自定义链
 -t   后接表名
 -P   policy,默认策略
 -p   protocol,后接协议名
 --dport  目标端口
 --sport  源端口
 -d  destination,目标地址
 -s  source,源地址
 -i  接网卡接口, 进入的网卡接口
 -o  接网卡接口, 出去的网卡接口
 -j  后接动作
 动作的分类:
 ACCEPT    接收数据包
 DROP    丢弃数据包
 REJECT   拒绝数据包,和DROP的区别就是REJECT会返回错误信息,DROP不会
 MASQUEREAD  IP地址伪装,使用NAT转换成外网IP,可以PPP拔号(外网IP不固定情况)
 SNAT   源地址转换,它与MASQUEREAD的区别是SNAT是接一个固定IP
 DNAT 目标地址转换
 LOG    记录日志
 
 例1,列规则
 iptables -L  --默认看的就是filter表
 iptables -L -t filter
 iptables -L -t  nat
 iptables -L -t   mangle
 iptables -L -t   raw
 
 例2,对ping的控制
 ICMP协议传输过程是双向的,可以对其INPUT或OUTPUT都可以控制
 10.1.1.0/24网段ping本机,会被拒绝(客户端会收到拒绝信息)
 # iptables -t filter -A INPUT -p icmp -s 10.1.1.0/24 -j REJECT
 # iptables -t filter -D INPUT -p icmp -s 10.1.1.0/24 -j REJECT --删除上一条规则
 # iptables -t filter -A INPUT -p icmp -s 10.1.1.0/24 -j DROP
 # iptables -t filter -D INPUT -p icmp -s 10.1.1.0/24 -j DROP
 # iptables -t filter -A OUTPUT -p icmp -d 10.1.1.0/24 -j REJECT
 # iptables -t filter -D OUTPUT -p icmp -d 10.1.1.0/24 -j REJECT
 
 # iptables -t filter -A OUTPUT -p icmp -d 10.1.1.0/24 -j DROP
 # iptables -t filter -D OUTPUT -p icmp -d 10.1.1.0/24 -j DROP
 --上面四种方法都可以控制拒绝10.1.1.0/24网段ping本机
 # iptables -t filter -A INPUT -p icmp  -j REJECT  --如果不写-s或-d,默认代表所有人
 扩展
 我想实现所有人都ping不通我,但是10.1.1.35这个IP能ping通我
 # iptables -t filter -A INPUT -p icmp -j REJECT
 # iptables -t filter -A INPUT -p icmp -s 10.1.1.35 -j ACCEPT
 --此写法错误的
 ------------------------------------------------
 规则就是一个访问控制列表(ACL),读取的顺序是从上往下一条一条匹配,匹配一条就不继续往下匹配,最后匹配默认策略,所以正确写法应该是把刚才允许10.1.1.35的写到最前面
 -----------------------------------------------
 # iptables -t filter -A INPUT -p icmp -j REJECT
 # iptables -t filter -I INPUT -p icmp -s 10.1.1.35 -j ACCEPT
 --正确写法,把第二条加到第一条前面
 
 # iptables -t filter -I INPUT 2 -p icmp -s 10.1.1.36 -j ACCEPT
 --链后面接数字2,表示插入到原来第二条的上面,成为新的第2条
 
 删除的方法:
 方法一:
 # iptables -t filter -D  INPUT -s 10.1.1.8  -p icmp -j ACCEPT
 --加的时候怎么写,删除时就要怎么写  A 参数换成 D就可以
 方法二;
 # iptables -L -n  --line
 # iptables  -D INPUT  2
 --在规则比较多或者不好写规则的情况下,可以先用--line或者--line-number列出行号,再用行号删除
 
 方法三:
 # iptables -F
 --直接清空filter表的所有规则
 iptables -X
 iptables -Z   --清除计数器,自定义链
 
 例3,规则的保存与还原
 # /etc/init.d/iptables save    --这样是默认保存到/etc/sysconfig/iptables
 # iptables-save > /etc/sysconfig/iptables   --将当前规则保存到这个文件,文件可以自定义
 # iptables -F
 # iptables -X
 # iptables -Z --使用这三条来清空filter表,如果别的表也要清空的话,就加-t 表名都清一次
 # iptables-restore < /etc/sysconfig/iptables --把保存的规则还原回去
 
 --/etc/sysconfig/iptables文件为默认保存文件,重启iptables服务会默认把此文件里的规则还原。当然也可以手工保存到另一个文件,就需要iptables-restore手工还原了。
 
 扩展,如何完全关闭rhel6的iptables服务
 因为rhel6在安全性有很多加强,就算是你把iptables服务关闭,并chkconfig iptables on,重启还是有可能会有规则
 所以可以用下面的方法
 # iptables -F
 # iptables -F -t nat
 # iptables -F -t mangle
 # /etc/init.d/iptables save --保存为空规则
 # chkconfig iptables on
 或者用下面的方法
 # echo > /etc/sysconfig/iptables
 # /etc/init.d/iptables restart
 # chkconfig iptables on
 
 
 例4,每个链的默认策略的修改
 # iptables -P INPUT DROP --INPUT键默认策略改为DROP,改回来把DROP换成ACCEPT就行了
 # iptables -P OUTPUT DROP --OUTPUT键默认策略改为DROP
 
 例5,实现允许ssh过来(代表本机为服务器身份),ssh出去(代表本机为客户端身份),别的都拒绝  (要求,INPUT和OUTPUT双链默认策略都为DROP)
 OUTPUT  INPUT
 客户端 随机端口 ---》  服务器  22
 
 客户端 随机端口 《---  服务器  22
 INPUT          OUTPUT
 实现允许10.1.1.0/24网段来ssh本机(服务器),其它任何访问都拒绝(在双链拒绝的情况下)
 # iptables -P INPUT DROP
 # iptables -P OUTPUT DROP
 # iptables -A INPUT -p tcp --dport 22 -s 10.1.1.0/24 -j ACCEPT
 # iptables -A OUTPUT -p tcp --sport 22 -d 10.1.1.0/24 -j ACCEPT
 
 实现允许从本机(客户端)ssh到10.1.1.0/24网段的服务器,其它任何访问都拒绝(在双链拒绝的情况下)
 # iptables -P INPUT DROP
 # iptables -P OUTPUT DROP
 # iptables -A OUTPUT -p tcp --dport 22 -d 10.1.1.0/24 -j ACCEPT
 # iptables -A INPUT -p tcp --sport 22 -s 10.1.1.0/24 -j ACCEPT
 
 
 例6,在例五的基础上允许ping自己的IP,本地回环127.0.0.1和10.1.1.35
 下面两条定义能ping自己和127本地回环
 # iptables -A INPUT -i lo -p icmp -j ACCEPT
 # iptables -A OUTPUT -o lo -p icmp -j ACCEPT
 --这里用lo设备是127网段的所有回环地址都可以。如果指定ip127.0.0.1的话,只能控制这一个IP。在控制的范围上还是有区别的
 下面两条定义此服务器和35这台机器可以互ping
 # iptables -A INPUT -p icmp -s 10.1.1.35 -j ACCEPT
 # iptables -A OUTPUT -p icmp -d 10.1.1.35 -j ACCEPT
 
 例7,
 在上面的基础上再加上只允许10.1.1.0/24这个网段访问你的httpd服务,和你只能访问10.1.1.0/24网段的httpd服务
 
 
 例8
 在上面的基础上再加上允许别人访问本台服务器的DNS
 只需要做udp的53端口就可以了,不用写tcp 53(因为tcp 53主要是用于主从DNS服务器同步的)
 
 
 -------------------------------
 一些特殊的写法
 连续端口或多端口写法
 iptables -A INPUT -p tcp --dport 1:1000 -j ACCEPT
 iptables -A INPUT -p tcp -m multiport  --dport 25,110 -j ACCEPT
 硬件地址
 iptables -A INPUT -m mac --mac-source 00:23:CD:95
  A:0B -p all  --dport 80 -j ACCEPT 
 
 例9 邮件服务器
 25 smtp   110 pop3
 
 例10 dhcp
 iptables 对dhcp端口控制无效
 应用层
 表示层
 会话层
 传输层
 网络层
 数据链路层
 物理层
 
 例11
 samba
 139   445
 
 例12
 nfs
 --因为nfs用到rpc调用,端口不固定,所以需要把端口给固定起来.nis服务也会用到rpc调用,也需要做端口绑定(鸟哥书上面nis那章节有)
 
 vim /etc/sysconfig/nfs     --在此文件里加上下面四句
 LOCKD_TCPPORT=3000
 LOCKD_UDPPORT=3000
 MOUNTD_PORT=3001
 STATD_PORT=3002
 /etc/init.d/nfs restart
 /etc/init.d/rpcbind restart --这里先把默认策略改成ACCEPT,再启动就可以启动起来,然后再把默认策略改回成DROP,再继续做下面的实验
 netstat -ntl |grep 300   去查看,看到rpc.的守护进程的端口为自己绑定的端口
 
 iptables -A INPUT -p tcp  --dport 3000:3002 -j ACCEPT
 iptables -A OUTPUT -p tcp  --sport 3000:3002 -j ACCEPT
 iptables -A INPUT -p udp  --dport 3000:3002 -j ACCEPT
 iptables -A OUTPUT -p udp  --sport 3000:3002 -j ACCEPT
 
 还要加上2049(nfs)和111(rpcbind)的端口的规则
 
 iptables -A  INPUT -p tcp  --dport 2049 -j ACCEPT
 iptables -A  OUTPUT -p tcp  --sport 2049 -j ACCEPT
 iptables -A  INPUT -p udp  --dport 2049 -j ACCEPT
 iptables -A  OUTPUT -p udp  --sport 2049 -j ACCEPT
 
 iptables -A  INPUT -p tcp  --dport 111 -j ACCEPT
 iptables -A  OUTPUT -p tcp  --sport 111 -j ACCEPT
 iptables -A  INPUT -p udp  --dport 111 -j ACCEPT
 iptables -A  OUTPUT -p udp  --sport 111 -j ACCEPT
 
 --现在就可以用另一台机showmount -e 查看并进行挂载了
 
 --练习:把上面的3000,3001,3002,2049,111合起来只写4条iptables来做
 [root@localhost ~]# iptables -A INPUT -p tcp -m multiport --dport 111,2049,3000,3001,3002 -j ACCEPT
 [root@localhost ~]# iptables -A INPUT -p udp -m multiport --dport 111,2049,3000,3001,3002 -j ACCEPT
 [root@localhost ~]# iptables -A OUTPUT -p tcp -m multiport --sport 111,2049,3000,3001,3002 -j ACCEPT
 [root@localhost ~]# iptables -A OUTPUT -p udp -m multiport --sport 111,2049,3000,3001,3002 -j ACCEPT
 
 
 练习:上面四条做的是为NFS服务器的身份允许别人访问
 如果你做为NFS客户端去访问别人的NFS服务器,又应该如何写?
 
 例13: yum
 视你做的yum类型而定
 file
 ftp
 http
 
 例14
 mysql
 3306
 
 例15
 oracle 监听
 1521
 
 例16
 rsync
 873
 还加一个22
 
 
 练习:
 ftp实现双链拒绝的情况下,客户端通过主动和被动都能访问进来
 服务器端准备:
 # yum install vsftpd -y
 # vim /etc/vsftpd/vsftpd.conf
 pasv_min_port=3000
 pasv_max_port=3005
 # /etc/init.d/vsftpd restart
 # iptables -P INPUT DROP
 # iptables -P OUTPUT DROP
 客户端测试方法:
 1,命令连接测试,能成功连接上就表示命令端口连接没问题
 # ftp 10.1.1.36
 2,数据传输测试,用上面的命令登录成功后,在客户端使用passive指令转换你的主动和被动模式,
 (服务器端不用转换,因为服务器端默认就是主动和被动都支持的)
 然后使用ls指令能看到里面的pub子目录就表示数据传输OK了(因为默认是登录到服务器的/var/ftp/目录,里面有一个pub子目录)
 
 主动:
 server   client
 20         21   n m
 <-------------
 
 -------------->
 ---------------------------------------->
 <---------------------------------------
 
 iptables -A INPUT -p tcp --dport 21 -j ACCEPT
 iptables -A OUTPUT -p tcp --sport 21 -j ACCEPT
 iptables -A OUTPUT -p tcp --sport 20 -j ACCEPT
 iptables -A INPUT -p tcp --dport 20 -j ACCEPT
 
 被动:
 server   client
 随机端口      21   n m
 3000-3005  <---------------
 ---------------->
 
 <--------------------------------------------
 
 --------------------------------------------->
 iptables -A INPUT -p tcp --dport 21 -j ACCEPT
 iptables -A OUTPUT -p tcp --sport 21 -j ACCEPT
 iptables -A INPUT -p tcp --dport 3000:3005 -j ACCEPT
 iptables -A OUTPUT -p tcp --sport 3000:3005 -j ACCEPT
 
 
 | 
 |