You cannot select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
150 lines
2.8 KiB
Go
150 lines
2.8 KiB
Go
<<<<<<< HEAD:reactor/needs_port/system/hwinfo.go
|
|
// package system uses linux commands to get hardware info for identifation
|
|
=======
|
|
// package system uses linux ip command to get hardware info from devices
|
|
>>>>>>> origin/wrapup:internal/pkg/system/hwinfo.go
|
|
package system
|
|
|
|
import (
|
|
"bytes"
|
|
"encoding/json"
|
|
"errors"
|
|
"hash/fnv"
|
|
"os/exec"
|
|
"strings"
|
|
)
|
|
|
|
var (
|
|
ErrBusNotFound = errors.New("bus not found for device")
|
|
ErrNoNetworkInterface = errors.New("no default network found")
|
|
)
|
|
|
|
var HardwareInfo = &hardwareInfo{}
|
|
|
|
type hardwareInfo struct {
|
|
MAC string
|
|
IP string
|
|
ID int
|
|
Model string
|
|
}
|
|
|
|
// NetInterfaces is a struct to unmarshal the ip command json.
|
|
type netInterfaces []network
|
|
|
|
// Networks holds relevant information for each network interface.
|
|
// Used to unmarshal ip command json.
|
|
type network struct {
|
|
Subnets []netInfo `json:"addr_info"`
|
|
Mac string `json:"address"`
|
|
Group string `json:"group"`
|
|
State string `json:"operstate"`
|
|
}
|
|
|
|
type netInfo struct {
|
|
Family string `json:"family"`
|
|
Ip string `json:"local"`
|
|
}
|
|
|
|
func getInfo() error {
|
|
|
|
var stderr, stdout bytes.Buffer
|
|
cmd := exec.Command("ip", "-j", "a")
|
|
cmd.Stdout = &stdout
|
|
cmd.Stderr = &stderr
|
|
|
|
if err := cmd.Run(); err != nil {
|
|
return err
|
|
}
|
|
|
|
var networks netInterfaces
|
|
|
|
if err := json.Unmarshal(stdout.Bytes(), &networks); err != nil {
|
|
return err
|
|
}
|
|
|
|
// loop over found networks finding first default, IPv4 network currently
|
|
// UP (active).
|
|
// Eventually need to look only at wg interface which simplifies
|
|
// implementation.
|
|
|
|
for _, network := range networks {
|
|
if network.Group == "default" && network.State == "UP" {
|
|
|
|
for _, subnet := range network.Subnets {
|
|
if subnet.Family == "inet" {
|
|
|
|
hash := fnv.New32a()
|
|
hash.Write([]byte(network.Mac))
|
|
id := hash.Sum32()
|
|
|
|
HardwareInfo.MAC = network.Mac
|
|
HardwareInfo.IP = subnet.Ip
|
|
HardwareInfo.ID = int(id)
|
|
|
|
return nil
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
return nil
|
|
}
|
|
|
|
func GetID() (int, error) {
|
|
|
|
if HardwareInfo.ID == 0 {
|
|
if err := getInfo(); err != nil {
|
|
return 0, err
|
|
}
|
|
}
|
|
|
|
return HardwareInfo.ID, nil
|
|
}
|
|
|
|
func GetIP() (string, error) {
|
|
|
|
if HardwareInfo.IP == "" {
|
|
if err := getInfo(); err != nil {
|
|
return "", err
|
|
}
|
|
}
|
|
|
|
return HardwareInfo.IP, nil
|
|
}
|
|
|
|
func GetModel() (string, error) {
|
|
|
|
if HardwareInfo.Model == "" {
|
|
|
|
var stderr, out bytes.Buffer
|
|
cmd := exec.Command("uname", "-n")
|
|
cmd.Stdout = &out
|
|
cmd.Stderr = &stderr
|
|
|
|
if err := cmd.Run(); err != nil {
|
|
return "", err
|
|
}
|
|
|
|
b := out.String()
|
|
HardwareInfo.Model = strings.Trim(b, " \n")
|
|
}
|
|
|
|
return HardwareInfo.Model, nil
|
|
}
|
|
|
|
func GetBus() (int, error) {
|
|
// preset busses
|
|
busList := map[string]int{"raspberrypi": 1, "beaglebone": 2}
|
|
// vars
|
|
var bus int
|
|
var ok bool
|
|
|
|
if name, err := GetModel(); err != nil {
|
|
return bus, err
|
|
} else if bus, ok = busList[name]; !ok {
|
|
return 0, ErrBusNotFound
|
|
}
|
|
|
|
return bus, nil
|
|
}
|