Add: 自宅ネットワークにIDSを導入した話
All checks were successful
Deploy Docusaurus Site / deploy (push) Successful in 37s
All checks were successful
Deploy Docusaurus Site / deploy (push) Successful in 37s
This commit is contained in:
parent
22e7f7d1db
commit
e1686d7acb
BIN
docs/home-network-ids-proxmox/banner.png
Normal file
BIN
docs/home-network-ids-proxmox/banner.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 75 KiB |
305
docs/home-network-ids-proxmox/index.md
Normal file
305
docs/home-network-ids-proxmox/index.md
Normal file
@ -0,0 +1,305 @@
|
|||||||
|
---
|
||||||
|
sidebar_position: 2
|
||||||
|
title: 自宅ネットワークにIDSを導入した話 — Proxmox LXC で Suricata + ntopng
|
||||||
|
description: Proxmox VE の LXC コンテナで Suricata と ntopng を使った自宅ネットワーク監視環境を構築した記録。TEEミラーリング、カスタムルール、Zabbix連携まで。
|
||||||
|
hide_table_of_contents: false
|
||||||
|
displayed_sidebar: null
|
||||||
|
image: ./banner.png
|
||||||
|
---
|
||||||
|
|
||||||
|
# 自宅ネットワークにIDSを導入した話
|
||||||
|
|
||||||
|
## きっかけ
|
||||||
|
|
||||||
|
自宅サーバーを運用してると、外向きのサービスも増えてくるし、IoTデバイスも増える。リバースプロキシの裏で何が起きてるか、正直あんまり把握できてなかった。
|
||||||
|
|
||||||
|
最近 OpenClaw(AIアシスタント基盤)を自宅で動かし始めて、外部APIとの通信も増えてきた。「そろそろネットワークの中身ちゃんと見ないとまずいかも」と思って、とりあえずやってみることにした。
|
||||||
|
|
||||||
|
## 構成
|
||||||
|
|
||||||
|
うちの環境は Proxmox VE でクラスタを組んでて、サービスは基本 LXC コンテナで動かしてる。専用のミラーリングスイッチとかは持ってないから、Proxmox の機能でなんとかする方針。
|
||||||
|
|
||||||
|
### 最終的な構成図
|
||||||
|
|
||||||
|
```
|
||||||
|
インターネット
|
||||||
|
│
|
||||||
|
├─ Nginx Proxy Manager (LXC, 192.168.1.189)
|
||||||
|
│ │
|
||||||
|
│ ├─ 各種サービス (Gitea, Docusaurus, etc.)
|
||||||
|
│ │
|
||||||
|
│ └─ [TEE mirror] ──→ Suricata + ntopng (LXC, 192.168.1.187)
|
||||||
|
│ │
|
||||||
|
│ ├─ eth0: サービスネットワーク (192.168.1.0/24)
|
||||||
|
│ └─ eth10: データプレーン (192.168.10.0/24)
|
||||||
|
│
|
||||||
|
├─ Proxmox VE ノード x4
|
||||||
|
│ └─ [TEE mirror] ──→ (同上)
|
||||||
|
│
|
||||||
|
└─ Zabbix (LXC, 192.168.1.172)
|
||||||
|
└─ Suricata アラート監視
|
||||||
|
```
|
||||||
|
|
||||||
|
### 使ったもの
|
||||||
|
|
||||||
|
| コンポーネント | 役割 |
|
||||||
|
|---|---|
|
||||||
|
| **Suricata 6.0.4** | IDS(侵入検知) |
|
||||||
|
| **ntopng Community** | トラフィック可視化・フロー分析 |
|
||||||
|
| **Zabbix 7.4** | アラート集約・通知 |
|
||||||
|
| **Proxmox TEE** | パケットミラーリング |
|
||||||
|
|
||||||
|
## LXC コンテナの作成
|
||||||
|
|
||||||
|
Proxmox の Web UI から Ubuntu 22.04 の LXC を作成。ポイントはいくつかある。
|
||||||
|
|
||||||
|
### スペック
|
||||||
|
|
||||||
|
- CPU: 2コア
|
||||||
|
- メモリ: 4GB(Suricata のルール読み込みで結構食う)
|
||||||
|
- ディスク: 20GB
|
||||||
|
- NIC: 2つ(サービス用 + データプレーン用)
|
||||||
|
|
||||||
|
### 特権コンテナにすること(重要)
|
||||||
|
|
||||||
|
最初は非特権コンテナで作ったんだけど、**Suricata の af-packet(パケットキャプチャ)が動かない**。ルールの読み込みまでは成功するのに、キャプチャスレッドが起動しない。
|
||||||
|
|
||||||
|
ログにはこう出る:
|
||||||
|
|
||||||
|
```
|
||||||
|
48714 rules successfully loaded, 0 rules failed
|
||||||
|
48719 signatures processed.
|
||||||
|
```
|
||||||
|
|
||||||
|
でも `All AFP capture threads are running.` が出ない。eve.json も更新されない。
|
||||||
|
|
||||||
|
原因は af-packet のプロミスキャスモードに必要な権限が非特権コンテナだと制限されるから。
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# /etc/pve/lxc/<CTID>.conf
|
||||||
|
# unprivileged: 1 ← これを削除
|
||||||
|
```
|
||||||
|
|
||||||
|
特権コンテナにしたら一発で動いた。
|
||||||
|
|
||||||
|
### NIC 設定
|
||||||
|
|
||||||
|
```
|
||||||
|
net0: name=eth0,bridge=vmbr0,ip=dhcp,type=veth
|
||||||
|
net1: name=eth10,bridge=vmbr1,ip=192.168.10.187/24,type=veth
|
||||||
|
```
|
||||||
|
|
||||||
|
- `eth0`: 管理・サービス用(192.168.1.0/24)
|
||||||
|
- `eth10`: TEE ミラートラフィック受信用(192.168.10.0/24)
|
||||||
|
|
||||||
|
**ゲートウェイの設定を忘れずに。** DHCPじゃない場合、`gw=192.168.1.1` を net0 に追加しないと外部に出られない(パッケージインストールで詰む)。
|
||||||
|
|
||||||
|
## Suricata のインストールと設定
|
||||||
|
|
||||||
|
```bash
|
||||||
|
sudo apt update
|
||||||
|
sudo apt install -y suricata suricata-update
|
||||||
|
sudo suricata-update
|
||||||
|
```
|
||||||
|
|
||||||
|
### suricata.yaml の設定ポイント
|
||||||
|
|
||||||
|
#### HOME_NET
|
||||||
|
|
||||||
|
```yaml
|
||||||
|
HOME_NET: "[192.168.1.0/24]"
|
||||||
|
```
|
||||||
|
|
||||||
|
#### HTTP_PORTS を拡張する
|
||||||
|
|
||||||
|
デフォルトだと `HTTP_PORTS: "80"` だけ。自宅サーバーは 8006(Proxmox)、3000(ntopng/Grafana)、8080(Zabbix)とか色んなポートで HTTP 使ってるから、これを広げないと HTTP の中身をパースしてくれない。
|
||||||
|
|
||||||
|
```yaml
|
||||||
|
HTTP_PORTS: "[80,443,3000,3128,8006,8007,8080,8443,9876]"
|
||||||
|
```
|
||||||
|
|
||||||
|
これに気づくまでかなりハマった。カスタムルールが全然発火しなくて、ログを見たら HTTP イベント自体が記録されてなかった。
|
||||||
|
|
||||||
|
#### ルールファイル
|
||||||
|
|
||||||
|
```yaml
|
||||||
|
rule-files:
|
||||||
|
- suricata.rules
|
||||||
|
- local.rules
|
||||||
|
```
|
||||||
|
|
||||||
|
`suricata-update` で取得したルールは `/var/lib/suricata/rules/suricata.rules` に保存される。`/etc/suricata/rules/` にシンボリックリンクを作っておくと楽。
|
||||||
|
|
||||||
|
```bash
|
||||||
|
sudo ln -s /var/lib/suricata/rules/suricata.rules /etc/suricata/rules/suricata.rules
|
||||||
|
```
|
||||||
|
|
||||||
|
## カスタムルールの作成
|
||||||
|
|
||||||
|
ET Open のルールセットだけだと、よくある Web 探索行為(`.env` を探すボットとか)は検知できない。自分で書く。
|
||||||
|
|
||||||
|
```bash title="/etc/suricata/rules/local.rules"
|
||||||
|
# === 探索行為の検知 ===
|
||||||
|
alert http any any -> $HOME_NET any (msg:"Scan: wp-admin access"; content:"/wp-admin"; http_uri; sid:2000001; rev:1;)
|
||||||
|
alert http any any -> $HOME_NET any (msg:"Scan: .env access"; content:"/.env"; http_uri; sid:2000002; rev:1;)
|
||||||
|
alert http any any -> $HOME_NET any (msg:"Scan: phpmyadmin access"; content:"/phpmyadmin"; nocase; http_uri; sid:2000003; rev:1;)
|
||||||
|
alert http any any -> $HOME_NET any (msg:"Scan: xmlrpc access"; content:"/xmlrpc.php"; http_uri; sid:2000004; rev:1;)
|
||||||
|
alert http any any -> $HOME_NET any (msg:"Scan: .git directory access"; content:"/.git/"; http_uri; sid:2000005; rev:1;)
|
||||||
|
alert http any any -> $HOME_NET any (msg:"Scan: admin panel probe"; content:"/admin"; http_uri; sid:2000009; rev:1;)
|
||||||
|
|
||||||
|
# === SQLインジェクション試行 ===
|
||||||
|
alert http any any -> $HOME_NET any (msg:"SQLi: UNION SELECT attempt"; content:"UNION"; nocase; http_uri; content:"SELECT"; nocase; http_uri; sid:2000011; rev:1;)
|
||||||
|
|
||||||
|
# === ディレクトリトラバーサル ===
|
||||||
|
alert http any any -> $HOME_NET any (msg:"Traversal: ../ attempt"; content:"../"; http_uri; sid:2000013; rev:1;)
|
||||||
|
|
||||||
|
# === ブルートフォース ===
|
||||||
|
alert http any any -> $HOME_NET any (msg:"Brute: login page flood"; content:"/login"; http_uri; threshold:type both, track by_src, count 20, seconds 60; sid:2000014; rev:1;)
|
||||||
|
```
|
||||||
|
|
||||||
|
テストは curl で簡単にできる:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
curl -s http://192.168.1.187:3000/.env
|
||||||
|
# → eve.json に "Scan: .env access" のアラートが記録される
|
||||||
|
```
|
||||||
|
|
||||||
|
## TEE によるパケットミラーリング
|
||||||
|
|
||||||
|
専用のミラーリングスイッチがなくても、Proxmox ホスト上で iptables の TEE ターゲットを使えばパケットをコピーできる。
|
||||||
|
|
||||||
|
```bash title="各 Proxmox ホスト上で実行"
|
||||||
|
# サービスネットワーク経由のトラフィックをデータプレーンにミラー
|
||||||
|
iptables -t mangle -A PREROUTING -i vmbr0 -j TEE --gateway 192.168.10.187
|
||||||
|
iptables -t mangle -A POSTROUTING -o vmbr0 -j TEE --gateway 192.168.10.187
|
||||||
|
```
|
||||||
|
|
||||||
|
データプレーン(vmbr1, 192.168.10.0/24)を別に用意してるのは、ミラートラフィックでサービス帯域を圧迫しないため。
|
||||||
|
|
||||||
|
## ntopng でトラフィック可視化
|
||||||
|
|
||||||
|
ntopng は Web UI でリアルタイムのトラフィック状況が見れる。Community 版でも十分使える。
|
||||||
|
|
||||||
|
```bash
|
||||||
|
sudo apt install -y ntopng
|
||||||
|
```
|
||||||
|
|
||||||
|
設定ファイル:
|
||||||
|
|
||||||
|
```ini title="/etc/ntopng/ntopng.conf"
|
||||||
|
-i=eth0
|
||||||
|
-w=3000
|
||||||
|
-m=192.168.1.0/24
|
||||||
|
```
|
||||||
|
|
||||||
|
### API でホストラベルを設定
|
||||||
|
|
||||||
|
ntopng の REST API でホストにわかりやすい名前をつけられる:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
curl -X POST -H "Authorization: Token <API_TOKEN>" \
|
||||||
|
"http://localhost:3000/lua/rest/v2/set/host/alias.lua" \
|
||||||
|
-d "host=192.168.1.7&custom_name=db975i"
|
||||||
|
```
|
||||||
|
|
||||||
|
### アラートフローの確認
|
||||||
|
|
||||||
|
```bash
|
||||||
|
curl -H "Authorization: Token <API_TOKEN>" \
|
||||||
|
"http://localhost:3000/lua/rest/v2/get/flow/active.lua?ifid=2&alert_type=1"
|
||||||
|
```
|
||||||
|
|
||||||
|
:::warning ntopng の Suricata 連携は Enterprise 版のみ
|
||||||
|
Community 版では ntopng 上で Suricata のアラートを直接表示できない。Zabbix 等の別ツールで集約する必要がある。
|
||||||
|
:::
|
||||||
|
|
||||||
|
## Zabbix 連携
|
||||||
|
|
||||||
|
Suricata のアラートを Zabbix で監視・通知する。
|
||||||
|
|
||||||
|
### Zabbix Agent2 のインストール
|
||||||
|
|
||||||
|
```bash
|
||||||
|
wget -O /tmp/zabbix-release.deb \
|
||||||
|
https://repo.zabbix.com/zabbix/7.4/release/ubuntu/pool/main/z/zabbix-release/zabbix-release_latest_7.4+ubuntu22.04_all.deb
|
||||||
|
sudo dpkg -i /tmp/zabbix-release.deb
|
||||||
|
sudo apt update && sudo apt install -y zabbix-agent2
|
||||||
|
```
|
||||||
|
|
||||||
|
### eve.json パーススクリプト
|
||||||
|
|
||||||
|
Zabbix の `log[]` アイテムだと JSON のフィルタが難しいので、UserParameter + スクリプトで対応。
|
||||||
|
|
||||||
|
```bash title="/etc/zabbix/scripts/suricata_alerts.sh"
|
||||||
|
#!/bin/bash
|
||||||
|
MODE=${1:-count}
|
||||||
|
SECONDS_AGO=${2:-60}
|
||||||
|
CUTOFF=$(date -u -d "-${SECONDS_AGO} seconds" +%Y-%m-%dT%H:%M:%S)
|
||||||
|
|
||||||
|
case $MODE in
|
||||||
|
count)
|
||||||
|
grep '"event_type":"alert"' /var/log/suricata/eve.json | \
|
||||||
|
awk -F'"timestamp":"' '{print $2}' | cut -d'"' -f1 | \
|
||||||
|
awk -v c="$CUTOFF" '$0 >= c' | wc -l ;;
|
||||||
|
custom_count)
|
||||||
|
grep 'signature_id.*200000' /var/log/suricata/eve.json | \
|
||||||
|
awk -F'"timestamp":"' '{print $2}' | cut -d'"' -f1 | \
|
||||||
|
awk -v c="$CUTOFF" '$0 >= c' | wc -l ;;
|
||||||
|
last)
|
||||||
|
grep '"event_type":"alert"' /var/log/suricata/eve.json | tail -1 ;;
|
||||||
|
esac
|
||||||
|
```
|
||||||
|
|
||||||
|
### 監視アイテムとトリガー
|
||||||
|
|
||||||
|
| アイテム | 種別 | 間隔 |
|
||||||
|
|---------|------|------|
|
||||||
|
| 全アラート数 (60s) | 数値 | 30秒 |
|
||||||
|
| カスタムルール数 (60s) | 数値 | 30秒 |
|
||||||
|
| 個別アラートログ | ログ | 10秒 |
|
||||||
|
|
||||||
|
トリガーはカスタムルール検知で「警告」、大量アラート(100件/分超)で「重大」に設定。
|
||||||
|
|
||||||
|
## やってみてわかったこと
|
||||||
|
|
||||||
|
### ハマりポイント
|
||||||
|
|
||||||
|
1. **非特権 LXC だと af-packet が動かない** — 特権コンテナ必須
|
||||||
|
2. **HTTP_PORTS がデフォルト 80 のみ** — 自宅サーバーのポートを追加しないと HTTP パースされない
|
||||||
|
3. **LXC のゲートウェイ設定漏れ** — パッケージインストール時に外に出られなくて詰む
|
||||||
|
4. **suricata.rules のパス** — `suricata-update` は `/var/lib/` に保存するが、設定は `/etc/suricata/rules/` を見る
|
||||||
|
|
||||||
|
### 実際に検知されたもの
|
||||||
|
|
||||||
|
初回スキャンで検知されたのは:
|
||||||
|
- Corosync (UDP:5405) のクラスタ通信
|
||||||
|
- Proxmox UI (8006/8007) のアクセス
|
||||||
|
- MDNS、SMB、SSH のプロトコル異常
|
||||||
|
- Tuya IoT デバイスの通信
|
||||||
|
|
||||||
|
**セキュリティ上の脅威はゼロだった。** 自宅ネットワークなので当たり前といえば当たり前だけど、「異常がない」ことを確認できるのが大事。
|
||||||
|
|
||||||
|
### Postfix がデフォルトで開いてる問題
|
||||||
|
|
||||||
|
Proxmox VE ノードの脆弱性スキャンをしたら、全ノードで SMTP (25/tcp) が外部から到達可能だった。Proxmox はデフォルトで Postfix を入れてる(通知メール用)けど、ローカルのみにリッスンを制限すべき:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
sudo postconf -e 'inet_interfaces = loopback-only'
|
||||||
|
sudo systemctl restart postfix
|
||||||
|
```
|
||||||
|
|
||||||
|
## まとめ
|
||||||
|
|
||||||
|
専用機材なしでも、Proxmox の LXC + TEE ミラーリングで実用的な IDS 環境が作れた。月額コストもゼロ。
|
||||||
|
|
||||||
|
「何が起きてるかわからない」状態から「異常があれば検知して通知される」状態になっただけで、だいぶ安心感が違う。自宅サーバー勢にはおすすめ。
|
||||||
|
|
||||||
|
## 参考リンク
|
||||||
|
|
||||||
|
- [Suricata公式ドキュメント](https://docs.suricata.io/)
|
||||||
|
- [ntopng公式](https://www.ntop.org/products/traffic-analysis/ntopng/)
|
||||||
|
- [Proxmox VE ドキュメント](https://pve.proxmox.com/pve-docs/)
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
*この記事は2026年2月時点の情報です。*
|
||||||
@ -8,6 +8,12 @@ slug: /
|
|||||||
|
|
||||||
日常の思考、情報収集、気になったことなど。
|
日常の思考、情報収集、気になったことなど。
|
||||||
|
|
||||||
|
## 記事
|
||||||
|
|
||||||
|
- [自宅ネットワークにIDSを導入した話 — Proxmox LXC で Suricata + ntopng](/blog/home-network-ids-proxmox/) 🆕
|
||||||
|
- [Ollama がローカルAIのハブとしてめちゃ最強な件](/blog/ollama-local-ai-hub/)
|
||||||
|
|
||||||
|
|
||||||
## AIヘッドライン
|
## AIヘッドライン
|
||||||
|
|
||||||
毎日のAI関連ニュースをまとめています。
|
毎日のAI関連ニュースをまとめています。
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user