1
0
mirror of https://github.com/OpenNebula/one.git synced 2025-03-26 06:50:09 +03:00

feature #1613: Triiger monitor actions when an image operation is made. Check datastore size before registering or cloning an image. RESERVED_SIZE and MAX_USED_SIZE control datastore capacity

This commit is contained in:
Ruben S. Montero 2013-07-05 21:14:34 +02:00
parent 0e2a876525
commit f689d1ea4a
8 changed files with 154 additions and 66 deletions

View File

@ -162,6 +162,27 @@ public:
used_mb = used;
}
unsigned int get_avail_mb()
{
float reserved_size;
float max_used_size;
unsigned int effective_free = free_mb;
if (get_template_attribute("MAX_USED_SIZE", max_used_size))
{
if (used_mb >= max_used_size)
{
effective_free = 0;
}
}
else if (get_template_attribute("RESERVED_SIZE", reserved_size))
{
effective_free -= reserved_size;
}
return effective_free;
}
private:
// -------------------------------------------------------------------------

View File

@ -182,6 +182,12 @@ public:
*/
int stat_image(Template* img_tmpl, const string& ds_tmpl, string& res);
/**
* Trigger a monitor action for the datastore.
* @param ds_id id of the datastore to monitor
*/
void monitor_datastore(int ds_id);
private:
/**
* Generic name for the Image driver
@ -264,7 +270,7 @@ private:
* @param ds_data Datastore XML representation
* @return the XML message
*/
string * format_message(const string& img_data, const string& ds_data);
static string * format_message(const string& img_data, const string& ds_data);
/**
* This function is executed periodically to monitor Datastores.

View File

@ -221,6 +221,14 @@ int DatastorePool::allocate(
*oid = PoolSQL::allocate(ds, error_str);
if ( *oid != -1 )
{
Nebula& nd = Nebula::instance();
ImageManager * im = nd.get_imagem();
im->monitor_datastore(*oid);
}
return *oid;
error_duplicated:

View File

@ -67,3 +67,5 @@ EOF
)
echo "$MONITOR_DATA"
#vgdisplay --units M -o vg_free -C vg --noheadings --nosuffix

View File

@ -165,8 +165,6 @@ void ImageManager::timer_action()
Nebula& nd = Nebula::instance();
DatastorePool * dspool = nd.get_dspool();
ostringstream oss;
rc = dspool->list(datastores);
if ( rc != 0 )
@ -174,33 +172,46 @@ void ImageManager::timer_action()
return;
}
const ImageManagerDriver* imd = get();
for(it = datastores.begin() ; it != datastores.end(); it++)
{
string ds_data;
string* drv_msg;
Datastore * ds = dspool->get(*it, true);
if ( ds == 0 )
{
continue;
}
drv_msg = format_message("", ds->to_xml(ds_data));
oss.str("");
oss << "Monitoring datastore " << ds->get_name() << " (" << *it << ")";
NebulaLog::log("InM", Log::INFO, oss);
ds->unlock();
imd->monitor(*it, *drv_msg);
delete drv_msg;
monitor_datastore(*it);
}
return;
}
/* -------------------------------------------------------------------------- */
/* -------------------------------------------------------------------------- */
void ImageManager::monitor_datastore(int ds_id)
{
string ds_data;
string* drv_msg;
Nebula& nd = Nebula::instance();
DatastorePool * dspool = nd.get_dspool();
ostringstream oss;
const ImageManagerDriver* imd = get();
Datastore * ds = dspool->get(ds_id, true);
if ( ds == 0 )
{
return;
}
drv_msg = ImageManager::format_message("", ds->to_xml(ds_data));
oss << "Monitoring datastore " << ds->get_name() << " (" << ds_id << ")";
NebulaLog::log("InM", Log::INFO, oss);
ds->unlock();
imd->monitor(ds_id, *drv_msg);
delete drv_msg;
}

View File

@ -132,13 +132,14 @@ static void stat_action(istringstream& is, int id, const string& result)
/* -------------------------------------------------------------------------- */
static void cp_action(istringstream& is,
ImagePool* ipool,
int id,
const string& result)
static int cp_action(istringstream& is,
ImagePool* ipool,
int id,
const string& result)
{
string source;
string info;
int ds_id = -1;
Image * image;
@ -166,9 +167,11 @@ static void cp_action(istringstream& is,
}
}
return;
return ds_id;
}
ds_id = image->get_ds_id();
if ( result == "FAILURE" )
{
goto error;
@ -194,7 +197,7 @@ static void cp_action(istringstream& is,
NebulaLog::log("ImM", Log::INFO, "Image copied and ready to use.");
return;
return ds_id;
error:
oss << "Error copying image in the datastore";
@ -215,17 +218,18 @@ error:
image->unlock();
return;
return ds_id;
}
/* -------------------------------------------------------------------------- */
static void clone_action(istringstream& is,
ImagePool* ipool,
int id,
const string& result)
static int clone_action(istringstream& is,
ImagePool* ipool,
int id,
const string& result)
{
int cloning_id;
int ds_id = -1;
string source;
string info;
@ -258,9 +262,10 @@ static void clone_action(istringstream& is,
}
}
return;
return ds_id;
}
ds_id = image->get_ds_id();
cloning_id = image->get_cloning_id();
if ( result == "FAILURE" )
@ -292,7 +297,7 @@ static void clone_action(istringstream& is,
im->release_cloning_image(cloning_id, id);
return;
return ds_id;
error:
oss << "Error cloning from Image " << cloning_id;
@ -317,15 +322,15 @@ error:
im->release_cloning_image(cloning_id, id);
return;
return ds_id;
}
/* -------------------------------------------------------------------------- */
static void mkfs_action(istringstream& is,
ImagePool* ipool,
int id,
const string& result)
static int mkfs_action(istringstream& is,
ImagePool* ipool,
int id,
const string& result)
{
string source;
Image * image;
@ -336,6 +341,8 @@ static void mkfs_action(istringstream& is,
int rc;
int vm_id = -1;
int ds_id = -1;
int disk_id;
VirtualMachine * vm;
@ -367,11 +374,12 @@ static void mkfs_action(istringstream& is,
}
}
return;
return ds_id;
}
is_saving = image->isSaving();
is_hot = image->isHot();
ds_id = image->get_ds_id();
if ( is_saving )
{
@ -408,7 +416,7 @@ static void mkfs_action(istringstream& is,
if ( !is_saving )
{
return;
return ds_id;
}
vm = vmpool->get(vm_id, true);
@ -445,7 +453,7 @@ static void mkfs_action(istringstream& is,
vm->unlock();
return;
return ds_id;
error_img:
oss << "Error creating datablock";
@ -465,7 +473,7 @@ error_save:
if ( image == 0 )
{
NebulaLog::log("ImM", Log::ERROR, oss);
return;
return ds_id;
}
error:
@ -496,17 +504,19 @@ error:
}
}
return ;
return ds_id;
}
/* -------------------------------------------------------------------------- */
static void rm_action(istringstream& is,
ImagePool* ipool,
int id,
const string& result)
static int rm_action(istringstream& is,
ImagePool* ipool,
int id,
const string& result)
{
int rc;
int rc;
int ds_id = -1;
string tmp_error;
string source;
string info;
@ -518,9 +528,10 @@ static void rm_action(istringstream& is,
if ( image == 0 )
{
return;
return ds_id;
}
ds_id = image->get_ds_id();
source = image->get_source();
rc = ipool->drop(image, tmp_error);
@ -538,14 +549,14 @@ static void rm_action(istringstream& is,
NebulaLog::log("ImM", Log::INFO, "Image successfully removed.");
return;
return ds_id;
error_drop:
oss << "Error removing image from DB: " << tmp_error
<< ". Remove image source " << source << " to completely delete image.";
NebulaLog::log("ImM", Log::ERROR, oss);
return;
return ds_id;
error:
oss << "Error removing image from datastore. Manually remove image source "
@ -560,7 +571,7 @@ error:
NebulaLog::log("ImM", Log::ERROR, oss);
return;
return ds_id;
}
/* -------------------------------------------------------------------------- */
@ -648,7 +659,9 @@ void ImageManagerDriver::protocol(const string& message) const
string result;
string source;
string info;
int id;
int id;
int ds_id = -1;
oss << "Message received: " << message;
NebulaLog::log("ImG", Log::DDEBUG, oss);
@ -691,19 +704,19 @@ void ImageManagerDriver::protocol(const string& message) const
}
else if ( action == "CP" )
{
cp_action(is, ipool, id, result);
ds_id = cp_action(is, ipool, id, result);
}
else if ( action == "CLONE" )
{
clone_action(is, ipool, id, result);
ds_id = clone_action(is, ipool, id, result);
}
else if ( action == "MKFS" )
{
mkfs_action(is, ipool, id, result);
ds_id = mkfs_action(is, ipool, id, result);
}
else if ( action == "RM" )
{
rm_action(is, ipool, id, result);
ds_id = rm_action(is, ipool, id, result);
}
else if ( action == "MONITOR" )
{
@ -715,6 +728,14 @@ void ImageManagerDriver::protocol(const string& message) const
NebulaLog::log("ImM", log_type(result[0]), info.c_str());
}
if (ds_id != -1)
{
Nebula& nd = Nebula::instance();
ImageManager * im = nd.get_imagem();
im->monitor_datastore(ds_id);
}
return;
}

View File

@ -342,7 +342,7 @@ void ImageAllocate::request_execute(xmlrpc_c::paramList const& params,
Datastore * ds;
Image::DiskType ds_disk_type;
int umask;
int umask, avail;
// ------------------------- Get user's umask ------------------------------
@ -407,6 +407,7 @@ void ImageAllocate::request_execute(xmlrpc_c::paramList const& params,
ds_name = ds->get_name();
ds_disk_type = ds->get_disk_type();
avail = ds->get_avail_mb();
ds->to_xml(ds_data);
@ -437,6 +438,14 @@ void ImageAllocate::request_execute(xmlrpc_c::paramList const& params,
return;
}
if ( size_mb > avail )
{
failure_response(ACTION, "Not enough space in datastore", att);
delete tmpl;
return;
}
tmpl->erase("SIZE");
tmpl->add("SIZE", size_str);

View File

@ -229,7 +229,7 @@ void ImageClone::request_execute(
int clone_id = xmlrpc_c::value_int(paramList.getInt(1));
string name = xmlrpc_c::value_string(paramList.getString(2));
int rc, new_id, ds_id, size, umask;
int rc, new_id, ds_id, size, umask, avail;
string error_str, ds_name, ds_data;
Image::DiskType disk_type;
@ -336,6 +336,8 @@ void ImageClone::request_execute(
ds->to_xml(ds_data);
avail = ds->get_avail_mb();
ds->unlock();
// ------------- Set authorization request ---------------------------------
@ -343,6 +345,14 @@ void ImageClone::request_execute(
img_usage.add("DATASTORE", ds_id);
img_usage.add("SIZE", size);
if ( size > avail )
{
failure_response(ACTION, "Not enough space in datastore", att);
delete tmpl;
return;
}
if ( att.uid != 0 )
{
AuthRequest ar(att.uid, att.gid);