nftables 本身不解析应用层内容,需与用户态或 eBPF 协作实现协议指纹识别:通过 socket 元数据(skuid/cgroupv2)做进程级过滤、conntrack helper 提取明文 SNI/Host 字段写入 map 查表、eBPF 解析 L7 字段并标记后由 nftables 决策,辅以非标端口白名单与行为检测双控。

nftables 本身不解析应用层内容,无法直接识别 HTTP User-Agent、TLS SNI、DNS 查询名等协议指纹,也不能原生判断“非标端口是否承载了标准协议”。所谓“基于指纹的精准控制”,本质是分层协作:nftables 做高速标记与执行,用户态或 eBPF 负责深度检测并反馈结果。
用 socket 元数据实现进程级“准指纹”过滤
这是最轻量、最稳定、无需解析载荷的方式——不看包内容,而看谁发的包:
- 通过 meta skuid 或 socket cgroupv2 匹配连接所属进程,例如只允许 nginx(运行在 www-data 用户下)监听 80/443,拒绝其他 UID 的同类端口绑定
- 配合 systemd 设置
Delegate=yes和 cgroup v2 划分,让每个微服务运行在独立 cgroup 中,再用socket cgroup匹配规则精准放行或拦截 - 示例规则:拒绝非指定 cgroup 的 TCP 出站连接:
nft add rule inet filter output meta l4proto tcp socket cgroupv2 ! @allowed_cgroups drop
用 conntrack helper 配合明文特征初筛非标端口流量
对 TLS 握手、HTTP 请求头等早期明文字段,可借助内核 conntrack helper 捕获关键信息:
- 启用
nf_conntrack_ftp、nf_conntrack_sane等模块,辅助提取初始报文中的 Host/SNI 字段 - 将提取到的域名写入 nftables 的 map(如
inet filter sni_map { type ipv4_addr . inet_service : verdict; }),供后续规则查表跳转 - 重点用于识别“伪装成 HTTPS 流量走非 443 端口”的行为,例如目标端口为 8443、8080 但携带有效 SNI,则允许;若端口为 31337 且无合法 SNI,则记录并限速
用 eBPF 提取 L7 字段并标记,nftables 快速决策
eBPF 是当前 Linux 下实现协议感知过滤的主流路径,与 nftables 集成度高:
- 编写 eBPF 程序(如用 libbpf 或 Cilium 工具链),在 TCP ESTABLISHED 后解析 payload,提取 HTTP Host、TLS SNI、DNS QNAME 等字段
- 将匹配结果写入 per-CPU map,并由用户态守护进程读取后调用
nft add element更新 ct mark 或 ipset - nftables 规则中使用
ct mark & 0x1 == 0x1判断是否命中恶意指纹,再执行 DROP / limit rate 5/second / queue to userspace 等动作 - 典型场景:对 SNI 包含 “cdn-attacker[.]xyz” 的所有连接,在 OUTPUT 链直接丢弃,无论其走的是 443 还是 8443
非标端口加固:白名单 + 协议行为双控
不能只封端口,要结合协议语义判断是否异常:
- 建立可信端口白名单(如 443/HTTPS、53/DNS、123/NTP),其余端口默认限制连接速率(
limit rate 2/minute) - 对常见攻击端口(4444、5555、6666、7777)无条件拦截,不依赖 IP 或协议类型:
nft add rule inet filter output meta l4proto tcp tcp dport { 4444, 5555 } log prefix "RCE_PORT_BLOCK: " drop - 补充行为检测:非白名单端口上出现 TLS ClientHello 或 HTTP/1.1 GET 请求头,视为可疑,触发日志+临时限流;若连续 3 次失败握手,则加入临时黑名单 ipset










