mirror of
https://github.com/OpenNebula/one.git
synced 2025-03-06 12:58:18 +03:00
feature #1233: Added quotas.Refactor Attach methods
This commit is contained in:
parent
554321c73b
commit
1dbeaa1719
@ -232,6 +232,7 @@ public:
|
||||
* Set the re-scheduling flag for the VM (must be in RUNNING state)
|
||||
* @param vid VirtualMachine identification
|
||||
* @param do_resched set or unset the flag
|
||||
*
|
||||
* @return 0 on success, -1 if the VM does not exits or -2 if the VM is
|
||||
* in a wrong a state
|
||||
*/
|
||||
@ -240,19 +241,14 @@ public:
|
||||
bool do_resched);
|
||||
|
||||
/**
|
||||
* Starts the attach disk action.
|
||||
* Starts the attach disk action.
|
||||
* @param vid VirtualMachine identification
|
||||
* @param tmpl Template containing the new DISK attribute.
|
||||
* @param error_str Error reason, if any
|
||||
*
|
||||
* @param vm pointer to a VirtualMachine with its mutex locked. It will be
|
||||
* unlocked
|
||||
* @param tmpl Template containing the new DISK attribute.
|
||||
* It will be deleted
|
||||
* @param error_str Error reason, if any
|
||||
* @return 0 on success, -1 action error, -2 if the VM is in a wrong a state
|
||||
* @return 0 on success, -1 otherwise
|
||||
*/
|
||||
int attach(
|
||||
VirtualMachine * vm,
|
||||
VirtualMachineTemplate * tmpl,
|
||||
string & error_str);
|
||||
int attach(int vid, VirtualMachineTemplate * tmpl, string & error_str);
|
||||
|
||||
private:
|
||||
/**
|
||||
|
135
include/Quotas.h
135
include/Quotas.h
@ -22,6 +22,8 @@
|
||||
#include "QuotaVirtualMachine.h"
|
||||
#include "QuotaImage.h"
|
||||
|
||||
class ObjectXML;
|
||||
|
||||
class Quotas
|
||||
{
|
||||
public:
|
||||
@ -44,52 +46,7 @@ public:
|
||||
*
|
||||
* @return 0 on success, -1 otherwise
|
||||
*/
|
||||
int set(Template *tmpl, string& error)
|
||||
{
|
||||
vector<Attribute *> vquotas;
|
||||
|
||||
if ( tmpl->get(datastore_quota.get_quota_name(), vquotas) > 0 )
|
||||
{
|
||||
if ( datastore_quota.set(&vquotas, error) != 0 )
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
vquotas.clear();
|
||||
}
|
||||
|
||||
if ( tmpl->get(network_quota.get_quota_name(), vquotas) > 0 )
|
||||
{
|
||||
if ( network_quota.set(&vquotas, error) != 0 )
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
vquotas.clear();
|
||||
}
|
||||
|
||||
if ( tmpl->get(image_quota.get_quota_name(), vquotas) > 0 )
|
||||
{
|
||||
if ( image_quota.set(&vquotas, error) != 0 )
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
vquotas.clear();
|
||||
}
|
||||
|
||||
if ( tmpl->get(vm_quota.get_quota_name(), vquotas) > 0 )
|
||||
{
|
||||
if ( vm_quota.set(&vquotas, error) != 0 )
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
vquotas.clear();
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
int set(Template *tmpl, string& error);
|
||||
|
||||
/**
|
||||
* Check Datastore quotas, it updates usage counters if quotas are not
|
||||
@ -159,76 +116,32 @@ public:
|
||||
* @param xml the string to store the XML
|
||||
* @return the same xml string to use it in << compounds
|
||||
*/
|
||||
string& to_xml(string& xml) const
|
||||
{
|
||||
ostringstream oss;
|
||||
|
||||
string ds_quota_xml;
|
||||
string net_quota_xml;
|
||||
string vm_quota_xml;
|
||||
string image_quota_xml;
|
||||
|
||||
oss << datastore_quota.to_xml(ds_quota_xml)
|
||||
<< network_quota.to_xml(net_quota_xml)
|
||||
<< vm_quota.to_xml(vm_quota_xml)
|
||||
<< image_quota.to_xml(image_quota_xml);
|
||||
|
||||
xml = oss.str();
|
||||
|
||||
return xml;
|
||||
}
|
||||
string& to_xml(string& xml) const;
|
||||
|
||||
/**
|
||||
* Builds quota object from an ObjectXML
|
||||
* @param object_xml pointer to the ObjectXML
|
||||
* @return 0 if success
|
||||
*/
|
||||
int from_xml(ObjectXML * object_xml)
|
||||
{
|
||||
vector<xmlNodePtr> content;
|
||||
int rc = 0;
|
||||
int from_xml(ObjectXML * object_xml);
|
||||
|
||||
object_xml->get_nodes(ds_xpath, content);
|
||||
/**
|
||||
* Delete VM related usage (network, image and compute) from quota counters.
|
||||
* for the given user and group
|
||||
* @param uid of the user
|
||||
* @param gid of the group
|
||||
* @param tmpl template for the image, with usage
|
||||
*/
|
||||
static void vm_del(int uid, int gid, Template * tmpl);
|
||||
|
||||
if (!content.empty())
|
||||
{
|
||||
rc += datastore_quota.from_xml_node(content[0]);
|
||||
}
|
||||
|
||||
object_xml->free_nodes(content);
|
||||
content.clear();
|
||||
|
||||
object_xml->get_nodes(net_xpath, content);
|
||||
|
||||
if (!content.empty())
|
||||
{
|
||||
rc += network_quota.from_xml_node(content[0]);
|
||||
}
|
||||
|
||||
object_xml->free_nodes(content);
|
||||
content.clear();
|
||||
|
||||
object_xml->get_nodes(vm_xpath, content);
|
||||
|
||||
if (!content.empty())
|
||||
{
|
||||
rc += vm_quota.from_xml_node(content[0]);
|
||||
}
|
||||
|
||||
object_xml->free_nodes(content);
|
||||
content.clear();
|
||||
|
||||
object_xml->get_nodes(img_xpath, content);
|
||||
|
||||
if (!content.empty())
|
||||
{
|
||||
rc += image_quota.from_xml_node(content[0]);
|
||||
}
|
||||
|
||||
object_xml->free_nodes(content);
|
||||
|
||||
return rc;
|
||||
}
|
||||
/**
|
||||
* Delete Datastore related usage from quota counters.
|
||||
* for the given user and group
|
||||
* @param uid of the user
|
||||
* @param gid of the group
|
||||
* @param tmpl template for the image, with usage
|
||||
*/
|
||||
static void ds_del(int uid, int gid, Template * tmpl);
|
||||
|
||||
private:
|
||||
//--------------------------------------------------------------------------
|
||||
@ -238,17 +151,17 @@ private:
|
||||
/**
|
||||
* Datastore Quotas
|
||||
*/
|
||||
QuotaDatastore datastore_quota;
|
||||
QuotaDatastore datastore_quota;
|
||||
|
||||
/**
|
||||
* Network Quotas
|
||||
*/
|
||||
QuotaNetwork network_quota;
|
||||
QuotaNetwork network_quota;
|
||||
|
||||
/**
|
||||
* Image Quotas
|
||||
*/
|
||||
QuotaImage image_quota;
|
||||
QuotaImage image_quota;
|
||||
|
||||
/**
|
||||
* Virtual Machine Quotas
|
||||
|
@ -49,11 +49,12 @@ protected:
|
||||
RequestAttributes& att) = 0;
|
||||
|
||||
bool vm_authorization(int id,
|
||||
ImageTemplate * tmpl,
|
||||
RequestAttributes& att,
|
||||
PoolObjectAuth * host_perms,
|
||||
PoolObjectAuth * ds_perm,
|
||||
AuthRequest::Operation op);
|
||||
ImageTemplate * tmpl,
|
||||
VirtualMachineTemplate* vtmpl,
|
||||
RequestAttributes& att,
|
||||
PoolObjectAuth * host_perms,
|
||||
PoolObjectAuth * ds_perm,
|
||||
AuthRequest::Operation op);
|
||||
|
||||
int get_host_information(int hid, string& name, string& vmm, string& vnm,
|
||||
RequestAttributes& att, PoolObjectAuth& host_perms);
|
||||
|
@ -169,6 +169,15 @@ public:
|
||||
const string& name,
|
||||
vector<Attribute *>& values);
|
||||
|
||||
/**
|
||||
* Removes an attribute from the template, but it DOES NOT free the
|
||||
* attribute.
|
||||
* @param att Attribute to remove. It will be deleted
|
||||
* @return pointer to the removed attribute or 0 if non attribute was
|
||||
* removed
|
||||
*/
|
||||
virtual Attribute * remove(Attribute * att);
|
||||
|
||||
/**
|
||||
* Removes an attribute from the template, and frees the attributes.
|
||||
* @param name of the attribute
|
||||
|
@ -24,6 +24,7 @@
|
||||
#include "NebulaLog.h"
|
||||
|
||||
#include <time.h>
|
||||
#include <set>
|
||||
#include <sstream>
|
||||
|
||||
using namespace std;
|
||||
@ -744,17 +745,31 @@ public:
|
||||
// ------------------------------------------------------------------------
|
||||
|
||||
/**
|
||||
* Attaches a new disk. It will acquire the Image used, if any, and add the
|
||||
* disk to the VM template. The VM must be updated in the DB afterwards.
|
||||
*
|
||||
* @param tmpl Template containing a single DISK vector attribute. The
|
||||
* caller must delete this template
|
||||
* @param error_str Returns the error reason, if any
|
||||
*
|
||||
* @return 0 on success
|
||||
* Collects information about VM DISKS
|
||||
* @param num_disks of the VM
|
||||
* @param used_targets by the DISKS of the VM
|
||||
*/
|
||||
int attach_disk(VirtualMachineTemplate * tmpl, string& error_str);
|
||||
void get_disk_info(int& num_disks, set<string>& used_targets);
|
||||
|
||||
/**
|
||||
* Generate a DISK attributed to be attached to the VM.
|
||||
* @param tmpl Template containing a single DISK vector attribute.
|
||||
* @param used_targets targets in use by current DISKS
|
||||
* @param num_disks of the VM
|
||||
* @param uid of the VM owner
|
||||
* @param image_id returns the id of the aquired image
|
||||
* @param error_str describes the error
|
||||
*
|
||||
* @return a new vectorattribute with the DISK (should be freed if not
|
||||
* added to the template), 0 in case of error;
|
||||
*/
|
||||
static VectorAttribute * set_up_attach_disk(
|
||||
VirtualMachineTemplate * tmpl,
|
||||
set<string>& used_targets,
|
||||
int num_disks,
|
||||
int uid,
|
||||
int& image_id,
|
||||
string& error_str);
|
||||
/**
|
||||
* Returns the disk that is waiting for an attachment action
|
||||
*
|
||||
@ -764,18 +779,27 @@ public:
|
||||
|
||||
/**
|
||||
* Cleans the ATTACH = YES attribute from the disks
|
||||
*
|
||||
* @return 0 on success, -1 otherwise
|
||||
*/
|
||||
int attach_success();
|
||||
void clear_attach_disk();
|
||||
|
||||
/**
|
||||
* Deletes the DISK that was in the process of being attached, and releases
|
||||
* the image, if any
|
||||
* Deletes the DISK that was in the process of being attached
|
||||
*
|
||||
* @return 0 on success, -1 otherwise
|
||||
* @return the DISK or 0 if no disk was deleted
|
||||
*/
|
||||
int attach_failure();
|
||||
VectorAttribute * delete_attach_disk();
|
||||
|
||||
/**
|
||||
* Adds a new disk to the virtual machine template. The disk should be
|
||||
* generated by the build_attach_disk
|
||||
* @param new_disk must be allocated in the heap
|
||||
*/
|
||||
void attach_disk(VectorAttribute * new_disk)
|
||||
{
|
||||
new_disk->replace("ATTACH", "YES");
|
||||
|
||||
obj_template->set(new_disk);
|
||||
}
|
||||
|
||||
private:
|
||||
|
||||
|
@ -685,9 +685,6 @@ int DispatchManager::finalize(
|
||||
VirtualMachine * vm;
|
||||
ostringstream oss;
|
||||
Template * tmpl;
|
||||
|
||||
User * user;
|
||||
Group * group;
|
||||
|
||||
int uid;
|
||||
int gid;
|
||||
@ -709,8 +706,6 @@ int DispatchManager::finalize(
|
||||
Nebula& nd = Nebula::instance();
|
||||
TransferManager * tm = nd.get_tm();
|
||||
LifeCycleManager * lcm = nd.get_lcm();
|
||||
UserPool * upool = nd.get_upool();
|
||||
GroupPool * gpool = nd.get_gpool();
|
||||
|
||||
switch (state)
|
||||
{
|
||||
@ -739,34 +734,7 @@ int DispatchManager::finalize(
|
||||
|
||||
vm->unlock();
|
||||
|
||||
if ( uid != UserPool::ONEADMIN_ID )
|
||||
{
|
||||
|
||||
user = upool->get(uid, true);
|
||||
|
||||
if ( user != 0 )
|
||||
{
|
||||
user->quota.vm_del(tmpl);
|
||||
|
||||
upool->update(user);
|
||||
|
||||
user->unlock();
|
||||
}
|
||||
}
|
||||
|
||||
if ( gid != GroupPool::ONEADMIN_ID )
|
||||
{
|
||||
group = gpool->get(gid, true);
|
||||
|
||||
if ( group != 0 )
|
||||
{
|
||||
group->quota.vm_del(tmpl);
|
||||
|
||||
gpool->update(group);
|
||||
|
||||
group->unlock();
|
||||
}
|
||||
}
|
||||
Quotas::vm_del(uid, gid, tmpl);
|
||||
|
||||
delete tmpl;
|
||||
break;
|
||||
@ -845,59 +813,96 @@ int DispatchManager::resubmit(int vid)
|
||||
/* -------------------------------------------------------------------------- */
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
int DispatchManager::attach(
|
||||
VirtualMachine * vm,
|
||||
VirtualMachineTemplate * tmpl,
|
||||
string & error_str)
|
||||
|
||||
int DispatchManager::attach(int vid,
|
||||
VirtualMachineTemplate * tmpl,
|
||||
string & error_str)
|
||||
{
|
||||
ostringstream oss;
|
||||
int rc;
|
||||
int vid = vm->get_oid();
|
||||
ostringstream oss;
|
||||
|
||||
Nebula& nd = Nebula::instance();
|
||||
VirtualMachineManager * vmm = nd.get_vmm();
|
||||
int num_disks;
|
||||
int uid;
|
||||
int image_id;
|
||||
|
||||
oss << "Attaching a new disk to VM " << vid;
|
||||
NebulaLog::log("DiM",Log::DEBUG,oss);
|
||||
set<string> used_targets;
|
||||
VectorAttribute * disk;
|
||||
|
||||
Nebula& nd = Nebula::instance();
|
||||
VirtualMachineManager* vmm = nd.get_vmm();
|
||||
|
||||
VirtualMachine * vm = vmpool->get(vid, true);
|
||||
|
||||
if ( vm == 0 )
|
||||
{
|
||||
oss << "VirtualMachine " << vid << " no longer exists";
|
||||
return -1;
|
||||
}
|
||||
|
||||
if ( vm->get_state() != VirtualMachine::ACTIVE ||
|
||||
vm->get_lcm_state() != VirtualMachine::RUNNING )
|
||||
{
|
||||
goto error_state;
|
||||
}
|
||||
oss << "Could not attach a new disk to VM " << vid << ", wrong state.";
|
||||
error_str = oss.str();
|
||||
|
||||
rc = vm->attach_disk(tmpl, error_str);
|
||||
NebulaLog::log("DiM", Log::ERROR, error_str);
|
||||
|
||||
if ( rc != 0 )
|
||||
{
|
||||
goto error;
|
||||
vm->unlock();
|
||||
return -1;
|
||||
}
|
||||
|
||||
vm->get_disk_info(num_disks, used_targets);
|
||||
|
||||
vm->set_state(VirtualMachine::HOTPLUG);
|
||||
|
||||
vm->set_resched(false);
|
||||
|
||||
uid = vm->get_uid();
|
||||
|
||||
vmpool->update(vm);
|
||||
|
||||
vm->unlock();
|
||||
delete tmpl;
|
||||
|
||||
vmm->trigger(VirtualMachineManager::ATTACH,vid);
|
||||
disk = VirtualMachine::set_up_attach_disk(tmpl,
|
||||
used_targets,
|
||||
num_disks,
|
||||
uid,
|
||||
image_id,
|
||||
error_str);
|
||||
vm = vmpool->get(vid, true);
|
||||
|
||||
if ( vm == 0 )
|
||||
{
|
||||
Nebula& nd = Nebula::instance();
|
||||
ImageManager* imagem = nd.get_imagem();
|
||||
|
||||
if ( image_id != -1 )
|
||||
{
|
||||
imagem->release_image(image_id, false);
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
if ( disk == 0 )
|
||||
{
|
||||
vm->set_state(VirtualMachine::RUNNING);
|
||||
|
||||
vmpool->update(vm);
|
||||
|
||||
vm->unlock();
|
||||
|
||||
return -1;
|
||||
}
|
||||
else
|
||||
{
|
||||
vm->attach_disk(disk);
|
||||
}
|
||||
|
||||
vmpool->update(vm);
|
||||
|
||||
vm->unlock();
|
||||
|
||||
vmm->trigger(VirtualMachineManager::ATTACH,vid);
|
||||
|
||||
return 0;
|
||||
|
||||
error:
|
||||
vm->unlock();
|
||||
delete tmpl;
|
||||
|
||||
return -1;
|
||||
|
||||
error_state:
|
||||
oss.str("");
|
||||
oss << "Could not attach a new disk to VM " << vid << ", wrong state.";
|
||||
error_str = oss.str();
|
||||
|
||||
NebulaLog::log("DiM", Log::ERROR, error_str);
|
||||
|
||||
vm->unlock();
|
||||
delete tmpl;
|
||||
|
||||
return -2;
|
||||
}
|
||||
|
@ -108,13 +108,6 @@ void DispatchManager::done_action(int vid)
|
||||
VirtualMachine::LcmState lcm_state;
|
||||
VirtualMachine::VmState dm_state;
|
||||
|
||||
Nebula& nd = Nebula::instance();
|
||||
UserPool * upool = nd.get_upool();
|
||||
GroupPool* gpool = nd.get_gpool();
|
||||
|
||||
User * user;
|
||||
Group * group;
|
||||
|
||||
vm = vmpool->get(vid,true);
|
||||
|
||||
if ( vm == 0 )
|
||||
@ -150,35 +143,7 @@ void DispatchManager::done_action(int vid)
|
||||
|
||||
vm->unlock();
|
||||
|
||||
/* ---------------- Update Group & User quota counters -------------- */
|
||||
|
||||
if ( uid != UserPool::ONEADMIN_ID )
|
||||
{
|
||||
user = upool->get(uid, true);
|
||||
|
||||
if ( user != 0 )
|
||||
{
|
||||
user->quota.vm_del(tmpl);
|
||||
|
||||
upool->update(user);
|
||||
|
||||
user->unlock();
|
||||
}
|
||||
}
|
||||
|
||||
if ( gid != GroupPool::ONEADMIN_ID )
|
||||
{
|
||||
group = gpool->get(gid, true);
|
||||
|
||||
if ( group != 0 )
|
||||
{
|
||||
group->quota.vm_del(tmpl);
|
||||
|
||||
gpool->update(group);
|
||||
|
||||
group->unlock();
|
||||
}
|
||||
}
|
||||
Quotas::vm_del(uid, gid, tmpl);
|
||||
|
||||
delete tmpl;
|
||||
}
|
||||
|
@ -274,13 +274,7 @@ int ImageManager::delete_image(int iid, const string& ds_data)
|
||||
|
||||
int uid;
|
||||
int gid;
|
||||
Group* group;
|
||||
User * user;
|
||||
|
||||
Nebula& nd = Nebula::instance();
|
||||
UserPool * upool = nd.get_upool();
|
||||
GroupPool* gpool = nd.get_gpool();
|
||||
|
||||
|
||||
img = ipool->get(iid,true);
|
||||
|
||||
if ( img == 0 )
|
||||
@ -354,33 +348,7 @@ int ImageManager::delete_image(int iid, const string& ds_data)
|
||||
img_usage.add("DATASTORE", ds_id);
|
||||
img_usage.add("SIZE", size);
|
||||
|
||||
if ( uid != UserPool::ONEADMIN_ID )
|
||||
{
|
||||
user = upool->get(uid, true);
|
||||
|
||||
if ( user != 0 )
|
||||
{
|
||||
user->quota.ds_del(&img_usage);
|
||||
|
||||
upool->update(user);
|
||||
|
||||
user->unlock();
|
||||
}
|
||||
}
|
||||
|
||||
if ( gid != GroupPool::ONEADMIN_ID )
|
||||
{
|
||||
group = gpool->get(gid, true);
|
||||
|
||||
if ( group != 0 )
|
||||
{
|
||||
group->quota.ds_del(&img_usage);
|
||||
|
||||
gpool->update(group);
|
||||
|
||||
group->unlock();
|
||||
}
|
||||
}
|
||||
Quotas::ds_del(uid, gid, &img_usage);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
@ -846,7 +846,7 @@ void LifeCycleManager::attach_success_action(int vid)
|
||||
return;
|
||||
}
|
||||
|
||||
vm->attach_success();
|
||||
vm->clear_attach_disk();
|
||||
|
||||
vm->set_state(VirtualMachine::RUNNING);
|
||||
|
||||
@ -860,7 +860,11 @@ void LifeCycleManager::attach_success_action(int vid)
|
||||
|
||||
void LifeCycleManager::attach_failure_action(int vid)
|
||||
{
|
||||
VirtualMachine * vm;
|
||||
VirtualMachine * vm;
|
||||
VectorAttribute * disk;
|
||||
|
||||
int uid;
|
||||
int gid;
|
||||
|
||||
vm = vmpool->get(vid,true);
|
||||
|
||||
@ -869,7 +873,9 @@ void LifeCycleManager::attach_failure_action(int vid)
|
||||
return;
|
||||
}
|
||||
|
||||
vm->attach_failure();
|
||||
disk = vm->delete_attach_disk();
|
||||
uid = vm->get_uid();
|
||||
gid = vm->get_gid();
|
||||
|
||||
vm->set_state(VirtualMachine::RUNNING);
|
||||
|
||||
@ -877,7 +883,14 @@ void LifeCycleManager::attach_failure_action(int vid)
|
||||
|
||||
vm->unlock();
|
||||
|
||||
// TODO: update quotas, here or in VirtualMachine::attach_failure
|
||||
if ( disk != 0 )
|
||||
{
|
||||
Template tmpl;
|
||||
|
||||
tmpl.set(disk);
|
||||
|
||||
Quotas::vm_del(uid, gid, &tmpl);
|
||||
}
|
||||
}
|
||||
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
@ -22,12 +22,13 @@
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
bool RequestManagerVirtualMachine::vm_authorization(
|
||||
int oid,
|
||||
ImageTemplate * tmpl,
|
||||
RequestAttributes& att,
|
||||
PoolObjectAuth * host_perm,
|
||||
PoolObjectAuth * ds_perm,
|
||||
AuthRequest::Operation op)
|
||||
int oid,
|
||||
ImageTemplate * tmpl,
|
||||
VirtualMachineTemplate* vtmpl,
|
||||
RequestAttributes& att,
|
||||
PoolObjectAuth * host_perm,
|
||||
PoolObjectAuth * ds_perm,
|
||||
AuthRequest::Operation op)
|
||||
{
|
||||
PoolObjectSQL * object;
|
||||
PoolObjectAuth vm_perms;
|
||||
@ -69,6 +70,11 @@ bool RequestManagerVirtualMachine::vm_authorization(
|
||||
ar.add_create_auth(PoolObjectSQL::IMAGE, tmpl->to_xml(t_xml));
|
||||
}
|
||||
|
||||
if ( vtmpl != 0 )
|
||||
{
|
||||
VirtualMachine::set_auth_request(att.uid, ar, vtmpl);
|
||||
}
|
||||
|
||||
if ( ds_perm != 0 )
|
||||
{
|
||||
ar.add_auth(AuthRequest::USE, *ds_perm);
|
||||
@ -196,7 +202,7 @@ void VirtualMachineAction::request_execute(xmlrpc_c::paramList const& paramList,
|
||||
op = AuthRequest::ADMIN;
|
||||
}
|
||||
|
||||
if ( vm_authorization(id, 0, att, 0, 0, op) == false )
|
||||
if ( vm_authorization(id, 0, 0, att, 0, 0, op) == false )
|
||||
{
|
||||
return;
|
||||
}
|
||||
@ -313,7 +319,7 @@ void VirtualMachineDeploy::request_execute(xmlrpc_c::paramList const& paramList,
|
||||
return;
|
||||
}
|
||||
|
||||
auth = vm_authorization(id, 0, att, &host_perms, 0, auth_op);
|
||||
auth = vm_authorization(id, 0, 0, att, &host_perms, 0, auth_op);
|
||||
|
||||
if ( auth == false )
|
||||
{
|
||||
@ -375,7 +381,7 @@ void VirtualMachineMigrate::request_execute(xmlrpc_c::paramList const& paramList
|
||||
return;
|
||||
}
|
||||
|
||||
auth = vm_authorization(id, 0, att, &host_perms, 0, auth_op);
|
||||
auth = vm_authorization(id, 0, 0, att, &host_perms, 0, auth_op);
|
||||
|
||||
if ( auth == false )
|
||||
{
|
||||
@ -546,7 +552,7 @@ void VirtualMachineSaveDisk::request_execute(xmlrpc_c::paramList const& paramLis
|
||||
// Authorize the operation & check quotas
|
||||
// -------------------------------------------------------------------------
|
||||
|
||||
if ( vm_authorization(id, itemplate, att, 0, &ds_perms, auth_op) == false )
|
||||
if ( vm_authorization(id, itemplate, 0, att, 0, &ds_perms, auth_op) == false )
|
||||
{
|
||||
delete itemplate;
|
||||
return;
|
||||
@ -598,7 +604,7 @@ void VirtualMachineMonitoring::request_execute(
|
||||
|
||||
ostringstream oss;
|
||||
|
||||
bool auth = vm_authorization(id, 0, att, 0, 0, auth_op);
|
||||
bool auth = vm_authorization(id, 0, 0, att, 0, 0, auth_op);
|
||||
|
||||
if ( auth == false )
|
||||
{
|
||||
@ -624,59 +630,66 @@ void VirtualMachineMonitoring::request_execute(
|
||||
void VirtualMachineAttach::request_execute(xmlrpc_c::paramList const& paramList,
|
||||
RequestAttributes& att)
|
||||
{
|
||||
Nebula& nd = Nebula::instance();
|
||||
DispatchManager * dm = nd.get_dm();
|
||||
Nebula& nd = Nebula::instance();
|
||||
DispatchManager * dm = nd.get_dm();
|
||||
|
||||
VirtualMachine * vm;
|
||||
VirtualMachineTemplate * tmpl;
|
||||
PoolObjectAuth host_perms;
|
||||
VirtualMachine * vm;
|
||||
VirtualMachineTemplate * tmpl = new VirtualMachineTemplate();
|
||||
PoolObjectAuth host_perms;
|
||||
|
||||
int rc;
|
||||
int rc;
|
||||
string error_str;
|
||||
|
||||
int id = xmlrpc_c::value_int(paramList.getInt(1));
|
||||
string str_tmpl = xmlrpc_c::value_string(paramList.getString(2));
|
||||
|
||||
tmpl = new VirtualMachineTemplate();
|
||||
// -------------------------------------------------------------------------
|
||||
// Parse Disk template
|
||||
// -------------------------------------------------------------------------
|
||||
|
||||
rc = tmpl->parse_str_or_xml(str_tmpl, error_str);
|
||||
rc = tmpl->parse_str_or_xml(str_tmpl, error_str);
|
||||
|
||||
if ( rc != 0 )
|
||||
{
|
||||
failure_response(INTERNAL, "", att); // TODO: error message
|
||||
failure_response(INTERNAL, error_str, att);
|
||||
delete tmpl;
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
// TODO: auth & quotas
|
||||
|
||||
// TODO: set vm state HOTPLUG & vm->set_resched(false); // Cancel re-scheduling actions
|
||||
|
||||
vm = get_vm(id, att);
|
||||
|
||||
if ( vm == 0 )
|
||||
// -------------------------------------------------------------------------
|
||||
// Authorize the operation & check quotas
|
||||
// -------------------------------------------------------------------------
|
||||
|
||||
if ( vm_authorization(id, 0, tmpl, att, 0, 0, auth_op) == false )
|
||||
{
|
||||
failure_response(NO_EXISTS,
|
||||
get_error(object_name(auth_object),id),
|
||||
att);
|
||||
delete tmpl;
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
rc = dm->attach(vm, tmpl, error_str);
|
||||
if ( quota_authorization(tmpl, att) == false )
|
||||
{
|
||||
delete tmpl;
|
||||
return;
|
||||
}
|
||||
|
||||
rc = dm->attach(id, tmpl, error_str);
|
||||
|
||||
if ( rc != 0 )
|
||||
{
|
||||
quota_rollback(tmpl, att);
|
||||
|
||||
failure_response(ACTION,
|
||||
request_error(error_str, ""),
|
||||
att);
|
||||
|
||||
return;
|
||||
}
|
||||
else
|
||||
{
|
||||
success_response(id, att);
|
||||
}
|
||||
|
||||
success_response(id, att);
|
||||
delete tmpl;
|
||||
return;
|
||||
}
|
||||
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
@ -309,6 +309,33 @@ int Template::erase(Attribute * att)
|
||||
/* -------------------------------------------------------------------------- */
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
Attribute * Template::remove(Attribute * att)
|
||||
{
|
||||
multimap<string, Attribute *>::iterator i;
|
||||
|
||||
pair<
|
||||
multimap<string, Attribute *>::iterator,
|
||||
multimap<string, Attribute *>::iterator
|
||||
> index;
|
||||
|
||||
index = attributes.equal_range( att->name() );
|
||||
|
||||
for ( i = index.first; i != index.second; i++ )
|
||||
{
|
||||
if ( i->second == att )
|
||||
{
|
||||
attributes.erase(i);
|
||||
|
||||
return att;
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* -------------------------------------------------------------------------- */
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
int Template::get(
|
||||
const string& name,
|
||||
vector<const Attribute*>& values) const
|
||||
|
222
src/um/Quotas.cc
Normal file
222
src/um/Quotas.cc
Normal file
@ -0,0 +1,222 @@
|
||||
/* -------------------------------------------------------------------------- */
|
||||
/* Copyright 2002-2012, OpenNebula Project Leads (OpenNebula.org) */
|
||||
/* */
|
||||
/* Licensed under the Apache License, Version 2.0 (the "License"); you may */
|
||||
/* not use this file except in compliance with the License. You may obtain */
|
||||
/* a copy of the License at */
|
||||
/* */
|
||||
/* http://www.apache.org/licenses/LICENSE-2.0 */
|
||||
/* */
|
||||
/* Unless required by applicable law or agreed to in writing, software */
|
||||
/* distributed under the License is distributed on an "AS IS" BASIS, */
|
||||
/* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. */
|
||||
/* See the License for the specific language governing permissions and */
|
||||
/* limitations under the License. */
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
#include "Quotas.h"
|
||||
#include "Nebula.h"
|
||||
|
||||
#include "ObjectXML.h"
|
||||
|
||||
|
||||
int Quotas::set(Template *tmpl, string& error)
|
||||
{
|
||||
vector<Attribute *> vquotas;
|
||||
|
||||
if ( tmpl->get(datastore_quota.get_quota_name(), vquotas) > 0 )
|
||||
{
|
||||
if ( datastore_quota.set(&vquotas, error) != 0 )
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
vquotas.clear();
|
||||
}
|
||||
|
||||
if ( tmpl->get(network_quota.get_quota_name(), vquotas) > 0 )
|
||||
{
|
||||
if ( network_quota.set(&vquotas, error) != 0 )
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
vquotas.clear();
|
||||
}
|
||||
|
||||
if ( tmpl->get(image_quota.get_quota_name(), vquotas) > 0 )
|
||||
{
|
||||
if ( image_quota.set(&vquotas, error) != 0 )
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
vquotas.clear();
|
||||
}
|
||||
|
||||
if ( tmpl->get(vm_quota.get_quota_name(), vquotas) > 0 )
|
||||
{
|
||||
if ( vm_quota.set(&vquotas, error) != 0 )
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
vquotas.clear();
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* -------------------------------------------------------------------------- */
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
string& Quotas::to_xml(string& xml) const
|
||||
{
|
||||
ostringstream oss;
|
||||
|
||||
string ds_quota_xml;
|
||||
string net_quota_xml;
|
||||
string vm_quota_xml;
|
||||
string image_quota_xml;
|
||||
|
||||
oss << datastore_quota.to_xml(ds_quota_xml)
|
||||
<< network_quota.to_xml(net_quota_xml)
|
||||
<< vm_quota.to_xml(vm_quota_xml)
|
||||
<< image_quota.to_xml(image_quota_xml);
|
||||
|
||||
xml = oss.str();
|
||||
|
||||
return xml;
|
||||
}
|
||||
|
||||
/* -------------------------------------------------------------------------- */
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
int Quotas::from_xml(ObjectXML * object_xml)
|
||||
{
|
||||
vector<xmlNodePtr> content;
|
||||
int rc = 0;
|
||||
|
||||
object_xml->get_nodes(ds_xpath, content);
|
||||
|
||||
if (!content.empty())
|
||||
{
|
||||
rc += datastore_quota.from_xml_node(content[0]);
|
||||
}
|
||||
|
||||
object_xml->free_nodes(content);
|
||||
content.clear();
|
||||
|
||||
object_xml->get_nodes(net_xpath, content);
|
||||
|
||||
if (!content.empty())
|
||||
{
|
||||
rc += network_quota.from_xml_node(content[0]);
|
||||
}
|
||||
|
||||
object_xml->free_nodes(content);
|
||||
content.clear();
|
||||
|
||||
object_xml->get_nodes(vm_xpath, content);
|
||||
|
||||
if (!content.empty())
|
||||
{
|
||||
rc += vm_quota.from_xml_node(content[0]);
|
||||
}
|
||||
|
||||
object_xml->free_nodes(content);
|
||||
content.clear();
|
||||
|
||||
object_xml->get_nodes(img_xpath, content);
|
||||
|
||||
if (!content.empty())
|
||||
{
|
||||
rc += image_quota.from_xml_node(content[0]);
|
||||
}
|
||||
|
||||
object_xml->free_nodes(content);
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
/* -------------------------------------------------------------------------- */
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
void Quotas::vm_del(int uid, int gid, Template * tmpl)
|
||||
{
|
||||
Nebula& nd = Nebula::instance();
|
||||
UserPool * upool = nd.get_upool();
|
||||
GroupPool * gpool = nd.get_gpool();
|
||||
|
||||
User * user;
|
||||
Group * group;
|
||||
|
||||
if ( uid != UserPool::ONEADMIN_ID )
|
||||
{
|
||||
user = upool->get(uid, true);
|
||||
|
||||
if ( user != 0 )
|
||||
{
|
||||
user->quota.vm_del(tmpl);
|
||||
|
||||
upool->update(user);
|
||||
|
||||
user->unlock();
|
||||
}
|
||||
}
|
||||
|
||||
if ( gid != GroupPool::ONEADMIN_ID )
|
||||
{
|
||||
group = gpool->get(gid, true);
|
||||
|
||||
if ( group != 0 )
|
||||
{
|
||||
group->quota.vm_del(tmpl);
|
||||
|
||||
gpool->update(group);
|
||||
|
||||
group->unlock();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* -------------------------------------------------------------------------- */
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
void Quotas::ds_del(int uid, int gid, Template * tmpl)
|
||||
{
|
||||
Nebula& nd = Nebula::instance();
|
||||
UserPool * upool = nd.get_upool();
|
||||
GroupPool * gpool = nd.get_gpool();
|
||||
|
||||
User * user;
|
||||
Group * group;
|
||||
|
||||
if ( uid != UserPool::ONEADMIN_ID )
|
||||
{
|
||||
user = upool->get(uid, true);
|
||||
|
||||
if ( user != 0 )
|
||||
{
|
||||
user->quota.ds_del(tmpl);
|
||||
|
||||
upool->update(user);
|
||||
|
||||
user->unlock();
|
||||
}
|
||||
}
|
||||
|
||||
if ( gid != GroupPool::ONEADMIN_ID )
|
||||
{
|
||||
group = gpool->get(gid, true);
|
||||
|
||||
if ( group != 0 )
|
||||
{
|
||||
group->quota.ds_del(tmpl);
|
||||
|
||||
gpool->update(group);
|
||||
|
||||
group->unlock();
|
||||
}
|
||||
}
|
||||
}
|
@ -28,7 +28,8 @@ source_files=[
|
||||
'QuotaDatastore.cc',
|
||||
'QuotaNetwork.cc',
|
||||
'QuotaVirtualMachine.cc',
|
||||
'QuotaImage.cc'
|
||||
'QuotaImage.cc',
|
||||
'Quotas.cc'
|
||||
]
|
||||
|
||||
# Build library
|
||||
|
@ -1109,77 +1109,16 @@ error_common:
|
||||
/* -------------------------------------------------------------------------- */
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
// TODO: this method requires the VM to be locked, and then it locks the Image
|
||||
// to acquire. Check if this can be troublesome
|
||||
|
||||
int VirtualMachine::attach_disk(VirtualMachineTemplate * tmpl, string& error_str)
|
||||
void VirtualMachine::get_disk_info(int& num_disks,
|
||||
set<string>& used_targets)
|
||||
{
|
||||
int num_disks, rc;
|
||||
vector<Attribute *> disks;
|
||||
ImagePool * ipool;
|
||||
VectorAttribute * disk;
|
||||
VectorAttribute * new_disk;
|
||||
vector<int> acquired_images;
|
||||
|
||||
int new_disk_id;
|
||||
int image_id;
|
||||
string dev_prefix;
|
||||
string target;
|
||||
string target;
|
||||
|
||||
queue<pair <string, VectorAttribute *> > disks_queue;
|
||||
|
||||
set<string> used_targets;
|
||||
|
||||
ostringstream oss;
|
||||
Image::ImageType img_type;
|
||||
|
||||
Nebula& nd = Nebula::instance();
|
||||
ipool = nd.get_ipool();
|
||||
|
||||
// -------------------------------------------------------------------------
|
||||
// Get the DISK attribute from the template
|
||||
// -------------------------------------------------------------------------
|
||||
|
||||
num_disks = tmpl->get("DISK", disks);
|
||||
|
||||
if ( num_disks != 1 )
|
||||
{
|
||||
goto error_no_disk;
|
||||
}
|
||||
|
||||
new_disk = new VectorAttribute( *(dynamic_cast<VectorAttribute * >(disks[0])) );
|
||||
|
||||
// -------------------------------------------------------------------------
|
||||
// See if there is a CONTEXT cdrom, and get the target it is using
|
||||
// -------------------------------------------------------------------------
|
||||
num_disks = obj_template->get("CONTEXT", disks);
|
||||
|
||||
if ( num_disks > 0 )
|
||||
{
|
||||
disk = dynamic_cast<VectorAttribute * >(disks[0]);
|
||||
|
||||
if ( disk != 0 )
|
||||
{
|
||||
target = disk->vector_value("TARGET");
|
||||
|
||||
if ( !target.empty() )
|
||||
{
|
||||
used_targets.insert(target);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// -------------------------------------------------------------------------
|
||||
// Check the used targets
|
||||
// -------------------------------------------------------------------------
|
||||
disks.clear();
|
||||
num_disks = obj_template->get("DISK", disks);
|
||||
|
||||
if ( num_disks >= 20 )
|
||||
{
|
||||
goto error_max_disks;
|
||||
}
|
||||
|
||||
for(int i=0; i<num_disks; i++)
|
||||
{
|
||||
disk = dynamic_cast<VectorAttribute * >(disks[i]);
|
||||
@ -1197,79 +1136,101 @@ int VirtualMachine::attach_disk(VirtualMachineTemplate * tmpl, string& error_str
|
||||
}
|
||||
}
|
||||
|
||||
if ( obj_template->get("CONTEXT", disks) > 0 )
|
||||
{
|
||||
disk = dynamic_cast<VectorAttribute * >(disks[0]);
|
||||
|
||||
if ( disk != 0 )
|
||||
{
|
||||
target = disk->vector_value("TARGET");
|
||||
|
||||
if ( !target.empty() )
|
||||
{
|
||||
used_targets.insert(target);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* -------------------------------------------------------------------------- */
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
VectorAttribute * VirtualMachine::set_up_attach_disk(
|
||||
VirtualMachineTemplate * tmpl,
|
||||
set<string>& used_targets,
|
||||
int num_disks,
|
||||
int uid,
|
||||
int& image_id,
|
||||
string& error_str)
|
||||
{
|
||||
vector<Attribute *> disks;
|
||||
VectorAttribute * new_disk;
|
||||
|
||||
string target;
|
||||
|
||||
Nebula& nd = Nebula::instance();
|
||||
ImagePool * ipool = nd.get_ipool();
|
||||
ImageManager* imagem = nd.get_imagem();
|
||||
|
||||
string dev_prefix;
|
||||
Image::ImageType img_type;
|
||||
|
||||
image_id = -1;
|
||||
|
||||
// -------------------------------------------------------------------------
|
||||
// Get the DISK attribute from the template
|
||||
// -------------------------------------------------------------------------
|
||||
|
||||
if ( tmpl->get("DISK", disks) != 1 )
|
||||
{
|
||||
error_str = "The template must contain one DISK attribute";
|
||||
return 0;
|
||||
}
|
||||
|
||||
new_disk = new VectorAttribute(*(dynamic_cast<VectorAttribute * >(disks[0])));
|
||||
|
||||
// -------------------------------------------------------------------------
|
||||
// Acquire the new disk image
|
||||
// -------------------------------------------------------------------------
|
||||
|
||||
// num_disks +1 because the context is not a DISK, but it takes the
|
||||
// ds/<vm_id>/disk.num_disks file
|
||||
new_disk_id = num_disks + 1;
|
||||
|
||||
rc = ipool->disk_attribute(new_disk,
|
||||
new_disk_id,
|
||||
img_type,
|
||||
dev_prefix,
|
||||
uid,
|
||||
image_id,
|
||||
error_str);
|
||||
if ( rc == 0 )
|
||||
|
||||
int rc = ipool->disk_attribute(new_disk,
|
||||
num_disks + 1, //Preserv CONTEXT disk.i file
|
||||
img_type,
|
||||
dev_prefix,
|
||||
uid,
|
||||
image_id,
|
||||
error_str);
|
||||
if ( rc != 0 )
|
||||
{
|
||||
acquired_images.push_back(image_id);
|
||||
return 0;
|
||||
}
|
||||
|
||||
target = new_disk->vector_value("TARGET");
|
||||
target = new_disk->vector_value("TARGET");
|
||||
|
||||
if ( !target.empty() )
|
||||
if ( !target.empty() )
|
||||
{
|
||||
if ( used_targets.insert(target).second == false )
|
||||
{
|
||||
if ( used_targets.insert(target).second == false )
|
||||
{
|
||||
goto error_duplicated_target;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
disks_queue.push( make_pair(dev_prefix, new_disk) );
|
||||
ostringstream oss;
|
||||
|
||||
oss << "Target " << target << "is already in use.";
|
||||
error_str = oss.str();
|
||||
|
||||
imagem->release_image(image_id, false);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
goto error_common;
|
||||
queue<pair <string, VectorAttribute *> > disks_queue;
|
||||
|
||||
disks_queue.push(make_pair(dev_prefix, new_disk));
|
||||
|
||||
assign_disk_targets(disks_queue, used_targets);
|
||||
}
|
||||
|
||||
assign_disk_targets(disks_queue, used_targets);
|
||||
|
||||
// -------------------------------------------------------------------------
|
||||
// Add the disk to the VM template
|
||||
// -------------------------------------------------------------------------
|
||||
|
||||
new_disk->replace("ATTACH", "YES");
|
||||
|
||||
obj_template->set(new_disk);
|
||||
|
||||
return 0;
|
||||
|
||||
error_no_disk:
|
||||
error_str = "The template must contain one DISK attribute";
|
||||
return -1;
|
||||
|
||||
error_max_disks:
|
||||
error_str = "Exceeded the maximum number of disks (20)";
|
||||
return -1;
|
||||
|
||||
error_duplicated_target:
|
||||
oss << "Two disks have defined the same target " << target;
|
||||
error_str = oss.str();
|
||||
|
||||
error_common:
|
||||
ImageManager * imagem = nd.get_imagem();
|
||||
|
||||
vector<int>::iterator it;
|
||||
|
||||
for ( it=acquired_images.begin() ; it < acquired_images.end(); it++ )
|
||||
{
|
||||
imagem->release_image(*it, false);
|
||||
}
|
||||
|
||||
return -1;
|
||||
return new_disk;
|
||||
}
|
||||
|
||||
/* -------------------------------------------------------------------------- */
|
||||
@ -1281,11 +1242,6 @@ VectorAttribute* VirtualMachine::get_attach_disk()
|
||||
vector<Attribute *> disks;
|
||||
VectorAttribute * disk;
|
||||
|
||||
ostringstream oss;
|
||||
|
||||
// -------------------------------------------------------------------------
|
||||
// Set DISK attributes & Targets
|
||||
// -------------------------------------------------------------------------
|
||||
num_disks = obj_template->get("DISK", disks);
|
||||
|
||||
for(int i=0; i<num_disks; i++)
|
||||
@ -1309,12 +1265,11 @@ VectorAttribute* VirtualMachine::get_attach_disk()
|
||||
/* -------------------------------------------------------------------------- */
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
int VirtualMachine::attach_success()
|
||||
void VirtualMachine::clear_attach_disk()
|
||||
{
|
||||
int num_disks;
|
||||
vector<Attribute *> disks;
|
||||
VectorAttribute * disk;
|
||||
bool removed;
|
||||
|
||||
num_disks = obj_template->get("DISK", disks);
|
||||
|
||||
@ -1330,46 +1285,25 @@ int VirtualMachine::attach_success()
|
||||
if ( disk->vector_value("ATTACH") == "YES" )
|
||||
{
|
||||
disk->remove("ATTACH");
|
||||
removed = true;
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
if ( removed )
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* -------------------------------------------------------------------------- */
|
||||
/* -------------------------------------------------------------------------- */
|
||||
|
||||
// TODO: this method requires the VM to be locked, and then it locks the Image
|
||||
// to release. Check if this can be troublesome
|
||||
|
||||
int VirtualMachine::attach_failure()
|
||||
VectorAttribute * VirtualMachine::delete_attach_disk()
|
||||
{
|
||||
int num_disks;
|
||||
vector<Attribute *> disks;
|
||||
VectorAttribute * disk;
|
||||
bool found = false;
|
||||
bool uses_image = false;
|
||||
int iid;
|
||||
|
||||
Nebula& nd = Nebula::instance();
|
||||
ImageManager * imagem = nd.get_imagem();
|
||||
int num_disks = obj_template->get("DISK", disks);
|
||||
|
||||
num_disks = obj_template->get("DISK", disks);
|
||||
|
||||
int i = 0;
|
||||
|
||||
while( !found && i<num_disks )
|
||||
for(int i=0; i<num_disks; i++)
|
||||
{
|
||||
disk = dynamic_cast<VectorAttribute * >(disks[i]);
|
||||
|
||||
i++;
|
||||
|
||||
if ( disk == 0 )
|
||||
{
|
||||
continue;
|
||||
@ -1377,23 +1311,10 @@ int VirtualMachine::attach_failure()
|
||||
|
||||
if ( disk->vector_value("ATTACH") == "YES" )
|
||||
{
|
||||
uses_image = ( disk->vector_value("IMAGE_ID", iid) != -1 );
|
||||
|
||||
obj_template->erase(disk);
|
||||
found = true;
|
||||
return static_cast<VectorAttribute * >(obj_template->remove(disk));
|
||||
}
|
||||
}
|
||||
|
||||
if ( !found )
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
if ( uses_image )
|
||||
{
|
||||
imagem->release_image(iid, false);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user