From b1baa06f2bc421c11049915facc7ffb023c68a9b Mon Sep 17 00:00:00 2001 From: "Ruben S. Montero" Date: Fri, 21 Aug 2015 17:23:08 +0200 Subject: [PATCH] feature #3028: Scheduler check and set PCI device requests --- src/host/HostShare.cc | 21 ++++--- src/scheduler/include/HostXML.h | 14 +++-- src/scheduler/include/VirtualMachineXML.h | 3 +- src/scheduler/src/pool/HostXML.cc | 60 ++++++++++++------- .../src/pool/VirtualMachinePoolXML.cc | 6 +- src/scheduler/src/pool/VirtualMachineXML.cc | 12 +++- src/scheduler/src/sched/Scheduler.cc | 22 ++++--- 7 files changed, 95 insertions(+), 43 deletions(-) diff --git a/src/host/HostShare.cc b/src/host/HostShare.cc index 1ca35ae7ed..8eb017b083 100644 --- a/src/host/HostShare.cc +++ b/src/host/HostShare.cc @@ -18,7 +18,8 @@ #include #include -#include +#include +#include #include "HostShare.h" @@ -258,16 +259,22 @@ ostream& operator<<(ostream& os, const HostSharePCI& pci) { map::const_iterator it; + os << right << setw(15)<< "PCI ADDRESS"<< " " + << right << setw(8) << "CLASS" << " " + << right << setw(8) << "VENDOR" << " " + << right << setw(8) << "DEVICE" << " " + << right << setw(8) << "VMID" << " " + << endl << setw(55) << setfill('-') << "-" << setfill(' ') << endl; + for (it=pci.pci_devices.begin(); it!=pci.pci_devices.end(); it++) { HostSharePCI::PCIDevice * dev = it->second; - os << endl << "CLASS : " << dev->class_id; - os << endl << "VENDOR : " << dev->vendor_id; - os << endl << "DEVICE : " << dev->device_id; - os << endl << "ADDRESS : " << dev->address; - os << endl << "VMID : " << dev->vmid; - os << endl; + os << right << setw(15)<< dev->address << " " + << right << setw(8) << dev->class_id << " " + << right << setw(8) << dev->vendor_id << " " + << right << setw(8) << dev->device_id << " " + << right << setw(8) << dev->vmid << " " << endl; } return os; diff --git a/src/scheduler/include/HostXML.h b/src/scheduler/include/HostXML.h index 4985076d71..15576ac6f7 100644 --- a/src/scheduler/include/HostXML.h +++ b/src/scheduler/include/HostXML.h @@ -51,21 +51,24 @@ public: * Tests whether a new VM can be hosted by the host or not * @param cpu needed by the VM (percentage) * @param mem needed by the VM (in KB) + * @param pci devices needed byt the VM * @param error error message * @return true if the share can host the VM */ - bool test_capacity(long long cpu, long long mem, string & error) const; + bool test_capacity(long long cpu, long long mem, vector &pci, + string & error); /** * Tests whether a new VM can be hosted by the host or not * @param cpu needed by the VM (percentage) * @param mem needed by the VM (in KB) + * @param pci devices needed byt the VM * @return true if the share can host the VM */ - bool test_capacity(long long cpu, long long mem) const + bool test_capacity(long long cpu,long long mem,vector &p) { string tmp_st; - return test_capacity(cpu, mem, tmp_st); + return test_capacity(cpu, mem, p, tmp_st); }; /** @@ -75,11 +78,14 @@ public: * @param mem needed by the VM (in KB) * @return 0 on success */ - void add_capacity(long long cpu, long long mem) + void add_capacity(int vmid, long long cpu, long long mem, + vector &p) { cpu_usage += cpu; mem_usage += mem; + pci.add(p, vmid); + running_vms++; }; diff --git a/src/scheduler/include/VirtualMachineXML.h b/src/scheduler/include/VirtualMachineXML.h index 4539608df3..521edf8a48 100644 --- a/src/scheduler/include/VirtualMachineXML.h +++ b/src/scheduler/include/VirtualMachineXML.h @@ -116,7 +116,8 @@ public: return ds_requirements; } - void get_requirements (int& cpu, int& memory, long long& disk); + void get_requirements (int& cpu, int& memory, long long& disk, + vector &pci); map get_storage_usage(); diff --git a/src/scheduler/src/pool/HostXML.cc b/src/scheduler/src/pool/HostXML.cc index df64375239..a6cc8a59ff 100644 --- a/src/scheduler/src/pool/HostXML.cc +++ b/src/scheduler/src/pool/HostXML.cc @@ -16,6 +16,8 @@ #include #include +#include +#include #include "HostXML.h" #include "NebulaUtil.h" @@ -125,30 +127,46 @@ int HostXML::search(const char *name, int& value) /* -------------------------------------------------------------------------- */ /* -------------------------------------------------------------------------- */ -bool HostXML::test_capacity(long long cpu, long long mem, string & error) const +bool HostXML::test_capacity(long long cpu, long long mem, + vector& p, string & error) { - bool fits = (((max_cpu - cpu_usage ) >= cpu) && - ((max_mem - mem_usage ) >= mem)); - + bool pci_fits = pci.test(p); + bool fits = ((max_cpu - cpu_usage ) >= cpu) && + ((max_mem - mem_usage ) >= mem) && + pci_fits; if (!fits) { if (NebulaLog::log_level() >= Log::DDEBUG) { - ostringstream oss; + if ( pci_fits ) + { + ostringstream oss; - oss << "Not enough capacity. " - << "Requested: " - << cpu << " CPU, " - << mem << " KB MEM; " - << "Available: " - << (max_cpu - cpu_usage ) << " CPU, " - << (max_mem - mem_usage ) << " KB MEM"; + oss << "Not enough capacity. " + << "Requested: " + << cpu << " CPU, " + << mem << " KB MEM; " + << "Available: " + << (max_cpu - cpu_usage ) << " CPU, " + << (max_mem - mem_usage ) << " KB MEM"; - error = oss.str(); + error = oss.str(); + } + else + { + error = "Unavailable PCI device."; + } } else { - error = "Not enough capacity."; + if ( pci_fits ) + { + error = "Not enough capacity."; + } + else + { + error = "Unavailable PCI device."; + } } } @@ -198,16 +216,18 @@ ostream& operator<<(ostream& o, const HostXML& p) o << "RUNNING_VMS : " << p.running_vms << endl; o << "PUBLIC : " << p.public_cloud << endl; - o << "DATASTORES" << endl; - o << "----------" << endl; + o << endl + << right << setw(5) << "DSID" << " " + << right << setw(15) << "FREE_MB" << " " + << endl << setw(30) << setfill('-') << "-" << setfill (' ') << endl; + for (it = p.ds_free_disk.begin() ; it != p.ds_free_disk.end() ; it++) { - o <<"\tDSID: "<< it->first << "\t\tFREE_MB: " << it->second << endl; + o << right << setw(5) << it->first << " " + << right << setw(15)<< it->second<< " " << endl; } - o << "PCI DEVICES"<< endl; - o << "-----------"<< endl; - o << p.pci; + o << endl << p.pci; return o; } diff --git a/src/scheduler/src/pool/VirtualMachinePoolXML.cc b/src/scheduler/src/pool/VirtualMachinePoolXML.cc index 16c9a23e3e..319b207f29 100644 --- a/src/scheduler/src/pool/VirtualMachinePoolXML.cc +++ b/src/scheduler/src/pool/VirtualMachinePoolXML.cc @@ -39,6 +39,7 @@ int VirtualMachinePoolXML::set_up() << right << setw(8) << "VM" << " " << right << setw(4) << "CPU" << " " << right << setw(11) << "Memory" << " " + << right << setw(2) << "PCI" << " " << right << setw(11) << "System DS" << " " << " Image DS" << endl << setw(60) << setfill('-') << "-" << setfill(' '); @@ -47,11 +48,13 @@ int VirtualMachinePoolXML::set_up() { int cpu, mem; long long disk; + vector pci; + string action = "DEPLOY"; VirtualMachineXML * vm = static_cast(it->second); - vm->get_requirements(cpu, mem, disk); + vm->get_requirements(cpu, mem, disk, pci); if (vm->is_resched()) { @@ -67,6 +70,7 @@ int VirtualMachinePoolXML::set_up() << right << setw(8) << it->first << " " << right << setw(4) << cpu << " " << right << setw(11) << mem << " " + << right << setw(2) << pci.size() << " " << right << setw(11) << disk << " "; map ds_usage = vm->get_storage_usage(); diff --git a/src/scheduler/src/pool/VirtualMachineXML.cc b/src/scheduler/src/pool/VirtualMachineXML.cc index b6ab5d2c8d..9532c414f1 100644 --- a/src/scheduler/src/pool/VirtualMachineXML.cc +++ b/src/scheduler/src/pool/VirtualMachineXML.cc @@ -202,8 +202,18 @@ ostream& operator<<(ostream& os, VirtualMachineXML& vm) /* -------------------------------------------------------------------------- */ /* -------------------------------------------------------------------------- */ -void VirtualMachineXML::get_requirements (int& cpu, int& memory, long long& disk) +void VirtualMachineXML::get_requirements (int& cpu, int& memory, + long long& disk, vector &pci) { + if (vm_template != 0) + { + vm_template->get("PCI", pci); + } + else + { + pci.clear(); + } + if (this->memory == 0 || this->cpu == 0) { cpu = 0; diff --git a/src/scheduler/src/sched/Scheduler.cc b/src/scheduler/src/sched/Scheduler.cc index e059b86d3a..0ed226f76e 100644 --- a/src/scheduler/src/sched/Scheduler.cc +++ b/src/scheduler/src/sched/Scheduler.cc @@ -502,6 +502,7 @@ int Scheduler::set_up_pools() * @param vm the virtual machine * @param vm_memory vm requirement * @param vm_cpu vm requirement + * @param vm_pci vm requirement * @param host to evaluate vm assgiment * @param n_auth number of hosts authorized for the user, incremented if needed * @param n_error number of requirement errors, incremented if needed @@ -511,8 +512,8 @@ int Scheduler::set_up_pools() * @return true for a positive match */ static bool match_host(AclXML * acls, VirtualMachineXML* vm, int vmem, int vcpu, - HostXML * host, int &n_auth, int& n_error, int &n_fits, int &n_matched, - string &error) + vector& vpci, HostXML * host, int &n_auth, int& n_error, + int &n_fits, int &n_matched, string &error) { // ------------------------------------------------------------------------- // Filter current Hosts for resched VMs @@ -560,7 +561,7 @@ static bool match_host(AclXML * acls, VirtualMachineXML* vm, int vmem, int vcpu, // ------------------------------------------------------------------------- // Check host capacity // ------------------------------------------------------------------------- - if (host->test_capacity(vcpu,vmem,error) != true) + if (host->test_capacity(vcpu, vmem, vpci, error) != true) { return false; } @@ -720,6 +721,7 @@ void Scheduler::match_schedule() int vm_memory; int vm_cpu; long long vm_disk; + vector vm_pci; int n_resources; int n_matched; @@ -750,7 +752,7 @@ void Scheduler::match_schedule() { vm = static_cast(vm_it->second); - vm->get_requirements(vm_cpu,vm_memory,vm_disk); + vm->get_requirements(vm_cpu, vm_memory, vm_disk, vm_pci); n_resources = 0; n_fits = 0; @@ -790,8 +792,8 @@ void Scheduler::match_schedule() { host = static_cast(h_it->second); - if (match_host(acls, vm, vm_memory, vm_cpu, host, n_auth, n_error, - n_fits, n_matched, m_error)) + if (match_host(acls, vm, vm_memory, vm_cpu, vm_pci, host, n_auth, + n_error, n_fits, n_matched, m_error)) { vm->add_match_host(host->get_hid()); @@ -1026,6 +1028,8 @@ void Scheduler::dispatch() int cpu, mem; long long dsk; + vector pci; + int hid, dsid, cid; bool test_cap_result; @@ -1074,7 +1078,7 @@ void Scheduler::dispatch() } } - vm->get_requirements(cpu,mem,dsk); + vm->get_requirements(cpu, mem, dsk, pci); //---------------------------------------------------------------------- // Get the highest ranked host and best System DS for it @@ -1094,7 +1098,7 @@ void Scheduler::dispatch() //------------------------------------------------------------------ // Test host capacity //------------------------------------------------------------------ - if (host->test_capacity(cpu,mem) != true) + if (host->test_capacity(cpu, mem, pci) != true) { continue; } @@ -1224,7 +1228,7 @@ void Scheduler::dispatch() vm->add_image_datastore_capacity(img_dspool); } - host->add_capacity(cpu,mem); + host->add_capacity(vm->get_oid(), cpu, mem, pci); host_vms[hid]++;