From mboxrd@z Thu Jan 1 00:00:00 1970 From: Eric Paris Subject: Re: [PATCH 2/5] audit: complex interfield comparison helper Date: Wed, 04 Jan 2012 15:51:55 -0500 Message-ID: <1325710315.17118.3.camel@localhost> References: <1325710033-32133-1-git-send-email-eparis@redhat.com> <1325710033-32133-2-git-send-email-eparis@redhat.com> Mime-Version: 1.0 Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: 7bit Return-path: In-Reply-To: <1325710033-32133-2-git-send-email-eparis@redhat.com> List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Sender: linux-audit-bounces@redhat.com Errors-To: linux-audit-bounces@redhat.com To: linux-audit@redhat.com List-Id: linux-audit@redhat.com On Wed, 2012-01-04 at 15:47 -0500, Eric Paris wrote: > Rather than code the same loop over and over implement a helper function which > uses some pointer magic to make it generic enough to be used numerous places > as we implement more audit interfield comparisons > > Signed-off-by: Eric Paris > --- The change from the last version is simply to take a uid_t and a pointer to a struct audit_name instead of taking two pointers. This allows us to get the first uid from either a cred or the task struct. > kernel/auditsc.c | 50 +++++++++++++++++++++++++++++++++++++++----------- > 1 files changed, 39 insertions(+), 11 deletions(-) > > diff --git a/kernel/auditsc.c b/kernel/auditsc.c > index efb1763..45c13c5 100644 > --- a/kernel/auditsc.c > +++ b/kernel/auditsc.c > @@ -463,25 +463,53 @@ static int match_tree_refs(struct audit_context *ctx, struct audit_tree *tree) > return 0; > } > > +static int audit_compare_id(uid_t uid1, > + struct audit_names *name, > + unsigned long name_offset, > + struct audit_field *f, > + struct audit_context *ctx) > +{ > + struct audit_names *n; > + unsigned long addr; > + uid_t uid2; > + int rc; > + > + if (name) { > + addr = (unsigned long)name; > + addr += name_offset; > + > + uid2 = *(uid_t *)addr; > + rc = audit_comparator(uid1, f->op, uid2); > + if (rc) > + return rc; > + } > + > + if (ctx) { > + list_for_each_entry(n, &ctx->names_list, list) { > + addr = (unsigned long)n; > + addr += name_offset; > + > + uid2 = *(uid_t *)addr; > + > + rc = audit_comparator(uid1, f->op, uid2); > + if (rc) > + return rc; > + } > + } > + return 0; > +} > + > static int audit_field_compare(struct task_struct *tsk, > const struct cred *cred, > struct audit_field *f, > struct audit_context *ctx, > struct audit_names *name) > { > - struct audit_names *n; > - > switch (f->val) { > case AUDIT_COMPARE_UID_TO_OBJ_UID: > - if (name) { > - return audit_comparator(cred->uid, f->op, name->uid); > - } else if (ctx) { > - list_for_each_entry(n, &ctx->names_list, list) { > - if (audit_comparator(cred->uid, f->op, n->uid)) > - return 1; > - } > - } > - break; > + return audit_compare_id(cred->uid, > + name, offsetof(struct audit_names, uid), > + f, ctx); > default: > WARN(1, "Missing AUDIT_COMPARE define. Report as a bug\n"); > return 0;