support single arguments that are large, not just large lists of execve 
args.
    This also means we never have to get a kernel buffer larger than
    MAX_EXECVE_AUDIT_LEN no matter how large the argument is.  Before this patch
    we could need to allocate 32 consecutive pages to hold one argument which 
could
    pretty easily oom.
    
    a single argument larger than MAX_EXECVE_AUDIT_LEN is broken into multiple
    records and have a format like   a10[0] a10[1] a10[2] etc.
    
    Signed-off-by: Eric Paris <[EMAIL PROTECTED]>
---

example audit log (about 50k long) for the whole patch series can be
found at http://people.redhat.com/~eparis/audit/audit.log the execve in
question was something like:

program_name [about 50 arguments] [one argument which is about 17k long] [about 
1000 arguments]

 kernel/auditsc.c |   42 +++++++++++++++++++++++++++++++++++++++++
 1 files changed, 42 insertions(+), 0 deletions(-)

diff --git a/kernel/auditsc.c b/kernel/auditsc.c
index 4176db6..ffc8d4b 100644
--- a/kernel/auditsc.c
+++ b/kernel/auditsc.c
@@ -853,6 +853,48 @@ static void audit_log_execve_info(struct audit_context 
*context,
                        send_sig(SIGKILL, current, 0);
                }
 
+               if (unlikely(len > MAX_EXECVE_AUDIT_LEN)) {
+                       /* deal with single arugments > MAX_EXECVE_AUDIT_LEN */
+                       int j;
+                       const long tmplen = sizeof(char) * MAX_EXECVE_AUDIT_LEN;
+
+                       buf = kmalloc(tmplen + 1, GFP_KERNEL);
+                       if (!buf) {
+                               audit_panic("out of memory for argv string\n");
+                               return;
+                       }
+                       buf[tmplen] = '\0';
+                       for (j = 0; len > 0; j++) {
+                               if (len > tmplen) {
+                                       ret = copy_from_user(buf, p, tmplen);
+                                       p += tmplen;
+                                       len -= tmplen;
+                               } else {
+                                       ret = copy_from_user(buf, p, len);
+                                       /* p is at the next arg */
+                                       p += len;
+                                       /* 27 is the max length of a%d[%d] */
+                                       len_sent = len + 27;
+                                       len  = 0;
+                               }
+                               if (ret) {
+                                       WARN_ON(1);
+                                       send_sig(SIGKILL, current, 0);
+                               }
+                               audit_log_end(*ab);
+                               *ab = audit_log_start(context, GFP_KERNEL,
+                                                     AUDIT_EXECVE);
+                               if (!*ab) {
+                                       kfree(buf);
+                                       return;
+                               }
+                               audit_log_format(*ab, "a%d[%d]=", i, j);
+                               audit_log_untrustedstring(*ab, buf);
+                               audit_log_format(*ab, "\n");
+                       }
+                       continue;
+               }
+
                buf = kmalloc(len, GFP_KERNEL);
                if (!buf) {
                        audit_panic("out of memory for argv string\n");


-
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Please read the FAQ at  http://www.tux.org/lkml/

Reply via email to