aboutsummaryrefslogtreecommitdiffstats
path: root/kernel/auditsc.c
diff options
context:
space:
mode:
Diffstat (limited to 'kernel/auditsc.c')
-rw-r--r--kernel/auditsc.c421
1 files changed, 44 insertions, 377 deletions
diff --git a/kernel/auditsc.c b/kernel/auditsc.c
index a371f857a0a9..3c8a601324a2 100644
--- a/kernel/auditsc.c
+++ b/kernel/auditsc.c
@@ -76,11 +76,6 @@
76#define AUDITSC_SUCCESS 1 76#define AUDITSC_SUCCESS 1
77#define AUDITSC_FAILURE 2 77#define AUDITSC_FAILURE 2
78 78
79/* AUDIT_NAMES is the number of slots we reserve in the audit_context
80 * for saving names from getname(). If we get more names we will allocate
81 * a name dynamically and also add those to the list anchored by names_list. */
82#define AUDIT_NAMES 5
83
84/* no execve audit message should be longer than this (userspace limits) */ 79/* no execve audit message should be longer than this (userspace limits) */
85#define MAX_EXECVE_AUDIT_LEN 7500 80#define MAX_EXECVE_AUDIT_LEN 7500
86 81
@@ -90,44 +85,6 @@ int audit_n_rules;
90/* determines whether we collect data for signals sent */ 85/* determines whether we collect data for signals sent */
91int audit_signals; 86int audit_signals;
92 87
93struct audit_cap_data {
94 kernel_cap_t permitted;
95 kernel_cap_t inheritable;
96 union {
97 unsigned int fE; /* effective bit of a file capability */
98 kernel_cap_t effective; /* effective set of a process */
99 };
100};
101
102/* When fs/namei.c:getname() is called, we store the pointer in name and
103 * we don't let putname() free it (instead we free all of the saved
104 * pointers at syscall exit time).
105 *
106 * Further, in fs/namei.c:path_lookup() we store the inode and device.
107 */
108struct audit_names {
109 struct list_head list; /* audit_context->names_list */
110 struct filename *name;
111 unsigned long ino;
112 dev_t dev;
113 umode_t mode;
114 kuid_t uid;
115 kgid_t gid;
116 dev_t rdev;
117 u32 osid;
118 struct audit_cap_data fcap;
119 unsigned int fcap_ver;
120 int name_len; /* number of name's characters to log */
121 unsigned char type; /* record type */
122 bool name_put; /* call __putname() for this name */
123 /*
124 * This was an allocated audit_names and not from the array of
125 * names allocated in the task audit context. Thus this name
126 * should be freed on syscall exit
127 */
128 bool should_free;
129};
130
131struct audit_aux_data { 88struct audit_aux_data {
132 struct audit_aux_data *next; 89 struct audit_aux_data *next;
133 int type; 90 int type;
@@ -175,106 +132,6 @@ struct audit_tree_refs {
175 struct audit_chunk *c[31]; 132 struct audit_chunk *c[31];
176}; 133};
177 134
178/* The per-task audit context. */
179struct audit_context {
180 int dummy; /* must be the first element */
181 int in_syscall; /* 1 if task is in a syscall */
182 enum audit_state state, current_state;
183 unsigned int serial; /* serial number for record */
184 int major; /* syscall number */
185 struct timespec ctime; /* time of syscall entry */
186 unsigned long argv[4]; /* syscall arguments */
187 long return_code;/* syscall return code */
188 u64 prio;
189 int return_valid; /* return code is valid */
190 /*
191 * The names_list is the list of all audit_names collected during this
192 * syscall. The first AUDIT_NAMES entries in the names_list will
193 * actually be from the preallocated_names array for performance
194 * reasons. Except during allocation they should never be referenced
195 * through the preallocated_names array and should only be found/used
196 * by running the names_list.
197 */
198 struct audit_names preallocated_names[AUDIT_NAMES];
199 int name_count; /* total records in names_list */
200 struct list_head names_list; /* anchor for struct audit_names->list */
201 char * filterkey; /* key for rule that triggered record */
202 struct path pwd;
203 struct audit_aux_data *aux;
204 struct audit_aux_data *aux_pids;
205 struct sockaddr_storage *sockaddr;
206 size_t sockaddr_len;
207 /* Save things to print about task_struct */
208 pid_t pid, ppid;
209 kuid_t uid, euid, suid, fsuid;
210 kgid_t gid, egid, sgid, fsgid;
211 unsigned long personality;
212 int arch;
213
214 pid_t target_pid;
215 kuid_t target_auid;
216 kuid_t target_uid;
217 unsigned int target_sessionid;
218 u32 target_sid;
219 char target_comm[TASK_COMM_LEN];
220
221 struct audit_tree_refs *trees, *first_trees;
222 struct list_head killed_trees;
223 int tree_count;
224
225 int type;
226 union {
227 struct {
228 int nargs;
229 long args[6];
230 } socketcall;
231 struct {
232 kuid_t uid;
233 kgid_t gid;
234 umode_t mode;
235 u32 osid;
236 int has_perm;
237 uid_t perm_uid;
238 gid_t perm_gid;
239 umode_t perm_mode;
240 unsigned long qbytes;
241 } ipc;
242 struct {
243 mqd_t mqdes;
244 struct mq_attr mqstat;
245 } mq_getsetattr;
246 struct {
247 mqd_t mqdes;
248 int sigev_signo;
249 } mq_notify;
250 struct {
251 mqd_t mqdes;
252 size_t msg_len;
253 unsigned int msg_prio;
254 struct timespec abs_timeout;
255 } mq_sendrecv;
256 struct {
257 int oflag;
258 umode_t mode;
259 struct mq_attr attr;
260 } mq_open;
261 struct {
262 pid_t pid;
263 struct audit_cap_data cap;
264 } capset;
265 struct {
266 int fd;
267 int flags;
268 } mmap;
269 };
270 int fds[2];
271
272#if AUDIT_DEBUG
273 int put_count;
274 int ino_count;
275#endif
276};
277
278static inline int open_arg(int flags, int mask) 135static inline int open_arg(int flags, int mask)
279{ 136{
280 int n = ACC_MODE(flags); 137 int n = ACC_MODE(flags);
@@ -633,9 +490,23 @@ static int audit_filter_rules(struct task_struct *tsk,
633 break; 490 break;
634 case AUDIT_GID: 491 case AUDIT_GID:
635 result = audit_gid_comparator(cred->gid, f->op, f->gid); 492 result = audit_gid_comparator(cred->gid, f->op, f->gid);
493 if (f->op == Audit_equal) {
494 if (!result)
495 result = in_group_p(f->gid);
496 } else if (f->op == Audit_not_equal) {
497 if (result)
498 result = !in_group_p(f->gid);
499 }
636 break; 500 break;
637 case AUDIT_EGID: 501 case AUDIT_EGID:
638 result = audit_gid_comparator(cred->egid, f->op, f->gid); 502 result = audit_gid_comparator(cred->egid, f->op, f->gid);
503 if (f->op == Audit_equal) {
504 if (!result)
505 result = in_egroup_p(f->gid);
506 } else if (f->op == Audit_not_equal) {
507 if (result)
508 result = !in_egroup_p(f->gid);
509 }
639 break; 510 break;
640 case AUDIT_SGID: 511 case AUDIT_SGID:
641 result = audit_gid_comparator(cred->sgid, f->op, f->gid); 512 result = audit_gid_comparator(cred->sgid, f->op, f->gid);
@@ -742,6 +613,9 @@ static int audit_filter_rules(struct task_struct *tsk,
742 if (ctx) 613 if (ctx)
743 result = audit_uid_comparator(tsk->loginuid, f->op, f->uid); 614 result = audit_uid_comparator(tsk->loginuid, f->op, f->uid);
744 break; 615 break;
616 case AUDIT_LOGINUID_SET:
617 result = audit_comparator(audit_loginuid_set(tsk), f->op, f->val);
618 break;
745 case AUDIT_SUBJ_USER: 619 case AUDIT_SUBJ_USER:
746 case AUDIT_SUBJ_ROLE: 620 case AUDIT_SUBJ_ROLE:
747 case AUDIT_SUBJ_TYPE: 621 case AUDIT_SUBJ_TYPE:
@@ -987,6 +861,8 @@ static inline void audit_free_names(struct audit_context *context)
987 861
988#if AUDIT_DEBUG == 2 862#if AUDIT_DEBUG == 2
989 if (context->put_count + context->ino_count != context->name_count) { 863 if (context->put_count + context->ino_count != context->name_count) {
864 int i = 0;
865
990 printk(KERN_ERR "%s:%d(:%d): major=%d in_syscall=%d" 866 printk(KERN_ERR "%s:%d(:%d): major=%d in_syscall=%d"
991 " name_count=%d put_count=%d" 867 " name_count=%d put_count=%d"
992 " ino_count=%d [NOT freeing]\n", 868 " ino_count=%d [NOT freeing]\n",
@@ -995,7 +871,7 @@ static inline void audit_free_names(struct audit_context *context)
995 context->name_count, context->put_count, 871 context->name_count, context->put_count,
996 context->ino_count); 872 context->ino_count);
997 list_for_each_entry(n, &context->names_list, list) { 873 list_for_each_entry(n, &context->names_list, list) {
998 printk(KERN_ERR "names[%d] = %p = %s\n", i, 874 printk(KERN_ERR "names[%d] = %p = %s\n", i++,
999 n->name, n->name->name ?: "(null)"); 875 n->name, n->name->name ?: "(null)");
1000 } 876 }
1001 dump_stack(); 877 dump_stack();
@@ -1010,7 +886,7 @@ static inline void audit_free_names(struct audit_context *context)
1010 list_for_each_entry_safe(n, next, &context->names_list, list) { 886 list_for_each_entry_safe(n, next, &context->names_list, list) {
1011 list_del(&n->list); 887 list_del(&n->list);
1012 if (n->name && n->name_put) 888 if (n->name && n->name_put)
1013 __putname(n->name); 889 final_putname(n->name);
1014 if (n->should_free) 890 if (n->should_free)
1015 kfree(n); 891 kfree(n);
1016 } 892 }
@@ -1034,21 +910,15 @@ static inline void audit_free_aux(struct audit_context *context)
1034 } 910 }
1035} 911}
1036 912
1037static inline void audit_zero_context(struct audit_context *context,
1038 enum audit_state state)
1039{
1040 memset(context, 0, sizeof(*context));
1041 context->state = state;
1042 context->prio = state == AUDIT_RECORD_CONTEXT ? ~0ULL : 0;
1043}
1044
1045static inline struct audit_context *audit_alloc_context(enum audit_state state) 913static inline struct audit_context *audit_alloc_context(enum audit_state state)
1046{ 914{
1047 struct audit_context *context; 915 struct audit_context *context;
1048 916
1049 if (!(context = kmalloc(sizeof(*context), GFP_KERNEL))) 917 context = kzalloc(sizeof(*context), GFP_KERNEL);
918 if (!context)
1050 return NULL; 919 return NULL;
1051 audit_zero_context(context, state); 920 context->state = state;
921 context->prio = state == AUDIT_RECORD_CONTEXT ? ~0ULL : 0;
1052 INIT_LIST_HEAD(&context->killed_trees); 922 INIT_LIST_HEAD(&context->killed_trees);
1053 INIT_LIST_HEAD(&context->names_list); 923 INIT_LIST_HEAD(&context->names_list);
1054 return context; 924 return context;
@@ -1099,88 +969,6 @@ static inline void audit_free_context(struct audit_context *context)
1099 kfree(context); 969 kfree(context);
1100} 970}
1101 971
1102void audit_log_task_context(struct audit_buffer *ab)
1103{
1104 char *ctx = NULL;
1105 unsigned len;
1106 int error;
1107 u32 sid;
1108
1109 security_task_getsecid(current, &sid);
1110 if (!sid)
1111 return;
1112
1113 error = security_secid_to_secctx(sid, &ctx, &len);
1114 if (error) {
1115 if (error != -EINVAL)
1116 goto error_path;
1117 return;
1118 }
1119
1120 audit_log_format(ab, " subj=%s", ctx);
1121 security_release_secctx(ctx, len);
1122 return;
1123
1124error_path:
1125 audit_panic("error in audit_log_task_context");
1126 return;
1127}
1128
1129EXPORT_SYMBOL(audit_log_task_context);
1130
1131void audit_log_task_info(struct audit_buffer *ab, struct task_struct *tsk)
1132{
1133 const struct cred *cred;
1134 char name[sizeof(tsk->comm)];
1135 struct mm_struct *mm = tsk->mm;
1136 char *tty;
1137
1138 if (!ab)
1139 return;
1140
1141 /* tsk == current */
1142 cred = current_cred();
1143
1144 spin_lock_irq(&tsk->sighand->siglock);
1145 if (tsk->signal && tsk->signal->tty)
1146 tty = tsk->signal->tty->name;
1147 else
1148 tty = "(none)";
1149 spin_unlock_irq(&tsk->sighand->siglock);
1150
1151
1152 audit_log_format(ab,
1153 " ppid=%ld pid=%d auid=%u uid=%u gid=%u"
1154 " euid=%u suid=%u fsuid=%u"
1155 " egid=%u sgid=%u fsgid=%u ses=%u tty=%s",
1156 sys_getppid(),
1157 tsk->pid,
1158 from_kuid(&init_user_ns, tsk->loginuid),
1159 from_kuid(&init_user_ns, cred->uid),
1160 from_kgid(&init_user_ns, cred->gid),
1161 from_kuid(&init_user_ns, cred->euid),
1162 from_kuid(&init_user_ns, cred->suid),
1163 from_kuid(&init_user_ns, cred->fsuid),
1164 from_kgid(&init_user_ns, cred->egid),
1165 from_kgid(&init_user_ns, cred->sgid),
1166 from_kgid(&init_user_ns, cred->fsgid),
1167 tsk->sessionid, tty);
1168
1169 get_task_comm(name, tsk);
1170 audit_log_format(ab, " comm=");
1171 audit_log_untrustedstring(ab, name);
1172
1173 if (mm) {
1174 down_read(&mm->mmap_sem);
1175 if (mm->exe_file)
1176 audit_log_d_path(ab, " exe=", &mm->exe_file->f_path);
1177 up_read(&mm->mmap_sem);
1178 }
1179 audit_log_task_context(ab);
1180}
1181
1182EXPORT_SYMBOL(audit_log_task_info);
1183
1184static int audit_log_pid_context(struct audit_context *context, pid_t pid, 972static int audit_log_pid_context(struct audit_context *context, pid_t pid,
1185 kuid_t auid, kuid_t uid, unsigned int sessionid, 973 kuid_t auid, kuid_t uid, unsigned int sessionid,
1186 u32 sid, char *comm) 974 u32 sid, char *comm)
@@ -1197,12 +985,14 @@ static int audit_log_pid_context(struct audit_context *context, pid_t pid,
1197 audit_log_format(ab, "opid=%d oauid=%d ouid=%d oses=%d", pid, 985 audit_log_format(ab, "opid=%d oauid=%d ouid=%d oses=%d", pid,
1198 from_kuid(&init_user_ns, auid), 986 from_kuid(&init_user_ns, auid),
1199 from_kuid(&init_user_ns, uid), sessionid); 987 from_kuid(&init_user_ns, uid), sessionid);
1200 if (security_secid_to_secctx(sid, &ctx, &len)) { 988 if (sid) {
1201 audit_log_format(ab, " obj=(none)"); 989 if (security_secid_to_secctx(sid, &ctx, &len)) {
1202 rc = 1; 990 audit_log_format(ab, " obj=(none)");
1203 } else { 991 rc = 1;
1204 audit_log_format(ab, " obj=%s", ctx); 992 } else {
1205 security_release_secctx(ctx, len); 993 audit_log_format(ab, " obj=%s", ctx);
994 security_release_secctx(ctx, len);
995 }
1206 } 996 }
1207 audit_log_format(ab, " ocomm="); 997 audit_log_format(ab, " ocomm=");
1208 audit_log_untrustedstring(ab, comm); 998 audit_log_untrustedstring(ab, comm);
@@ -1396,35 +1186,6 @@ static void audit_log_execve_info(struct audit_context *context,
1396 kfree(buf); 1186 kfree(buf);
1397} 1187}
1398 1188
1399static void audit_log_cap(struct audit_buffer *ab, char *prefix, kernel_cap_t *cap)
1400{
1401 int i;
1402
1403 audit_log_format(ab, " %s=", prefix);
1404 CAP_FOR_EACH_U32(i) {
1405 audit_log_format(ab, "%08x", cap->cap[(_KERNEL_CAPABILITY_U32S-1) - i]);
1406 }
1407}
1408
1409static void audit_log_fcaps(struct audit_buffer *ab, struct audit_names *name)
1410{
1411 kernel_cap_t *perm = &name->fcap.permitted;
1412 kernel_cap_t *inh = &name->fcap.inheritable;
1413 int log = 0;
1414
1415 if (!cap_isclear(*perm)) {
1416 audit_log_cap(ab, "cap_fp", perm);
1417 log = 1;
1418 }
1419 if (!cap_isclear(*inh)) {
1420 audit_log_cap(ab, "cap_fi", inh);
1421 log = 1;
1422 }
1423
1424 if (log)
1425 audit_log_format(ab, " cap_fe=%d cap_fver=%x", name->fcap.fE, name->fcap_ver);
1426}
1427
1428static void show_special(struct audit_context *context, int *call_panic) 1189static void show_special(struct audit_context *context, int *call_panic)
1429{ 1190{
1430 struct audit_buffer *ab; 1191 struct audit_buffer *ab;
@@ -1522,68 +1283,6 @@ static void show_special(struct audit_context *context, int *call_panic)
1522 audit_log_end(ab); 1283 audit_log_end(ab);
1523} 1284}
1524 1285
1525static void audit_log_name(struct audit_context *context, struct audit_names *n,
1526 int record_num, int *call_panic)
1527{
1528 struct audit_buffer *ab;
1529 ab = audit_log_start(context, GFP_KERNEL, AUDIT_PATH);
1530 if (!ab)
1531 return; /* audit_panic has been called */
1532
1533 audit_log_format(ab, "item=%d", record_num);
1534
1535 if (n->name) {
1536 switch (n->name_len) {
1537 case AUDIT_NAME_FULL:
1538 /* log the full path */
1539 audit_log_format(ab, " name=");
1540 audit_log_untrustedstring(ab, n->name->name);
1541 break;
1542 case 0:
1543 /* name was specified as a relative path and the
1544 * directory component is the cwd */
1545 audit_log_d_path(ab, " name=", &context->pwd);
1546 break;
1547 default:
1548 /* log the name's directory component */
1549 audit_log_format(ab, " name=");
1550 audit_log_n_untrustedstring(ab, n->name->name,
1551 n->name_len);
1552 }
1553 } else
1554 audit_log_format(ab, " name=(null)");
1555
1556 if (n->ino != (unsigned long)-1) {
1557 audit_log_format(ab, " inode=%lu"
1558 " dev=%02x:%02x mode=%#ho"
1559 " ouid=%u ogid=%u rdev=%02x:%02x",
1560 n->ino,
1561 MAJOR(n->dev),
1562 MINOR(n->dev),
1563 n->mode,
1564 from_kuid(&init_user_ns, n->uid),
1565 from_kgid(&init_user_ns, n->gid),
1566 MAJOR(n->rdev),
1567 MINOR(n->rdev));
1568 }
1569 if (n->osid != 0) {
1570 char *ctx = NULL;
1571 u32 len;
1572 if (security_secid_to_secctx(
1573 n->osid, &ctx, &len)) {
1574 audit_log_format(ab, " osid=%u", n->osid);
1575 *call_panic = 2;
1576 } else {
1577 audit_log_format(ab, " obj=%s", ctx);
1578 security_release_secctx(ctx, len);
1579 }
1580 }
1581
1582 audit_log_fcaps(ab, n);
1583
1584 audit_log_end(ab);
1585}
1586
1587static void audit_log_exit(struct audit_context *context, struct task_struct *tsk) 1286static void audit_log_exit(struct audit_context *context, struct task_struct *tsk)
1588{ 1287{
1589 int i, call_panic = 0; 1288 int i, call_panic = 0;
@@ -1701,7 +1400,7 @@ static void audit_log_exit(struct audit_context *context, struct task_struct *ts
1701 1400
1702 i = 0; 1401 i = 0;
1703 list_for_each_entry(n, &context->names_list, list) 1402 list_for_each_entry(n, &context->names_list, list)
1704 audit_log_name(context, n, i++, &call_panic); 1403 audit_log_name(context, n, NULL, i++, &call_panic);
1705 1404
1706 /* Send end of event record to help user space know we are finished */ 1405 /* Send end of event record to help user space know we are finished */
1707 ab = audit_log_start(context, GFP_KERNEL, AUDIT_EOE); 1406 ab = audit_log_start(context, GFP_KERNEL, AUDIT_EOE);
@@ -2036,18 +1735,18 @@ void audit_putname(struct filename *name)
2036 BUG_ON(!context); 1735 BUG_ON(!context);
2037 if (!context->in_syscall) { 1736 if (!context->in_syscall) {
2038#if AUDIT_DEBUG == 2 1737#if AUDIT_DEBUG == 2
2039 printk(KERN_ERR "%s:%d(:%d): __putname(%p)\n", 1738 printk(KERN_ERR "%s:%d(:%d): final_putname(%p)\n",
2040 __FILE__, __LINE__, context->serial, name); 1739 __FILE__, __LINE__, context->serial, name);
2041 if (context->name_count) { 1740 if (context->name_count) {
2042 struct audit_names *n; 1741 struct audit_names *n;
2043 int i; 1742 int i = 0;
2044 1743
2045 list_for_each_entry(n, &context->names_list, list) 1744 list_for_each_entry(n, &context->names_list, list)
2046 printk(KERN_ERR "name[%d] = %p = %s\n", i, 1745 printk(KERN_ERR "name[%d] = %p = %s\n", i++,
2047 n->name, n->name->name ?: "(null)"); 1746 n->name, n->name->name ?: "(null)");
2048 } 1747 }
2049#endif 1748#endif
2050 __putname(name); 1749 final_putname(name);
2051 } 1750 }
2052#if AUDIT_DEBUG 1751#if AUDIT_DEBUG
2053 else { 1752 else {
@@ -2066,41 +1765,6 @@ void audit_putname(struct filename *name)
2066#endif 1765#endif
2067} 1766}
2068 1767
2069static inline int audit_copy_fcaps(struct audit_names *name, const struct dentry *dentry)
2070{
2071 struct cpu_vfs_cap_data caps;
2072 int rc;
2073
2074 if (!dentry)
2075 return 0;
2076
2077 rc = get_vfs_caps_from_disk(dentry, &caps);
2078 if (rc)
2079 return rc;
2080
2081 name->fcap.permitted = caps.permitted;
2082 name->fcap.inheritable = caps.inheritable;
2083 name->fcap.fE = !!(caps.magic_etc & VFS_CAP_FLAGS_EFFECTIVE);
2084 name->fcap_ver = (caps.magic_etc & VFS_CAP_REVISION_MASK) >> VFS_CAP_REVISION_SHIFT;
2085
2086 return 0;
2087}
2088
2089
2090/* Copy inode data into an audit_names. */
2091static void audit_copy_inode(struct audit_names *name, const struct dentry *dentry,
2092 const struct inode *inode)
2093{
2094 name->ino = inode->i_ino;
2095 name->dev = inode->i_sb->s_dev;
2096 name->mode = inode->i_mode;
2097 name->uid = inode->i_uid;
2098 name->gid = inode->i_gid;
2099 name->rdev = inode->i_rdev;
2100 security_inode_getsecid(inode, &name->osid);
2101 audit_copy_fcaps(name, dentry);
2102}
2103
2104/** 1768/**
2105 * __audit_inode - store the inode and device from a lookup 1769 * __audit_inode - store the inode and device from a lookup
2106 * @name: name being audited 1770 * @name: name being audited
@@ -2309,7 +1973,7 @@ int audit_set_loginuid(kuid_t loginuid)
2309 unsigned int sessionid; 1973 unsigned int sessionid;
2310 1974
2311#ifdef CONFIG_AUDIT_LOGINUID_IMMUTABLE 1975#ifdef CONFIG_AUDIT_LOGINUID_IMMUTABLE
2312 if (uid_valid(task->loginuid)) 1976 if (audit_loginuid_set(task))
2313 return -EPERM; 1977 return -EPERM;
2314#else /* CONFIG_AUDIT_LOGINUID_IMMUTABLE */ 1978#else /* CONFIG_AUDIT_LOGINUID_IMMUTABLE */
2315 if (!capable(CAP_AUDIT_CONTROL)) 1979 if (!capable(CAP_AUDIT_CONTROL))
@@ -2477,17 +2141,20 @@ int __audit_bprm(struct linux_binprm *bprm)
2477 2141
2478/** 2142/**
2479 * audit_socketcall - record audit data for sys_socketcall 2143 * audit_socketcall - record audit data for sys_socketcall
2480 * @nargs: number of args 2144 * @nargs: number of args, which should not be more than AUDITSC_ARGS.
2481 * @args: args array 2145 * @args: args array
2482 * 2146 *
2483 */ 2147 */
2484void __audit_socketcall(int nargs, unsigned long *args) 2148int __audit_socketcall(int nargs, unsigned long *args)
2485{ 2149{
2486 struct audit_context *context = current->audit_context; 2150 struct audit_context *context = current->audit_context;
2487 2151
2152 if (nargs <= 0 || nargs > AUDITSC_ARGS || !args)
2153 return -EINVAL;
2488 context->type = AUDIT_SOCKETCALL; 2154 context->type = AUDIT_SOCKETCALL;
2489 context->socketcall.nargs = nargs; 2155 context->socketcall.nargs = nargs;
2490 memcpy(context->socketcall.args, args, nargs * sizeof(unsigned long)); 2156 memcpy(context->socketcall.args, args, nargs * sizeof(unsigned long));
2157 return 0;
2491} 2158}
2492 2159
2493/** 2160/**