Linux-audit Archive on lore.kernel.org
 help / color / mirror / Atom feed
From: Casey Schaufler <casey@schaufler-ca.com>
To: Paul Moore <paul@paul-moore.com>
Cc: john.johansen@canonical.com, selinux@vger.kernel.org,
	jmorris@namei.org, linux-kernel@vger.kernel.org,
	linux-security-module@vger.kernel.org, linux-audit@redhat.com,
	casey.schaufler@intel.com, sds@tycho.nsa.gov
Subject: Re: [PATCH v32 24/28] Audit: Add framework for auxiliary records
Date: Thu, 3 Mar 2022 18:13:47 -0800	[thread overview]
Message-ID: <0bbd2d61-415f-08f2-251e-2dd6b8991d6a@schaufler-ca.com> (raw)
In-Reply-To: <CAHC9VhS6An9L7LavYTP57QXdOugQf62NCjDmS4kQq3wk+yemcg@mail.gmail.com>

On 3/3/2022 3:36 PM, Paul Moore wrote:
> On Wed, Feb 2, 2022 at 7:20 PM Casey Schaufler <casey@schaufler-ca.com> wrote:
>> Add a list for auxiliary record data to the audit_buffer structure.
>> Add the audit_stamp information to the audit_buffer as there's no
>> guarantee that there will be an audit_context containing the stamp
>> associated with the event. At audit_log_end() time create auxiliary
>> records (none are currently defined) as have been added to the list.
>>
>> Signed-off-by: Casey Schaufler <casey@schaufler-ca.com>
>> ---
>>   kernel/audit.c | 84 ++++++++++++++++++++++++++++++++++++++++++++------
>>   1 file changed, 74 insertions(+), 10 deletions(-)
>>
>> diff --git a/kernel/audit.c b/kernel/audit.c
>> index f012c3786264..559fb14e0380 100644
>> --- a/kernel/audit.c
>> +++ b/kernel/audit.c
>> @@ -191,15 +191,25 @@ static struct audit_ctl_mutex {
>>    * should be at least that large. */
>>   #define AUDIT_BUFSIZ 1024
>>
>> +/* The audit_context_entry contains data required to create an
>> + * auxiliary record.
>> + */
>> +struct audit_context_entry {
>> +       struct list_head        list;
>> +       int                     type;   /* Audit record type */
>> +};
> Looking at how this ends up being used later in the patchset I think
> we would be better off if we stored a fully formed audit_buffer in the
> struct above instead of data fields which we would use to generate an
> audit_buffer in audit_log_end().  This helps tie the buffer generation
> logic in with the existing code with which it is most closely related,
> it allows us to report errors back to the caller as audit_log_end()
> doesn't historically return an error code, and it helps us get ahead
> of any future data lifetime issues we might run into by storing the
> data in this audit struct.

OK, I'll buy that.

> This would also simplify things with respect to the audit_buffer
> struct.  Instead of having a dedicated struct for the aux data, you
> could simply leverage the existing sk_buff list mechanisms:

I can't say that "simply" is the adverb I'd choose, but sure,
I can do this.

>    struct audit_buffer {
>      struct sk_buff *skb;  /* part of @skb_list, kept for audit_log funcs */
>      struct sk_buff_head skb_list;
>      struct audit_context *ctx;
>      struct audit_stamp stamp;
>      gfp_t gfp_mask;
>    }
>
> The only sneaky bit in the struct above is that we likely want to
> preserve audit_buffer::skb as a dedicated skb pointer so we don't have
> to modify all of the audit_log_*() functions; you could of course, but
> I'm guessing there is little appetite for that in the context of this
> patchset.

I will give it a go without making the massive interface change.

> Adding a new aux record would involve calling some private audit
> function (no one outside of the audit subsystem should need access)
> that would allocate a new skb similar to what we do in
> audit_buffer_alloc() and add it to the end of the sk_buff_head list
> via skb_queue_tail() and resetting audit_buffer::skb to point to the
> newly allocated skb.

Good naming may be tricky as we need to indicate that a new buffer is
being allocated for an attached aux record and that the buffer to which
it's being attached is going to temporarily be in a curious state.
audit_buffer_add_aux() seems wordy, but it's what I'll start with lacking
a better suggestion.

>    This would allow all of the existing
> audit_log*() functions to work correctly, and when you are done you
> can restore the "main" skb with skb_peek().

audit_buffer_close_aux()

>    If for some reason you
> need to fail the new aux record mid-creation you just dequeue the list
> tail, free the skb, and skb_peek() the "main" skb back into place.

Why do I always get nervous when I hear "just" and "skb" in the
same sentence?

>>   /* The audit_buffer is used when formatting an audit record.  The caller
>>    * locks briefly to get the record off the freelist or to allocate the
>>    * buffer, and locks briefly to send the buffer to the netlink layer or
>>    * to place it on a transmit queue.  Multiple audit_buffers can be in
>>    * use simultaneously. */
>>   struct audit_buffer {
>> -       struct sk_buff       *skb;      /* formatted skb ready to send */
>> -       struct audit_context *ctx;      /* NULL or associated context */
>> -       gfp_t                gfp_mask;
>> +       struct sk_buff          *skb;   /* formatted skb ready to send */
>> +       struct audit_context    *ctx;   /* NULL or associated context */
>> +       struct list_head        aux_records;    /* aux record data */
>> +       struct audit_stamp      stamp;  /* event stamp */
>> +       gfp_t                   gfp_mask;
>>   };
> ...
>
>> @@ -2408,6 +2418,60 @@ void audit_log_end(struct audit_buffer *ab)
>>                  wake_up_interruptible(&kauditd_wait);
>>          } else
>>                  audit_log_lost("rate limit exceeded");
>> +}
>> +
>> +/**
>> + * audit_log_end - end one audit record
>> + * @ab: the audit_buffer
>> + *
>> + * Let __audit_log_end() handle the message while the buffer housekeeping
>> + * is done here.
>> + * If there are other records that have been deferred for the event
>> + * create them here.
>> + */
>> +void audit_log_end(struct audit_buffer *ab)
>> +{
>> +       struct audit_context_entry *entry;
>> +       struct audit_context mcontext;
>> +       struct audit_context *mctx;
>> +       struct audit_buffer *mab;
>> +       struct list_head *l;
>> +       struct list_head *n;
>> +
>> +       if (!ab)
>> +               return;
>> +
>> +       __audit_log_end(ab);
>> +
>> +       if (list_empty(&ab->aux_records)) {
>> +               audit_buffer_free(ab);
>> +               return;
>> +       }
>> +
>> +       if (ab->ctx == NULL) {
>> +               mcontext.stamp = ab->stamp;
>> +               mctx = &mcontext;
>> +       } else
>> +               mctx = ab->ctx;
>> +
>> +       list_for_each_safe(l, n, &ab->aux_records) {
>> +               entry = list_entry(l, struct audit_context_entry, list);
>> +               mab = audit_log_start(mctx, ab->gfp_mask, entry->type);
>> +               if (!mab) {
>> +                       audit_panic("alloc error in audit_log_end");
>> +                       continue;
>> +               }
>> +               switch (entry->type) {
>> +               /* Don't know of any quite yet. */
>> +               default:
>> +                       audit_panic("Unknown type in audit_log_end");
>> +                       break;
>> +               }
>> +               __audit_log_end(mab);
>> +               audit_buffer_free(mab);
>> +               list_del(&entry->list);
>> +               kfree(entry);
>> +       }
>>
>>          audit_buffer_free(ab);
>>   }
> This would also allow you to simplify audit_log_end() greatly, I'm
> sure I'm missing a detail or two, but I suspect it would end up
> looking something like this:

Agreed. That is a much better fit for the existing code flow.

>
>    void __audit_log_end(skb)
>    {
>      /* ... current audit_log_end() but with only the sk_buff ... */
>    }
>
>    void audit_log_end(ab)
>    {
>      if (!ab)
>        return;
>      while ((skb = skb_dequeue(ab->skb_list)))
>        __audit_log_end(skb);
>      audit_buffer_free(ab);
>    }
>
>
> --
> paul-moore.com

--
Linux-audit mailing list
Linux-audit@redhat.com
https://listman.redhat.com/mailman/listinfo/linux-audit


  reply	other threads:[~2022-03-04  2:14 UTC|newest]

Thread overview: 41+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
     [not found] <20220202235323.23929-1-casey.ref@schaufler-ca.com>
2022-02-02 23:52 ` [PATCH v32 00/28] LSM: Module stacking for AppArmor Casey Schaufler
2022-02-02 23:52   ` [PATCH v32 01/28] integrity: disassociate ima_filter_rule from security_audit_rule Casey Schaufler
2022-02-02 23:52   ` [PATCH v32 02/28] LSM: Infrastructure management of the sock security Casey Schaufler
2022-02-02 23:52   ` [PATCH v32 03/28] LSM: Add the lsmblob data structure Casey Schaufler
2022-03-04 10:48     ` Mickaël Salaün
2022-03-04 19:14       ` Casey Schaufler
2022-02-02 23:52   ` [PATCH v32 04/28] LSM: provide lsm name and id slot mappings Casey Schaufler
2022-02-02 23:53   ` [PATCH v32 05/28] IMA: avoid label collisions with stacked LSMs Casey Schaufler
2022-02-02 23:53   ` [PATCH v32 06/28] LSM: Use lsmblob in security_audit_rule_match Casey Schaufler
2022-02-02 23:53   ` [PATCH v32 07/28] LSM: Use lsmblob in security_kernel_act_as Casey Schaufler
2022-02-02 23:53   ` [PATCH v32 08/28] LSM: Use lsmblob in security_secctx_to_secid Casey Schaufler
2022-02-02 23:53   ` [PATCH v32 09/28] LSM: Use lsmblob in security_secid_to_secctx Casey Schaufler
2022-02-02 23:53   ` [PATCH v32 10/28] LSM: Use lsmblob in security_ipc_getsecid Casey Schaufler
2022-02-02 23:53   ` [PATCH v32 11/28] LSM: Use lsmblob in security_current_getsecid Casey Schaufler
2022-02-02 23:53   ` [PATCH v32 12/28] LSM: Use lsmblob in security_inode_getsecid Casey Schaufler
2022-02-02 23:53   ` [PATCH v32 13/28] LSM: Use lsmblob in security_cred_getsecid Casey Schaufler
2022-02-02 23:53   ` [PATCH v32 14/28] LSM: Specify which LSM to display Casey Schaufler
2022-02-02 23:53   ` [PATCH v32 15/28] LSM: Ensure the correct LSM context releaser Casey Schaufler
2022-02-02 23:53   ` [PATCH v32 16/28] LSM: Use lsmcontext in security_secid_to_secctx Casey Schaufler
2022-02-02 23:53   ` [PATCH v32 17/28] LSM: Use lsmcontext in security_inode_getsecctx Casey Schaufler
2022-02-02 23:53   ` [PATCH v32 18/28] LSM: security_secid_to_secctx in netlink netfilter Casey Schaufler
2022-02-02 23:53   ` [PATCH v32 19/28] NET: Store LSM netlabel data in a lsmblob Casey Schaufler
2022-02-02 23:53   ` [PATCH v32 20/28] binder: Pass LSM identifier for confirmation Casey Schaufler
2022-02-02 23:53   ` [PATCH v32 21/28] LSM: Extend security_secid_to_secctx to include module selection Casey Schaufler
2022-02-02 23:53   ` [PATCH v32 22/28] Audit: Keep multiple LSM data in audit_names Casey Schaufler
2022-02-02 23:53   ` [PATCH v32 23/28] Audit: Create audit_stamp structure Casey Schaufler
2022-02-02 23:53   ` [PATCH v32 24/28] Audit: Add framework for auxiliary records Casey Schaufler
2022-03-02 22:32     ` Casey Schaufler
2022-03-03 22:27       ` Paul Moore
2022-03-03 22:33         ` Casey Schaufler
2022-03-03 22:43           ` Paul Moore
2022-03-03 22:55             ` Casey Schaufler
2022-03-03 23:36     ` Paul Moore
2022-03-04  2:13       ` Casey Schaufler [this message]
2022-03-04 14:43         ` Paul Moore
2022-02-02 23:53   ` [PATCH v32 25/28] Audit: Add record for multiple task security contexts Casey Schaufler
2022-02-02 23:53   ` [PATCH v32 26/28] Audit: Add record for multiple object " Casey Schaufler
2022-03-03 23:36     ` Paul Moore
2022-03-04  1:26       ` Casey Schaufler
2022-02-02 23:53   ` [PATCH v32 27/28] LSM: Add /proc attr entry for full LSM context Casey Schaufler
2022-02-02 23:53   ` [PATCH v32 28/28] AppArmor: Remove the exclusive flag Casey Schaufler

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=0bbd2d61-415f-08f2-251e-2dd6b8991d6a@schaufler-ca.com \
    --to=casey@schaufler-ca.com \
    --cc=casey.schaufler@intel.com \
    --cc=jmorris@namei.org \
    --cc=john.johansen@canonical.com \
    --cc=linux-audit@redhat.com \
    --cc=linux-kernel@vger.kernel.org \
    --cc=linux-security-module@vger.kernel.org \
    --cc=paul@paul-moore.com \
    --cc=sds@tycho.nsa.gov \
    --cc=selinux@vger.kernel.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox