sefs_fclist Class Reference

#include <fclist.hh>

Inheritance diagram for sefs_fclist:

sefs_db sefs_fcfile sefs_filesystem List of all members.

Detailed Description

An abstract class the represents a list of file contexts.

Contexts may be read from a filesystem, inferred from a file_contexts file, or read from a database.

Definition at line 109 of file fclist.hh.


Public Member Functions

virtual ~sefs_fclist ()
virtual int runQueryMap (sefs_query *query, sefs_fclist_map_fn_t fn, void *data)=0 throw (std::runtime_error, std::invalid_argument)
 Perform a sefs query on the given file context list object, and then invoke a callback upon each matching entry.
apol_vector_trunQuery (sefs_query *query) throw (std::bad_alloc, std::runtime_error, std::invalid_argument)
 Perform a sefs query on the given file context list object and return a list of matching entries.
virtual bool isMLS () const =0
 Determine if the contexts in the fclist contain MLS fields.
void associatePolicy (apol_policy_t *new_policy)
 Associate a policy with the fclist.
apol_policy_tassociatePolicy () const
 Return the policy currently associated with this fclist.
sefs_fclist_type_e fclist_type () const
 Get the type of fclist object represented by fclist.

Protected Member Functions

 sefs_fclist (sefs_fclist_type_e type, sefs_callback_fn_t callback, void *varg) throw (std::bad_alloc)
sefs_context_nodegetContext (const char *user, const char *role, const char *type, const char *range) throw (std::bad_alloc)
 Given the parts of a context, return a context node (which would contain an apol_context_t).
sefs_context_nodegetContext (const security_context_t scon) throw (std::bad_alloc)
 Given a SELinux security context, return a context node (which would contain an apol_context_t).

Protected Attributes

apol_policy_tpolicy
apol_bstuser_tree
apol_bstrole_tree
apol_bsttype_tree
apol_bstrange_tree
apol_bstpath_tree
apol_bstdev_tree
apol_bstcontext_tree

Private Member Functions

void handleMsg (int level, const char *fmt, va_list va_args) const
 Write a message to the callback stored within a fclist error handler.

Private Attributes

sefs_callback_fn_t _callback
void * _varg
sefs_fclist_type_e _fclist_type

Friends

class sefs_entry
void sefs_fclist_handleMsg (const sefs_fclist *fclist, int level, const char *fmt,...)

Constructor & Destructor Documentation

sefs_fclist::~sefs_fclist  )  [virtual]
 

Definition at line 125 of file fclist.cc.

References apol_bst_destroy(), context_tree, dev_tree, path_tree, range_tree, role_tree, type_tree, and user_tree.

00126 {
00127         apol_bst_destroy(&user_tree);
00128         apol_bst_destroy(&role_tree);
00129         apol_bst_destroy(&type_tree);
00130         apol_bst_destroy(&range_tree);
00131         apol_bst_destroy(&path_tree);
00132         apol_bst_destroy(&dev_tree);
00133         apol_bst_destroy(&context_tree);
00134 }

sefs_fclist::sefs_fclist sefs_fclist_type_e  type,
sefs_callback_fn_t  callback,
void *  varg
throw (std::bad_alloc) [protected]
 

Definition at line 202 of file fclist.cc.

References apol_bst_create(), apol_bst_destroy(), apol_str_strcmp(), fclist_sefs_context_node_comp(), and fclist_sefs_context_node_free().

00203 {
00204         _fclist_type = type;
00205         _callback = callback;
00206         _varg = varg;
00207         policy = NULL;
00208         user_tree = role_tree = type_tree = range_tree = path_tree = NULL;
00209         dev_tree = NULL;
00210         context_tree = NULL;
00211         try
00212         {
00213                 if ((user_tree = apol_bst_create(apol_str_strcmp, free)) == NULL)
00214                 {
00215                         throw std::bad_alloc();
00216                 }
00217                 if ((role_tree = apol_bst_create(apol_str_strcmp, free)) == NULL)
00218                 {
00219                         throw std::bad_alloc();
00220                 }
00221                 if ((type_tree = apol_bst_create(apol_str_strcmp, free)) == NULL)
00222                 {
00223                         throw std::bad_alloc();
00224                 }
00225                 if ((range_tree = apol_bst_create(apol_str_strcmp, free)) == NULL)
00226                 {
00227                         throw std::bad_alloc();
00228                 }
00229                 if ((path_tree = apol_bst_create(apol_str_strcmp, free)) == NULL)
00230                 {
00231                         throw std::bad_alloc();
00232                 }
00233                 if ((dev_tree = apol_bst_create(apol_str_strcmp, free)) == NULL)
00234                 {
00235                         throw std::bad_alloc();
00236                 }
00237                 if ((context_tree = apol_bst_create(fclist_sefs_context_node_comp, fclist_sefs_context_node_free)) == NULL)
00238                 {
00239                         throw std::bad_alloc();
00240                 }
00241         }
00242         catch(...)
00243         {
00244                 apol_bst_destroy(&user_tree);
00245                 apol_bst_destroy(&role_tree);
00246                 apol_bst_destroy(&type_tree);
00247                 apol_bst_destroy(&range_tree);
00248                 apol_bst_destroy(&path_tree);
00249                 apol_bst_destroy(&dev_tree);
00250                 apol_bst_destroy(&context_tree);
00251                 throw;
00252         }
00253 }


Member Function Documentation

virtual int sefs_fclist::runQueryMap sefs_query query,
sefs_fclist_map_fn_t  fn,
void *  data
throw (std::runtime_error, std::invalid_argument) [pure virtual]
 

Perform a sefs query on the given file context list object, and then invoke a callback upon each matching entry.

Mapping occurs in the order of entries as specified by the file context list.

Parameters:
query Query object containing search parameters. If NULL, invoke the callback on all entries.
fn Function to invoke upon matching entries. This function will be called with three parameters: a pointer to this fclist, pointer to a matching entry, and an arbitrary data pointer. It should return a non-negative value upon success, negative value upon error and to abort the mapping. Be aware that the entry may go out of scope upon conclusion of runQueryMap(), so fn will need to clone the entry if it needs it later.
This function must not throw any exceptions. Doing so will most likely corrupt fclist's internal state. Instead, return a negative value to abort processing.
Parameters:
data Arbitrary pointer to be passed into fn as a third parameter.
Returns:
Last value returned by fn() (i.e., >= on success, < 0 on failure). If the fclist has no entries then return 0.
Exceptions:
std::runtime_error Error while reading contexts from the fclist.
std::invalid_argument One or more query arguments is invalid.

Implemented in sefs_db, sefs_fcfile, and sefs_filesystem.

Referenced by main(), and sefs_fclist_run_query_map().

apol_vector_t * sefs_fclist::runQuery sefs_query query  )  throw (std::bad_alloc, std::runtime_error, std::invalid_argument)
 

Perform a sefs query on the given file context list object and return a list of matching entries.

Parameters:
query Query object containing search parameters. If NULL, return all contexts.
Returns:
A newly allocated unsorted vector (of class sefs_entry *) containing all entries matching the query. Do not modify the returned entries. Note that the vector may be empty. The caller is responsible for calling apol_vector_destroy() on the returned vector.
Exceptions:
std::bad_alloc Out of memory.
std::runtime_error Error while reading contexts from the fclist.
std::invalid_argument One or more query arguments is invalid.

Definition at line 156 of file fclist.cc.

References apol_vector_create(), apol_vector_destroy(), apol_vector_t, fclist_entry_free(), and map_to_vector().

Referenced by fcfile_query(), and sefs_fclist_run_query().

00157 {
00158         apol_vector_t *v = NULL;
00159         try
00160         {
00161                 if ((v = apol_vector_create(fclist_entry_free)) == NULL)
00162                 {
00163                         throw std::bad_alloc();
00164                 }
00165                 if (runQueryMap(query, map_to_vector, v) < 0)
00166                 {
00167                         throw std::bad_alloc();
00168                 }
00169         }
00170         catch(...)
00171         {
00172                 apol_vector_destroy(&v);
00173                 throw;
00174         }
00175         return v;
00176 }

virtual bool sefs_fclist::isMLS  )  const [pure virtual]
 

Determine if the contexts in the fclist contain MLS fields.

Returns:
true if MLS fields are present, false if not or undeterminable.

Implemented in sefs_db, sefs_fcfile, and sefs_filesystem.

Referenced by main(), and sefs_fclist_get_is_mls().

void sefs_fclist::associatePolicy apol_policy_t new_policy  ) 
 

Associate a policy with the fclist.

This is needed to resolve attributes and MLS ranges in queries. If a policy is already associated, then calling this function removes that previous association.

Parameters:
policy Policy to associate with fclist. If NULL, remove any policy association. While policy is associated with fclist the caller should not destroy policy.
See also:
sefs_query_set_type()

sefs_query_set_range()

Definition at line 178 of file fclist.cc.

References apol_bst_inorder_map(), apol_policy_t, context_tree, fclist_sefs_node_convert(), and policy.

Referenced by fclist_sefs_node_convert(), and sefs_fclist_associate_policy().

00179 {
00180         policy = new_policy;
00181         if (policy != NULL)
00182         {
00183                 if (apol_bst_inorder_map(context_tree, fclist_sefs_node_convert, policy) < 0)
00184                 {
00185                         throw new std::bad_alloc();
00186                 }
00187         }
00188 }

apol_policy_t * sefs_fclist::associatePolicy  )  const
 

Return the policy currently associated with this fclist.

Do not destroy the policy without first unassociating it (via call to sefs_fclist::associatePolicy(NULL)).

Returns:
Currently associated policy, or NULL if none is set.

Definition at line 190 of file fclist.cc.

References apol_policy_t.

00191 {
00192         return policy;
00193 }

sefs_fclist_type_e sefs_fclist::fclist_type  )  const
 

Get the type of fclist object represented by fclist.

Returns:
The type of fclist object or SEFS_FCLIST_TYPE_NONE on error.

Definition at line 195 of file fclist.cc.

References sefs_fclist_type_e.

Referenced by sefs_fclist_get_fclist_type().

00196 {
00197         return _fclist_type;
00198 }

struct sefs_context_node * sefs_fclist::getContext const char *  user,
const char *  role,
const char *  type,
const char *  range
throw (std::bad_alloc) [protected]
 

Given the parts of a context, return a context node (which would contain an apol_context_t).

If the context already exists, then a pointer to the existing one is returned.

Parameters:
user User component of the context. The string will be duplicated.
role Role component of the context. The string will be duplicated.
type Type component of the context. The string will be duplicated.
range Range component of the context. The string will be duplicated, or NULL if no range exists.
Returns:
A context node. Do not free() it.

Definition at line 282 of file fclist.cc.

References apol_bst_get_element(), apol_bst_insert(), apol_bst_insert_and_get(), apol_context_create(), apol_context_destroy(), apol_context_set_range(), apol_context_set_role(), apol_context_set_type(), apol_context_set_user(), apol_context_t, apol_mls_range_create_from_literal(), apol_mls_range_destroy(), apol_mls_range_t, fclist_sefs_context_node_free(), fclist_sefs_node_make_string(), and SEFS_ERR.

00284 {
00285         char *u = NULL, *r = NULL, *t = NULL, *m = NULL;
00286         if ((u = strdup(user)) == NULL)
00287         {
00288                 SEFS_ERR(this, "%s", strerror(errno));
00289                 throw std::runtime_error(strerror(errno));
00290         }
00291         if (apol_bst_insert_and_get(user_tree, (void **)&u, NULL) < 0)
00292         {
00293                 free(u);
00294                 SEFS_ERR(this, "%s", strerror(errno));
00295                 throw std::runtime_error(strerror(errno));
00296         }
00297 
00298         if ((r = strdup(role)) == NULL)
00299         {
00300                 SEFS_ERR(this, "%s", strerror(errno));
00301                 throw std::runtime_error(strerror(errno));
00302         }
00303         if (apol_bst_insert_and_get(role_tree, (void **)&r, NULL) < 0)
00304         {
00305                 free(r);
00306                 SEFS_ERR(this, "%s", strerror(errno));
00307                 throw std::runtime_error(strerror(errno));
00308         }
00309 
00310         if ((t = strdup(type)) == NULL)
00311         {
00312                 SEFS_ERR(this, "%s", strerror(errno));
00313                 throw std::runtime_error(strerror(errno));
00314         }
00315         if (apol_bst_insert_and_get(type_tree, (void **)&t, NULL) < 0)
00316         {
00317                 free(t);
00318                 SEFS_ERR(this, "%s", strerror(errno));
00319                 throw std::runtime_error(strerror(errno));
00320         }
00321 
00322         if (range == NULL || range[0] == '\0')
00323         {
00324                 m = NULL;
00325         }
00326         else
00327         {
00328                 if ((m = strdup(range)) == NULL)
00329                 {
00330                         SEFS_ERR(this, "%s", strerror(errno));
00331                         throw std::runtime_error(strerror(errno));
00332                 }
00333                 if (apol_bst_insert_and_get(range_tree, (void **)&m, NULL) < 0)
00334                 {
00335                         free(m);
00336                         SEFS_ERR(this, "%s", strerror(errno));
00337                         throw std::runtime_error(strerror(errno));
00338                 }
00339         }
00340 
00341         struct sefs_context_node *node = NULL;
00342         apol_context_t *context = NULL;
00343         try
00344         {
00345                 if ((node = static_cast < struct sefs_context_node * >(calloc(1, sizeof(*node)))) == NULL)
00346                 {
00347                         SEFS_ERR(this, "%s", strerror(errno));
00348                         throw std::runtime_error(strerror(errno));
00349                 }
00350 
00351                 node->user = u;
00352                 node->role = r;
00353                 node->type = t;
00354                 node->range = m;
00355 
00356                 void *v;
00357                 if (apol_bst_get_element(context_tree, node, NULL, &v) == 0)
00358                 {
00359                         // context already exists
00360                         fclist_sefs_context_node_free(node);
00361                         return static_cast < struct sefs_context_node *>(v);
00362                 }
00363 
00364                 apol_mls_range_t *apol_range = NULL;
00365                 if (m != NULL)
00366                 {
00367                         if ((apol_range = apol_mls_range_create_from_literal(m)) == NULL)
00368                         {
00369                                 SEFS_ERR(this, "%s", strerror(errno));
00370                                 throw std::bad_alloc();
00371                         }
00372                 }
00373 
00374                 if ((context = apol_context_create()) == NULL)
00375                 {
00376                         SEFS_ERR(this, "%s", strerror(errno));
00377                         apol_mls_range_destroy(&apol_range);
00378                         throw std::runtime_error(strerror(errno));
00379                 }
00380                 if (apol_context_set_user(NULL, context, u) < 0 ||
00381                     apol_context_set_role(NULL, context, r) < 0 || apol_context_set_type(NULL, context, t) < 0 ||
00382                     apol_context_set_range(NULL, context, apol_range) < 0)
00383                 {
00384                         SEFS_ERR(this, "%s", strerror(errno));
00385                         apol_mls_range_destroy(&apol_range);
00386                         throw std::runtime_error(strerror(errno));
00387                 }
00388 
00389                 node->context = context;
00390                 context = NULL;
00391 
00392                 if (fclist_sefs_node_make_string(node) < 0)
00393                 {
00394                         SEFS_ERR(this, "%s", strerror(errno));
00395                         throw std::runtime_error(strerror(errno));
00396                 }
00397 
00398                 if (apol_bst_insert(context_tree, node, NULL) != 0)
00399                 {
00400                         SEFS_ERR(this, "%s", strerror(errno));
00401                         throw std::runtime_error(strerror(errno));
00402                 }
00403         }
00404         catch(...)
00405         {
00406                 fclist_sefs_context_node_free(node);
00407                 apol_context_destroy(&context);
00408                 throw;
00409         }
00410 
00411         return node;
00412 }

struct sefs_context_node * sefs_fclist::getContext const security_context_t  scon  )  throw (std::bad_alloc) [protected]
 

Given a SELinux security context, return a context node (which would contain an apol_context_t).

If the context already exists, then a pointer to the existing one is returned.

Parameters:
scon Security context from which to obtain a node.
Returns:
A context node. Do not free() it.

Definition at line 414 of file fclist.cc.

00415 {
00416         context_t con;
00417         if ((con = context_new(scon)) == 0)
00418         {
00419                 throw std::bad_alloc();
00420         }
00421         const char *user = context_user_get(con);
00422         const char *role = context_role_get(con);
00423         const char *type = context_type_get(con);
00424         const char *range = context_range_get(con);
00425         struct sefs_context_node *node = NULL;
00426         try
00427         {
00428                 node = getContext(user, role, type, range);
00429         }
00430         catch(...)
00431         {
00432                 context_free(con);
00433                 throw;
00434         }
00435         context_free(con);
00436         return node;
00437 }

void sefs_fclist::handleMsg int  level,
const char *  fmt,
va_list  va_args
const [private]
 

Write a message to the callback stored within a fclist error handler.

If the msg_callback field is empty, then the default message callback will be used.

Parameters:
level Severity of message, one of SEFS_MSG_*.
fmt Format string to print, using syntax of printf(3).

Definition at line 441 of file fclist.cc.

References _callback, _varg, fmt, level, and sefs_handle_default_callback().

Referenced by sefs_fclist_handleMsg().

00442 {
00443         if (_callback == NULL)
00444         {
00445                 sefs_handle_default_callback(NULL, this, level, fmt, va_args);
00446         }
00447         else
00448         {
00449                 _callback(_varg, this, level, fmt, va_args);
00450         }
00451 }


Friends And Related Function Documentation

friend class sefs_entry [friend]
 

Definition at line 113 of file fclist.hh.

void sefs_fclist_handleMsg const sefs_fclist fclist,
int  level,
const char *  fmt,
  ...
[friend]
 


Member Data Documentation

apol_policy_t* sefs_fclist::policy [protected]
 

Definition at line 239 of file fclist.hh.

Referenced by associatePolicy().

struct apol_bst* sefs_fclist::user_tree [protected]
 

Definition at line 240 of file fclist.hh.

Referenced by ~sefs_fclist().

struct apol_bst * sefs_fclist::role_tree [protected]
 

Definition at line 240 of file fclist.hh.

Referenced by ~sefs_fclist().

struct apol_bst * sefs_fclist::type_tree [protected]
 

Definition at line 240 of file fclist.hh.

Referenced by ~sefs_fclist().

struct apol_bst * sefs_fclist::range_tree [protected]
 

Definition at line 240 of file fclist.hh.

Referenced by ~sefs_fclist().

struct apol_bst * sefs_fclist::path_tree [protected]
 

Definition at line 240 of file fclist.hh.

Referenced by ~sefs_fclist().

struct apol_bst* sefs_fclist::dev_tree [protected]
 

Definition at line 241 of file fclist.hh.

Referenced by ~sefs_fclist().

struct apol_bst* sefs_fclist::context_tree [protected]
 

Definition at line 242 of file fclist.hh.

Referenced by associatePolicy(), and ~sefs_fclist().

sefs_callback_fn_t sefs_fclist::_callback [private]
 

Definition at line 256 of file fclist.hh.

Referenced by handleMsg().

void* sefs_fclist::_varg [private]
 

Definition at line 257 of file fclist.hh.

Referenced by handleMsg().

sefs_fclist_type_e sefs_fclist::_fclist_type [private]
 

Definition at line 258 of file fclist.hh.


The documentation for this class was generated from the following files: