Comparative analysis of Suricata IDS/IPS memory consumption across two UniFi gateway models tested approximately two weeks apart. Focuses on per‑category memory impact, cgroup limits, fail‑closed behaviour on OOM, and the observed link between scheduled speed tests and memory spikes.
- Per‑category memory impact for Emerging Threats rulesets
- UDM‑SE (4 GB) vs UCG‑Ultra (3 GB) comparison
- Production outages linked to auto speed‑test spikes
- Cgroup resource limits and OOM behaviour
- Methodology: 60–90 s stabilisation after each restart
Observed three separate Unifi gateways suffer from IPS crashes leading to network failure until hardware restart.
Under traffic spikes (e.g., speed tests), if the full IDS/IPS ruleset is enabled, the cgroup memory limit can be hit, causing the kernel to OOM-kill Suricata. Traffic is then dropped until the device is manually rebooted.
- Model: UniFi Cloud Gateway Ultra
- RAM: 3 GB
- Test Date: 6 Oct 2025
- Firmware: 4.4.3
- Suricata Version: 6.0.12
- Model: UniFi Dream Machine Special Edition
- RAM: 4 GB (3.9 GB usable)
- Test Date: 17 Oct 2025
- Firmware: 4.4.3
- Suricata Version: 6.0.12
- On 4.4.3 in my testing, every category change triggered a full Suricata restart (not a hot rule reload).
- Old PID terminates, new PID spawns.
- ~60–90 s required for initialisation and memory stabilisation; 30 s waits were insufficient for accurate measurements.
| Category | UDM‑SE delta | UDM‑SE Total | UCG‑Ultra delta | Change |
|---|---|---|---|---|
| Baseline (empty) | — | 52 MB | — | — |
| emerging‑malware | +312 MB | 364 MB | +203.7 MB | +108.3 MB |
| emerging‑webapps | +98 MB | 150 MB | +94.0 MB | +4.0 MB |
| emerging‑exploit | +48 MB | 100 MB | +42.9 MB | +5.1 MB |
| emerging‑mobile | +27 MB | 79 MB | +21.1 MB | +5.9 MB |
| emerging‑attackresponse | +16 MB | 68 MB | +14.0 MB | +2.0 MB |
| emerging‑webclient | +19 MB | 71 MB | +13.6 MB | +5.4 MB |
| emerging‑smtp | +2 MB | 54 MB | +12.1 MB | −10.1 MB |
| emerging‑sql | +7 MB | 59 MB | +5.3 MB | +1.7 MB |
| emerging‑activex | +7 MB | 59 MB | +5.1 MB | +1.9 MB |
| emerging‑useragent | +5 MB | 57 MB | +3.2 MB | +1.8 MB |
| emerging‑shellcode | +4 MB | 56 MB | +2.0 MB | +2.0 MB |
| emerging‑worm | +3 MB | 55 MB | +1.6 MB | +1.4 MB |
| emerging‑dns | +3 MB | 55 MB | +0.3 MB | +2.7 MB |
| emerging‑voip | +3 MB | 55 MB | +0.3 MB | +2.7 MB |
| emerging‑snmp | +2 MB | 54 MB | +0.3 MB | +1.7 MB |
Change column = (UDM‑SE delta) − (UCG‑Ultra delta). Baseline row shows absolute totals only.
Swap usage remained constant.
Cgroup: /sys/fs/cgroup/idsIps/
| Resource | Limit | File | Behaviour |
|---|---|---|---|
| RAM (hard) | 1.5 GiB | memory.max |
OOM kill if exceeded |
| RAM (soft) | 1.4 GiB | memory.high |
Throttling if exceeded |
| Swap | 250 MiB | memory.swap.max |
Max swap allowed on UCG-Ultra, UDM-SE, UXG-Pro |
Total budget: 1,786 MiB (1,536 MiB RAM + 250 MiB swap)
Current usage: ~444 MiB RAM (~25% of budget)
Swap usage: 0 MiB (observed, swappiness=10)
Manual tests on UDM‑SE at 100/20 and 350/32 Mbps showed zero memory spike over ~2.4 minutes (291 samples @ 0.5 s). Suricata RSS remained ~443 MB. Current WAN speeds did not create enough concurrent flows to stress memory.
Why spikes occur (theory):
- Speed tests potentially open hundreds of parallel connections.
- Each flow consumes a table entry, TCP reassembly buffers, protocol state, and pattern‑matching state per rule.
- Memory scales with
throughput × active_rules × concurrent_flows.
- Cgroup limit reached (~1,786 MiB budget) → memory exhaustion.
- Kernel OOM killer sends
SIGKILLto Suricata. - Suricata did not auto‑restart in my tests.
- NFQUEUE path fails closed: queue fills and drops new packets.
- Recovery required a gateway restart (power cycle in my case).
Check OOM events: cat /sys/fs/cgroup/idsIps/memory.events | grep oom_kill
- Normal: Internet → WAN → nfqueue → Suricata → verdict → LAN
- When Suricata exits: Internet → WAN → nfqueue → [no consumer] → queue fills → drop
- Did not observe
--queue-bypassenabled. NFQUEUE length appeared ~1024 packets by default.
| Component | Baseline | High‑Throughput | Config Limit |
|---|---|---|---|
| Rule signatures | 440 MB | 440 MB | Static |
| Flow tracking | Minimal | +400–1,200 MB | 32 MB (exceeded under load in testing) |
| Stream reassembly | Minimal | +50–200 MB | 16 MB (exceeded under load in testing) |
| Pattern buffers | Minimal | +30–100 MB | 32 MB (exceeded under load in testing) |
| Total | 440 MB | 930–1,840 MB | Scales with WAN speed |
Config: /usr/share/ubios-udapi-server/ips/config/suricata_ubios_high.yaml
Note: The configured memcaps (~80 MB total) were exceeded under load in testing.
Immediate mitigation with no IPS changes; manual tests remain possible. Extremely high sustained throughput can still exhaust memory, and I have not verified whether results are used by "Smart Queues" feature.
Disabling heavier categories (e.g., emerging‑webapps ~−98 MB, emerging‑mobile ~−27 MB) reduced steady‑state RSS. With 9 categories, baseline measured ~440 MB, leaving ~1.28 GiB of headroom for flow spikes.
- On UDM‑SE and UXG‑Pro running 4.4.3 (observed Oct 2025), signature files appeared bundled with firmware.
- I did not observe a separate updater or cloud‑based “real‑time” rule updates on my (non-CyberSecure) devices.
- Location:
/usr/share/ubios-udapi-server/ips/rules/*.rules(86+ files)
- Update scripts are present but were not scheduled by default on my devices immediately after enabling IPS; unfortunately I did not test before toggling.
- Manual updates had no measurable memory impact (RSS ~441–442 MB), and no Suricata restart/reload was observed (simple ipset file swap).
- Scripts:
/usr/share/ubios-udapi-server/ips/bin/ips-update.sh(manual)/usr/share/ubios-udapi-server/ips/bin/ips-update-service.sh(scheduler)
Results reflect my own 2 (+ borrowed UXG-Pro) devices and test conditions only.
Interestingly on the UXG-Pro, definition updates were attempted overnight but failed repeatedly.
I considered testing simulated 2.5 gbps throughput to definitively prove a memory issue, but don't have the time.
Author: Alex Findlay
License: MIT