Commit 53bdc46f authored by John Johansen's avatar John Johansen
Browse files

apparmor: combine file_rules and aa_policydb into a single shared struct



file_rules and policydb are almost the same and will need the same
features in the future so combine them.

Signed-off-by: default avatarJohn Johansen <john.johansen@canonical.com>
parent e2967ede
Loading
Loading
Loading
Loading
+2 −1
Original line number Diff line number Diff line
@@ -619,7 +619,8 @@ static void profile_query_cb(struct aa_profile *profile, struct aa_perms *perms,
		return;
	if (profile->file.dfa && *match_str == AA_CLASS_FILE) {
		dfa = profile->file.dfa;
		state = aa_dfa_match_len(dfa, profile->file.start,
		state = aa_dfa_match_len(dfa,
					 profile->file.start[AA_CLASS_FILE],
					 match_str + 1, match_len - 1);
		if (state) {
			struct path_cond cond = { };
+4 −3
Original line number Diff line number Diff line
@@ -627,7 +627,7 @@ static struct aa_label *profile_transition(struct aa_profile *profile,
{
	struct aa_label *new = NULL;
	const char *info = NULL, *name = NULL, *target = NULL;
	unsigned int state = profile->file.start;
	unsigned int state = profile->file.start[AA_CLASS_FILE];
	struct aa_perms perms = {};
	bool nonewprivs = false;
	int error = 0;
@@ -723,7 +723,7 @@ static int profile_onexec(struct aa_profile *profile, struct aa_label *onexec,
			  char *buffer, struct path_cond *cond,
			  bool *secure_exec)
{
	unsigned int state = profile->file.start;
	unsigned int state = profile->file.start[AA_CLASS_FILE];
	struct aa_perms perms = {};
	const char *xname = NULL, *info = "change_profile onexec";
	int error = -EACCES;
@@ -1267,7 +1267,8 @@ static int change_profile_perms_wrapper(const char *op, const char *name,

	if (!error)
		error = change_profile_perms(profile, target, stack, request,
					     profile->file.start, perms);
					     profile->file.start[AA_CLASS_FILE],
					     perms);
	if (error)
		error = aa_audit_file(profile, perms, op, request, name,
				      NULL, target, GLOBAL_ROOT_UID, info,
+11 −9
Original line number Diff line number Diff line
@@ -185,16 +185,16 @@ static int path_name(const char *op, struct aa_label *label,
 * Returns: a pointer to a file permission set
 */
struct aa_perms default_perms = {};
struct aa_perms *aa_lookup_fperms(struct aa_file_rules *file_rules,
struct aa_perms *aa_lookup_fperms(struct aa_policydb *file_rules,
				 unsigned int state, struct path_cond *cond)
{
	if (!(file_rules->fperms_table))
	if (!(file_rules->perms))
		return &default_perms;

	if (uid_eq(current_fsuid(), cond->uid))
		return &(file_rules->fperms_table[state * 2]);
		return &(file_rules->perms[state * 2]);

	return &(file_rules->fperms_table[state * 2 + 1]);
	return &(file_rules->perms[state * 2 + 1]);
}

/**
@@ -207,7 +207,7 @@ struct aa_perms *aa_lookup_fperms(struct aa_file_rules *file_rules,
 *
 * Returns: the final state in @dfa when beginning @start and walking @name
 */
unsigned int aa_str_perms(struct aa_file_rules *file_rules, unsigned int start,
unsigned int aa_str_perms(struct aa_policydb *file_rules, unsigned int start,
			  const char *name, struct path_cond *cond,
			  struct aa_perms *perms)
{
@@ -226,7 +226,8 @@ int __aa_path_perm(const char *op, struct aa_profile *profile, const char *name,

	if (profile_unconfined(profile))
		return 0;
	aa_str_perms(&(profile->file), profile->file.start, name, cond, perms);
	aa_str_perms(&(profile->file), profile->file.start[AA_CLASS_FILE],
		     name, cond, perms);
	if (request & ~perms->allow)
		e = -EACCES;
	return aa_audit_file(profile, perms, op, request, name, NULL, NULL,
@@ -333,7 +334,8 @@ static int profile_path_link(struct aa_profile *profile,

	error = -EACCES;
	/* aa_str_perms - handles the case of the dfa being NULL */
	state = aa_str_perms(&(profile->file), profile->file.start, lname,
	state = aa_str_perms(&(profile->file),
			     profile->file.start[AA_CLASS_FILE], lname,
			     cond, &lperms);

	if (!(lperms.allow & AA_MAY_LINK))
@@ -363,8 +365,8 @@ static int profile_path_link(struct aa_profile *profile,
	/* Do link perm subset test requiring allowed permission on link are
	 * a subset of the allowed permissions on target.
	 */
	aa_str_perms(&(profile->file), profile->file.start, tname, cond,
		     &perms);
	aa_str_perms(&(profile->file), profile->file.start[AA_CLASS_FILE],
		     tname, cond, &perms);

	/* AA_MAY_LINK is not considered in the subset test */
	request = lperms.allow & ~AA_MAY_LINK;
+4 −35
Original line number Diff line number Diff line
@@ -17,6 +17,7 @@
#include "match.h"
#include "perms.h"

struct aa_policydb;
struct aa_profile;
struct path;

@@ -164,29 +165,9 @@ int aa_audit_file(struct aa_profile *profile, struct aa_perms *perms,
		  const char *target, struct aa_label *tlabel, kuid_t ouid,
		  const char *info, int error);

/**
 * struct aa_file_rules - components used for file rule permissions
 * @dfa: dfa to match path names and conditionals against
 * @perms: permission table indexed by the matched state accept entry of @dfa
 * @trans: transition table for indexed by named x transitions
 *
 * File permission are determined by matching a path against @dfa and
 * then using the value of the accept entry for the matching state as
 * an index into @perms.  If a named exec transition is required it is
 * looked up in the transition table.
 */
struct aa_file_rules {
	unsigned int start;
	struct aa_dfa *dfa;
	/* struct perms perms; */
	struct aa_domain trans;
	/* TODO: add delegate table */
	struct aa_perms *fperms_table;
};

struct aa_perms *aa_lookup_fperms(struct aa_file_rules *file_rules,
struct aa_perms *aa_lookup_fperms(struct aa_policydb *file_rules,
				  unsigned int state, struct path_cond *cond);
unsigned int aa_str_perms(struct aa_file_rules *file_rules, unsigned int start,
unsigned int aa_str_perms(struct aa_policydb *file_rules, unsigned int start,
			  const char *name, struct path_cond *cond,
			  struct aa_perms *perms);

@@ -205,18 +186,6 @@ int aa_file_perm(const char *op, struct aa_label *label, struct file *file,

void aa_inherit_files(const struct cred *cred, struct files_struct *files);

static inline void aa_free_fperms_table(struct aa_perms *fperms_table)
{
	if (fperms_table)
		kvfree(fperms_table);
}

static inline void aa_free_file_rules(struct aa_file_rules *rules)
{
	aa_put_dfa(rules->dfa);
	aa_free_domain_entries(&rules->trans);
	aa_free_fperms_table(rules->fperms_table);
}

/**
 * aa_map_file_perms - map file flags to AppArmor permissions
+11 −3
Original line number Diff line number Diff line
@@ -75,13 +75,21 @@ enum profile_mode {
 * start: set of start states for the different classes of data
 */
struct aa_policydb {
	/* Generic policy DFA specific rule types will be subsections of it */
	struct aa_dfa *dfa;
	struct aa_perms *perms;
	struct aa_domain trans;
	unsigned int start[AA_CLASS_LAST + 1];

};

static inline void aa_destroy_policydb(struct aa_policydb *policy)
{
	aa_put_dfa(policy->dfa);
	if (policy->perms)
		kvfree(policy->perms);
	aa_free_domain_entries(&policy->trans);

}

/* struct aa_data - generic data structure
 * key: name for retrieving this data
 * size: size of data in bytes
@@ -151,7 +159,7 @@ struct aa_profile {
	int size;

	struct aa_policydb policy;
	struct aa_file_rules file;
	struct aa_policydb file;
	struct aa_caps caps;

	int xattr_count;
Loading