9. Services — DHCP, ACME, Zabbix/SNMP, Suricata/Wazuh¶
Mixed per-node / primary-only — each section says which. Get the edge routing/firewall (pages 5–8) solid first; these ride on top.
9.1 DHCP for server VLANs (primary — syncs)¶
Services ▸ Kea DHCP (the current OPNsense DHCP). One subnet per routed server VLAN that needs leases:
| VLAN | Subnet | Pool (example) | Gateway | DNS |
|---|---|---|---|---|
| 910 | 10.128.10.0/24 |
.50–.200 |
10.128.10.1 |
Tier-1 resolvers |
| 930 | 10.128.32.0/22 |
carve per need | 10.128.32.1 |
10.128.32.3/.4 |
| 931 | 10.128.36.0/22 |
carve per need | 10.128.36.1 |
10.128.32.3/.4 |
| 940 | 10.128.44.0/24 |
mgmt hosts | 10.128.44.1 |
Tier-1 |
Gateway = each VLAN's CARP VIP (.1), so leases point at the floating gateway.
Enable HA/failover peer between the nodes if you want lease-state redundancy, or rely
on config sync + short leases.
9.2 Split-horizon DNS (primary — syncs)¶
Services ▸ Unbound DNS ▸ Overrides. Add the internal service records that make the
hairpin (page 6 §6.3) go away:
service.pubinvest.co.uk → 10.128.x (real internal target). Public DNS keeps the
public IP; internal clients resolve internal and preserve their source IP.
9.3 ACME client — GUI admin certificate (primary — syncs)¶
System ▸ Firmware ▸ Plugins → install os-acme-client.
- Services ▸ ACME Client ▸ Accounts — register (Let's Encrypt prod, your email).
- Challenge Types — DNS-01 against your DNS provider is cleanest for an admin cert (no inbound 80 needed); or HTTP-01 if you expose a validation path.
- Certificates — issue for the GUI admin FQDN.
- Automations — restart the GUI on renewal.
- System ▸ Settings ▸ Administration — set the GUI to use the issued cert.
9.4 Zabbix agent + SNMPv3 (both nodes — per-node)¶
Monitor both nodes over the OOB interface — never the data path, so a data-path or CARP event never reads as "host down" (§14).
- Install
os-zabbix-agent(agent) and configure active mode pointing at<ZABBIX_IP>. Prefer agent-active so the firewall pushes (no inbound poll holes in the OOB firewall). - Install
os-net-snmpfor SNMPv3, source-locked to<ZABBIX_IP>, for high-rate per-port counters on the X710s. - Apply the FreeBSD by Zabbix agent template; then trim it (§14b):
- Filter interface LLD — exclude
^(lo|pflog|enc|pfsync|usbus|gif|gre)and the ~8 intentionally-down spare SFP+. KeepOOBin and alert on its link-down (the rescue path is monitored — page 8). - Don't apply SNMP and agent to the same metric (double graphs/triggers).
- Point ICMP host-availability at the OOB address, not a VIP.
- Filter interface LLD — exclude
CARP-aware custom items (the firewall-specific metrics)¶
Ship as agent UserParameters. Every "is it down" item must gate on CARP role (§14d) — on the backup, stopped FRR / BACKUP VIPs / ~0 pps are normal and must not alert:
| Item | Source | Alert (when MASTER) |
|---|---|---|
| CARP master/backup per VIP | ifconfig \| grep carp |
designated master unexpectedly BACKUP; both MASTER = split-brain; neither = no gateway |
| pfSync health | pfsync0 up + state delta vs peer |
iface down; large divergence |
| pf state table | pfctl -si vs pfctl -sm |
> 80% of max states |
| BGP sessions | vtysh -c 'show bgp summary json' |
any neighbour ≠ Established while MASTER |
| Suricata | EVE stats: capture.kernel_drops, *.memcap_drops |
drops > 0 sustained; alert-rate spike |
| NIC HW counters | sysctl dev.ixl.N.mac.rx_discards/rx_no_buffers |
rising |
| Per-core CPU | kern.cp_times |
one hot core = RSS/NUMA imbalance |
| Temp/PSU/fan | IPMI over OOB | over-temp, PSU redundancy lost |
Pair-level triggers¶
Split-brain (both MASTER), no-master (neither), redundancy-lost (backup down while master fine → you're a SPOF), config drift (master vs backup config revision differ).
9.5 Suricata IDS/IPS + Wazuh (both nodes — per-node config, identical)¶
Placement is the whole game (§11): inline IPS on WAN/DMZ only; never the server trunk.
- Services ▸ Intrusion Detection → enable.
- Interfaces: assign Suricata to
WAN,WAN2,VL_DMZonly. NeverSRVTRUNK— inline inspection would crush the 20G east-west/backup path, and it's already behind the zone firewall. - IPS mode on, capture = netmap inline. Netmap needs LRO/TSO off on those NICs (Suricata must see un-coalesced packets) — set per-interface on tunables, offloads on everywhere else.
- Runmode workers,
cpu-affinitypinned to one NUMA node's cores;detect.profile high; generous flow/stream memcaps (§12e). - Ruleset: ET Open/Pro, prune with rule-profiling for inline throughput.
- EVE/alert logging → remote, ship to
<WAZUH_IP>(Tier-2) — don't let logging chew the BOSS card. Configure Services ▸ Syslog to forward EVE JSON to<SYSLOG_IP>/<WAZUH_IP>.
Action on the firewall (§ your requirement)¶
Two automated layers:
- Inline drop — Suricata IPS drops matching traffic in real time at the WAN/DMZ edge.
- Wazuh active-response → block alias — Wazuh decodes the Suricata EVE feed and
pushes offender IPs into an OPNsense alias (Firewall ▸ Aliases, e.g.
wazuh-blocklist) referenced by a block rule on WAN. Point Wazuh's active response at the OPNsense API (a scoped API key) so confirmed offenders are blocked fleet-fast without a human in the loop.
HA & IDS
Suricata runs on both nodes but only the master inspects live traffic. Keep rulesets identical (do the config the same on both nodes) so a failover doesn't change security posture. Zabbix watches Suricata health (drops, running); the alerts live in Wazuh — don't turn Zabbix into an IDS console (§14f).