Files
SentinelMesh/agents/agent-scan-network/src/oui.rs
T
gilles 57b5fd6b77 feat(agent-scan-network): implémentation Phase 2 — découverte réseau
- Scan ping TCP multi-ports (sans root requis)
- Lecture table ARP Linux (/proc/net/arp)
- Détection 20 services par scan de ports TCP
- Base OUI embarquée (~70 constructeurs courants)
- API JSON locale Axum sur :9100 (GET /devices, GET /health)
- Push automatique vers backend /api/v1/network
- Enregistrement agent au démarrage
- Config YAML (subnet 10.0.0.0/22, concurrence, timeouts)
- ROADMAP Phase 1 et 2 marquées complètes

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-19 06:13:24 +02:00

76 lines
3.9 KiB
Rust

use std::collections::HashMap;
// Base OUI simplifiée — préfixes MAC 3 octets → constructeur
// Source : IEEE OUI registry (vendeurs les plus courants en homelab)
pub fn lookup(mac: &str) -> Option<&'static str> {
let prefix = mac.to_uppercase().replace('-', ":").chars().take(8).collect::<String>();
OUI_MAP.get(prefix.as_str()).copied()
}
static OUI_MAP: std::sync::LazyLock<HashMap<&'static str, &'static str>> =
std::sync::LazyLock::new(|| {
HashMap::from([
// Apple
("00:17:F2", "Apple"), ("00:1E:52", "Apple"), ("00:23:32", "Apple"),
("00:25:00", "Apple"), ("00:26:B9", "Apple"), ("3C:15:C2", "Apple"),
("DC:A4:CA", "Apple"), ("F4:5C:89", "Apple"), ("A8:BE:27", "Apple"),
// Raspberry Pi
("B8:27:EB", "Raspberry Pi Foundation"), ("DC:A6:32", "Raspberry Pi Ltd"),
("E4:5F:01", "Raspberry Pi Ltd"),
// Intel
("00:1B:21", "Intel"), ("00:1F:3B", "Intel"), ("8C:EC:4B", "Intel"),
("AC:FD:CE", "Intel"),
// Ubiquiti
("00:15:6D", "Ubiquiti"), ("00:27:22", "Ubiquiti"), ("04:18:D6", "Ubiquiti"),
("24:A4:3C", "Ubiquiti"), ("44:D9:E7", "Ubiquiti"), ("68:72:51", "Ubiquiti"),
("78:8A:20", "Ubiquiti"), ("80:2A:A8", "Ubiquiti"), ("DC:9F:DB", "Ubiquiti"),
("F0:9F:C2", "Ubiquiti"), ("FC:EC:DA", "Ubiquiti"),
// TP-Link
("00:1D:0F", "TP-Link"), ("14:CC:20", "TP-Link"), ("50:C7:BF", "TP-Link"),
("54:A7:03", "TP-Link"), ("60:32:B1", "TP-Link"), ("98:DA:C4", "TP-Link"),
("C4:E9:84", "TP-Link"), ("EC:08:6B", "TP-Link"),
// Netgear
("00:09:5B", "Netgear"), ("00:14:6C", "Netgear"), ("00:1B:2F", "Netgear"),
("20:4E:7F", "Netgear"), ("28:C6:8E", "Netgear"), ("A0:40:A0", "Netgear"),
// Cisco
("00:0B:BE", "Cisco"), ("00:1A:A1", "Cisco"), ("00:1E:49", "Cisco"),
("00:23:AC", "Cisco"), ("00:25:45", "Cisco"), ("00:26:99", "Cisco"),
("58:AC:78", "Cisco"), ("7C:AD:74", "Cisco"),
// Synology
("00:11:32", "Synology"), ("BC:14:EF", "Synology"),
// QNAP
("00:08:9B", "QNAP"), ("24:5E:BE", "QNAP"),
// Dell
("00:14:22", "Dell"), ("00:1A:A0", "Dell"), ("00:1C:23", "Dell"),
("00:21:70", "Dell"), ("14:18:77", "Dell"), ("18:66:DA", "Dell"),
("D4:BE:D9", "Dell"), ("F0:1F:AF", "Dell"),
// HP / Hewlett-Packard
("00:17:08", "HP"), ("00:1C:C4", "HP"), ("3C:D9:2B", "HP"),
("70:10:6F", "HP"), ("98:E7:F4", "HP"), ("B4:99:BA", "HP"),
// Proxmox VE (virtual MAC range)
("BC:24:11", "Proxmox VE"),
// VMware
("00:0C:29", "VMware"), ("00:50:56", "VMware"), ("00:05:69", "VMware"),
// Amazon / AWS
("0A:FE:1A", "Amazon"), ("02:42:AC", "Docker (bridge)"),
// Samsung
("00:16:32", "Samsung"), ("00:21:19", "Samsung"), ("00:23:39", "Samsung"),
("2C:AE:2B", "Samsung"), ("94:35:0A", "Samsung"),
// ASUS
("00:1A:92", "ASUS"), ("00:1D:60", "ASUS"), ("00:26:18", "ASUS"),
("10:BF:48", "ASUS"), ("AC:22:0B", "ASUS"),
// Mikrotik
("00:0C:42", "MikroTik"), ("4C:5E:0C", "MikroTik"),
// Xiaomi
("28:6C:07", "Xiaomi"), ("34:CE:00", "Xiaomi"), ("50:64:2B", "Xiaomi"),
// Google
("F4:F5:D8", "Google"), ("54:60:09", "Google"),
// Espressif (ESP32/ESP8266 IoT)
("24:0A:C4", "Espressif"), ("30:AE:A4", "Espressif"), ("3C:71:BF", "Espressif"),
("58:BF:25", "Espressif"), ("84:CC:A8", "Espressif"), ("A4:CF:12", "Espressif"),
("B4:E6:2D", "Espressif"), ("EC:62:60", "Espressif"),
// Arduino / Melchior
("04:E9:E5", "Arduino"),
])
});