]> err.no Git - linux-2.6/blobdiff - kernel/auditsc.c
[AUDIT] return EINTR not ERESTART*
[linux-2.6] / kernel / auditsc.c
index 80ecab0942ef5fc6753db68ef64189ba2c2e718a..ce8c957201efbe2e95d731e07a31c1e277ed5618 100644 (file)
@@ -192,7 +192,6 @@ struct audit_context {
        enum audit_state    state;
        unsigned int        serial;     /* serial number for record */
        struct timespec     ctime;      /* time of syscall entry */
-       uid_t               loginuid;   /* login uid (identity) */
        int                 major;      /* syscall number */
        unsigned long       argv[4];    /* syscall arguments */
        int                 return_valid; /* return code is valid */
@@ -506,7 +505,7 @@ static int audit_filter_rules(struct task_struct *tsk,
                case AUDIT_LOGINUID:
                        result = 0;
                        if (ctx)
-                               result = audit_comparator(ctx->loginuid, f->op, f->val);
+                               result = audit_comparator(tsk->loginuid, f->op, f->val);
                        break;
                case AUDIT_SUBJ_USER:
                case AUDIT_SUBJ_ROLE:
@@ -702,7 +701,24 @@ static inline struct audit_context *audit_get_context(struct task_struct *tsk,
        if (likely(!context))
                return NULL;
        context->return_valid = return_valid;
-       context->return_code  = return_code;
+
+       /*
+        * we need to fix up the return code in the audit logs if the actual
+        * return codes are later going to be fixed up by the arch specific
+        * signal handlers
+        *
+        * This is actually a test for:
+        * (rc == ERESTARTSYS ) || (rc == ERESTARTNOINTR) ||
+        * (rc == ERESTARTNOHAND) || (rc == ERESTART_RESTARTBLOCK)
+        *
+        * but is faster than a bunch of ||
+        */
+       if (unlikely(return_code <= -ERESTARTSYS) &&
+           (return_code >= -ERESTART_RESTARTBLOCK) &&
+           (return_code != -ENOIOCTLCMD))
+               context->return_code = -EINTR;
+       else
+               context->return_code  = return_code;
 
        if (context->in_syscall && !context->dummy && !context->auditable) {
                enum audit_state state;
@@ -783,11 +799,8 @@ static inline void audit_free_aux(struct audit_context *context)
 static inline void audit_zero_context(struct audit_context *context,
                                      enum audit_state state)
 {
-       uid_t loginuid = context->loginuid;
-
        memset(context, 0, sizeof(*context));
        context->state      = state;
-       context->loginuid   = loginuid;
 }
 
 static inline struct audit_context *audit_alloc_context(enum audit_state state)
@@ -826,11 +839,6 @@ int audit_alloc(struct task_struct *tsk)
                return -ENOMEM;
        }
 
-                               /* Preserve login uid */
-       context->loginuid = -1;
-       if (current->audit_context)
-               context->loginuid = current->audit_context->loginuid;
-
        tsk->audit_context  = context;
        set_tsk_thread_flag(tsk, TIF_SYSCALL_AUDIT);
        return 0;
@@ -1047,7 +1055,7 @@ static void audit_log_exit(struct audit_context *context, struct task_struct *ts
                  context->name_count,
                  context->ppid,
                  context->pid,
-                 context->loginuid,
+                 tsk->loginuid,
                  context->uid,
                  context->gid,
                  context->euid, context->suid, context->fsuid,
@@ -1615,7 +1623,7 @@ static void audit_copy_inode(struct audit_names *name, const struct inode *inode
 /**
  * audit_inode - store the inode and device from a lookup
  * @name: name being audited
- * @inode: inode being audited
+ * @dentry: dentry being audited
  *
  * Called from fs/namei.c:path_lookup().
  */
@@ -1650,7 +1658,7 @@ void __audit_inode(const char *name, const struct dentry *dentry)
 /**
  * audit_inode_child - collect inode info for created/removed objects
  * @dname: inode's dentry name
- * @inode: inode being audited
+ * @dentry: dentry being audited
  * @parent: inode of dentry parent
  *
  * For syscalls that create or remove filesystem objects, audit_inode
@@ -1779,38 +1787,22 @@ int audit_set_loginuid(struct task_struct *task, uid_t loginuid)
 {
        struct audit_context *context = task->audit_context;
 
-       if (context) {
-               /* Only log if audit is enabled */
-               if (context->in_syscall) {
-                       struct audit_buffer *ab;
-
-                       ab = audit_log_start(NULL, GFP_KERNEL, AUDIT_LOGIN);
-                       if (ab) {
-                               audit_log_format(ab, "login pid=%d uid=%u "
-                                       "old auid=%u new auid=%u",
-                                       task->pid, task->uid,
-                                       context->loginuid, loginuid);
-                               audit_log_end(ab);
-                       }
+       if (context && context->in_syscall) {
+               struct audit_buffer *ab;
+
+               ab = audit_log_start(NULL, GFP_KERNEL, AUDIT_LOGIN);
+               if (ab) {
+                       audit_log_format(ab, "login pid=%d uid=%u "
+                               "old auid=%u new auid=%u",
+                               task->pid, task->uid,
+                               task->loginuid, loginuid);
+                       audit_log_end(ab);
                }
-               context->loginuid = loginuid;
        }
+       task->loginuid = loginuid;
        return 0;
 }
 
-/**
- * audit_get_loginuid - get the loginuid for an audit_context
- * @ctx: the audit_context
- *
- * Returns the context's loginuid or -1 if @ctx is NULL.
- */
-uid_t audit_get_loginuid(struct audit_context *ctx)
-{
-       return ctx ? ctx->loginuid : -1;
-}
-
-EXPORT_SYMBOL(audit_get_loginuid);
-
 /**
  * __audit_mq_open - record audit data for a POSIX MQ open
  * @oflag: open flag
@@ -2216,8 +2208,8 @@ int __audit_signal_info(int sig, struct task_struct *t)
        if (audit_pid && t->tgid == audit_pid) {
                if (sig == SIGTERM || sig == SIGHUP || sig == SIGUSR1) {
                        audit_sig_pid = tsk->pid;
-                       if (ctx)
-                               audit_sig_uid = ctx->loginuid;
+                       if (tsk->loginuid != -1)
+                               audit_sig_uid = tsk->loginuid;
                        else
                                audit_sig_uid = tsk->uid;
                        selinux_get_task_sid(tsk, &audit_sig_sid);
@@ -2273,7 +2265,7 @@ void audit_core_dumps(long signr)
 
        ab = audit_log_start(NULL, GFP_KERNEL, AUDIT_ANOM_ABEND);
        audit_log_format(ab, "auid=%u uid=%u gid=%u",
-                       audit_get_loginuid(current->audit_context),
+                       audit_get_loginuid(current),
                        current->uid, current->gid);
        selinux_get_task_sid(current, &sid);
        if (sid) {