diff --git a/arp.go b/arp.go index 5a07e0c..983fec9 100644 --- a/arp.go +++ b/arp.go @@ -37,7 +37,7 @@ func (t *Tendrils) readARPTable() { entries := t.parseARPTable() for _, entry := range entries { - if t.iface != "" && entry.iface != t.iface { + if t.Interface != "" && entry.iface != t.Interface { continue } if isBroadcastOrZero(entry.mac) { diff --git a/cmd/tendrils/main.go b/cmd/tendrils/main.go index ee11f95..e978450 100644 --- a/cmd/tendrils/main.go +++ b/cmd/tendrils/main.go @@ -7,9 +7,20 @@ import ( ) func main() { - iface := flag.String("i", "", "interface to use (default: all interfaces)") + iface := flag.String("i", "", "interface to use") + noARP := flag.Bool("no-arp", false, "disable ARP discovery") + noLLDP := flag.Bool("no-lldp", false, "disable LLDP discovery") + noSNMP := flag.Bool("no-snmp", false, "disable SNMP discovery") + logTree := flag.Bool("log-tree", false, "log full tree on changes") + logReasons := flag.Bool("log-reasons", false, "log addition reasons") flag.Parse() - t := tendrils.New(*iface) + t := tendrils.New() + t.Interface = *iface + t.DisableARP = *noARP + t.DisableLLDP = *noLLDP + t.DisableSNMP = *noSNMP + t.LogTree = *logTree + t.LogReasons = *logReasons t.Run() } diff --git a/nodes.go b/nodes.go index 0af9a8e..8b331a3 100644 --- a/nodes.go +++ b/nodes.go @@ -44,14 +44,16 @@ type Nodes struct { ipIndex map[string]int macIndex map[string]int nextID int + t *Tendrils } -func NewNodes() *Nodes { +func NewNodes(t *Tendrils) *Nodes { n := &Nodes{ nodes: map[int]*Node{}, ipIndex: map[string]int{}, macIndex: map[string]int{}, nextID: 1, + t: t, } n.nodes[0] = &Node{ @@ -122,10 +124,14 @@ func (n *Nodes) UpdateWithParent(parentIP net.IP, ips []net.IP, macs []net.Hardw merging = append(merging, n.nodes[ids[i]].String()) n.mergeNodes(targetID, ids[i]) } - log.Printf("merged nodes %v into %s (via %s)", merging, n.nodes[targetID], source) - n.mu.Unlock() - n.LogTree() - n.mu.Lock() + if n.t.LogReasons { + log.Printf("merged nodes %v into %s (via %s)", merging, n.nodes[targetID], source) + } + if n.t.LogTree { + n.mu.Unlock() + n.LogTree() + n.mu.Lock() + } } node := n.nodes[targetID] @@ -162,10 +168,14 @@ func (n *Nodes) UpdateWithParent(parentIP net.IP, ips []net.IP, macs []net.Hardw } if len(added) > 0 { - log.Printf("updated %s +%v (via %s)", node, added, source) - n.mu.Unlock() - n.LogTree() - n.mu.Lock() + if n.t.LogReasons { + log.Printf("updated %s +%v (via %s)", node, added, source) + } + if n.t.LogTree { + n.mu.Unlock() + n.LogTree() + n.mu.Lock() + } } } diff --git a/tendrils.go b/tendrils.go index 54d7da8..95b127d 100644 --- a/tendrils.go +++ b/tendrils.go @@ -11,15 +11,21 @@ import ( type Tendrils struct { activeInterfaces map[string]context.CancelFunc nodes *Nodes - iface string + + Interface string + DisableARP bool + DisableLLDP bool + DisableSNMP bool + LogTree bool + LogReasons bool } -func New(iface string) *Tendrils { - return &Tendrils{ +func New() *Tendrils { + t := &Tendrils{ activeInterfaces: map[string]context.CancelFunc{}, - nodes: NewNodes(), - iface: iface, } + t.nodes = NewNodes(t) + return t } func (t *Tendrils) Run() { @@ -28,8 +34,12 @@ func (t *Tendrils) Run() { t.populateLocalAddresses() - go t.pollARP(ctx) - go t.pollSNMP(ctx) + if !t.DisableARP { + go t.pollARP(ctx) + } + if !t.DisableSNMP { + go t.pollSNMP(ctx) + } ticker := time.NewTicker(1 * time.Second) defer ticker.Stop() @@ -90,7 +100,7 @@ func (t *Tendrils) listInterfaces() []net.Interface { var validInterfaces []net.Interface for _, iface := range interfaces { - if t.iface != "" && iface.Name != t.iface { + if t.Interface != "" && iface.Name != t.Interface { continue } if iface.Flags&net.FlagUp == 0 { @@ -145,5 +155,7 @@ func (t *Tendrils) updateInterfaces(interfaces []net.Interface) { } func (t *Tendrils) startInterface(ctx context.Context, iface net.Interface) { - go t.listenLLDP(ctx, iface) + if !t.DisableLLDP { + go t.listenLLDP(ctx, iface) + } }