improve device and function (subdevice) types
This commit is contained in:
parent
bf5196763d
commit
e99a9c8c79
37
app/model.go
37
app/model.go
@ -101,6 +101,15 @@ func (cluster *Cluster) RebuildHost(hostName string) error {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// check node device reserved by iterating over each function, we will assume that a single reserved function means the device is also reserved
|
||||||
|
for _, device := range host.Devices {
|
||||||
|
reserved := false
|
||||||
|
for _, function := range device.Functions {
|
||||||
|
reserved = reserved || function.Reserved
|
||||||
|
}
|
||||||
|
device.Reserved = reserved
|
||||||
|
}
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -113,7 +122,7 @@ func (host *Node) GetInstance(vmid uint) (*Instance, error) {
|
|||||||
host.lock.Lock()
|
host.lock.Lock()
|
||||||
defer host.lock.Unlock()
|
defer host.lock.Unlock()
|
||||||
// get instance
|
// get instance
|
||||||
instance, ok := host.Instances[vmid]
|
instance, ok := host.Instances[InstanceID(vmid)]
|
||||||
if !ok {
|
if !ok {
|
||||||
instance_ch <- nil
|
instance_ch <- nil
|
||||||
err_ch <- fmt.Errorf("vmid %d not in host %s", vmid, host.Name)
|
err_ch <- fmt.Errorf("vmid %d not in host %s", vmid, host.Name)
|
||||||
@ -153,7 +162,7 @@ func (host *Node) RebuildInstance(instancetype InstanceType, vmid uint) error {
|
|||||||
instance.lock.Lock()
|
instance.lock.Lock()
|
||||||
defer instance.lock.Unlock()
|
defer instance.lock.Unlock()
|
||||||
|
|
||||||
host.Instances[vmid] = instance
|
host.Instances[InstanceID(vmid)] = instance
|
||||||
|
|
||||||
for volid := range instance.configDisks {
|
for volid := range instance.configDisks {
|
||||||
instance.RebuildVolume(host, volid)
|
instance.RebuildVolume(host, volid)
|
||||||
@ -178,7 +187,7 @@ func (instance *Instance) RebuildVolume(host *Node, volid string) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
instance.Volumes[volid] = volume
|
instance.Volumes[VolumeID(volid)] = volume
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
@ -195,7 +204,7 @@ func (instance *Instance) RebuildNet(netid string) error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
instance.Nets[uint(idnum)] = netinfo
|
instance.Nets[NetID(idnum)] = netinfo
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
@ -206,27 +215,21 @@ func (instance *Instance) RebuildDevice(host *Node, deviceid string) error {
|
|||||||
return fmt.Errorf("%s not found in devices", deviceid)
|
return fmt.Errorf("%s not found in devices", deviceid)
|
||||||
}
|
}
|
||||||
|
|
||||||
hostDeviceBusID := strings.Split(instanceDevice, ",")[0]
|
hostDeviceBusID := DeviceID(strings.Split(instanceDevice, ",")[0])
|
||||||
|
|
||||||
instanceDeviceBusID, err := strconv.ParseUint(strings.TrimPrefix(deviceid, "hostpci"), 10, 64)
|
idbid, err := strconv.ParseUint(strings.TrimPrefix(deviceid, "hostpci"), 10, 64)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
instanceDeviceBusID := InstanceDeviceID(idbid)
|
||||||
|
|
||||||
if DeviceBusIDIsSuperDevice(hostDeviceBusID) {
|
if DeviceBusIDIsSuperDevice(hostDeviceBusID) {
|
||||||
devices := []*Device{}
|
instance.Devices[InstanceDeviceID(instanceDeviceBusID)] = host.Devices[DeviceID(hostDeviceBusID)]
|
||||||
for k, v := range host.Devices {
|
for _, function := range instance.Devices[InstanceDeviceID(instanceDeviceBusID)].Functions {
|
||||||
if DeviceBusIDIsSubDevice(k, hostDeviceBusID) {
|
function.Reserved = true
|
||||||
v.Reserved = true
|
|
||||||
devices = append(devices, v)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
instance.Devices[uint(instanceDeviceBusID)] = devices
|
|
||||||
} else {
|
} else {
|
||||||
devices := []*Device{}
|
// sub function assignment not supported yet
|
||||||
v := host.Devices[hostDeviceBusID]
|
|
||||||
v.Reserved = true
|
|
||||||
instance.Devices[uint(instanceDeviceBusID)] = devices
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
|
@ -59,22 +59,41 @@ func (pve ProxmoxClient) Nodes() ([]string, error) {
|
|||||||
// Gets a Node's resources but does not recursively expand instances
|
// Gets a Node's resources but does not recursively expand instances
|
||||||
func (pve ProxmoxClient) Node(nodeName string) (*Node, error) {
|
func (pve ProxmoxClient) Node(nodeName string) (*Node, error) {
|
||||||
host := Node{}
|
host := Node{}
|
||||||
host.Devices = make(map[string]*Device)
|
host.Devices = make(map[DeviceID]*Device)
|
||||||
host.Instances = make(map[uint]*Instance)
|
host.Instances = make(map[InstanceID]*Instance)
|
||||||
|
|
||||||
node, err := pve.client.Node(context.Background(), nodeName)
|
node, err := pve.client.Node(context.Background(), nodeName)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &host, err
|
return &host, err
|
||||||
}
|
}
|
||||||
|
|
||||||
devices := []Device{}
|
devices := []PVEDevice{}
|
||||||
err = pve.client.Get(context.Background(), fmt.Sprintf("/nodes/%s/hardware/pci", nodeName), &devices)
|
err = pve.client.Get(context.Background(), fmt.Sprintf("/nodes/%s/hardware/pci", nodeName), &devices)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return &host, err
|
return &host, err
|
||||||
}
|
}
|
||||||
|
|
||||||
for _, device := range devices {
|
for _, device := range devices {
|
||||||
host.Devices[device.BusID] = &device
|
x := strings.Split(device.ID, ".")
|
||||||
|
if len(x) != 2 { // this should always be true, but skip if not
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
deviceid := DeviceID(x[0])
|
||||||
|
functionid := FunctionID(x[1])
|
||||||
|
if _, ok := host.Devices[deviceid]; !ok {
|
||||||
|
host.Devices[deviceid] = &Device{
|
||||||
|
DeviceID: deviceid,
|
||||||
|
DeviceName: device.DeviceName,
|
||||||
|
VendorName: device.VendorName,
|
||||||
|
Functions: make(map[FunctionID]*Function),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
host.Devices[deviceid].Functions[functionid] = &Function{
|
||||||
|
FunctionID: functionid,
|
||||||
|
FunctionName: device.SubsystemDeviceName,
|
||||||
|
VendorName: device.SubsystemVendorName,
|
||||||
|
Reserved: false,
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
host.Name = node.Name
|
host.Name = node.Name
|
||||||
@ -119,9 +138,9 @@ func (host *Node) VirtualMachine(VMID uint) (*Instance, error) {
|
|||||||
instance.Proctype = vm.VirtualMachineConfig.CPU
|
instance.Proctype = vm.VirtualMachineConfig.CPU
|
||||||
instance.Cores = uint64(vm.VirtualMachineConfig.Cores)
|
instance.Cores = uint64(vm.VirtualMachineConfig.Cores)
|
||||||
instance.Memory = uint64(vm.VirtualMachineConfig.Memory) * MiB
|
instance.Memory = uint64(vm.VirtualMachineConfig.Memory) * MiB
|
||||||
instance.Volumes = make(map[string]*Volume)
|
instance.Volumes = make(map[VolumeID]*Volume)
|
||||||
instance.Nets = make(map[uint]*Net)
|
instance.Nets = make(map[NetID]*Net)
|
||||||
instance.Devices = make(map[uint][]*Device)
|
instance.Devices = make(map[InstanceDeviceID]*Device)
|
||||||
|
|
||||||
return &instance, nil
|
return &instance, nil
|
||||||
}
|
}
|
||||||
@ -167,8 +186,8 @@ func (host *Node) Container(VMID uint) (*Instance, error) {
|
|||||||
instance.Cores = uint64(ct.ContainerConfig.Cores)
|
instance.Cores = uint64(ct.ContainerConfig.Cores)
|
||||||
instance.Memory = uint64(ct.ContainerConfig.Memory) * MiB
|
instance.Memory = uint64(ct.ContainerConfig.Memory) * MiB
|
||||||
instance.Swap = uint64(ct.ContainerConfig.Swap) * MiB
|
instance.Swap = uint64(ct.ContainerConfig.Swap) * MiB
|
||||||
instance.Volumes = make(map[string]*Volume)
|
instance.Volumes = make(map[VolumeID]*Volume)
|
||||||
instance.Nets = make(map[uint]*Net)
|
instance.Nets = make(map[NetID]*Net)
|
||||||
|
|
||||||
return &instance, nil
|
return &instance, nil
|
||||||
}
|
}
|
||||||
@ -206,7 +225,7 @@ func GetVolumeInfo(host *Node, volume string) (*Volume, error) {
|
|||||||
volumeData.Storage = storageID
|
volumeData.Storage = storageID
|
||||||
volumeData.Format = c.Format
|
volumeData.Format = c.Format
|
||||||
volumeData.Size = uint64(c.Size)
|
volumeData.Size = uint64(c.Size)
|
||||||
volumeData.Volid = volumeID
|
volumeData.Volid = VolumeID(volumeID)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -232,5 +251,7 @@ func GetNetInfo(net string) (*Net, error) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
n.Value = net
|
||||||
|
|
||||||
return &n, nil
|
return &n, nil
|
||||||
}
|
}
|
||||||
|
69
app/types.go
69
app/types.go
@ -14,15 +14,16 @@ type Cluster struct {
|
|||||||
|
|
||||||
type Node struct {
|
type Node struct {
|
||||||
lock sync.Mutex
|
lock sync.Mutex
|
||||||
Name string `json:"name"`
|
Name string `json:"name"`
|
||||||
Cores uint64 `json:"cores"`
|
Cores uint64 `json:"cores"`
|
||||||
Memory uint64 `json:"memory"`
|
Memory uint64 `json:"memory"`
|
||||||
Swap uint64 `json:"swap"`
|
Swap uint64 `json:"swap"`
|
||||||
Devices map[string]*Device `json:"devices"`
|
Devices map[DeviceID]*Device `json:"devices"`
|
||||||
Instances map[uint]*Instance `json:"instances"`
|
Instances map[InstanceID]*Instance `json:"instances"`
|
||||||
pvenode *proxmox.Node
|
pvenode *proxmox.Node
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type InstanceID uint64
|
||||||
type InstanceType string
|
type InstanceType string
|
||||||
|
|
||||||
const (
|
const (
|
||||||
@ -32,38 +33,58 @@ const (
|
|||||||
|
|
||||||
type Instance struct {
|
type Instance struct {
|
||||||
lock sync.Mutex
|
lock sync.Mutex
|
||||||
Type InstanceType `json:"type"`
|
Type InstanceType `json:"type"`
|
||||||
Name string `json:"name"`
|
Name string `json:"name"`
|
||||||
Proctype string `json:"cpu"`
|
Proctype string `json:"cpu"`
|
||||||
Cores uint64 `json:"cores"`
|
Cores uint64 `json:"cores"`
|
||||||
Memory uint64 `json:"memory"`
|
Memory uint64 `json:"memory"`
|
||||||
Swap uint64 `json:"swap"`
|
Swap uint64 `json:"swap"`
|
||||||
Volumes map[string]*Volume `json:"volumes"`
|
Volumes map[VolumeID]*Volume `json:"volumes"`
|
||||||
Nets map[uint]*Net `json:"nets"`
|
Nets map[NetID]*Net `json:"nets"`
|
||||||
Devices map[uint][]*Device `json:"devices"`
|
Devices map[InstanceDeviceID]*Device `json:"devices"`
|
||||||
pveconfig interface{}
|
pveconfig interface{}
|
||||||
configDisks map[string]string
|
configDisks map[string]string
|
||||||
configNets map[string]string
|
configNets map[string]string
|
||||||
configHostPCIs map[string]string
|
configHostPCIs map[string]string
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type VolumeID string
|
||||||
type Volume struct {
|
type Volume struct {
|
||||||
Storage string `json:"storage"`
|
Storage string `json:"storage"`
|
||||||
Format string `json:"format"`
|
Format string `json:"format"`
|
||||||
Size uint64 `json:"size"`
|
Size uint64 `json:"size"`
|
||||||
Volid string `json:"volid"`
|
Volid VolumeID `json:"volid"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type NetID uint64
|
||||||
type Net struct {
|
type Net struct {
|
||||||
Rate uint64 `json:"rate"`
|
Value string `json:"value"`
|
||||||
VLAN uint64 `json:"vlan"`
|
Rate uint64 `json:"rate"`
|
||||||
|
VLAN uint64 `json:"vlan"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type Device struct {
|
type PVEDevice struct {
|
||||||
BusID string `json:"id"`
|
ID string `json:"id"`
|
||||||
DeviceName string `json:"device_name"`
|
DeviceName string `json:"device_name"`
|
||||||
VendorName string `json:"vendor_name"`
|
VendorName string `json:"vendor_name"`
|
||||||
SubsystemDeviceName string `json:"subsystem_device_name"`
|
SubsystemDeviceName string `json:"subsystem_device_name"`
|
||||||
SubsystemVendorName string `json:"subsystem_vendor_name"`
|
SubsystemVendorName string `json:"subsystem_vendor_name"`
|
||||||
Reserved bool `json:"reserved"`
|
}
|
||||||
|
|
||||||
|
type DeviceID string
|
||||||
|
type InstanceDeviceID uint64
|
||||||
|
type Device struct {
|
||||||
|
DeviceID DeviceID `json:"device_id"`
|
||||||
|
DeviceName string `json:"device_name"`
|
||||||
|
VendorName string `json:"vendor_name"`
|
||||||
|
Functions map[FunctionID]*Function `json:"functions"`
|
||||||
|
Reserved bool `json:"reserved"`
|
||||||
|
}
|
||||||
|
|
||||||
|
type FunctionID string
|
||||||
|
type Function struct {
|
||||||
|
FunctionID FunctionID `json:"function_id"`
|
||||||
|
FunctionName string `json:"subsystem_device_name"`
|
||||||
|
VendorName string `json:"subsystem_vendor_name"`
|
||||||
|
Reserved bool `json:"reserved"`
|
||||||
}
|
}
|
||||||
|
@ -41,8 +41,8 @@ func GetConfig(configPath string) Config {
|
|||||||
// subsystem devices always has the format xxxx:yy.z, whereas super devices have the format xxxx:yy
|
// subsystem devices always has the format xxxx:yy.z, whereas super devices have the format xxxx:yy
|
||||||
//
|
//
|
||||||
// returns true if BusID has format xxxx:yy
|
// returns true if BusID has format xxxx:yy
|
||||||
func DeviceBusIDIsSuperDevice(BusID string) bool {
|
func DeviceBusIDIsSuperDevice(BusID DeviceID) bool {
|
||||||
return !strings.ContainsRune(BusID, '.')
|
return !strings.ContainsRune(string(BusID), '.')
|
||||||
}
|
}
|
||||||
|
|
||||||
// returns if a device pcie bus id is a subdevice of specified super device
|
// returns if a device pcie bus id is a subdevice of specified super device
|
||||||
@ -50,6 +50,8 @@ func DeviceBusIDIsSuperDevice(BusID string) bool {
|
|||||||
// subsystem devices always has the format xxxx:yy.z, whereas super devices have the format xxxx:yy
|
// subsystem devices always has the format xxxx:yy.z, whereas super devices have the format xxxx:yy
|
||||||
//
|
//
|
||||||
// returns true if BusID has prefix SuperDeviceBusID and SuperDeviceBusID is a Super Device
|
// returns true if BusID has prefix SuperDeviceBusID and SuperDeviceBusID is a Super Device
|
||||||
|
/*
|
||||||
func DeviceBusIDIsSubDevice(BusID string, SuperDeviceBusID string) bool {
|
func DeviceBusIDIsSubDevice(BusID string, SuperDeviceBusID string) bool {
|
||||||
return DeviceBusIDIsSuperDevice(SuperDeviceBusID) && strings.HasPrefix(BusID, SuperDeviceBusID)
|
return DeviceBusIDIsSuperDevice(SuperDeviceBusID) && strings.HasPrefix(BusID, SuperDeviceBusID)
|
||||||
}
|
}
|
||||||
|
*/
|
||||||
|
Loading…
x
Reference in New Issue
Block a user