123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263 |
- package neighbors
- import (
- "context"
- "encoding/json"
- "fmt"
- "os/exec"
- "goa.design/clue/log"
- )
- const (
- arpCmd = "arp"
- arpOutputVersion = "1"
- )
- type (
- arpOutput struct {
- Version string `json:"__version"`
- ARP struct {
- Cache []arpEntry `json:"arp-cache"`
- } `json:"arp"`
- }
- arpEntry struct {
- IPAddress string `json:"ip-address"`
- MACAddress string `json:"mac-address"`
- Interface string `json:"interface"`
- }
- )
- func (a *arp) entries(ctx context.Context, ifs Interfaces) (entries []arpEntry, err error) {
- cmd := exec.CommandContext(ctx, a.cmd, "--libxo=json", "-an")
- if len(ifs) == 1 {
- for ifi := range ifs {
- cmd.Args = append(cmd.Args, "-i", ifi)
- }
- }
- log.Debug(ctx, log.KV{K: "cmd", V: cmd})
- b, err := cmd.Output()
- if err != nil {
- return
- }
- o := &arpOutput{}
- if err = json.Unmarshal(b, o); err != nil {
- return
- }
- if o.Version != arpOutputVersion {
- err = fmt.Errorf("arp output version mismatch (got %v, expected %v)", o.Version, arpOutputVersion)
- return
- }
- entries = make([]arpEntry, 0, len(o.ARP.Cache))
- for _, e := range o.ARP.Cache {
- if e.IPAddress != "" {
- entries = append(entries, e)
- }
- }
- return
- }
|