Files
MeshSate/docs/策略配置说明.md
zhaolei f1a176aae0 fix: 裁决口径重构 — rule_overrides 改处置地板,YARA 权重分档与阈值解耦
三件事,都围绕"分数只反映证据,不放行由地板保证":

- rule_overrides 的 manual_review 旧实现是 score=max(score,65) 并跳过该规则自身权重:
  注进去的 65 不是证据,再叠任意 ≥5 分噪声就越过 block_score=70 变拒绝,同时显示分数
  与真实证据脱钩。改为步骤 9「复核地板」:权重照常累加,裁决后处置低于复核才抬到
  manual_review,已判 reject 不降回。3661 条历史扫描重放 0 收紧 0 放行;把 review_score
  下界抬到 36/40/50 或把 DEE 权重降到 10,无地板时干净 exe 静默放行,有地板恒为人工复核。
- DangerousExecutableExtension 进 rule_overrides(manual_review),落实光闸口径「EXE/DLL/
  脚本不自动放行」,不再依赖 weight=30 恰好等于 review_score 下界这种数值巧合。
- YARA 权重分档 85/65/45/25 → 85/60/30/10,只有 critical 一档能独立越过 70;
  档位与 rules/*.yar 的 meta.risk_level 一一对应,控制台注释与 policy.html 同步。
- 词表:RemoteDownloadUnix/PowerShell 移出零容忍、改判"工具与 URL/IP 同框",
  新增 RemoteDownloadExec(40)/PayloadDropToDisk(45) 带内网源站白名单。裸 cmdlet 名会把
  nvidiaInspector.exe 的 add_DownloadFileCompleted 白送 30 分,把 45 分复核顶成 75 分拒绝。
- 风险等级文案:裁决已是 malicious/error 时仍输出"打开风险低"是自相矛盾的对外文案,
  强制收敛到 critical。
- 靶场 L5-005 expected_verdict reject→review:旧 85 分靠载体45+时间戳20+未签名10+架构10
  堆叠,属权重堆叠误报;真实注入器由 C1_PE_ProcessInjection(85) 拦截。
2026-11-02 20:27:30 +08:00

16 KiB
Raw Blame History

MeshSafe 策略配置说明

项目 内容
适用对象 安全管理员、系统管理员
配置文件 config/policy.yaml
生效方式 修改后调用 POST /api/v1/policies/reload 或重启服务
文档版本 v1.0

目录

  1. 配置总览
  2. 字段详解
  3. 裁决流程
  4. 调整场景手册
  5. 校验与错误处理
  6. 变更管理

1. 配置总览

策略文件采用 YAML 格式,路径由环境变量 MESHSAFE_POLICY_FILE 指定(默认 /app/config/policy.yaml)。

核心原则:策略与代码分离。 调整判定规则、阈值、白名单只需修改本文件,不需要重新构建或发布镜像。

version: "2026.10.1"
description: "MeshSafe 默认全局策略(法院文书摆渡场景)"

global:
  block_score: 70
  review_score: [30, 70]
  engine_failure_mode: fail_closed
  max_file_size: 52428800
  sync_max_size: 52428800
  allow_encrypted_archive: false
  allow_encrypted_document: false

allowed_extensions: [ ... ]
sandbox_required_extensions: [ ... ]
rule_overrides: { ... }
notification: { ... }
audit: { ... }

顶层结构

键 类型 必填 说明
version string 是 策略版本号,建议用日期格式。写入每条扫描结果
description string 否 策略说明
global map 是 全局阈值与行为开关
allowed_extensions list 是 允许传输的扩展名白名单
sandbox_required_extensions list 否 强制走沙箱深检的类型
rule_overrides map 否 特定规则的强制处置
notification map 否 判定理由的输出控制
audit map 否 审计记录内容控制

2. 字段详解

2.1 global

2.1.1 block_score

项 说明
类型 整数,0~100
默认 70
含义 风险评分 ≥ 此值 时判定为 malicious,处置动作为 reject

调整方向:调低 → 更严格(更多文件被拒),调高 → 更宽松(需积累更多信号才拒绝)。

注意:单条 critical 级信号通常权重已达 50~90,因此 block_score 低于 50 时,大量正常文档会因多条低级信号叠加被拒。

2.1.2 review_score

项 说明
类型 数组 [下界, 上界]
默认 [30, 70]
含义 评分落在该区间时判定为 suspicious,处置动作为 manual_review(转人工复核)

这是误报缓冲的关键参数。 调整方向:调低下界 → 更多文件进入人工复核(更安全但人工压力大);调高下界 → 更少人工复核(但风险文件可能被直接放行)。

2.1.3 engine_failure_mode

项 说明
类型 字符串 fail_closed / fail_open
默认 fail_closed
含义 检测引擎不可用时的整体行为
取值 行为 适用
fail_closed 直接拒绝,并说明引擎不可用 生产环境必须使用此项
fail_open 放行但标记 仅限测试环境

等保三级要求"安全优先",生产环境使用 fail_open 会在测评时被判定为不符合项。

2.1.4 max_file_size

项 说明
类型 整数(字节)
默认 52428800(50 MB)
含义 单文件大小上限。超限直接拒绝

2.1.5 sync_max_size

项 说明
类型 整数(字节)
默认 52428800(50 MB)
含义 同步模式处理的文件大小上限。超限转异步

必须 ≤ max_file_size。若大于,则会出现"文件本身允许但无法同步处理"的中间态。

2.1.6 allow_encrypted_archive / allow_encrypted_document

项 说明
类型 布尔
默认 false
含义 是否允许加密的压缩包 / 加密的文档

加密文件无法被静态分析,在无法确认内容安全的前提下不应放行。确需放行时,应配合人工复核流程。

2.2 allowed_extensions

允许传输的扩展名白名单。

allowed_extensions:
  - .docx
  - .pdf
  - .xlsx
  - .jpg
  - .png
  - .zip

规则:

  • 必须以 . 开头(小写),否则加载校验失败
  • 比较时统一转小写,配置中的大写会被拒绝
  • 列表为空表示不限制,生产环境强烈不建议
  • 只校验顶层文件的扩展名;归档内的子文件由各自规则判定(受 rule_overrides 控制)

白名单是第一道也是最粗的一道防线。它挡不住"扩展名正确但内容是恶意"的攻击——那是 L1/L2 层的职责。

2.3 sandbox_required_extensions

强制走沙箱异步深检的扩展名。

sandbox_required_extensions:
  - .exe
  - .msi
  - .js
  - .vbs
  - .iso

当前版本(P3 一期)沙箱未实现,配置此项的效果是:命中的文件会走异步模式,并在 meta 中标注需要深检。P4 阶段接入 CAPE 后无需修改本项。

2.4 rule_overrides

特定规则的强制处置。这是绕过评分直接裁决的能力,用于把"一票否决"型规则固化下来。

rule_overrides:
  MRaptorAutoExecSuspicious:
    action: reject
    reason: "文档宏具备自动执行且包含可疑行为,按策略直接拒绝"
  DDEAutoExecution:
    action: reject
    reason: "检测到 DDE/DDEAUTO 自动执行字段,按策略直接拒绝"
字段 说明
action 处置动作,见下表
reason 判定理由,可直接展示给用户(支持中文)

action 取值

取值 行为
pass 放行
pass_with_flag 放行并标记
manual_review 处置地板:该文件最终不低于人工复核(评分不变,低于复核区间时只抬处置)
reject 拒绝
reject_and_notify 拒绝并通知(当前实现等同 reject)

生效逻辑

  1. 命中 rule_overrides 的规则会优先于评分处理
  2. 若 action 为 reject 类 → 立即返回拒绝结论,不再累加评分
  3. 若 action 为 manual_review → 登记"复核地板",规则自身权重照常累加,评分累加与阈值裁决完成后,处置若低于 manual_review 才抬到 manual_review(已判 reject 的不会被降回来)

旧实现是"评分提升至 65",有两个副作用:注进去的 65 分本身不是证据,再叠加任意 ≥5 分的噪声信号就会越过 block_score=70 变成拒绝;同时该规则自身的权重被跳过不再计分,控制台显示的分数与真实证据脱钩。现改为处置地板后,分数只反映权重,"不放行"由地板保证,与 review_score 阈值数值解耦——DangerousExecutableExtension(光闸口径:EXE/DLL/脚本不自动放行)正是靠这条地板生效,而不是靠 weight=30/35 恰好等于 review_score 下界。

为什么用覆盖而不是纯评分:像 PathTraversal、DDEAutoExecution 这类信号,一旦出现就足以判定不可放行,不应依赖其他信号累加来"凑够"阈值。

规则名必须与《接口文档》§6 中的 rule 字段完全一致,包括大小写。写错不会报错,只是永不生效——因此每次修改后应实际测试验证。

2.5 notification

notification:
  include_reason: true
  max_reason_length: 500
字段 说明
include_reason 是否在结果中返回判定理由。关闭后 reason 为空字符串
max_reason_length 理由最大长度,超出截断(末尾加 ...)

include_reason 只影响返回给调用方的内容,不影响审计日志。审计日志始终记录完整信息。

2.6 audit

audit:
  log_findings: true
  log_extracted_paths: true
字段 说明
log_findings 审计日志中是否记录命中的规则明细
log_extracted_paths 是否记录归档内提取出的文件路径

关闭 log_findings 可显著降低审计日志体积,代价是事后无法还原"当初为什么判定为恶意"。建议保持开启。


3. 裁决流程

                    ┌─────────────────────────┐
   检测信号 ────────▶│ 步骤 1:引擎可用性检查    │──▶ 引擎不可用 → fail_closed 拒绝
                    └─────────────────────────┘
                                    │
                                    ▼
                    ┌─────────────────────────┐
                    │ 步骤 2:文件大小检查      │──▶ 超限 → 拒绝
                    └─────────────────────────┘
                                    │
                                    ▼
                    ┌─────────────────────────┐
                    │ 步骤 3:扩展名白名单      │──▶ 不在清单 → 拒绝
                    └─────────────────────────┘
                                    │
                                    ▼
                    ┌─────────────────────────┐
                    │ 步骤 4:加密文件检查      │──▶ 加密且不允许 → 拒绝
                    └─────────────────────────┘
                                    │
                                    ▼
                    ┌─────────────────────────┐
                    │ 步骤 5:规则覆盖匹配      │──▶ 命中 reject 类 → 立即拒绝
                    └─────────────────────────┘
                                    │
                                    ▼
                    ┌─────────────────────────┐
                    │ 步骤 6:权重累加评分      │
                    └─────────────────────────┘
                                    │
                                    ▼
                    ┌─────────────────────────┐
                    │ 步骤 7:阈值映射处置      │
                    └─────────────────────────┘

3.1 评分计算

score = min(Σ(命中信号的 weight), 100)

已被 rule_overrides 处理的信号不重复累加。

3.2 阈值映射

评分区间 verdict action
score == 0 clean pass
0 < score < review_low suspicious pass_with_flag
review_low ≤ score < block_score suspicious manual_review
score ≥ block_score malicious reject

3.3 权重来源

层级 典型权重
L0 结构层 10 ~ 50
L1 ClamAV 25 ~ 90
L2 文档深度 15 ~ 80
L2B YARA / 二进制 10 ~ 85

权重定义在各检测引擎内部,调整权重要改代码——因此优先用 rule_overrides 表达策略意图,而不是频繁改权重。


4. 调整场景手册

4.1 场景:误报过多,业务被阻塞

症状:大量正常文档被判为 manual_review 或 reject。

排查步骤

  1. 查审计日志,找出被拒文件的命中规则
  2. 判断是哪条规则在误报

处理方式

误报来源 处理
某条规则过于敏感 用 rule_overrides 将该规则降级为 pass_with_flag,并改写 reason 说明
阈值过低 提高 review_score 下界,或提高 block_score
白名单缺少某类型 在 allowed_extensions 补充
正常文件确实含宏(如模板文件) 用 rule_overrides 对特定规则放行,但需评估该文件是否会成为攻击载体

建议不要直接调高 block_score——那会让真正的恶意文件更容易通过。优先降级具体规则。

4.2 场景:漏报,需要提升严格度

措施 配置
降低复核门槛 调低 review_score 下界
直接提高拒绝门槛 调低 block_score
某类风险必须拦截 在 rule_overrides 中加 reject
禁用某类可执行文件 确认 allowed_extensions 中不含该类型
加密文件也拦截 保持 allow_encrypted_* 为 false

4.3 场景:新增业务通道,需要独立策略

当前版本为全局单策略。 如需按通道区分,两种做法:

做法 A(不推荐,需改代码):在策略中引入 channels 段,裁决时按 channel 取对应子策略。

做法 B(推荐,零代码改动):在摆渡系统侧做分流。摆渡系统按通道自行维护白名单,检测服务只做统一的恶意性判定。

本期方案已确认采用全局策略。通道字段贯穿全链路(数据库、审计日志、API),后续扩展无需重构。

4.4 场景:允许某类加密文件

global:
  allow_encrypted_document: true

同时必须配套:加密文件无法静态检测,风险由人工复核承担。建议同时把该类文件的处置设为 manual_review:

rule_overrides:
  PdfEncrypted:
    action: manual_review
    reason: "PDF 已加密,无法自动检测,转人工复核"

4.5 场景:新增一种文件类型要放行

  1. 在 allowed_extensions 补充扩展名
  2. 确认该类型没有对应的深度检测引擎(否则即使放行也只是"未检测",不是"已检测通过")
  3. 若该类型有特殊风险(如脚本类),评估是否需要新增检测规则

5. 校验与错误处理

5.1 加载时校验项

策略文件在加载时执行严格校验,任一项不通过则拒绝加载并保留原有策略:

校验项 规则
根节点类型 必须是映射结构
review_score 下界必须小于上界
block_score 不应低于 review_score 上界;须在 0~100 之间
rule_overrides[].action 必须是合法动作枚举
allowed_extensions 每项必须以 . 开头
sync_max_size 须 ≤ max_file_size

为什么校验失败要保留旧策略:如果加载失败时回退到"默认策略"或"空策略",等于把生产环境的判定逻辑悄悄改掉了,比直接报错危险得多。

5.2 重载失败的表现

{
  "detail": "策略校验失败: block_score (50) 不应低于 review_score 上界 (70)"
}

原策略继续生效。修正后重新调用重载接口。

5.3 常见配置错误

错误 后果 修正
扩展名写成 docx(漏点) 加载校验失败 改为 .docx
扩展名大写 .DOCX 加载校验失败 改为小写
rule_overrides 规则名拼错 静默失效 对照接口文档 §6 核对,并实际测试
block_score 调得极低(如 10) 正常文件大量被拒 回调至 60~80
allowed_extensions 留空 所有类型都被拒 补充清单

规则名拼错是唯一会静默失效的配置错误,务必实测。


6. 变更管理

6.1 变更流程

提出变更 → 安全管理员评审 → 备份当前策略 → 修改配置
    → 语法校验(本地) → 重载 → 用样本文件验证 → 记录变更

6.2 变更记录要求

每次策略变更应记录:

项 说明
变更时间 精确到分钟
变更人 姓名与账号
变更内容 具体字段的前后值
变更原因 业务或安全需求说明
影响评估 是否影响在途文件、是否需要通知对接方
验证方式 用哪些样本文件验证、结果如何

6.3 版本追溯

每次扫描结果携带 meta.policy_version 与 meta.policy_sha256。数据库中保留策略版本快照,可用于按历史策略复现某一历史文件的判定结果。

6.4 灰度建议

策略变更影响面大时,建议:

  1. 先在测试环境用真实样本文件验证
  2. 对比新旧策略的判定差异(可通过 rescan 接口批量重跑)
  3. 差异符合预期后再在生产重载

附录:完整默认策略

见 config/policy.yaml。本文档说明各字段含义,实际以配置文件为准。


文档结束 · 配套文档:《总体方案》《接口文档》《等保三级对照表》《运维手册》