diff --git a/include/AclManager.h b/include/AclManager.h index c870e6a7fb..b1a7fa57d2 100644 --- a/include/AclManager.h +++ b/include/AclManager.h @@ -174,6 +174,9 @@ public: const set& user_groups, PoolObjectSQL::ObjectType obj_type, AuthRequest::Operation op, + bool disable_all_acl, + bool disable_cluster_acl, + bool disable_group_acl, bool& all, vector& oids, vector& gids, diff --git a/include/PoolSQL.h b/include/PoolSQL.h index 2dbe1a13f3..6704092feb 100644 --- a/include/PoolSQL.h +++ b/include/PoolSQL.h @@ -201,14 +201,20 @@ public: * @param user_groups Set of group IDs that the user is part of * @param auth_object object type * @param all returns if the user can access all objects + * @param disable_all_acl e.g. NET\* + * @param disable_cluster_acl e.g. NET/%100 + * @param disable_group_acl e.g. NET/@102 * @param filter the resulting filter string + * */ static void acl_filter(int uid, const set& user_groups, PoolObjectSQL::ObjectType auth_object, bool& all, + bool disable_all_acl, + bool disable_cluster_acl, + bool disable_group_acl, string& filter); - /** * Creates a filter for the objects owned by a given user/group * @param uid the user id diff --git a/include/RequestManagerPoolInfoFilter.h b/include/RequestManagerPoolInfoFilter.h index ea94851aa5..75b74f8cdb 100644 --- a/include/RequestManagerPoolInfoFilter.h +++ b/include/RequestManagerPoolInfoFilter.h @@ -47,8 +47,13 @@ public: * @return true if the use_filter is empty and access to all objects * should be granted. */ - static bool use_filter(RequestAttributes& att, PoolObjectSQL::ObjectType aobj, - string& where_str); + static bool use_filter(RequestAttributes& att, + PoolObjectSQL::ObjectType aobj, + bool disable_all_acl, + bool disable_cluster_acl, + bool disable_group_acl, + const string& and_str, + string& where_str); protected: RequestManagerPoolInfoFilter(const string& method_name, @@ -72,6 +77,9 @@ protected: int end_id, const string& and_clause, const string& or_clause, + bool disable_all_acl, + bool disable_cluster_acl, + bool disable_group_acl, string& where_string); /* -------------------------------------------------------------------- */ @@ -201,6 +209,9 @@ public: }; ~VirtualNetworkPoolInfo(){}; + + void request_execute( + xmlrpc_c::paramList const& paramList, RequestAttributes& att); }; /* ------------------------------------------------------------------------- */ diff --git a/src/acl/AclManager.cc b/src/acl/AclManager.cc index c12f68232f..08fe240f4f 100644 --- a/src/acl/AclManager.cc +++ b/src/acl/AclManager.cc @@ -917,6 +917,9 @@ void AclManager::reverse_search(int uid, const set& user_groups, PoolObjectSQL::ObjectType obj_type, AuthRequest::Operation op, + bool disable_all_acl, + bool disable_cluster_acl, + bool disable_group_acl, bool& all, vector& oids, vector& gids, @@ -1009,30 +1012,29 @@ void AclManager::reverse_search(int uid, NebulaLog::log("ACL",Log::DDEBUG,oss); // Rule grants permission for all objects of this type - if ( ( it->second->resource & resource_all_req ) == resource_all_req ) + if ((!disable_all_acl) && + ((it->second->resource & resource_all_req) == resource_all_req)) { all = true; break; } - // Rule grants permission for all objects of a group - if ( ( it->second->resource & resource_gid_mask ) == resource_gid_req ) + else if ((!disable_group_acl) && + ((it->second->resource & resource_gid_mask) == resource_gid_req)) { gids.push_back(it->second->resource_id()); } - - // Rule grants permission for an individual object - else if ( ( it->second->resource & resource_oid_mask ) == resource_oid_req ) - { - oids.push_back(it->second->resource_id()); - } - // Rule grants permission for all objects of a cluster - if ( ( it->second->resource & resource_cid_mask ) == resource_cid_req ) + else if ((!disable_cluster_acl) && + ((it->second->resource & resource_cid_mask) == resource_cid_req)) { cids.push_back(it->second->resource_id()); } - + // Rule grants permission for an individual object + else if ((it->second->resource & resource_oid_mask) == resource_oid_req) + { + oids.push_back(it->second->resource_id()); + } } } diff --git a/src/pool/PoolSQL.cc b/src/pool/PoolSQL.cc index 30aae011a5..ad7787007b 100644 --- a/src/pool/PoolSQL.cc +++ b/src/pool/PoolSQL.cc @@ -695,6 +695,9 @@ void PoolSQL::acl_filter(int uid, const set& user_groups, PoolObjectSQL::ObjectType auth_object, bool& all, + bool disable_all_acl, + bool disable_cluster_acl, + bool disable_group_acl, string& filter) { filter.clear(); @@ -719,6 +722,9 @@ void PoolSQL::acl_filter(int uid, user_groups, auth_object, AuthRequest::USE, + disable_all_acl, + disable_cluster_acl, + disable_group_acl, all, oids, gids, diff --git a/src/rm/RequestManagerInfo.cc b/src/rm/RequestManagerInfo.cc index ed8e6fbea3..3ce18d9bac 100644 --- a/src/rm/RequestManagerInfo.cc +++ b/src/rm/RequestManagerInfo.cc @@ -74,31 +74,31 @@ void VirtualNetworkInfo::to_xml(RequestAttributes& att, PoolObjectSQL * object, vector vms; vector vnets; - string where_str; + string where_vnets; + string where_vms; - bool all = RequestManagerPoolInfoFilter::use_filter(att, PoolObjectSQL::NET, - where_str); + bool all_reservations = RequestManagerPoolInfoFilter::use_filter(att, + PoolObjectSQL::NET, true, true, false, "(pid != -1)", where_vnets); - if (all) + bool all_vms = RequestManagerPoolInfoFilter::use_filter(att, + PoolObjectSQL::VM, false, false, false, "", where_vms); + + if ( all_reservations == true ) { vnets.push_back(-1); + } + else + { + Nebula::instance().get_vnpool()->search(vnets, where_vnets); + } + + if ( all_vms == true ) + { vms.push_back(-1); } else { - if ( Nebula::instance().get_vnpool()->search(vnets, where_str) != 0 ) - { - //Log warning - } - - where_str = ""; - - RequestManagerPoolInfoFilter::use_filter(att, PoolObjectSQL::VM, where_str); - - if ( Nebula::instance().get_vmpool()->search(vms, where_str) != 0 ) - { - //Log warning - } + Nebula::instance().get_vmpool()->search(vms, where_vms); } static_cast(object)->to_xml_extended(str, vms, vnets); diff --git a/src/rm/RequestManagerPoolInfoFilter.cc b/src/rm/RequestManagerPoolInfoFilter.cc index beb248831a..f75d2275fd 100644 --- a/src/rm/RequestManagerPoolInfoFilter.cc +++ b/src/rm/RequestManagerPoolInfoFilter.cc @@ -52,16 +52,32 @@ void RequestManagerPoolInfoFilter::request_execute( bool RequestManagerPoolInfoFilter::use_filter(RequestAttributes& att, PoolObjectSQL::ObjectType aobj, + bool disable_all_acl, + bool disable_cluster_acl, + bool disable_group_acl, + const string& and_str, string& where_str) { bool all; string acl_str; + string usr_str; - PoolSQL::acl_filter(att.uid, att.group_ids, aobj, all, acl_str); + + PoolSQL::acl_filter(att.uid, att.group_ids, aobj, all, + disable_all_acl, disable_cluster_acl, disable_group_acl, acl_str); PoolSQL::usr_filter(att.uid, att.group_ids, ALL, all, acl_str, where_str); + if (!and_str.empty()) + { + ostringstream filter; + + filter << "( " << where_str << " ) AND ( " << and_str << " )"; + + where_str = filter.str(); + } + return all; }; @@ -129,7 +145,7 @@ void VirtualMachinePoolAccounting::request_execute( return; } - where_filter(att, filter_flag, -1, -1, "", "", where); + where_filter(att, filter_flag, -1, -1, "", "", false, false, false, where); rc = (static_cast(pool))->dump_acct(oss, where, @@ -167,7 +183,7 @@ void VirtualMachinePoolMonitoring::request_execute( return; } - where_filter(att, filter_flag, -1, -1, "", "", where); + where_filter(att, filter_flag, -1, -1, "", "", false, false, false, where); rc = (static_cast(pool))->dump_monitoring(oss, where); @@ -203,7 +219,7 @@ void HostPoolMonitoring::request_execute( string where; int rc; - where_filter(att, ALL, -1, -1, "", "", where); + where_filter(att, ALL, -1, -1, "", "", false, false, false, where); rc = (static_cast(pool))->dump_monitoring(oss, where); @@ -296,6 +312,9 @@ void RequestManagerPoolInfoFilter::where_filter( int end_id, const string& and_clause, const string& or_clause, + bool disable_all_acl, + bool disable_cluster_acl, + bool disable_group_acl, string& filter_str) { bool empty = true; @@ -307,7 +326,8 @@ void RequestManagerPoolInfoFilter::where_filter( ostringstream filter; - PoolSQL::acl_filter(att.uid, att.group_ids, auth_object, all, acl_str); + PoolSQL::acl_filter(att.uid, att.group_ids, auth_object, all, + disable_all_acl, disable_cluster_acl, disable_group_acl, acl_str); PoolSQL::usr_filter(att.uid, att.group_ids, filter_flag, all, acl_str, uid_str); @@ -388,6 +408,9 @@ void RequestManagerPoolInfoFilter::dump( end_id, and_clause, or_clause, + false, + false, + false, where_string); if ( end_id < -1 ) @@ -409,3 +432,69 @@ void RequestManagerPoolInfoFilter::dump( return; } + +/* ------------------------------------------------------------------------- */ +/* ------------------------------------------------------------------------- */ + +void VirtualNetworkPoolInfo::request_execute( + xmlrpc_c::paramList const& paramList, RequestAttributes& att) +{ + int filter_flag = xmlrpc_c::value_int(paramList.getInt(1)); + int start_id = xmlrpc_c::value_int(paramList.getInt(2)); + int end_id = xmlrpc_c::value_int(paramList.getInt(3)); + + if ( filter_flag < MINE ) + { + failure_response(XML_RPC_API, + request_error("Incorrect filter_flag",""), + att); + return; + } + + /* ---------------------------------------------------------------------- */ + /* Build where filters to get ois from: */ + /* - vnets (owner, permissions & ACL) */ + /* - reservations (owner, permission & not VNET\* nor VNET/% ACLs) */ + /* ---------------------------------------------------------------------- */ + + string where_vnets, where_reserv; + ostringstream where_string; + + where_filter(att, filter_flag, start_id, end_id, "pid == -1", "", false, + false, false, where_vnets); + + where_filter(att, filter_flag, -1, -1, "pid != -1", "", true, true, false, + where_reserv); + + where_string << "( " << where_vnets << " ) OR ( " << where_reserv << " ) "; + + /* ---------------------------------------------------------------------- */ + /* Build pagination limits */ + /* ---------------------------------------------------------------------- */ + + ostringstream limit_clause; + + if ( end_id < -1 ) + { + limit_clause << start_id << "," << -end_id; + } + + /* ---------------------------------------------------------------------- */ + /* Get the VNET pool */ + /* ---------------------------------------------------------------------- */ + + ostringstream pool_oss; + + int rc = pool->dump(pool_oss, where_string.str(), limit_clause.str()); + + if ( rc != 0 ) + { + failure_response(INTERNAL,request_error("Internal Error",""), att); + return; + } + + success_response(pool_oss.str(), att); + + return; +} +