Commit 3cfcc19e authored by John Johansen's avatar John Johansen

apparmor: add utility function to get an arbitrary tasks profile.

Signed-off-by: default avatarJohn Johansen <john.johansen@canonical.com>
Acked-by: default avatarSteve Beattie <sbeattie@ubuntu.com>
parent e573cc30
...@@ -68,6 +68,23 @@ void aa_dup_task_context(struct aa_task_cxt *new, const struct aa_task_cxt *old) ...@@ -68,6 +68,23 @@ void aa_dup_task_context(struct aa_task_cxt *new, const struct aa_task_cxt *old)
aa_get_profile(new->onexec); aa_get_profile(new->onexec);
} }
/**
* aa_get_task_profile - Get another task's profile
* @task: task to query (NOT NULL)
*
* Returns: counted reference to @task's profile
*/
struct aa_profile *aa_get_task_profile(struct task_struct *task)
{
struct aa_profile *p;
rcu_read_lock();
p = aa_get_profile(__aa_task_profile(task));
rcu_read_unlock();
return p;
}
/** /**
* aa_replace_current_profile - replace the current tasks profiles * aa_replace_current_profile - replace the current tasks profiles
* @profile: new profile (NOT NULL) * @profile: new profile (NOT NULL)
......
...@@ -62,17 +62,14 @@ static int may_change_ptraced_domain(struct task_struct *task, ...@@ -62,17 +62,14 @@ static int may_change_ptraced_domain(struct task_struct *task,
struct aa_profile *to_profile) struct aa_profile *to_profile)
{ {
struct task_struct *tracer; struct task_struct *tracer;
const struct cred *cred = NULL;
struct aa_profile *tracerp = NULL; struct aa_profile *tracerp = NULL;
int error = 0; int error = 0;
rcu_read_lock(); rcu_read_lock();
tracer = ptrace_parent(task); tracer = ptrace_parent(task);
if (tracer) { if (tracer)
/* released below */ /* released below */
cred = get_task_cred(tracer); tracerp = aa_get_task_profile(tracer);
tracerp = aa_cred_profile(cred);
}
/* not ptraced */ /* not ptraced */
if (!tracer || unconfined(tracerp)) if (!tracer || unconfined(tracerp))
...@@ -82,8 +79,7 @@ static int may_change_ptraced_domain(struct task_struct *task, ...@@ -82,8 +79,7 @@ static int may_change_ptraced_domain(struct task_struct *task,
out: out:
rcu_read_unlock(); rcu_read_unlock();
if (cred) aa_put_profile(tracerp);
put_cred(cred);
return error; return error;
} }
......
...@@ -80,23 +80,8 @@ int aa_replace_current_profile(struct aa_profile *profile); ...@@ -80,23 +80,8 @@ int aa_replace_current_profile(struct aa_profile *profile);
int aa_set_current_onexec(struct aa_profile *profile); int aa_set_current_onexec(struct aa_profile *profile);
int aa_set_current_hat(struct aa_profile *profile, u64 token); int aa_set_current_hat(struct aa_profile *profile, u64 token);
int aa_restore_previous_profile(u64 cookie); int aa_restore_previous_profile(u64 cookie);
struct aa_profile *aa_get_task_profile(struct task_struct *task);
/**
* __aa_task_is_confined - determine if @task has any confinement
* @task: task to check confinement of (NOT NULL)
*
* If @task != current needs to be called in RCU safe critical section
*/
static inline bool __aa_task_is_confined(struct task_struct *task)
{
struct aa_task_cxt *cxt = __task_cred(task)->security;
BUG_ON(!cxt || !cxt->profile);
if (unconfined(aa_newest_version(cxt->profile)))
return 0;
return 1;
}
/** /**
* aa_cred_profile - obtain cred's profiles * aa_cred_profile - obtain cred's profiles
...@@ -113,6 +98,30 @@ static inline struct aa_profile *aa_cred_profile(const struct cred *cred) ...@@ -113,6 +98,30 @@ static inline struct aa_profile *aa_cred_profile(const struct cred *cred)
return aa_newest_version(cxt->profile); return aa_newest_version(cxt->profile);
} }
/**
* __aa_task_profile - retrieve another task's profile
* @task: task to query (NOT NULL)
*
* Returns: @task's profile without incrementing its ref count
*
* If @task != current needs to be called in RCU safe critical section
*/
static inline struct aa_profile *__aa_task_profile(struct task_struct *task)
{
return aa_cred_profile(__task_cred(task));
}
/**
* __aa_task_is_confined - determine if @task has any confinement
* @task: task to check confinement of (NOT NULL)
*
* If @task != current needs to be called in RCU safe critical section
*/
static inline bool __aa_task_is_confined(struct task_struct *task)
{
return !unconfined(__aa_task_profile(task));
}
/** /**
* __aa_current_profile - find the current tasks confining profile * __aa_current_profile - find the current tasks confining profile
* *
......
...@@ -95,23 +95,18 @@ int aa_ptrace(struct task_struct *tracer, struct task_struct *tracee, ...@@ -95,23 +95,18 @@ int aa_ptrace(struct task_struct *tracer, struct task_struct *tracee,
* - tracer profile has CAP_SYS_PTRACE * - tracer profile has CAP_SYS_PTRACE
*/ */
struct aa_profile *tracer_p; struct aa_profile *tracer_p = aa_get_task_profile(tracer);
/* cred released below */
const struct cred *cred = get_task_cred(tracer);
int error = 0; int error = 0;
tracer_p = aa_cred_profile(cred);
if (!unconfined(tracer_p)) { if (!unconfined(tracer_p)) {
/* lcred released below */ struct aa_profile *tracee_p = aa_get_task_profile(tracee);
const struct cred *lcred = get_task_cred(tracee);
struct aa_profile *tracee_p = aa_cred_profile(lcred);
error = aa_may_ptrace(tracer, tracer_p, tracee_p, mode); error = aa_may_ptrace(tracer, tracer_p, tracee_p, mode);
error = aa_audit_ptrace(tracer_p, tracee_p, error); error = aa_audit_ptrace(tracer_p, tracee_p, error);
put_cred(lcred); aa_put_profile(tracee_p);
} }
put_cred(cred); aa_put_profile(tracer_p);
return error; return error;
} }
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment