diff options
-rw-r--r-- | include/linux/audit.h | 2 | ||||
-rw-r--r-- | include/linux/init_task.h | 7 | ||||
-rw-r--r-- | include/linux/sched.h | 3 | ||||
-rw-r--r-- | kernel/auditsc.c | 56 |
4 files changed, 26 insertions, 42 deletions
diff --git a/include/linux/audit.h b/include/linux/audit.h index f63117fab305..d7c6a12f4d1c 100644 --- a/include/linux/audit.h +++ b/include/linux/audit.h | |||
@@ -409,7 +409,7 @@ extern unsigned int audit_serial(void); | |||
409 | extern void auditsc_get_stamp(struct audit_context *ctx, | 409 | extern void auditsc_get_stamp(struct audit_context *ctx, |
410 | struct timespec *t, unsigned int *serial); | 410 | struct timespec *t, unsigned int *serial); |
411 | extern int audit_set_loginuid(struct task_struct *task, uid_t loginuid); | 411 | extern int audit_set_loginuid(struct task_struct *task, uid_t loginuid); |
412 | extern uid_t audit_get_loginuid(struct task_struct *task); | 412 | #define audit_get_loginuid(t) ((t)->loginuid) |
413 | extern void audit_log_task_context(struct audit_buffer *ab); | 413 | extern void audit_log_task_context(struct audit_buffer *ab); |
414 | extern int __audit_ipc_obj(struct kern_ipc_perm *ipcp); | 414 | extern int __audit_ipc_obj(struct kern_ipc_perm *ipcp); |
415 | extern int __audit_ipc_set_perm(unsigned long qbytes, uid_t uid, gid_t gid, mode_t mode); | 415 | extern int __audit_ipc_set_perm(unsigned long qbytes, uid_t uid, gid_t gid, mode_t mode); |
diff --git a/include/linux/init_task.h b/include/linux/init_task.h index e6b3f7080679..ea3e9efd7396 100644 --- a/include/linux/init_task.h +++ b/include/linux/init_task.h | |||
@@ -114,6 +114,12 @@ extern struct group_info init_groups; | |||
114 | .pid = &init_struct_pid, \ | 114 | .pid = &init_struct_pid, \ |
115 | } | 115 | } |
116 | 116 | ||
117 | #ifdef CONFIG_AUDITSYSCALL | ||
118 | #define INIT_IDS \ | ||
119 | .loginuid = -1, | ||
120 | #else | ||
121 | #define INIT_IDS | ||
122 | #endif | ||
117 | /* | 123 | /* |
118 | * INIT_TASK is used to set up the first task table, touch at | 124 | * INIT_TASK is used to set up the first task table, touch at |
119 | * your own risk!. Base=0, limit=0x1fffff (=2MB) | 125 | * your own risk!. Base=0, limit=0x1fffff (=2MB) |
@@ -173,6 +179,7 @@ extern struct group_info init_groups; | |||
173 | [PIDTYPE_SID] = INIT_PID_LINK(PIDTYPE_SID), \ | 179 | [PIDTYPE_SID] = INIT_PID_LINK(PIDTYPE_SID), \ |
174 | }, \ | 180 | }, \ |
175 | .dirties = INIT_PROP_LOCAL_SINGLE(dirties), \ | 181 | .dirties = INIT_PROP_LOCAL_SINGLE(dirties), \ |
182 | INIT_IDS \ | ||
176 | INIT_TRACE_IRQFLAGS \ | 183 | INIT_TRACE_IRQFLAGS \ |
177 | INIT_LOCKDEP \ | 184 | INIT_LOCKDEP \ |
178 | } | 185 | } |
diff --git a/include/linux/sched.h b/include/linux/sched.h index 6c333579d9da..5e2730389089 100644 --- a/include/linux/sched.h +++ b/include/linux/sched.h | |||
@@ -1139,6 +1139,9 @@ struct task_struct { | |||
1139 | void *security; | 1139 | void *security; |
1140 | #endif | 1140 | #endif |
1141 | struct audit_context *audit_context; | 1141 | struct audit_context *audit_context; |
1142 | #ifdef CONFIG_AUDITSYSCALL | ||
1143 | uid_t loginuid; | ||
1144 | #endif | ||
1142 | seccomp_t seccomp; | 1145 | seccomp_t seccomp; |
1143 | 1146 | ||
1144 | /* Thread group tracking */ | 1147 | /* Thread group tracking */ |
diff --git a/kernel/auditsc.c b/kernel/auditsc.c index bd4e0a2443fb..c95173a194bf 100644 --- a/kernel/auditsc.c +++ b/kernel/auditsc.c | |||
@@ -192,7 +192,6 @@ struct audit_context { | |||
192 | enum audit_state state; | 192 | enum audit_state state; |
193 | unsigned int serial; /* serial number for record */ | 193 | unsigned int serial; /* serial number for record */ |
194 | struct timespec ctime; /* time of syscall entry */ | 194 | struct timespec ctime; /* time of syscall entry */ |
195 | uid_t loginuid; /* login uid (identity) */ | ||
196 | int major; /* syscall number */ | 195 | int major; /* syscall number */ |
197 | unsigned long argv[4]; /* syscall arguments */ | 196 | unsigned long argv[4]; /* syscall arguments */ |
198 | int return_valid; /* return code is valid */ | 197 | int return_valid; /* return code is valid */ |
@@ -506,7 +505,7 @@ static int audit_filter_rules(struct task_struct *tsk, | |||
506 | case AUDIT_LOGINUID: | 505 | case AUDIT_LOGINUID: |
507 | result = 0; | 506 | result = 0; |
508 | if (ctx) | 507 | if (ctx) |
509 | result = audit_comparator(ctx->loginuid, f->op, f->val); | 508 | result = audit_comparator(tsk->loginuid, f->op, f->val); |
510 | break; | 509 | break; |
511 | case AUDIT_SUBJ_USER: | 510 | case AUDIT_SUBJ_USER: |
512 | case AUDIT_SUBJ_ROLE: | 511 | case AUDIT_SUBJ_ROLE: |
@@ -783,11 +782,8 @@ static inline void audit_free_aux(struct audit_context *context) | |||
783 | static inline void audit_zero_context(struct audit_context *context, | 782 | static inline void audit_zero_context(struct audit_context *context, |
784 | enum audit_state state) | 783 | enum audit_state state) |
785 | { | 784 | { |
786 | uid_t loginuid = context->loginuid; | ||
787 | |||
788 | memset(context, 0, sizeof(*context)); | 785 | memset(context, 0, sizeof(*context)); |
789 | context->state = state; | 786 | context->state = state; |
790 | context->loginuid = loginuid; | ||
791 | } | 787 | } |
792 | 788 | ||
793 | static inline struct audit_context *audit_alloc_context(enum audit_state state) | 789 | static inline struct audit_context *audit_alloc_context(enum audit_state state) |
@@ -826,11 +822,6 @@ int audit_alloc(struct task_struct *tsk) | |||
826 | return -ENOMEM; | 822 | return -ENOMEM; |
827 | } | 823 | } |
828 | 824 | ||
829 | /* Preserve login uid */ | ||
830 | context->loginuid = -1; | ||
831 | if (current->audit_context) | ||
832 | context->loginuid = current->audit_context->loginuid; | ||
833 | |||
834 | tsk->audit_context = context; | 825 | tsk->audit_context = context; |
835 | set_tsk_thread_flag(tsk, TIF_SYSCALL_AUDIT); | 826 | set_tsk_thread_flag(tsk, TIF_SYSCALL_AUDIT); |
836 | return 0; | 827 | return 0; |
@@ -1047,7 +1038,7 @@ static void audit_log_exit(struct audit_context *context, struct task_struct *ts | |||
1047 | context->name_count, | 1038 | context->name_count, |
1048 | context->ppid, | 1039 | context->ppid, |
1049 | context->pid, | 1040 | context->pid, |
1050 | context->loginuid, | 1041 | tsk->loginuid, |
1051 | context->uid, | 1042 | context->uid, |
1052 | context->gid, | 1043 | context->gid, |
1053 | context->euid, context->suid, context->fsuid, | 1044 | context->euid, context->suid, context->fsuid, |
@@ -1779,40 +1770,23 @@ int audit_set_loginuid(struct task_struct *task, uid_t loginuid) | |||
1779 | { | 1770 | { |
1780 | struct audit_context *context = task->audit_context; | 1771 | struct audit_context *context = task->audit_context; |
1781 | 1772 | ||
1782 | if (context) { | 1773 | if (context && context->in_syscall) { |
1783 | /* Only log if audit is enabled */ | 1774 | struct audit_buffer *ab; |
1784 | if (context->in_syscall) { | 1775 | |
1785 | struct audit_buffer *ab; | 1776 | ab = audit_log_start(NULL, GFP_KERNEL, AUDIT_LOGIN); |
1786 | 1777 | if (ab) { | |
1787 | ab = audit_log_start(NULL, GFP_KERNEL, AUDIT_LOGIN); | 1778 | audit_log_format(ab, "login pid=%d uid=%u " |
1788 | if (ab) { | 1779 | "old auid=%u new auid=%u", |
1789 | audit_log_format(ab, "login pid=%d uid=%u " | 1780 | task->pid, task->uid, |
1790 | "old auid=%u new auid=%u", | 1781 | task->loginuid, loginuid); |
1791 | task->pid, task->uid, | 1782 | audit_log_end(ab); |
1792 | context->loginuid, loginuid); | ||
1793 | audit_log_end(ab); | ||
1794 | } | ||
1795 | } | 1783 | } |
1796 | context->loginuid = loginuid; | ||
1797 | } | 1784 | } |
1785 | task->loginuid = loginuid; | ||
1798 | return 0; | 1786 | return 0; |
1799 | } | 1787 | } |
1800 | 1788 | ||
1801 | /** | 1789 | /** |
1802 | * audit_get_loginuid - get the loginuid for an audit_context | ||
1803 | * @ctx: the audit_context | ||
1804 | * | ||
1805 | * Returns the context's loginuid or -1 if @ctx is NULL. | ||
1806 | */ | ||
1807 | uid_t audit_get_loginuid(struct task_struct *task) | ||
1808 | { | ||
1809 | struct audit_context *ctx = task->audit_context; | ||
1810 | return ctx ? ctx->loginuid : -1; | ||
1811 | } | ||
1812 | |||
1813 | EXPORT_SYMBOL(audit_get_loginuid); | ||
1814 | |||
1815 | /** | ||
1816 | * __audit_mq_open - record audit data for a POSIX MQ open | 1790 | * __audit_mq_open - record audit data for a POSIX MQ open |
1817 | * @oflag: open flag | 1791 | * @oflag: open flag |
1818 | * @mode: mode bits | 1792 | * @mode: mode bits |
@@ -2217,8 +2191,8 @@ int __audit_signal_info(int sig, struct task_struct *t) | |||
2217 | if (audit_pid && t->tgid == audit_pid) { | 2191 | if (audit_pid && t->tgid == audit_pid) { |
2218 | if (sig == SIGTERM || sig == SIGHUP || sig == SIGUSR1) { | 2192 | if (sig == SIGTERM || sig == SIGHUP || sig == SIGUSR1) { |
2219 | audit_sig_pid = tsk->pid; | 2193 | audit_sig_pid = tsk->pid; |
2220 | if (ctx) | 2194 | if (tsk->loginuid != -1) |
2221 | audit_sig_uid = ctx->loginuid; | 2195 | audit_sig_uid = tsk->loginuid; |
2222 | else | 2196 | else |
2223 | audit_sig_uid = tsk->uid; | 2197 | audit_sig_uid = tsk->uid; |
2224 | selinux_get_task_sid(tsk, &audit_sig_sid); | 2198 | selinux_get_task_sid(tsk, &audit_sig_sid); |