2. 实验环境与数据面搭建

上一节我们明确了Zeek在网络安全监测中的定位:它不是简单的特征匹配IDS,而是把原始流量还原成协议级事件与连接日志的分析引擎。要让这套引擎稳定产出可用的日志,第一步不是写脚本,而是把“数据面”搭对——也就是让Zeek节点真正看到需要分析的流量,并且只看到需要分析的流量。本节围绕三件事展开:节点部署形态、采集模式选择、网卡与BPF过滤配置,最终形成一套可复现的实验环境。

一、先确定节点部署形态:旁路镜像还是串接直通

Zeek节点在实验环境中有两种典型接入方式。第一种是旁路镜像:交换机把被监测链路的流量复制一份到监控口,Zeek节点的采集网卡接在监控口上,只收不发。这种方式对生产链路零影响,适合教学实验和现网旁路监测。第二种是串接直通:Zeek节点作为网桥或使用支持直通采集的网卡,流量物理经过节点,节点在转发的同时把副本交给Zeek进程。串接方式能看到链路两端全部流量,但一旦节点故障会中断业务,实验环境中通常只在隔离网段使用。

对于本课程的可复现实验,推荐采用“隔离实验网段 + 旁路镜像”的组合:用一台虚拟交换机或物理交换机划分出监测VLAN,把攻击机、靶机、Zeek节点放在同一实验网段,交换机镜像口连接Zeek采集网卡。这样既不影响宿主机网络,又能完整复现东西向与南北向流量。

二、镜像/直通采集模式的选择依据

采集模式决定了Zeek能看到什么、看不到什么。常见选项包括:

  • SPAN镜像口:交换机复制指定端口或VLAN流量。优点是部署简单、无侵入;缺点是镜像口带宽可能过载,且默认不保证复制完整性,高负载下会丢包。
  • TAP分光器:物理层分光,把光信号按比例分成两路,一路给生产、一路给Zeek。无丢包、无延迟,但需要硬件投入,实验环境可用虚拟TAP替代。
  • 网卡直通(PCIe Passthrough / SR-IOV):在虚拟化环境中把物理网卡直接分配给Zeek虚拟机,绕过虚拟交换机,减少复制开销,适合高吞吐实验。
  • AF_PACKET / PF_RING:Linux下的高性能抓包框架,配合多队列网卡可显著降低丢包率。Zeek默认使用libpcap,实验环境若流量不大可先用默认;若要做吞吐对比实验,可切换到AF_PACKET。

选择原则可以概括为:实验目的决定采集模式。如果只是验证协议解析和日志格式,SPAN镜像足够;如果要测量Zeek在高pps下的丢包行为,就需要TAP或直通网卡,并配合多队列与CPU亲和性。

三、网卡配置:让采集口“只收不发”

Zeek采集网卡应配置为混杂模式,并且不分配IP地址,避免内核协议栈对流量做出响应。以Linux为例,典型配置如下:

# 查看网卡名称与驱动
ip link show
ethtool -i eth1

# 关闭网卡offload,避免抓包时校验和/分段被硬件改写
ethtool -K eth1 gro off gso off tso off lro off

# 开启混杂模式,不分配IP
ip link set eth1 promisc on
ip addr flush dev eth1
ip link set eth1 up

# 增大环形缓冲区,降低突发丢包
ethtool -G eth1 rx 4096 tx 4096

这里有两个容易忽略的点。第一,关闭offload:如果网卡开启了GRO/TSO,抓到的包可能是合并后的大包,Zeek解析出的TCP流会与真实报文不一致,导致日志中的字节数、包数偏差。第二,环形缓冲区:默认RX ring往往只有256或512,突发流量下容易丢包,实验前应调大并观察ethtool -S eth1 | grep drop。

四、BPF过滤:把不需要的流量挡在Zeek之前

BPF(Berkeley Packet Filter)是内核层的过滤机制,Zeek通过-f参数或capture_filter配置项传入BPF表达式。它的价值在于:在数据进入Zeek用户态之前就丢弃无关流量,降低CPU和内存开销。实验环境中常见的过滤需求包括:

  • 只分析实验网段:net 192.168.56.0/24
  • 排除管理流量:not port 22 and not port 3389
  • 只关注HTTP/DNS/TLS:tcp port 80 or tcp port 443 or udp port 53
  • 排除Zeek自身管理口:not host 192.168.56.10

组合后的典型表达式为:

zeek -i eth1 -f "net 192.168.56.0/24 and not port 22 and not host 192.168.56.10" local

需要强调的是,BPF过滤是“粗筛”,Zeek脚本层的过滤是“精筛”。BPF只认IP、端口、协议等五元组信息,无法识别HTTP Host或TLS SNI;如果实验需要按域名筛选,应在Zeek脚本中用Site::local_nets或自定义事件处理,而不是硬塞进BPF。

五、可复现实验环境的关键参数与验证

为了让实验可复现,建议把节点角色、网卡、IP、采集模式、BPF表达式固定成一张环境清单。下面是一个示例配置,读者可根据自己的实验平台调整:

角色网卡IP/网段采集模式BPF过滤
攻击机eth0192.168.56.20/24——
靶机eth0192.168.56.30/24——
Zeek节点eth0管理192.168.56.10/24——
Zeek节点eth1采集无IP,混杂模式SPAN镜像net 192.168.56.0/24 and not host 192.168.56.10

部署完成后,用以下方式验证数据面是否正常:

  1. 在攻击机上执行ping 192.168.56.30,在Zeek节点上运行tcpdump -i eth1 -c 5,确认能抓到ICMP包。
  2. 启动Zeek:zeek -i eth1 -f "net 192.168.56.0/24" local,观察conn.log是否出现对应连接记录。
  3. 检查丢包:cat /proc/net/dev | grep eth1,对比RX packets与Zeek统计的pkts_recv,若差距持续增大,说明BPF或缓冲区需要调整。
  4. 用zeekctl status确认节点状态为running,日志目录/usr/local/zeek/logs/current/下有conn.log、dns.log等文件生成。
实验环境建议固定网卡名称、IP和BPF表达式,并把配置写入zeekctl.cfg与node.cfg,这样每次重建环境时只需恢复配置文件,就能得到一致的采集行为。

六、数据面搭建的常见问题与判断

实际搭建中最常遇到三类问题。第一类是抓不到包:检查网卡是否up、是否开启混杂模式、镜像口是否配置正确;在虚拟化环境中还要确认虚拟交换机是否允许混杂模式。第二类是抓到了但Zeek不产生日志:通常是BPF表达式写错,把目标流量过滤掉了,可以先用tcpdump加相同BPF验证。第三类是日志中包数偏少:优先检查网卡offload是否关闭、RX ring是否过小、Zeek是否因CPU瓶颈丢包,可用zeek -i eth1 -f ... -w trace.pcap同时落盘,对比pcap与日志的差异。

Zeek实验环境数据面:从镜像口到日志的采集链路 隔离实验网段 192.168.56.0/24 攻击机 192.168.56.20 靶机 192.168.56.30 实验交换机 SPAN镜像口 复制VLAN流量 镜像副本 Zeek监测节点 192.168.56.10 eth0 管理口 IP: 192.168.56.10 SSH / zeekctl eth1 采集口 无IP / 混杂模式 offload关闭 / RX 4096 BPF过滤(内核层粗筛) net 192.168.56.0/24 and not host 192.168.56.10 Zeek进程(用户态解析) conn.log / dns.log / http.log / ssl.log 数据面验证 1. tcpdump -i eth1 -c 5 2. 检查 conn.log 记录 3. 对比 RX packets 与 pkts_recv 4. zeekctl status 确认运行 5. 观察 ethtool -S 丢包计数