[PATCH v2 05/25] Use lsmblob in security_audit_rule_match
Kees Cook
keescook at chromium.org
Wed Jun 19 04:55:57 UTC 2019
On Tue, Jun 18, 2019 at 04:05:31PM -0700, Casey Schaufler wrote:
> Change the secid parameter of security_audit_rule_match
> to a lsmblob structure pointer. Pass the entry from the
> lsmblob structure for the approprite slot to the LSM hook.
>
> Change the users of security_audit_rule_match to use the
> lsmblob instead of a u32. In some cases this requires a
> temporary conversion using lsmblob_init() that will go
> away when other interfaces get converted.
I like this much better with the LSM-infrastructure "slot" logic.
I do think it's be easier to read if the lsmblob instances were called
"blob" instead of "le" and "l"...
-Kees
>
> Signed-off-by: Casey Schaufler <casey at schaufler-ca.com>
> ---
> include/linux/security.h | 7 ++++---
> kernel/auditfilter.c | 4 +++-
> kernel/auditsc.c | 13 +++++++++----
> security/integrity/ima/ima.h | 4 ++--
> security/integrity/ima/ima_policy.c | 7 +++++--
> security/security.c | 14 ++++++++++++--
> 6 files changed, 35 insertions(+), 14 deletions(-)
>
> diff --git a/include/linux/security.h b/include/linux/security.h
> index 28d074866895..067fabc63e51 100644
> --- a/include/linux/security.h
> +++ b/include/linux/security.h
> @@ -1757,7 +1757,8 @@ static inline int security_key_getsecurity(struct key *key, char **_buffer)
> #ifdef CONFIG_SECURITY
> int security_audit_rule_init(u32 field, u32 op, char *rulestr, void **lsmrule);
> int security_audit_rule_known(struct audit_krule *krule);
> -int security_audit_rule_match(u32 secid, u32 field, u32 op, void *lsmrule);
> +int security_audit_rule_match(struct lsmblob *l, u32 field, u32 op,
> + void *lsmrule);
> void security_audit_rule_free(void *lsmrule);
>
> #else
> @@ -1773,8 +1774,8 @@ static inline int security_audit_rule_known(struct audit_krule *krule)
> return 0;
> }
>
> -static inline int security_audit_rule_match(u32 secid, u32 field, u32 op,
> - void *lsmrule)
> +static inline int security_audit_rule_match(struct lsmblob *l, u32 field,
> + u32 op, void *lsmrule)
> {
> return 0;
> }
> diff --git a/kernel/auditfilter.c b/kernel/auditfilter.c
> index 63f8b3f26fab..934ceae1ff70 100644
> --- a/kernel/auditfilter.c
> +++ b/kernel/auditfilter.c
> @@ -1324,6 +1324,7 @@ int audit_filter(int msgtype, unsigned int listtype)
> struct audit_field *f = &e->rule.fields[i];
> pid_t pid;
> u32 sid;
> + struct lsmblob le;
>
> switch (f->type) {
> case AUDIT_PID:
> @@ -1354,7 +1355,8 @@ int audit_filter(int msgtype, unsigned int listtype)
> case AUDIT_SUBJ_CLR:
> if (f->lsm_rule) {
> security_task_getsecid(current, &sid);
> - result = security_audit_rule_match(sid,
> + lsmblob_init(&le, sid);
> + result = security_audit_rule_match(&le,
> f->type, f->op, f->lsm_rule);
> }
> break;
> diff --git a/kernel/auditsc.c b/kernel/auditsc.c
> index d1eab1d4a930..93c74205ef40 100644
> --- a/kernel/auditsc.c
> +++ b/kernel/auditsc.c
> @@ -445,6 +445,7 @@ static int audit_filter_rules(struct task_struct *tsk,
> const struct cred *cred;
> int i, need_sid = 1;
> u32 sid;
> + struct lsmblob le;
> unsigned int sessionid;
>
> cred = rcu_dereference_check(tsk->cred, tsk == current || task_creation);
> @@ -630,7 +631,8 @@ static int audit_filter_rules(struct task_struct *tsk,
> security_task_getsecid(tsk, &sid);
> need_sid = 0;
> }
> - result = security_audit_rule_match(sid, f->type,
> + lsmblob_init(&le, sid);
> + result = security_audit_rule_match(&le, f->type,
> f->op,
> f->lsm_rule);
> }
> @@ -645,15 +647,17 @@ static int audit_filter_rules(struct task_struct *tsk,
> if (f->lsm_rule) {
> /* Find files that match */
> if (name) {
> + lsmblob_init(&le, name->osid);
> result = security_audit_rule_match(
> - name->osid,
> + &le,
> f->type,
> f->op,
> f->lsm_rule);
> } else if (ctx) {
> list_for_each_entry(n, &ctx->names_list, list) {
> + lsmblob_init(&le, n->osid);
> if (security_audit_rule_match(
> - n->osid,
> + &le,
> f->type,
> f->op,
> f->lsm_rule)) {
> @@ -665,7 +669,8 @@ static int audit_filter_rules(struct task_struct *tsk,
> /* Find ipc objects that match */
> if (!ctx || ctx->type != AUDIT_IPC)
> break;
> - if (security_audit_rule_match(ctx->ipc.osid,
> + lsmblob_init(&le, ctx->ipc.osid);
> + if (security_audit_rule_match(&le,
> f->type, f->op,
> f->lsm_rule))
> ++result;
> diff --git a/security/integrity/ima/ima.h b/security/integrity/ima/ima.h
> index d213e835c498..fe5e921d621d 100644
> --- a/security/integrity/ima/ima.h
> +++ b/security/integrity/ima/ima.h
> @@ -307,8 +307,8 @@ static inline int security_filter_rule_init(u32 field, u32 op, char *rulestr,
> return -EINVAL;
> }
>
> -static inline int security_filter_rule_match(u32 secid, u32 field, u32 op,
> - void *lsmrule)
> +static inline int security_filter_rule_match(struct lsmblob *l, u32 field,
> + u32 op, void *lsmrule)
> {
> return -EINVAL;
> }
> diff --git a/security/integrity/ima/ima_policy.c b/security/integrity/ima/ima_policy.c
> index e0cc323f948f..ae525a89e07f 100644
> --- a/security/integrity/ima/ima_policy.c
> +++ b/security/integrity/ima/ima_policy.c
> @@ -327,6 +327,7 @@ static bool ima_match_rules(struct ima_rule_entry *rule, struct inode *inode,
> for (i = 0; i < MAX_LSM_RULES; i++) {
> int rc = 0;
> u32 osid;
> + struct lsmblob le;
> int retried = 0;
>
> if (!rule->lsm[i].rule)
> @@ -337,7 +338,8 @@ static bool ima_match_rules(struct ima_rule_entry *rule, struct inode *inode,
> case LSM_OBJ_ROLE:
> case LSM_OBJ_TYPE:
> security_inode_getsecid(inode, &osid);
> - rc = security_filter_rule_match(osid,
> + lsmblob_init(&le, osid);
> + rc = security_filter_rule_match(&le,
> rule->lsm[i].type,
> Audit_equal,
> rule->lsm[i].rule);
> @@ -345,7 +347,8 @@ static bool ima_match_rules(struct ima_rule_entry *rule, struct inode *inode,
> case LSM_SUBJ_USER:
> case LSM_SUBJ_ROLE:
> case LSM_SUBJ_TYPE:
> - rc = security_filter_rule_match(secid,
> + lsmblob_init(&le, secid);
> + rc = security_filter_rule_match(&le,
> rule->lsm[i].type,
> Audit_equal,
> rule->lsm[i].rule);
> diff --git a/security/security.c b/security/security.c
> index 5aa3c052d702..45541053df89 100644
> --- a/security/security.c
> +++ b/security/security.c
> @@ -2447,9 +2447,19 @@ void security_audit_rule_free(void *lsmrule)
> call_void_hook(audit_rule_free, lsmrule);
> }
>
> -int security_audit_rule_match(u32 secid, u32 field, u32 op, void *lsmrule)
> +int security_audit_rule_match(struct lsmblob *l, u32 field, u32 op,
> + void *lsmrule)
> {
> - return call_int_hook(audit_rule_match, 0, secid, field, op, lsmrule);
> + struct security_hook_list *hp;
> + int rc;
> +
> + hlist_for_each_entry(hp, &security_hook_heads.audit_rule_match, list) {
> + rc = hp->hook.audit_rule_match(l->secid[hp->slot], field,
> + op, lsmrule);
> + if (rc != 0)
> + return rc;
> + }
> + return 0;
> }
> #endif /* CONFIG_AUDIT */
>
> --
> 2.20.1
>
--
Kees Cook
More information about the Linux-security-module-archive
mailing list