📡 第五章 防火墙功能与防范威胁的对策
📄 一句话概括

安全策略不是集合,是序列——先匹配先生效。 所以在最前面写一条「允许所有」,后面的规则全部作废。

📝 本节和前面几节的关系

上一节讲区域(策略的维度),这一节讲策略本身。 这一节的坑是「顺序」,而它偏偏最难在测试里发现。

一、一条策略由什么组成

五个要素:源区域、目的区域、源地址、目的地址、服务(协议加端口)。 再加上一个动作:允许、拒绝、或者丢弃。

注意「源区域」与「源地址」是两个不同的维度:前者说「从哪个方向来」,后者说「具体是谁」。 先用区域粗筛,再用地址细筛,这是策略的组织方式。

动作有三档,不是两档:允许(放行)、拒绝(回 RST 或 ICMP,让对方立刻知道)、 丢弃(不回应,让对方等超时)。对外用丢弃、对内用拒绝,是常见约定。

二、顺序为什么致命

假设写了这么三条: ① 允许 any → any 的所有服务。 ② 拒绝 10.0.0.5 → any 的 HTTP。 ③ 允许 10.0.0.6 → any 的 SSH。

第 1 条已经放行了一切,所以第 2、3 条永远查不到。 实际效果是「全通」,而不是「禁一台、放一台」。

这个错误之所以危险,是因为「策略列表看起来是对的」:第 2 条明明写着「拒绝」。 而设备不会报错,日志里也只会出现「被第 1 条命中」。

正确的排法是「先细后粗」:具体禁止 → 具体允许 → 默认拒绝。 注意最后一条不是「允许所有」,而是「拒绝所有」——默认拒绝才是安全的默认值。

三、策略规模怎么压

逐条写的代价可以算:3 个区域 6 个方向 × 20 个服务 = 120 条。

压的办法有三种,层层递进: 一、用服务组:把「Web 服务」定义为「80 加 443」,120 条变 60 条。 二、用区域组:把「几个区域」打包成一个组,方向数再减。 三、先放行区域对、再在区域内做例外:这是最常见的做法——主干几条、例外若干条。

但压缩有个不能碰的底线:「允许」可以用组,「拒绝」必须具体。 因为一条过宽的允许等于开了个洞,而一条过宽的拒绝只是多挡了点东西。 这个不对称是策略管理的核心经验。

四、动手 Demo:策略是「先匹配先生效」

这段摆出两份策略:一份把「允许所有」写在最前面(错),一份先细后粗(对), 再看两者的实际效果差在哪。

rules = [
    (1, u"permit", u"any", u"any", u"any"),
    (2, u"deny", u"10.0.0.5", u"any", u"http"),
    (3, u"permit", u"10.0.0.6", u"any", u"ssh"),
]

实跑输出:

--------------------------------------------------------------------
策略是「先匹配先生效」
--------------------------------------------------------------------
**安全策略不是集合,是序列。**
**顺序一错,后面的规则等于没写。**

**下面这份策略,第 3 条永远不会命中**:

  #1  permit any        any    any
  #2  deny   10.0.0.5   any    http
  #3  permit 10.0.0.6   any    ssh

**第 1 条已经放行了所有流量**,**第 2、3 条排在它后面,永远不会被查到。**
**实际效果是「全通」,而不是「禁掉一台、放行一台」。**

**改成「先细后粗」才对**:

  #1  deny   10.0.0.5   any    http
  #2  permit 10.0.0.6   any    ssh
  #3  permit any        any    any

**算一下策略规模**(3 区域 6 方向 × 20 个服务):

  逐条写:6 × 20 = 120 条。
  按区域组合归类后:6 条「默认策略」+ 少量例外。
**差 20 倍**——**这就是为什么真实设备都提供「区域组」与「服务组」。**

这段的输出很短,但结论很重:第 1 条一旦放行所有,第 2、3 条就成了摆设。 而「策略列表里有拒绝条目」这个假象,会让人以为已经禁掉了。

排查这类问题有个笨办法但很有效:从第 1 条往下读,问自己「这一条会不会把后面的都吃掉」。 任何一条动作是「允许」且范围为「any」的策略,都意味着它后面的策略需要重新审视。

最后那句「允许可以粗、拒绝必须细」要记住: 因为两者的风险不对称——过宽的允许是漏,过宽的拒绝只是麻烦。 所以策略评审时,重点看「允许」那几条的范围。

30 秒实验

  1. 把你手上的策略从上往下读一遍,找有没有「允许 any」的条目。
  2. 数一下现有策略的条数,想想能不能用服务组压一压。
  3. 想一想:为什么「默认拒绝」比「默认允许」安全?

常见误区

  1. 以为策略顺序不影响结果。先匹配先生效,顺序完全决定结果。
  2. 以为写了「拒绝」就一定拒绝。前面若有「允许所有」,它不会生效。
  3. 以为策略越少越好。压过头会写成「允许一整类」,等于开大洞。
自测三问(点开对答案) 1. 一条安全策略由哪五个要素加一个动作组成? —— 源区域、目的区域、源地址、目的地址、服务,加动作。 2. 为什么「允许 any any」写在第 1 条会让后面全部失效? —— 因为策略是先匹配先生效,第一个包就被第 1 条命中,后面的不再查。 3. 为什么「允许可以粗、拒绝必须细」? —— 过宽的允许是安全漏洞,过宽的拒绝只是多挡了一些流量,风险不对称。

下一节:地址转换——把私网地址变成公网地址的那台机器。

相关笔记