image.png

R1路由器有5条路由,4条明细,以及一条对4条明细汇总的路由信息。

现在要求R1将路由传递给R2的时候,只将汇总的路由干掉,留下4条明细到R2路由器。

 

这种需求,用ACL是做不到的,因为ACL只能匹配路由的前缀部分,ACL却无法匹配到路由的前缀长度部分。

但是一条完整的路由信息是由:前缀(网络号)+前缀长度(掩码长度)=完整的路由条目

这就是为什么提到ACL做不到上边的需求根本原因。

所以这个需求只能用到prefix-list(前缀列表)来解决,前缀列表是一个强大的路由匹配工具,prefix-list不但可以匹配前缀而且还可以匹配前缀长度也就是掩码部分,这样做的好处就是匹配的路由信息更加精确,更加灵活。


使用前缀列表只需要这一条命令就可以把R1的汇总路由给干掉,并且不会干掉明细路由中的192.168.0.0/24这条路由信息

R1(config)#ip prefix-list 10 seq 5 deny 192.168.0.0/22

如果你使用ACL这么写,汇总路由被你干掉了,相应的明细路由中的192.168.0.0/24这条路由信息也被你给干掉了,因为这条ACL匹配不到掩码部分,也就是它只匹配到了192.168.0.0这里,掩码信息/24没有匹配到。

R1(config)#access-list 10 deny 192.168.0.0 0.0.0.0

有些人用ACL在匹配路由的时候喜欢用下边的写法:

R1(config)#access-list 10 deny 192.168.0.0 0.0.0.255

用上边的0.0.0.255其实是要比0.0.0.0这种写法更不精确,匹配出的路由条目会更广更多


上边只是对前缀列表和ACL的简单的比较说明,下边先讲下ACL的通配符,深入的了解下上边的几个问题。

----------------------------------------------------手动分割----------------------------------------------------------------

ACL有标准ACL和扩展ACL两种

标准ACL编号:1-99

扩展ACL编号:100-199

ACL有命名式标准ACL和命名式扩展ACL两种,命名式ACL和上边标准ACL是没有本质区别的,只是命名式ACL更加简单明了,可以支持针对某个ACL中的某条ACL语句进行删除和添加,所以现网中建议使用命名式ACL,方便做事。

 

标准ACL访问控制列表:

access-list access-list-number { permit | deny } {source [source-wildcard] | any}

命令解释如下:

access-list:访问列表命令

access-list-number:访问列表号码,值为1~99.

permit:允许

deny:拒绝

source:源IP地址

source-wildcard:源IP地址的通配符

扩展ACL访问控制列表:

access-list access-list-number { permit | deny } { protocol \ protocol-keyword } { source [ source-wildcard ] | any } { destination destination-wildcard } | any }[protocol-specific options][log]

命令解释如下:

access-list-number:访问列表号码,值为100~199

protocol \ protocol-keyword:可使用的协议,包括IPICMPIGRPEIGRPOSPF等。

destination destination-wild:目的IP地址,格式与源IP地址相同

protocol-specific options:协议制定的选项

log:记录有关数据报进入访问列表的信息


先看下标准ACL,在ACL源地址后边跟的是一个通配符掩码,而不是反掩码,通配符和反掩码还是有一些细微的差别(EIGRP/OSPF进程network后边跟的是反掩码)

access-list access-list-number { permit | deny } {source [source-wildcard] | any}

先说下通配符和反掩码最本质区别,通配符支持不连续的1或者0,但是反掩码只支持连续的1或者0

举个例子:

R1(config)#router ospf 89

R1(config-router)#network 192.168.1.1 0.0.0.9 area 0

% OSPF: Invalid address/mask combination (discontiguous mask)

系统会提示你,% OSPF:无效地址/掩码组合(不连续掩码)


0.0.0.9-------------0.0.0.00001001,因为不是连续的1所以在OSPF进程是敲不上去的

R1(config)#access-list 10 permit 192.168.1.1 0.0.0.9

但是在ACL的通配符中,这条命令式可以敲进去的,因为ACL的通配符支持不连续的1或者0

ACL中通配符使用规则:0为严格匹配,1为无所谓任意的


举几个ACL的例子:

例一:

R1(config)#access-list 10 permit 192.168.0.0 0.0.0.0

这条ACL匹配的范围:

192.168.0.0/16

192.168.0.0/17

192.168.0.0/18

         **

         **

192.168.0.0/29

192.168.0.0/30

192.168.0.0/31

192.168.0.0/32

(最后两个/31/32的是可以忽略的,因为我们最少使用的掩码就是/30的,但是ACL确实是可以匹配到最后两个掩码。)


例二:

R1(config)#access-list 10 permit 192.168.1.0 0.0.1.0

这条ACL匹配的范围:

192.168.0.0/16

192.168.0.0/17

192.168.0.0/18

         **

         **

192.168.0.0/29

192.168.0.0/30

192.168.0.0/31

192.168.0.0/32

----------------------

192.168.1.0/16

192.168.1.0/17

192.168.1.0/18

         **

         **

192.168.1.0/29

192.168.1.0/30

192.168.1.0/31

192.168.1.0/32

(其实说白了,192.168.1.0/16~192.168.1.0/23这部分路由,都是192.168.0.0/16~192.168.0.0/23任意一个的一部分,这里其实如果你对划分子网不是很熟悉很熟悉感觉很难理解出这句话的含义)


例三:

R1(config)#access-list 10 permit 192.168.1.0 0.0.2.0

这条ACL匹配的范围:

192.168.1.0/24

192.168.1.0/25

192.168.1.0/26

192.168.1.0/27

192.168.1.0/28

192.168.1.0/29

192.168.1.0/30

192.168.1.0/31

192.168.1.0/32

----------------------

192.168.3.0/24

192.168.3.0/25

192.168.3.0/26

192.168.3.0/27

192.168.3.0/28

192.168.3.0/29

192.168.3.0/30

192.168.3.0/31

192.168.3.0/32

先拿例二讲:

R1(config)#access-list 10 permit 192.168.1.0 0.0.0.0

192.168.00000001.0=== 00000001       源地址(标记红色的是可以变化的)

0.0.00000001.0======= 00000001       通配符(最后1位为1,所以源地址最后1位可变化)

ACL中通配符使用规则:0为严格匹配,1为无所谓任意的

通配符中第38位组中为1的只有1位,也就是说这1位是可以变化的,也就是这一位可以是0也可以是1,所以变化出下列的两种:

192.168.00000000.0=192.168.0.0

192.168.00000001.0=192.168.1.0

上边举例为什么会有从192.168.0.0/16~192.168.0.0/32192.168.1.0/16~192.168.1.0/32这些路由条目是因为ACL它无法匹配前缀长度部分(/16~/32这些,对于路由器来讲,严格意义上,192.168.0.0/16192.168.0.0/17~192.168.0.0/32这些是两条完全不同的路由条目)

在路由表中,路由前缀相同,但是路由前缀长度不同的就是两条不同的路由信息

对于人来讲,192.168.0.0/17~192.168.0.0/32192.168.0.0/16的一部分,但是对于路由器而言这些路由的前缀相同,但是它们的前缀长度不同,它们就是不同的路由信息。

再拿例三讲:

R1(config)#access-list 10 permit 192.168.1.0 0.0.2.0

192.168.00000001.0===00000001                 源地址(标记红色的是可以变化的)

0.0.00000010.0======  00000010        通配符(倒数第2位为1,所以源地址标红位可变化)

ACL中通配符使用规则:0为严格匹配,1为无所谓任意的

通配符中第38位组中为1的只有1位,也就是说这1位是可以变化的,也就是这一位可以是0也可以是1,所以变化出下列的两种:

192.168.00000001.0=192.168.1.0

192.168.00000011.0=192.168.3.0

因为ACL无法匹配前缀长度信息,所以上边例三举出了192.168.1.0/24~192.168.1.0/32192.168.3.0/24~192.168.3.0/32

我这里为什么192.168.1.0192.168.3.0的举出可匹配到的掩码都是从/24开始的,而不是/16~/23的。

我们假设拿出192.168.1.0/23的来讲

192.168.1.0 255.255.254.0

范围:192.168.0.0~192.168.1.255

网络号:192.168.0.0

广播地址:192.168.1.255

可用IP范围:192.168.0.1~92.168.1.254

根据上边的列出的,可以看出192.168.1.0/23的路由信息,它的前缀(或者叫网络号)是192.168.0.0 的,咱们的ACL匹配的网络号部分是:192.168.1.0的,所以很明显的192.168.1.0/23的是不会被举例中的ACL匹配住的,更别说/22~/16的这些掩码了。

像上边的举例对一个人的VLSM子网划分是有一定的要求的,你心里要很明确的清楚,192.168.0.0/16这个路由,它所包含的范围到底有多广。

像什么192.168.1.0/16~192.168.255.0/16说白了都是192.168.0.0/16的一部分子网嘛

到这里,我觉得我们可以回到最初的问题上(贴心的粘贴拓扑图过来)

image.png

R1路由器有5条路由,4条明细,以及一条对4条明细汇总的路由信息。

现在要求R1将路由传递给R2的时候,只将汇总的路由干掉,留下4条明细到R2路由器。

上边提到了这种需求ACL是做不到的,因为无法匹配前缀长度部分。

R1(config)#access-list 10 deny 192.168.0.0 0.0.0.0

这条ACL其实就只匹配到了前缀(网络号)部分,并没有匹配到前缀长度(掩码)部分

192.168.0.0 255.255.255.0=192.168.0.0/24

范围:192.168.0.0~192.168.0.255

网络号:192.168.0.0

广播地址:192.168.0.255

可用IP范围:192.168.0.1~192.168.0254

 

192.168.0.0 255.255.252.0=192.168.0.0/22

范围:192.168.0.0~192.168.3.255

网络号:192.168.0.0

广播地址:192.168.3.255

可用IP范围:192.168.0.1~192.168.3.254

透过上边的举例可以看出,它们两个的网络号部分(也就是前缀部分)是一样的,不一样的只是前缀长度(掩码长度)部分。但是偏偏ACL就是因为不能匹配到掩码长度部分,只能匹配到网络号部分,所以这两条路由就被一并的干掉了。

 

在这里还是想强调一下,大部分人在用ACL匹配路由的时候喜欢这么写:

R1(config)#access-list 10 deny 192.168.0.0 0.0.0.255

这么写的ACL其实在匹配的范围来讲是比0.0.0.0更广的,因为通配符最后一个8位组是255,也就是你不关心最后一个8位组。

本来你用 access-list 10 deny 192.168.0.0 0.0.0.0

像下边路由:192.168.0.4/30192.168.0.8/30192.168.0.12/30这些路由是不会被上边ACL所匹配到的,因为上边的通配符最后一个8位组是00代表精确匹配。

我们拿出192.168.0.4/30的来拆开看

192.168.0.00000100=192.168.0.4

范围:192.168.0.4~192.168.0.7

网络号:192.168.0.4

广播地址:192.168.0.7

可用IP范围:192.168.0.5~192.168.0.6

透过上边解析,该路由条目的网络号是192.168.0.4并不是192.168.0.0所以它一定不会被access-list 10 deny 192.168.0.0 0.0.0.0这条ACL所匹配住的。

 

但是如果你的ACL是这样:access-list 10 deny 192.168.0.0 0.0.0.255
这样子代表最后一个8位组不关心,可0可1,所以像192.168.0.4/30,192.168.0.8/30一定会被access-list 10 deny 192.168.0.0 0.0.0.255这条ACL所匹配住的。

这就是为什么在用ACL匹配路由的时候,不建议你去跟0.0.0.255因为ACL本身就不严谨,你这样写只会让ACL更为的不严谨。


ACL最神奇的部分就是可以抓奇偶网段路由,下边来演示一下具体流程:

192.168.0.0~192.168.0.7.0这8条路由中,想用ACL去匹配住奇数网段和偶数网段

192.168.00000  000.0/24=192.168.0.0/24

192.168.00000  001.0/24=192.168.1.0/24

192.168.00000  010.0/24=192.168.2.0/24

192.168.00000  011.0/24=192.168.3.0/24

192.168.00000  100.0/24=192.168.4.0/24

192.168.00000  101.0/24=192.168.5.0/24

192.168.00000  110.0/24=192.168.6.0/24

192.168.00000  111.0/24=192.168.7.0/24

观察上边的路由信息,发现凡是偶数网段第38位组的最后1位必定为0,相反的道理,凡是奇数网段第38位组的最后1位必定为1

所以根据这个特性再加上ACL 通配符0为严格匹配,1为无所谓任意的规则

抓偶数网段我们就可以得出下边的ACL写法:

R1(config)#access-list 10 permit 192.168.0.0 0.0.6.0

192.168.00000000.0===00000000                 源地址(标红可变的)

0.0.0000110.0======== 00000110                 通配符(标红为不严格匹配的)

上边通配符第3个八位组为1的有2位,代表这2是可以变化的,变化出以下:

192.168.00000  000.0/24=192.168.0.0/24

192.168.00000  010.0/24=192.168.2.0/24

192.168.00000  100.0/24=192.168.4.0/24

192.168.00000  110.0/24=192.168.6.0/24

抓奇数网段我们就可以得出下边的ACL写法:

R1(config)#access-list 10 permit 192.168.1.0 0.0.6.0

192.168.00000001.0===00000001                 源地址(标红可变的)

0.0.00000110.0=======00000110                 通配符(标红为不严格匹配的)

上边通配符第3个八位组为1的有2位,代表这2位是可以变化的,变化出以下:

192.168.00000  001.0/24=192.168.1.0/24

192.168.00000  011.0/24=192.168.3.0/24

192.168.00000  101.0/24=192.168.5.0/24

192.168.00000  111.0/24=192.168.7.0/24

举例一:

192.168.0.0~192.168.0.15这16条路由中,想用ACL去匹配住奇数网段和偶数网段

00000000=0    192.168.0.0

00000001=1    192.168.0.1

00000010=2    192.168.0.2

00000011=3    192.168.0.3

00000100=4    192.168.0.4

00000101=5    192.168.0.5

00000110=6    192.168.0.6

00000111=7    192.168.0.7

00001000=8    192.168.0.8

00001001=9    192.168.0.9

00001010=10  192.168.0.10

00001011=11  192.168.0.11

00001100=12  192.168.0.12

00001101=13  192.168.0.13

00001110=14  192.168.0.14

00001111=15  192.168.0.15

还是老规矩,凡是偶数网段,第48位组的最后一位一定为0。凡是奇数网段,第48位组的最后一位一定为1

如果你想抓取这个16条路由的偶数IP地址:

access-list 10 permit 192.168.0.0 0.0.0.14

0000         0000=0             192.168.0.0

0000         0010=2             192.168.0.2    

0000         0100=4             192.168.0.4    

0000         0110=6             192.168.0.6    

0000         1000=8             192.168.0.8    

0000         1010=10           192.168.0.10 

0000         1100=12           192.168.0.12 

0000         1110=14           192.168.0.14

如果你想抓取这个16条路由的奇数IP地址:

access-list 10 permit 192.168.0.1 0.0.0.14

0000         0001                 192.168.0.1    

0000         0011                 192.168.0.3    

0000         0101                 192.168.0.5    

0000         0111                 192.168.0.7    

0000         1001                 192.168.0.9            

0000         1011                 192.168.0.11 

0000         1101                 192.168.0.13 

0000         1111                 192.168.0.15