Files
AetherForge/agent/deploy/arp_windows.go

52 lines
1.2 KiB
Go

//go:build windows
package deploy
import (
"net"
"os/exec"
"strings"
)
// arpHosts returns the list of IPv4 hosts currently in the OS ARP cache
// that share a subnet with one of our local interfaces. These are machines
// that have recently communicated on the LAN — a far smaller and more
// targeted set than a blind /24 sweep.
//
// Falls back to nil (caller will do a full scan) on any error.
func arpHosts() []string {
out, err := exec.Command("arp", "-a").Output()
if err != nil {
return nil
}
local := getLocalIPs()
subnets := make(map[string]bool)
for _, ip := range local {
subnets[getSubnet(ip)] = true
}
var hosts []string
seen := make(map[string]bool)
for _, line := range strings.Split(string(out), "\n") {
line = strings.TrimSpace(line)
// arp -a lines look like:
// 192.168.1.1 00-11-22-33-44-55 dynamic
fields := strings.Fields(line)
if len(fields) < 2 {
continue
}
ip := net.ParseIP(fields[0])
if ip == nil || ip.To4() == nil || ip.IsLoopback() || ip.IsMulticast() {
continue
}
ipStr := ip.To4().String()
sub := getSubnet(ipStr)
if !subnets[sub] || seen[ipStr] {
continue
}
seen[ipStr] = true
hosts = append(hosts, ipStr)
}
return hosts
}