https://github.com/msune/l2radar
An eBPF L2 neighbour tracker
https://github.com/msune/l2radar
ebpf l2 security sniffing
Last synced: 12 days ago
JSON representation
An eBPF L2 neighbour tracker
- Host: GitHub
- URL: https://github.com/msune/l2radar
- Owner: msune
- License: other
- Created: 2026-02-13T20:52:19.000Z (4 months ago)
- Default Branch: main
- Last Pushed: 2026-02-28T01:21:07.000Z (4 months ago)
- Last Synced: 2026-02-28T05:46:23.207Z (4 months ago)
- Topics: ebpf, l2, security, sniffing
- Language: Go
- Homepage:
- Size: 6.78 MB
- Stars: 11
- Watchers: 0
- Forks: 0
- Open Issues: 1
-
Metadata Files:
- Readme: README.md
- License: LICENSE
Awesome Lists containing this project
README
(Mostly) generated Claude Code Β· Directed & reviewed by a human π§
# π‘ `l2radar`
**Passive L2 neighbour monitor powered by eBPF.** See every device on your
network β MACs, IPs, vendors β without sending a single packet.
L2 Radar attaches eBPF probes to your network interfaces via
[TCX ingress](https://docs.kernel.org/bpf/), silently observes regular traffic,
ARP and NDP traffic, and presents everything in a slick dark-themed dashboard.
## π¬ Demo
## β¨ Features
- π **eBPF-powered** β zero packet injection, zero interference, zero overhead
- π **ARP + NDP parsing** β discovers IPv4 and IPv6 neighbours automatically
- π **OUI vendor lookup** β resolves MAC addresses to manufacturer names
- π **Web dashboard** β real-time, searchable, sortable, mobile-friendly
- π **HTTPS + auth** β TLS and basic auth out of the box
## π Quick Start
**1. Install `l2rctl`:**
```bash
curl -fsSL https://raw.githubusercontent.com/msune/l2radar/latest/install-l2rctl.sh | bash
```
To install a specific version:
```bash
curl -fsSL https://raw.githubusercontent.com/msune/l2radar/latest/install-l2rctl.sh | bash -s -- v0.1.0
```
**2. Start everything:**
```bash
l2rctl start
```
**3. Open the dashboard:**
π **https://localhost** (accept the self-signed cert)
That's it! L2 Radar is now watching all your external interfaces. π
## π Usage
```bash
# Start only the probe (headless)
l2rctl start probe --iface eth0 --iface wlan0
# Start with custom TLS certs
l2rctl start --tls-dir /etc/mycerts --user admin:secret
# Check what's running
l2rctl status
# Dump the neighbour table from the terminal
l2rctl dump --iface eth0
# Stop everything
l2rctl stop
```
### Interface Keywords
| Keyword | Meaning |
|---------|---------|
| `external` (default) | All external interfaces (skips docker, veth, bridges) |
| `any` | Every non-loopback L2 interface (includes docker, veth, bridges) |
## ποΈ Architecture
L2 Radar has three components:
| Component | Container | What it does |
|-----------|-----------|-------------|
| **eBPF Probe** | `l2radar` | Attaches to NICs, writes neighbour data to BPF maps, exports JSON |
| **Web UI** | `l2radar-ui` | nginx + React dashboard, serves JSON data read-only |
| **l2rctl** | _(host binary)_ | Orchestrates the containers via Docker CLI |
The probe and UI communicate through **JSON files on a shared Docker named
volume** (default `l2radar-data`, mounted at `/var/lib/l2radar` in both
containers) β no network calls between them.
```
ββββββββββββββββββββββββ l2radar-data volume ββββββββββββββββββββββββ
β eBPF Probe β neigh-eth0.json β Web UI β
β ββββββββββββββββββββββββββββββββΆβ β
β TCX ingress hooks β neigh-wlan0.json β nginx + React SPA β
β ARP/NDP parsing ββββββββββββββββββββββββββββββββΆβ auto-refresh polls β
β JSON export loop β (read-only) β OUI vendor lookup β
ββββββββββββββββββββββββ ββββββββββββββββββββββββ
privileged ports 443 (80)
--network=host unprivileged
```
π **[Full architecture docs β](docs/architecture.md)**
## π Requirements
- Linux with kernel **6.6+** (for TCX)
- Docker
- Go 1.24+ (for installing `l2rctl`)
## π οΈ Development
TODO
## π License
BSD 2-Clause. eBPF code (`probe/bpf/`) is dual-licensed BSD-2-Clause OR
GPL-2.0. See [LICENSE](LICENSE).
Made with β€οΈ from Barcelona Β· Powered by π eBPF