1/*
2 * Copyright (c) 1999-2020 Apple Inc. All rights reserved.
3 *
4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions
6 * are met:
7 * 1. Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer.
9 * 2. Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
12 * 3. Neither the name of Apple Inc. ("Apple") nor the names of
13 * its contributors may be used to endorse or promote products derived
14 * from this software without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND
17 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19 * ARE DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR
20 * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
21 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
22 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
23 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
24 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
25 * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
26 * POSSIBILITY OF SUCH DAMAGE.
27 */
28/*
29 * NOTICE: This file was modified by SPARTA, Inc. in 2005 to introduce
30 * support for mandatory and extensible security protections. This notice
31 * is included in support of clause 2.2 (b) of the Apple Public License,
32 * Version 2.0.
33 */
34
35#include <sys/types.h>
36#include <sys/vnode_internal.h>
37#include <sys/ipc.h>
38#include <sys/sem.h>
39#include <sys/socketvar.h>
40#include <sys/socket.h>
41#include <sys/queue.h>
42#include <sys/fcntl.h>
43#include <sys/user.h>
44#include <sys/ipc.h>
45
46#include <bsm/audit.h>
47#include <bsm/audit_internal.h>
48#include <bsm/audit_record.h>
49#include <bsm/audit_kevents.h>
50
51#include <security/audit/audit.h>
52#include <security/audit/audit_bsd.h>
53#include <security/audit/audit_private.h>
54
55#include <netinet/in_systm.h>
56#include <netinet/in.h>
57#include <netinet/ip.h>
58
59#if CONFIG_AUDIT
60MALLOC_DEFINE(M_AUDITBSM, "audit_bsm", "Audit BSM data");
61
62#if CONFIG_MACF
63#include <security/mac_framework.h>
64#endif
65
66static void audit_sys_auditon(struct audit_record *ar,
67 struct au_record *rec);
68static void audit_sys_fcntl(struct kaudit_record *kar,
69 struct au_record *rec);
70
71/*
72 * Initialize the BSM auditing subsystem.
73 */
74void
75kau_init(void)
76{
77 au_evclassmap_init();
78}
79
80/*
81 * This call reserves memory for the audit record. Memory must be guaranteed
82 * before any auditable event can be generated. The au_record structure
83 * maintains a reference to the memory allocated above and also the list of
84 * tokens associated with this record.
85 */
86static struct au_record *
87kau_open(void)
88{
89 struct au_record *rec;
90
91 rec = kalloc_type(struct au_record, Z_WAITOK | Z_ZERO | Z_NOFAIL);
92 TAILQ_INIT(&rec->token_q);
93 rec->used = 1;
94 rec->data = NULL;
95
96 return rec;
97}
98
99/*
100 * Store the token with the record descriptor.
101 */
102static void
103kau_write(struct au_record *rec, struct au_token *tok)
104{
105 KASSERT(tok != NULL, ("kau_write: tok == NULL"));
106
107 TAILQ_INSERT_TAIL(&rec->token_q, tok, tokens);
108 rec->len += tok->len;
109}
110
111/*
112 * Close out the audit record by adding the header token, identifying any
113 * missing tokens. Write out the tokens to the record memory.
114 */
115static int
116kau_close(struct au_record *rec, struct timespec *ctime, short event)
117{
118 u_char *dptr;
119 size_t tot_rec_size;
120 token_t *cur, *hdr, *trail;
121 struct timeval tm;
122 size_t hdrsize;
123 struct auditinfo_addr ak;
124 struct in6_addr *ap;
125
126 audit_get_kinfo(&ak);
127 hdrsize = 0;
128 switch (ak.ai_termid.at_type) {
129 case AU_IPv4:
130 hdrsize = (ak.ai_termid.at_addr[0] == INADDR_ANY) ?
131 AUDIT_HEADER_SIZE : AUDIT_HEADER_EX_SIZE(&ak);
132 break;
133 case AU_IPv6:
134 ap = (struct in6_addr *)&ak.ai_termid.at_addr[0];
135 hdrsize = (IN6_IS_ADDR_UNSPECIFIED(ap)) ? AUDIT_HEADER_SIZE :
136 AUDIT_HEADER_EX_SIZE(&ak);
137 break;
138 default:
139 panic("kau_close: invalid address family");
140 }
141 tot_rec_size = rec->len + AUDIT_HEADER_SIZE + AUDIT_TRAILER_SIZE;
142 rec->data = kalloc_data(tot_rec_size, Z_WAITOK | Z_ZERO);
143 if (rec->data == NULL) {
144 return ENOMEM;
145 }
146
147 tm.tv_usec = ctime->tv_nsec / 1000;
148 tm.tv_sec = ctime->tv_sec;
149 if (hdrsize != AUDIT_HEADER_SIZE) {
150 hdr = au_to_header32_ex_tm(rec_size: tot_rec_size, e_type: event, e_mod: 0, tm, aia: &ak);
151 } else {
152 hdr = au_to_header32_tm(rec_size: tot_rec_size, e_type: event, e_mod: 0, tm);
153 }
154 TAILQ_INSERT_HEAD(&rec->token_q, hdr, tokens);
155
156 trail = au_to_trailer(rec_size: tot_rec_size);
157 TAILQ_INSERT_TAIL(&rec->token_q, trail, tokens);
158
159 rec->len = tot_rec_size;
160 dptr = rec->data;
161 TAILQ_FOREACH(cur, &rec->token_q, tokens) {
162 memcpy(dst: dptr, src: cur->t_data, n: cur->len);
163 dptr += cur->len;
164 }
165
166 return 0;
167}
168
169/*
170 * Free a BSM audit record by releasing all the tokens and clearing the audit
171 * record information.
172 */
173void
174kau_free(struct au_record *rec)
175{
176 struct au_token *tok;
177
178 /* Free the token list. */
179 while ((tok = TAILQ_FIRST(&rec->token_q))) {
180 TAILQ_REMOVE(&rec->token_q, tok, tokens);
181 kfree_data(tok->t_data, tok->len);
182 kfree_type(token_t, tok);
183 }
184
185 if (rec->data != NULL) {
186 kfree_data(rec->data, rec->len);
187 }
188 kfree_type(struct au_record, rec);
189}
190
191/*
192 * XXX: May want turn some (or all) of these macros into functions in order
193 * to reduce the generated code size.
194 *
195 * XXXAUDIT: These macros assume that 'kar', 'ar', 'rec', and 'tok' in the
196 * caller are OK with this.
197 */
198#if CONFIG_MACF
199#define MAC_VNODE1_LABEL_TOKEN do { \
200 if (ar->ar_vnode1_mac_labels != NULL && \
201 strlen(ar->ar_vnode1_mac_labels) != 0) { \
202 tok = au_to_text(ar->ar_vnode1_mac_labels); \
203 kau_write(rec, tok); \
204 } \
205} while (0)
206
207#define MAC_VNODE2_LABEL_TOKEN do { \
208 if (ar->ar_vnode2_mac_labels != NULL && \
209 strlen(ar->ar_vnode2_mac_labels) != 0) { \
210 tok = au_to_text(ar->ar_vnode2_mac_labels); \
211 kau_write(rec, tok); \
212 } \
213} while (0)
214#else
215#define MAC_VNODE1_LABEL_TOKEN
216#define MAC_VNODE2_LABEL_TOKEN
217#endif
218#define UPATH1_TOKENS do { \
219 if (ARG_IS_VALID(kar, ARG_UPATH1)) { \
220 tok = au_to_path(ar->ar_arg_upath1); \
221 kau_write(rec, tok); \
222 } \
223} while (0)
224
225#define UPATH2_TOKENS do { \
226 if (ARG_IS_VALID(kar, ARG_UPATH2)) { \
227 tok = au_to_path(ar->ar_arg_upath2); \
228 kau_write(rec, tok); \
229 } \
230} while (0)
231
232#define KPATH2_TOKENS do { \
233 if (ARG_IS_VALID(kar, ARG_KPATH2)) { \
234 tok = au_to_path(ar->ar_arg_kpath2); \
235 kau_write(rec, tok); \
236 } \
237} while (0)
238
239#define VNODE1_TOKENS do { \
240 if (ARG_IS_VALID(kar, ARG_KPATH1)) { \
241 tok = au_to_path(ar->ar_arg_kpath1); \
242 kau_write(rec, tok); \
243 } \
244 if (ARG_IS_VALID(kar, ARG_VNODE1)) { \
245 tok = au_to_attr32(&ar->ar_arg_vnode1); \
246 kau_write(rec, tok); \
247 MAC_VNODE1_LABEL_TOKEN; \
248 } \
249} while (0)
250
251#define UPATH1_VNODE1_TOKENS do { \
252 if (ARG_IS_VALID(kar, ARG_UPATH1)) { \
253 tok = au_to_path(ar->ar_arg_upath1); \
254 kau_write(rec, tok); \
255 } \
256 if (ARG_IS_VALID(kar, ARG_KPATH1)) { \
257 tok = au_to_path(ar->ar_arg_kpath1); \
258 kau_write(rec, tok); \
259 } \
260 if (ARG_IS_VALID(kar, ARG_VNODE1)) { \
261 tok = au_to_attr32(&ar->ar_arg_vnode1); \
262 kau_write(rec, tok); \
263 MAC_VNODE1_LABEL_TOKEN; \
264 } \
265} while (0)
266
267#define VNODE2_TOKENS do { \
268 if (ARG_IS_VALID(kar, ARG_VNODE2)) { \
269 tok = au_to_attr32(&ar->ar_arg_vnode2); \
270 kau_write(rec, tok); \
271 MAC_VNODE2_LABEL_TOKEN; \
272 } \
273} while (0)
274
275#define VNODE2_PATH_TOKENS do { \
276 if (ARG_IS_VALID(kar, ARG_KPATH2)) { \
277 tok = au_to_path(ar->ar_arg_kpath2); \
278 kau_write(rec, tok); \
279 } \
280 if (ARG_IS_VALID(kar, ARG_VNODE2)) { \
281 tok = au_to_attr32(&ar->ar_arg_vnode2); \
282 kau_write(rec, tok); \
283 MAC_VNODE2_LABEL_TOKEN; \
284 } \
285} while (0)
286
287#define FD_VNODE1_TOKENS do { \
288 if (ARG_IS_VALID(kar, ARG_VNODE1)) { \
289 if (ARG_IS_VALID(kar, ARG_KPATH1)) { \
290 tok = au_to_path(ar->ar_arg_kpath1); \
291 kau_write(rec, tok); \
292 } \
293 if (ARG_IS_VALID(kar, ARG_FD)) { \
294 tok = au_to_arg32(1, "fd", ar->ar_arg_fd); \
295 kau_write(rec, tok); \
296 MAC_VNODE1_LABEL_TOKEN; \
297 } \
298 tok = au_to_attr32(&ar->ar_arg_vnode1); \
299 kau_write(rec, tok); \
300 } else { \
301 if (ARG_IS_VALID(kar, ARG_FD)) { \
302 tok = au_to_arg32(1, "fd", \
303 ar->ar_arg_fd); \
304 kau_write(rec, tok); \
305 MAC_VNODE1_LABEL_TOKEN; \
306 } \
307 } \
308} while (0)
309
310#define PROCESS_PID_TOKENS(argn) do { \
311 if ((ar->ar_arg_pid > 0) /* Reference a single process */ \
312 && (ARG_IS_VALID(kar, ARG_PROCESS))) { \
313 tok = au_to_process32_ex(ar->ar_arg_auid, \
314 ar->ar_arg_euid, ar->ar_arg_egid, \
315 ar->ar_arg_ruid, ar->ar_arg_rgid, \
316 ar->ar_arg_pid, ar->ar_arg_asid, \
317 &ar->ar_arg_termid_addr); \
318 kau_write(rec, tok); \
319 } else if (ARG_IS_VALID(kar, ARG_PID)) { \
320 tok = au_to_arg32(argn, "process", ar->ar_arg_pid); \
321 kau_write(rec, tok); \
322 } \
323} while (0)
324
325#define EXTATTR_TOKENS do { \
326 if (ARG_IS_VALID(kar, ARG_VALUE32)) { \
327 switch (ar->ar_arg_value32) { \
328 case EXTATTR_NAMESPACE_USER: \
329 tok = au_to_text(EXTATTR_NAMESPACE_USER_STRING);\
330 break; \
331 case EXTATTR_NAMESPACE_SYSTEM: \
332 tok = au_to_text(EXTATTR_NAMESPACE_SYSTEM_STRING);\
333 break; \
334 default: \
335 tok = au_to_arg32(3, "attrnamespace", \
336 ar->ar_arg_value32); \
337 break; \
338 } \
339 kau_write(rec, tok); \
340 } \
341 /* attrname is in the text field */ \
342 if (ARG_IS_VALID(kar, ARG_TEXT)) { \
343 tok = au_to_text(ar->ar_arg_text); \
344 kau_write(rec, tok); \
345 } \
346} while (0)
347
348#define EXTENDED_TOKENS(n) do { \
349 /* ACL data */ \
350 if (ARG_IS_VALID(kar, ARG_OPAQUE)) { \
351 tok = au_to_opaque(ar->ar_arg_opaque, \
352 ar->ar_arg_opq_size); \
353 kau_write(rec, tok); \
354 } \
355 if (ARG_IS_VALID(kar, ARG_MODE)) { \
356 tok = au_to_arg32(n+2, "mode", ar->ar_arg_mode);\
357 kau_write(rec, tok); \
358 } \
359 if (ARG_IS_VALID(kar, ARG_GID)) { \
360 tok = au_to_arg32(n+1, "gid", ar->ar_arg_gid); \
361 kau_write(rec, tok); \
362 } \
363 if (ARG_IS_VALID(kar, ARG_UID)) { \
364 tok = au_to_arg32(n, "uid", ar->ar_arg_uid); \
365 kau_write(rec, tok); \
366 } \
367} while (0)
368
369#define PROCESS_MAC_TOKENS do { \
370 if (ar->ar_valid_arg & ARG_MAC_STRING) { \
371 tok = au_to_text(ar->ar_arg_mac_string); \
372 kau_write(rec, tok); \
373 } \
374} while (0)
375
376/*
377 * Implement auditing for the auditon() system call. The audit tokens that
378 * are generated depend on the command that was sent into the auditon()
379 * system call.
380 */
381static void
382audit_sys_auditon(struct audit_record *ar, struct au_record *rec)
383{
384 struct au_token *tok;
385
386 switch (ar->ar_arg_cmd) {
387 case A_OLDSETPOLICY:
388 if (ar->ar_arg_len > sizeof(int)) {
389 tok = au_to_arg32(n: 3, text: "length", v: ar->ar_arg_len);
390 kau_write(rec, tok);
391 tok = au_to_arg64(n: 2, text: "policy",
392 v: ar->ar_arg_auditon.au_policy64);
393 kau_write(rec, tok);
394 break;
395 }
396 OS_FALLTHROUGH;
397 case A_SETPOLICY:
398 tok = au_to_arg32(n: 3, text: "length", v: ar->ar_arg_len);
399 kau_write(rec, tok);
400 tok = au_to_arg32(n: 2, text: "policy", v: ar->ar_arg_auditon.au_policy);
401 kau_write(rec, tok);
402 break;
403
404 case A_SETKMASK:
405 tok = au_to_arg32(n: 3, text: "length", v: ar->ar_arg_len);
406 kau_write(rec, tok);
407 tok = au_to_arg32(n: 2, text: "setkmask:as_success",
408 v: ar->ar_arg_auditon.au_mask.am_success);
409 kau_write(rec, tok);
410 tok = au_to_arg32(n: 2, text: "setkmask:as_failure",
411 v: ar->ar_arg_auditon.au_mask.am_failure);
412 kau_write(rec, tok);
413 break;
414
415 case A_OLDSETQCTRL:
416 if (ar->ar_arg_len > sizeof(au_qctrl_t)) {
417 tok = au_to_arg32(n: 3, text: "length", v: ar->ar_arg_len);
418 kau_write(rec, tok);
419 tok = au_to_arg64(n: 2, text: "setqctrl:aq_hiwater",
420 v: ar->ar_arg_auditon.au_qctrl64.aq64_hiwater);
421 kau_write(rec, tok);
422 tok = au_to_arg64(n: 2, text: "setqctrl:aq_lowater",
423 v: ar->ar_arg_auditon.au_qctrl64.aq64_lowater);
424 kau_write(rec, tok);
425 tok = au_to_arg64(n: 2, text: "setqctrl:aq_bufsz",
426 v: ar->ar_arg_auditon.au_qctrl64.aq64_bufsz);
427 kau_write(rec, tok);
428 tok = au_to_arg64(n: 2, text: "setqctrl:aq_delay",
429 v: ar->ar_arg_auditon.au_qctrl64.aq64_delay);
430 kau_write(rec, tok);
431 tok = au_to_arg32(n: 2, text: "setqctrl:aq_minfree",
432 v: ar->ar_arg_auditon.au_qctrl64.aq64_minfree);
433 kau_write(rec, tok);
434 break;
435 }
436 OS_FALLTHROUGH;
437 case A_SETQCTRL:
438 tok = au_to_arg32(n: 3, text: "length", v: ar->ar_arg_len);
439 kau_write(rec, tok);
440 tok = au_to_arg32(n: 2, text: "setqctrl:aq_hiwater",
441 v: ar->ar_arg_auditon.au_qctrl.aq_hiwater);
442 kau_write(rec, tok);
443 tok = au_to_arg32(n: 2, text: "setqctrl:aq_lowater",
444 v: ar->ar_arg_auditon.au_qctrl.aq_lowater);
445 kau_write(rec, tok);
446 tok = au_to_arg32(n: 2, text: "setqctrl:aq_bufsz",
447 v: ar->ar_arg_auditon.au_qctrl.aq_bufsz);
448 kau_write(rec, tok);
449 tok = au_to_arg32(n: 2, text: "setqctrl:aq_delay",
450 v: ar->ar_arg_auditon.au_qctrl.aq_delay);
451 kau_write(rec, tok);
452 tok = au_to_arg32(n: 2, text: "setqctrl:aq_minfree",
453 v: ar->ar_arg_auditon.au_qctrl.aq_minfree);
454 kau_write(rec, tok);
455 break;
456
457 case A_SETUMASK:
458 tok = au_to_arg32(n: 3, text: "length", v: ar->ar_arg_len);
459 kau_write(rec, tok);
460 tok = au_to_arg32(n: 2, text: "setumask:as_success",
461 v: ar->ar_arg_auditon.au_auinfo.ai_mask.am_success);
462 kau_write(rec, tok);
463 tok = au_to_arg32(n: 2, text: "setumask:as_failure",
464 v: ar->ar_arg_auditon.au_auinfo.ai_mask.am_failure);
465 kau_write(rec, tok);
466 break;
467
468 case A_SETSMASK:
469 tok = au_to_arg32(n: 3, text: "length", v: ar->ar_arg_len);
470 kau_write(rec, tok);
471 tok = au_to_arg32(n: 2, text: "setsmask:as_success",
472 v: ar->ar_arg_auditon.au_auinfo.ai_mask.am_success);
473 kau_write(rec, tok);
474 tok = au_to_arg32(n: 2, text: "setsmask:as_failure",
475 v: ar->ar_arg_auditon.au_auinfo.ai_mask.am_failure);
476 kau_write(rec, tok);
477 break;
478
479 case A_OLDSETCOND:
480 if (ar->ar_arg_len > sizeof(int)) {
481 tok = au_to_arg32(n: 3, text: "length", v: ar->ar_arg_len);
482 kau_write(rec, tok);
483 tok = au_to_arg64(n: 2, text: "setcond",
484 v: ar->ar_arg_auditon.au_cond64);
485 kau_write(rec, tok);
486 break;
487 }
488 OS_FALLTHROUGH;
489 case A_SETCOND:
490 tok = au_to_arg32(n: 3, text: "length", v: ar->ar_arg_len);
491 kau_write(rec, tok);
492 tok = au_to_arg32(n: 2, text: "setcond", v: ar->ar_arg_auditon.au_cond);
493 kau_write(rec, tok);
494 break;
495
496 case A_SETCLASS:
497 tok = au_to_arg32(n: 3, text: "length", v: ar->ar_arg_len);
498 kau_write(rec, tok);
499 tok = au_to_arg32(n: 2, text: "setclass:ec_event",
500 v: ar->ar_arg_auditon.au_evclass.ec_number);
501 kau_write(rec, tok);
502 tok = au_to_arg32(n: 3, text: "setclass:ec_class",
503 v: ar->ar_arg_auditon.au_evclass.ec_class);
504 kau_write(rec, tok);
505 break;
506
507 case A_SETPMASK:
508 tok = au_to_arg32(n: 3, text: "length", v: ar->ar_arg_len);
509 kau_write(rec, tok);
510 tok = au_to_arg32(n: 2, text: "setpmask:as_success",
511 v: ar->ar_arg_auditon.au_aupinfo.ap_mask.am_success);
512 kau_write(rec, tok);
513 tok = au_to_arg32(n: 2, text: "setpmask:as_failure",
514 v: ar->ar_arg_auditon.au_aupinfo.ap_mask.am_failure);
515 kau_write(rec, tok);
516 break;
517
518 case A_SETFSIZE:
519 tok = au_to_arg32(n: 3, text: "length", v: ar->ar_arg_len);
520 kau_write(rec, tok);
521 tok = au_to_arg32(n: 2, text: "setfsize:filesize",
522 v: ar->ar_arg_auditon.au_fstat.af_filesz);
523 kau_write(rec, tok);
524 break;
525
526 default:
527 break;
528 }
529 tok = au_to_arg32(n: 1, text: "cmd", v: ar->ar_arg_cmd);
530 kau_write(rec, tok);
531}
532
533/*
534 * Implement auditing for the fcntl() system call. The audit tokens that
535 * are generated depend on the command that was sent into the fcntl()
536 * system call.
537 */
538static void
539audit_sys_fcntl(struct kaudit_record *kar, struct au_record *rec)
540{
541 struct au_token *tok;
542 struct audit_record *ar = &kar->k_ar;
543
544 switch (ar->ar_arg_cmd) {
545 case F_DUPFD:
546 if (ARG_IS_VALID(kar, ARG_VALUE32)) {
547 tok = au_to_arg32(n: 3, text: "min fd", v: ar->ar_arg_value32);
548 kau_write(rec, tok);
549 }
550 break;
551
552 case F_SETFD:
553 if (ARG_IS_VALID(kar, ARG_VALUE32)) {
554 tok = au_to_arg32(n: 3, text: "close-on-exec flag",
555 v: ar->ar_arg_value32);
556 kau_write(rec, tok);
557 }
558 break;
559
560 case F_SETFL:
561 if (ARG_IS_VALID(kar, ARG_VALUE32)) {
562 tok = au_to_arg32(n: 3, text: "fd flags", v: ar->ar_arg_value32);
563 kau_write(rec, tok);
564 }
565 break;
566
567 case F_SETOWN:
568 if (ARG_IS_VALID(kar, ARG_VALUE32)) {
569 tok = au_to_arg32(n: 3, text: "pid", v: ar->ar_arg_value32);
570 kau_write(rec, tok);
571 }
572 break;
573
574#ifdef F_SETSIZE
575 case F_SETSIZE:
576 if (ARG_IS_VALID(kar, ARG_VALUE64)) {
577 tok = au_to_arg64(n: 3, text: "offset", v: ar->ar_arg_value64);
578 kau_write(rec, tok);
579 }
580 break;
581#endif /* F_SETSIZE */
582
583#ifdef F_PATHPKG_CHECK
584 case F_PATHPKG_CHECK:
585 if (ARG_IS_VALID(kar, ARG_TEXT)) {
586 tok = au_to_text(text: ar->ar_arg_text);
587 kau_write(rec, tok);
588 }
589 break;
590#endif
591
592 default:
593 break;
594 }
595 tok = au_to_arg32(n: 2, text: "cmd", v: au_fcntl_cmd_to_bsm(local_fcntl_command: ar->ar_arg_cmd));
596 kau_write(rec, tok);
597}
598
599/*
600 * Convert an internal kernel audit record to a BSM record and return a
601 * success/failure indicator. The BSM record is passed as an out parameter to
602 * this function.
603 *
604 * Return conditions:
605 * BSM_SUCCESS: The BSM record is valid
606 * BSM_FAILURE: Failure; the BSM record is NULL.
607 * BSM_NOAUDIT: The event is not auditable for BSM; the BSM record is NULL.
608 */
609int
610kaudit_to_bsm(struct kaudit_record *kar, struct au_record **pau)
611{
612 struct au_token *tok = NULL, *subj_tok;
613 struct au_record *rec = NULL;
614 au_tid_t tid;
615 struct audit_record *ar;
616 int ctr;
617 u_int uctr;
618 int rv;
619
620 KASSERT(kar != NULL, ("kaudit_to_bsm: kar == NULL"));
621
622 *pau = NULL;
623 ar = &kar->k_ar;
624 rec = kau_open();
625
626 /*
627 * Create the subject token.
628 */
629 switch (ar->ar_subj_term_addr.at_type) {
630 case AU_IPv4:
631 tid.port = ar->ar_subj_term_addr.at_port;
632 tid.machine = ar->ar_subj_term_addr.at_addr[0];
633 subj_tok = au_to_subject32(auid: ar->ar_subj_auid, /* audit ID */
634 euid: ar->ar_subj_cred.cr_uid, /* eff uid */
635 egid: ar->ar_subj_egid, /* eff group id */
636 ruid: ar->ar_subj_ruid, /* real uid */
637 rgid: ar->ar_subj_rgid, /* real group id */
638 pid: ar->ar_subj_pid, /* process id */
639 sid: ar->ar_subj_asid, /* session ID */
640 tid: &tid);
641 break;
642 case AU_IPv6:
643 subj_tok = au_to_subject32_ex(auid: ar->ar_subj_auid,
644 euid: ar->ar_subj_cred.cr_uid,
645 egid: ar->ar_subj_egid,
646 ruid: ar->ar_subj_ruid,
647 rgid: ar->ar_subj_rgid,
648 pid: ar->ar_subj_pid,
649 sid: ar->ar_subj_asid,
650 tid: &ar->ar_subj_term_addr);
651 break;
652 default:
653 bzero(s: &tid, n: sizeof(tid));
654 subj_tok = au_to_subject32(auid: ar->ar_subj_auid,
655 euid: ar->ar_subj_cred.cr_uid,
656 egid: ar->ar_subj_egid,
657 ruid: ar->ar_subj_ruid,
658 rgid: ar->ar_subj_rgid,
659 pid: ar->ar_subj_pid,
660 sid: ar->ar_subj_asid,
661 tid: &tid);
662 }
663
664 /*
665 * The logic inside each case fills in the tokens required for the
666 * event, except for the header, trailer, and return tokens. The
667 * header and trailer tokens are added by the kau_close() function.
668 * The return token is added outside of the switch statement.
669 */
670 switch (ar->ar_event) {
671 case AUE_SENDFILE:
672 /* For sendfile the file and socket descriptor are both saved */
673 if (ARG_IS_VALID(kar, ARG_VALUE32)) {
674 tok = au_to_arg32(n: 2, text: "sd", v: ar->ar_arg_value32);
675 kau_write(rec, tok);
676 }
677 OS_FALLTHROUGH;
678 case AUE_ACCEPT:
679 case AUE_BIND:
680 case AUE_LISTEN:
681 case AUE_CONNECT:
682 case AUE_RECVFROM:
683 case AUE_RECVMSG:
684 case AUE_SENDMSG:
685 case AUE_SENDTO:
686 /*
687 * Socket-related events.
688 */
689 if (ARG_IS_VALID(kar, ARG_FD)) {
690 tok = au_to_arg32(n: 1, text: "fd", v: ar->ar_arg_fd);
691 kau_write(rec, tok);
692 }
693 if (ARG_IS_VALID(kar, ARG_SADDRINET)) {
694 tok = au_to_sock_inet(so: (struct sockaddr_in *)
695 &ar->ar_arg_sockaddr);
696 kau_write(rec, tok);
697 }
698 if (ARG_IS_VALID(kar, ARG_SADDRUNIX)) {
699 tok = au_to_sock_unix(so: (struct sockaddr_un *)
700 &ar->ar_arg_sockaddr);
701 kau_write(rec, tok);
702 UPATH1_TOKENS;
703 }
704 if (ARG_IS_VALID(kar, ARG_SADDRINET6)) {
705 tok = au_to_sock_inet128(so: (struct sockaddr_in6 *)
706 &ar->ar_arg_sockaddr);
707 kau_write(rec, tok);
708 }
709 break;
710
711 case AUE_SOCKET:
712 case AUE_SOCKETPAIR:
713 if (ARG_IS_VALID(kar, ARG_SOCKINFO)) {
714 tok = au_to_arg32(n: 1, text: "domain",
715 v: au_domain_to_bsm(local_domain: ar->ar_arg_sockinfo.sai_domain));
716 kau_write(rec, tok);
717 tok = au_to_arg32(n: 2, text: "type",
718 v: au_socket_type_to_bsm(local_socket_type: ar->ar_arg_sockinfo.sai_type));
719 kau_write(rec, tok);
720 tok = au_to_arg32(n: 3, text: "protocol",
721 v: ar->ar_arg_sockinfo.sai_protocol);
722 kau_write(rec, tok);
723 }
724 break;
725
726 case AUE_SETSOCKOPT:
727 case AUE_SHUTDOWN:
728 if (ARG_IS_VALID(kar, ARG_FD)) {
729 tok = au_to_arg32(n: 1, text: "fd", v: ar->ar_arg_fd);
730 kau_write(rec, tok);
731 }
732 break;
733
734 case AUE_ACCT:
735 if (ARG_IS_VALID(kar, (ARG_KPATH1 | ARG_UPATH1))) {
736 UPATH1_VNODE1_TOKENS;
737 } else {
738 tok = au_to_arg32(n: 1, text: "accounting off", v: 0);
739 kau_write(rec, tok);
740 }
741 break;
742
743 case AUE_SETAUID:
744 if (ARG_IS_VALID(kar, ARG_AUID)) {
745 tok = au_to_arg32(n: 2, text: "setauid", v: ar->ar_arg_auid);
746 kau_write(rec, tok);
747 }
748 break;
749
750 case AUE_SETAUDIT:
751 if (ARG_IS_VALID(kar, ARG_AUID) &&
752 ARG_IS_VALID(kar, ARG_ASID) &&
753 ARG_IS_VALID(kar, ARG_AMASK) &&
754 ARG_IS_VALID(kar, ARG_TERMID)) {
755 tok = au_to_arg32(n: 1, text: "setaudit:auid",
756 v: ar->ar_arg_auid);
757 kau_write(rec, tok);
758 tok = au_to_arg32(n: 1, text: "setaudit:port",
759 v: ar->ar_arg_termid.port);
760 kau_write(rec, tok);
761 tok = au_to_arg32(n: 1, text: "setaudit:machine",
762 v: ar->ar_arg_termid.machine);
763 kau_write(rec, tok);
764 tok = au_to_arg32(n: 1, text: "setaudit:as_success",
765 v: ar->ar_arg_amask.am_success);
766 kau_write(rec, tok);
767 tok = au_to_arg32(n: 1, text: "setaudit:as_failure",
768 v: ar->ar_arg_amask.am_failure);
769 kau_write(rec, tok);
770 tok = au_to_arg32(n: 1, text: "setaudit:asid",
771 v: ar->ar_arg_asid);
772 kau_write(rec, tok);
773 }
774 break;
775
776 case AUE_SETAUDIT_ADDR:
777 if (ARG_IS_VALID(kar, ARG_AUID) &&
778 ARG_IS_VALID(kar, ARG_ASID) &&
779 ARG_IS_VALID(kar, ARG_AMASK) &&
780 ARG_IS_VALID(kar, ARG_TERMID_ADDR)) {
781 tok = au_to_arg32(n: 1, text: "setaudit_addr:auid",
782 v: ar->ar_arg_auid);
783 kau_write(rec, tok);
784 tok = au_to_arg32(n: 1, text: "setaudit_addr:as_success",
785 v: ar->ar_arg_amask.am_success);
786 kau_write(rec, tok);
787 tok = au_to_arg32(n: 1, text: "setaudit_addr:as_failure",
788 v: ar->ar_arg_amask.am_failure);
789 kau_write(rec, tok);
790 tok = au_to_arg32(n: 1, text: "setaudit_addr:asid",
791 v: ar->ar_arg_asid);
792 kau_write(rec, tok);
793 tok = au_to_arg32(n: 1, text: "setaudit_addr:type",
794 v: ar->ar_arg_termid_addr.at_type);
795 kau_write(rec, tok);
796 tok = au_to_arg32(n: 1, text: "setaudit_addr:port",
797 v: ar->ar_arg_termid_addr.at_port);
798 kau_write(rec, tok);
799 switch (ar->ar_arg_termid_addr.at_type) {
800 case AU_IPv6:
801 tok = au_to_in_addr_ex(internet_addr: (struct in6_addr *)
802 &ar->ar_arg_termid_addr.at_addr[0]);
803 kau_write(rec, tok);
804 break;
805 case AU_IPv4:
806 tok = au_to_in_addr(internet_addr: (struct in_addr *)
807 &ar->ar_arg_termid_addr.at_addr[0]);
808 kau_write(rec, tok);
809 break;
810 }
811 }
812 break;
813
814 case AUE_AUDITON:
815 /*
816 * For AUDITON commands without own event, audit the cmd.
817 */
818 if (ARG_IS_VALID(kar, ARG_CMD)) {
819 tok = au_to_arg32(n: 1, text: "cmd", v: ar->ar_arg_cmd);
820 kau_write(rec, tok);
821 }
822 OS_FALLTHROUGH;
823
824 case AUE_AUDITON_GETCAR:
825 case AUE_AUDITON_GETCLASS:
826 case AUE_AUDITON_GETCOND:
827 case AUE_AUDITON_GETCWD:
828 case AUE_AUDITON_GETKMASK:
829 case AUE_AUDITON_GETSTAT:
830 case AUE_AUDITON_GPOLICY:
831 case AUE_AUDITON_GQCTRL:
832 case AUE_AUDITON_SETCLASS:
833 case AUE_AUDITON_SETCOND:
834 case AUE_AUDITON_SETKMASK:
835 case AUE_AUDITON_SETSMASK:
836 case AUE_AUDITON_SETSTAT:
837 case AUE_AUDITON_SETUMASK:
838 case AUE_AUDITON_SPOLICY:
839 case AUE_AUDITON_SQCTRL:
840 if (ARG_IS_VALID(kar, ARG_AUDITON)) {
841 audit_sys_auditon(ar, rec);
842 }
843 break;
844
845 case AUE_AUDITCTL:
846 UPATH1_VNODE1_TOKENS;
847 break;
848
849 case AUE_EXIT:
850 if (ARG_IS_VALID(kar, ARG_EXIT)) {
851 tok = au_to_exit(retval: ar->ar_arg_exitretval,
852 err: ar->ar_arg_exitstatus);
853 kau_write(rec, tok);
854 }
855 break;
856
857 case AUE_ADJTIME:
858 case AUE_AUDIT:
859 case AUE_DUP2:
860 case AUE_GETAUDIT:
861 case AUE_GETAUDIT_ADDR:
862 case AUE_GETAUID:
863 case AUE_GETFSSTAT:
864 case AUE_KQUEUE:
865 case AUE_LSEEK:
866#if 0
867/* XXXss replace with kext */
868 case AUE_MODLOAD:
869 case AUE_MODUNLOAD:
870#endif
871 case AUE_MAC_GETFSSTAT:
872 case AUE_PIPE:
873 case AUE_PROFILE:
874 case AUE_SEMSYS:
875 case AUE_SHMSYS:
876 case AUE_SETPGRP:
877 case AUE_SETRLIMIT:
878 case AUE_SETSID:
879 case AUE_SETTIMEOFDAY:
880 case AUE_KDEBUGTRACE:
881 case AUE_PTHREADSIGMASK:
882 /*
883 * Header, subject, and return tokens added at end.
884 */
885 break;
886
887 case AUE_MKFIFO:
888 if (ARG_IS_VALID(kar, ARG_MODE)) {
889 tok = au_to_arg32(n: 2, text: "mode", v: ar->ar_arg_mode);
890 kau_write(rec, tok);
891 }
892 UPATH1_VNODE1_TOKENS;
893 break;
894
895 case AUE_ACCESS_EXTENDED:
896 /*
897 * The access_extended() argument vector is stored in an
898 * opaque token.
899 */
900 if (ARG_IS_VALID(kar, ARG_OPAQUE)) {
901 tok = au_to_opaque(data: ar->ar_arg_opaque,
902 bytes: ar->ar_arg_opq_size);
903 kau_write(rec, tok);
904 }
905 /*
906 * The access_extended() result vector is stored in an arbitrary
907 * data token.
908 */
909 if (ARG_IS_VALID(kar, ARG_DATA)) {
910 tok = au_to_data(AUP_DECIMAL, unit_type: ar->ar_arg_data_type,
911 unit_count: ar->ar_arg_data_count, p: ar->ar_arg_data);
912 kau_write(rec, tok);
913 }
914 UPATH1_VNODE1_TOKENS;
915 break;
916
917 case AUE_LSTAT_EXTENDED:
918 case AUE_STAT_EXTENDED:
919 case AUE_ACCESS:
920 case AUE_CHDIR:
921 case AUE_CHROOT:
922 case AUE_GETATTRLIST:
923 case AUE_NFS_GETFH:
924 case AUE_LSTAT:
925 case AUE_PATHCONF:
926 case AUE_READLINK:
927 case AUE_REVOKE:
928 case AUE_RMDIR:
929 case AUE_SEARCHFS:
930 case AUE_SETATTRLIST:
931 case AUE_STAT:
932 case AUE_STATFS:
933 case AUE_TRUNCATE:
934 case AUE_UNDELETE:
935 case AUE_UNLINK:
936 case AUE_UTIMES:
937 UPATH1_VNODE1_TOKENS;
938 break;
939
940 case AUE_FHOPEN:
941 break;
942
943 case AUE_CHFLAGS:
944 if (ARG_IS_VALID(kar, ARG_FFLAGS)) {
945 tok = au_to_arg32(n: 2, text: "flags", v: ar->ar_arg_fflags);
946 kau_write(rec, tok);
947 }
948 UPATH1_VNODE1_TOKENS;
949 break;
950
951 case AUE_CHMOD:
952 if (ARG_IS_VALID(kar, ARG_MODE)) {
953 tok = au_to_arg32(n: 2, text: "new file mode",
954 v: ar->ar_arg_mode);
955 kau_write(rec, tok);
956 }
957 UPATH1_VNODE1_TOKENS;
958 break;
959
960 case AUE_CHOWN:
961 case AUE_LCHOWN:
962 if (ARG_IS_VALID(kar, ARG_UID)) {
963 tok = au_to_arg32(n: 2, text: "new file uid", v: ar->ar_arg_uid);
964 kau_write(rec, tok);
965 }
966 if (ARG_IS_VALID(kar, ARG_GID)) {
967 tok = au_to_arg32(n: 3, text: "new file gid", v: ar->ar_arg_gid);
968 kau_write(rec, tok);
969 }
970 UPATH1_VNODE1_TOKENS;
971 break;
972
973 case AUE_EXCHANGEDATA:
974 UPATH1_VNODE1_TOKENS;
975 UPATH2_TOKENS;
976 break;
977
978 case AUE_CLOSE:
979 if (ARG_IS_VALID(kar, ARG_FD)) {
980 tok = au_to_arg32(n: 2, text: "fd", v: ar->ar_arg_fd);
981 kau_write(rec, tok);
982 }
983 UPATH1_VNODE1_TOKENS;
984 break;
985
986 case AUE_CORE:
987 if (ARG_IS_VALID(kar, ARG_SIGNUM)) {
988 tok = au_to_arg32(n: 0, text: "signal", v: ar->ar_arg_signum);
989 kau_write(rec, tok);
990 }
991 UPATH1_VNODE1_TOKENS;
992 break;
993
994 case AUE_POSIX_SPAWN:
995 if (ARG_IS_VALID(kar, ARG_PID)) {
996 tok = au_to_arg32(n: 0, text: "child PID", v: ar->ar_arg_pid);
997 kau_write(rec, tok);
998 }
999 OS_FALLTHROUGH;
1000
1001 case AUE_EXECVE:
1002 if (ARG_IS_VALID(kar, ARG_ARGV)) {
1003 tok = au_to_exec_args(args: ar->ar_arg_argv,
1004 argc: ar->ar_arg_argc);
1005 kau_write(rec, tok);
1006 }
1007 if (ARG_IS_VALID(kar, ARG_ENVV)) {
1008 tok = au_to_exec_env(envs: ar->ar_arg_envv,
1009 envc: ar->ar_arg_envc);
1010 kau_write(rec, tok);
1011 }
1012 UPATH1_VNODE1_TOKENS;
1013 VNODE2_PATH_TOKENS;
1014 if (ARG_IS_VALID(kar, ARG_DATA)) {
1015 tok = au_to_data(AUP_HEX, unit_type: ar->ar_arg_data_type,
1016 unit_count: ar->ar_arg_data_count, p: ar->ar_arg_data);
1017 kau_write(rec, tok);
1018 }
1019 break;
1020
1021 case AUE_FCHMOD_EXTENDED:
1022 EXTENDED_TOKENS(2);
1023 FD_VNODE1_TOKENS;
1024 break;
1025
1026 case AUE_FCHMOD:
1027 if (ARG_IS_VALID(kar, ARG_MODE)) {
1028 tok = au_to_arg32(n: 2, text: "new file mode",
1029 v: ar->ar_arg_mode);
1030 kau_write(rec, tok);
1031 }
1032 FD_VNODE1_TOKENS;
1033 break;
1034
1035 case AUE_NFS_SVC:
1036 tok = au_to_arg32(n: 1, text: "request", v: ar->ar_arg_cmd);
1037 kau_write(rec, tok);
1038 if (ar->ar_valid_arg & (ARG_KPATH1 | ARG_UPATH1)) {
1039 UPATH1_VNODE1_TOKENS;
1040 }
1041 break;
1042
1043 /*
1044 * XXXRW: Some of these need to handle non-vnode cases as well.
1045 */
1046 case AUE_FSTAT_EXTENDED:
1047 case AUE_FCHDIR:
1048 case AUE_FPATHCONF:
1049 case AUE_FSTAT: /* XXX Need to handle sockets and shm */
1050 case AUE_FSTATFS:
1051 case AUE_FSYNC:
1052 case AUE_FTRUNCATE:
1053 case AUE_FUTIMES:
1054 case AUE_GETDIRENTRIES:
1055 case AUE_GETDIRENTRIESATTR:
1056 case AUE_GETATTRLISTBULK:
1057#if 0 /* XXXss new */
1058 case AUE_POLL:
1059#endif
1060 case AUE_READ:
1061 case AUE_READV:
1062 case AUE_PREAD:
1063 case AUE_PREADV:
1064 case AUE_WRITE:
1065 case AUE_WRITEV:
1066 case AUE_PWRITE:
1067 case AUE_PWRITEV:
1068 FD_VNODE1_TOKENS;
1069 break;
1070
1071 case AUE_FCHOWN:
1072 if (ARG_IS_VALID(kar, ARG_UID)) {
1073 tok = au_to_arg32(n: 2, text: "new file uid", v: ar->ar_arg_uid);
1074 kau_write(rec, tok);
1075 }
1076 if (ARG_IS_VALID(kar, ARG_GID)) {
1077 tok = au_to_arg32(n: 3, text: "new file gid", v: ar->ar_arg_gid);
1078 kau_write(rec, tok);
1079 }
1080 FD_VNODE1_TOKENS;
1081 break;
1082
1083 case AUE_FCNTL:
1084 if (ARG_IS_VALID(kar, ARG_CMD)) {
1085 audit_sys_fcntl(kar, rec);
1086 }
1087 FD_VNODE1_TOKENS;
1088 break;
1089
1090 case AUE_FSCTL:
1091 if (ARG_IS_VALID(kar, ARG_VALUE32)) {
1092 tok = au_to_arg32(n: 4, text: "options", v: ar->ar_arg_value32);
1093 kau_write(rec, tok);
1094 }
1095 if (ARG_IS_VALID(kar, ARG_CMD)) {
1096 tok = au_to_arg32(n: 2, text: "cmd", v: ar->ar_arg_cmd);
1097 kau_write(rec, tok);
1098 }
1099 UPATH1_VNODE1_TOKENS;
1100 break;
1101
1102 case AUE_FFSCTL:
1103 if (ARG_IS_VALID(kar, ARG_VALUE32)) {
1104 tok = au_to_arg32(n: 4, text: "options", v: ar->ar_arg_value32);
1105 kau_write(rec, tok);
1106 }
1107 if (ARG_IS_VALID(kar, ARG_CMD)) {
1108 tok = au_to_arg32(n: 2, text: "cmd", v: ar->ar_arg_cmd);
1109 kau_write(rec, tok);
1110 }
1111 FD_VNODE1_TOKENS;
1112 break;
1113
1114
1115 case AUE_FCHFLAGS:
1116 if (ARG_IS_VALID(kar, ARG_FFLAGS)) {
1117 tok = au_to_arg32(n: 2, text: "flags", v: ar->ar_arg_fflags);
1118 kau_write(rec, tok);
1119 }
1120 FD_VNODE1_TOKENS;
1121 break;
1122
1123 case AUE_FLOCK:
1124 if (ARG_IS_VALID(kar, ARG_CMD)) {
1125 tok = au_to_arg32(n: 2, text: "operation", v: ar->ar_arg_cmd);
1126 kau_write(rec, tok);
1127 }
1128 FD_VNODE1_TOKENS;
1129 break;
1130
1131 case AUE_FORK:
1132 case AUE_VFORK:
1133 if (ARG_IS_VALID(kar, ARG_PID)) {
1134 tok = au_to_arg32(n: 0, text: "child PID", v: ar->ar_arg_pid);
1135 kau_write(rec, tok);
1136 }
1137 break;
1138
1139 case AUE_GETLCID:
1140 if (ARG_IS_VALID(kar, ARG_PID)) {
1141 tok = au_to_arg32(n: 1, text: "pid", v: (u_int32_t)ar->ar_arg_pid);
1142 kau_write(rec, tok);
1143 }
1144 break;
1145
1146 case AUE_SETLCID:
1147 if (ARG_IS_VALID(kar, ARG_PID)) {
1148 tok = au_to_arg32(n: 1, text: "pid", v: (u_int32_t)ar->ar_arg_pid);
1149 kau_write(rec, tok);
1150 }
1151 if (ARG_IS_VALID(kar, ARG_VALUE32)) {
1152 tok = au_to_arg32(n: 2, text: "lcid",
1153 v: (u_int32_t)ar->ar_arg_value32);
1154 kau_write(rec, tok);
1155 }
1156 break;
1157
1158 case AUE_IOCTL:
1159 if (ARG_IS_VALID(kar, ARG_CMD)) {
1160 tok = au_to_arg32(n: 2, text: "cmd", v: ar->ar_arg_cmd);
1161 kau_write(rec, tok);
1162 }
1163 if (ARG_IS_VALID(kar, ARG_VALUE64)) {
1164 tok = au_to_arg64(n: 2, text: "cmd", v: ar->ar_arg_value64);
1165 kau_write(rec, tok);
1166 }
1167 if (ARG_IS_VALID(kar, ARG_ADDR64)) {
1168 tok = au_to_arg64(n: 3, text: "arg", v: ar->ar_arg_addr);
1169 kau_write(rec, tok);
1170 } else if (ARG_IS_VALID(kar, ARG_ADDR32)) {
1171 tok = au_to_arg32(n: 3, text: "arg",
1172 v: (u_int32_t)ar->ar_arg_addr);
1173 kau_write(rec, tok);
1174 }
1175 if (ARG_IS_VALID(kar, ARG_VNODE1)) {
1176 FD_VNODE1_TOKENS;
1177 } else {
1178 if (ARG_IS_VALID(kar, ARG_SOCKINFO)) {
1179 tok = au_to_socket_ex(
1180 so_domain: ar->ar_arg_sockinfo.sai_domain,
1181 so_type: ar->ar_arg_sockinfo.sai_type,
1182 sa_local: (struct sockaddr *)
1183 &ar->ar_arg_sockinfo.sai_laddr,
1184 sa_remote: (struct sockaddr *)
1185 &ar->ar_arg_sockinfo.sai_faddr);
1186 kau_write(rec, tok);
1187 } else {
1188 if (ARG_IS_VALID(kar, ARG_FD)) {
1189 tok = au_to_arg32(n: 1, text: "fd",
1190 v: ar->ar_arg_fd);
1191 kau_write(rec, tok);
1192 }
1193 }
1194 }
1195 break;
1196
1197 case AUE_KILL:
1198 if (ARG_IS_VALID(kar, ARG_SIGNUM)) {
1199 tok = au_to_arg32(n: 2, text: "signal", v: ar->ar_arg_signum);
1200 kau_write(rec, tok);
1201 }
1202 PROCESS_PID_TOKENS(1);
1203 break;
1204
1205 case AUE_LINK:
1206 case AUE_RENAME:
1207 UPATH1_VNODE1_TOKENS;
1208 UPATH2_TOKENS;
1209 KPATH2_TOKENS;
1210 break;
1211
1212 case AUE_MKDIR_EXTENDED:
1213 case AUE_CHMOD_EXTENDED:
1214 case AUE_MKFIFO_EXTENDED:
1215 EXTENDED_TOKENS(2);
1216 UPATH1_VNODE1_TOKENS;
1217 break;
1218
1219 case AUE_MKDIR:
1220 if (ARG_IS_VALID(kar, ARG_MODE)) {
1221 tok = au_to_arg32(n: 2, text: "mode", v: ar->ar_arg_mode);
1222 kau_write(rec, tok);
1223 }
1224 UPATH1_VNODE1_TOKENS;
1225 break;
1226
1227 case AUE_MKNOD:
1228 if (ARG_IS_VALID(kar, ARG_MODE)) {
1229 tok = au_to_arg32(n: 2, text: "mode", v: ar->ar_arg_mode);
1230 kau_write(rec, tok);
1231 }
1232 if (ARG_IS_VALID(kar, ARG_VALUE32)) {
1233 tok = au_to_arg32(n: 3, text: "dev", v: ar->ar_arg_value32);
1234 kau_write(rec, tok);
1235 }
1236 UPATH1_VNODE1_TOKENS;
1237 break;
1238
1239 case AUE_MMAP:
1240 case AUE_MUNMAP:
1241 case AUE_MPROTECT:
1242 case AUE_MLOCK:
1243 case AUE_MUNLOCK:
1244 case AUE_MINHERIT:
1245 if (ARG_IS_VALID(kar, ARG_ADDR64)) {
1246 tok = au_to_arg64(n: 1, text: "addr", v: ar->ar_arg_addr);
1247 kau_write(rec, tok);
1248 } else if (ARG_IS_VALID(kar, ARG_ADDR32)) {
1249 tok = au_to_arg32(n: 1, text: "addr",
1250 v: (u_int32_t)ar->ar_arg_addr);
1251 kau_write(rec, tok);
1252 }
1253 if (ARG_IS_VALID(kar, ARG_LEN)) {
1254 tok = au_to_arg64(n: 2, text: "len", v: ar->ar_arg_len);
1255 kau_write(rec, tok);
1256 }
1257 if (ar->ar_event == AUE_MMAP) {
1258 FD_VNODE1_TOKENS;
1259 }
1260 if (ar->ar_event == AUE_MPROTECT) {
1261 if (ARG_IS_VALID(kar, ARG_VALUE32)) {
1262 tok = au_to_arg32(n: 3, text: "protection",
1263 v: ar->ar_arg_value32);
1264 kau_write(rec, tok);
1265 }
1266 }
1267 if (ar->ar_event == AUE_MINHERIT) {
1268 if (ARG_IS_VALID(kar, ARG_VALUE32)) {
1269 tok = au_to_arg32(n: 3, text: "inherit",
1270 v: ar->ar_arg_value32);
1271 kau_write(rec, tok);
1272 }
1273 }
1274 break;
1275
1276#if CONFIG_MACF
1277 case AUE_MAC_MOUNT:
1278 PROCESS_MAC_TOKENS;
1279 OS_FALLTHROUGH;
1280#endif
1281 case AUE_MOUNT:
1282 /* XXX Need to handle NFS mounts */
1283 if (ARG_IS_VALID(kar, ARG_FFLAGS)) {
1284 tok = au_to_arg32(n: 3, text: "flags", v: ar->ar_arg_fflags);
1285 kau_write(rec, tok);
1286 }
1287 if (ARG_IS_VALID(kar, ARG_TEXT)) {
1288 tok = au_to_text(text: ar->ar_arg_text);
1289 kau_write(rec, tok);
1290 }
1291 OS_FALLTHROUGH;
1292
1293 case AUE_UMOUNT:
1294 case AUE_UNMOUNT:
1295 UPATH1_VNODE1_TOKENS;
1296 break;
1297 case AUE_FMOUNT:
1298 if (ARG_IS_VALID(kar, ARG_FD)) {
1299 tok = au_to_arg32(n: 2, text: "dir fd", v: ar->ar_arg_fd);
1300 kau_write(rec, tok);
1301 }
1302 if (ARG_IS_VALID(kar, ARG_FFLAGS)) {
1303 tok = au_to_arg32(n: 3, text: "flags", v: ar->ar_arg_fflags);
1304 kau_write(rec, tok);
1305 }
1306 if (ARG_IS_VALID(kar, ARG_TEXT)) {
1307 tok = au_to_text(text: ar->ar_arg_text);
1308 kau_write(rec, tok);
1309 }
1310 break;
1311
1312 case AUE_MSGCTL:
1313 ar->ar_event = audit_msgctl_to_event(cmd: ar->ar_arg_svipc_cmd);
1314 OS_FALLTHROUGH;
1315
1316 case AUE_MSGRCV:
1317 case AUE_MSGSND:
1318 tok = au_to_arg32(n: 1, text: "msg ID", v: ar->ar_arg_svipc_id);
1319 kau_write(rec, tok);
1320 if (ar->ar_errno != EINVAL) {
1321 tok = au_to_ipc(AT_IPC_MSG, id: ar->ar_arg_svipc_id);
1322 kau_write(rec, tok);
1323 }
1324 break;
1325
1326 case AUE_MSGGET:
1327 if (ar->ar_errno == 0) {
1328 if (ARG_IS_VALID(kar, ARG_SVIPC_ID)) {
1329 tok = au_to_ipc(AT_IPC_MSG,
1330 id: ar->ar_arg_svipc_id);
1331 kau_write(rec, tok);
1332 }
1333 }
1334 break;
1335
1336 case AUE_OPEN:
1337 case AUE_OPEN_R:
1338 case AUE_OPEN_RT:
1339 case AUE_OPEN_RW:
1340 case AUE_OPEN_RWT:
1341 case AUE_OPEN_W:
1342 case AUE_OPEN_WT:
1343 if (ARG_IS_VALID(kar, ARG_FFLAGS)) {
1344 tok = au_to_arg32(n: 2, text: "flags", v: ar->ar_arg_fflags);
1345 kau_write(rec, tok);
1346 }
1347 UPATH1_VNODE1_TOKENS;
1348 break;
1349
1350 case AUE_OPEN_RC:
1351 case AUE_OPEN_RTC:
1352 case AUE_OPEN_RWC:
1353 case AUE_OPEN_RWTC:
1354 case AUE_OPEN_WC:
1355 case AUE_OPEN_WTC:
1356 if (ARG_IS_VALID(kar, ARG_MODE)) {
1357 tok = au_to_arg32(n: 3, text: "mode", v: ar->ar_arg_mode);
1358 kau_write(rec, tok);
1359 }
1360 if (ARG_IS_VALID(kar, ARG_FFLAGS)) {
1361 tok = au_to_arg32(n: 2, text: "flags", v: ar->ar_arg_fflags);
1362 kau_write(rec, tok);
1363 }
1364 UPATH1_VNODE1_TOKENS;
1365 break;
1366
1367 case AUE_OPEN_EXTENDED:
1368 case AUE_OPEN_EXTENDED_R:
1369 case AUE_OPEN_EXTENDED_RT:
1370 case AUE_OPEN_EXTENDED_RW:
1371 case AUE_OPEN_EXTENDED_RWT:
1372 case AUE_OPEN_EXTENDED_W:
1373 case AUE_OPEN_EXTENDED_WT:
1374 EXTENDED_TOKENS(3);
1375 if (ARG_IS_VALID(kar, ARG_FFLAGS)) {
1376 tok = au_to_arg32(n: 2, text: "flags", v: ar->ar_arg_fflags);
1377 kau_write(rec, tok);
1378 }
1379 UPATH1_VNODE1_TOKENS;
1380 break;
1381
1382 case AUE_OPEN_EXTENDED_RC:
1383 case AUE_OPEN_EXTENDED_RTC:
1384 case AUE_OPEN_EXTENDED_RWC:
1385 case AUE_OPEN_EXTENDED_RWTC:
1386 case AUE_OPEN_EXTENDED_WC:
1387 case AUE_OPEN_EXTENDED_WTC:
1388 EXTENDED_TOKENS(3);
1389 if (ARG_IS_VALID(kar, ARG_FFLAGS)) {
1390 tok = au_to_arg32(n: 2, text: "flags", v: ar->ar_arg_fflags);
1391 kau_write(rec, tok);
1392 }
1393 UPATH1_VNODE1_TOKENS;
1394 break;
1395
1396 case AUE_OPENAT:
1397 case AUE_OPENAT_R:
1398 case AUE_OPENAT_RT:
1399 case AUE_OPENAT_RW:
1400 case AUE_OPENAT_RWT:
1401 case AUE_OPENAT_W:
1402 case AUE_OPENAT_WT:
1403 if (ARG_IS_VALID(kar, ARG_FFLAGS)) {
1404 tok = au_to_arg32(n: 3, text: "flags", v: ar->ar_arg_fflags);
1405 kau_write(rec, tok);
1406 }
1407 if (ARG_IS_VALID(kar, ARG_FD)) {
1408 tok = au_to_arg32(n: 1, text: "dir fd", v: ar->ar_arg_fd);
1409 kau_write(rec, tok);
1410 }
1411 UPATH1_VNODE1_TOKENS;
1412 break;
1413
1414 case AUE_OPENAT_RC:
1415 case AUE_OPENAT_RTC:
1416 case AUE_OPENAT_RWC:
1417 case AUE_OPENAT_RWTC:
1418 case AUE_OPENAT_WC:
1419 case AUE_OPENAT_WTC:
1420 if (ARG_IS_VALID(kar, ARG_MODE)) {
1421 tok = au_to_arg32(n: 4, text: "mode", v: ar->ar_arg_mode);
1422 kau_write(rec, tok);
1423 }
1424 if (ARG_IS_VALID(kar, ARG_FFLAGS)) {
1425 tok = au_to_arg32(n: 3, text: "flags", v: ar->ar_arg_fflags);
1426 kau_write(rec, tok);
1427 }
1428 if (ARG_IS_VALID(kar, ARG_FD)) {
1429 tok = au_to_arg32(n: 1, text: "dir fd", v: ar->ar_arg_fd);
1430 kau_write(rec, tok);
1431 }
1432 UPATH1_VNODE1_TOKENS;
1433 break;
1434
1435 case AUE_OPENBYID:
1436 case AUE_OPENBYID_R:
1437 case AUE_OPENBYID_RT:
1438 case AUE_OPENBYID_RW:
1439 case AUE_OPENBYID_RWT:
1440 case AUE_OPENBYID_W:
1441 case AUE_OPENBYID_WT:
1442 if (ARG_IS_VALID(kar, ARG_FFLAGS)) {
1443 tok = au_to_arg32(n: 3, text: "flags", v: ar->ar_arg_fflags);
1444 kau_write(rec, tok);
1445 }
1446 if (ARG_IS_VALID(kar, ARG_VALUE32)) {
1447 tok = au_to_arg32(n: 1, text: "volfsid", v: ar->ar_arg_value32);
1448 kau_write(rec, tok);
1449 }
1450 if (ARG_IS_VALID(kar, ARG_VALUE64)) {
1451 tok = au_to_arg64(n: 2, text: "objid", v: ar->ar_arg_value64);
1452 kau_write(rec, tok);
1453 }
1454 break;
1455
1456 case AUE_RENAMEAT:
1457 case AUE_FACCESSAT:
1458 case AUE_FCHMODAT:
1459 case AUE_FCHOWNAT:
1460 case AUE_FSTATAT:
1461 case AUE_LINKAT:
1462 case AUE_UNLINKAT:
1463 case AUE_READLINKAT:
1464 case AUE_SYMLINKAT:
1465 case AUE_MKDIRAT:
1466 case AUE_GETATTRLISTAT:
1467 case AUE_SETATTRLISTAT:
1468 case AUE_MKFIFOAT:
1469 case AUE_MKNODAT:
1470 if (ARG_IS_VALID(kar, ARG_FD)) {
1471 tok = au_to_arg32(n: 1, text: "dir fd", v: ar->ar_arg_fd);
1472 kau_write(rec, tok);
1473 }
1474 UPATH1_VNODE1_TOKENS;
1475 break;
1476
1477 case AUE_CLONEFILEAT:
1478 if (ARG_IS_VALID(kar, ARG_FD)) {
1479 tok = au_to_arg32(n: 1, text: "src dir fd", v: ar->ar_arg_fd);
1480 kau_write(rec, tok);
1481 }
1482 UPATH1_VNODE1_TOKENS;
1483 if (ARG_IS_VALID(kar, ARG_FD2)) {
1484 tok = au_to_arg32(n: 1, text: "dst dir fd", v: ar->ar_arg_fd2);
1485 kau_write(rec, tok);
1486 }
1487 UPATH2_TOKENS;
1488 if (ARG_IS_VALID(kar, ARG_VALUE32)) {
1489 tok = au_to_arg32(n: 1, text: "flags", v: ar->ar_arg_value32);
1490 kau_write(rec, tok);
1491 }
1492 break;
1493
1494 case AUE_FCLONEFILEAT:
1495 FD_VNODE1_TOKENS;
1496 if (ARG_IS_VALID(kar, ARG_FD2)) {
1497 tok = au_to_arg32(n: 1, text: "dst dir fd", v: ar->ar_arg_fd2);
1498 kau_write(rec, tok);
1499 }
1500 UPATH2_TOKENS;
1501 if (ARG_IS_VALID(kar, ARG_VALUE32)) {
1502 tok = au_to_arg32(n: 1, text: "flags", v: ar->ar_arg_value32);
1503 kau_write(rec, tok);
1504 }
1505 break;
1506
1507 case AUE_PTRACE:
1508 if (ARG_IS_VALID(kar, ARG_CMD)) {
1509 tok = au_to_arg32(n: 1, text: "request", v: ar->ar_arg_cmd);
1510 kau_write(rec, tok);
1511 }
1512 if (ARG_IS_VALID(kar, ARG_ADDR64)) {
1513 tok = au_to_arg64(n: 3, text: "addr", v: ar->ar_arg_addr);
1514 kau_write(rec, tok);
1515 } else if (ARG_IS_VALID(kar, ARG_ADDR32)) {
1516 tok = au_to_arg32(n: 3, text: "addr",
1517 v: (u_int32_t)ar->ar_arg_addr);
1518 kau_write(rec, tok);
1519 }
1520 if (ARG_IS_VALID(kar, ARG_VALUE32)) {
1521 tok = au_to_arg32(n: 4, text: "data", v: ar->ar_arg_value32);
1522 kau_write(rec, tok);
1523 }
1524 PROCESS_PID_TOKENS(2);
1525 break;
1526
1527 case AUE_QUOTACTL:
1528 if (ARG_IS_VALID(kar, ARG_CMD)) {
1529 tok = au_to_arg32(n: 2, text: "command", v: ar->ar_arg_cmd);
1530 kau_write(rec, tok);
1531 }
1532 if (ARG_IS_VALID(kar, ARG_UID)) {
1533 tok = au_to_arg32(n: 3, text: "uid", v: ar->ar_arg_uid);
1534 kau_write(rec, tok);
1535 }
1536 UPATH1_VNODE1_TOKENS;
1537 break;
1538
1539 case AUE_REBOOT:
1540 if (ARG_IS_VALID(kar, ARG_CMD)) {
1541 tok = au_to_arg32(n: 1, text: "howto", v: ar->ar_arg_cmd);
1542 kau_write(rec, tok);
1543 }
1544 break;
1545
1546 case AUE_SEMCTL:
1547 ar->ar_event = audit_semctl_to_event(cmr: ar->ar_arg_svipc_cmd);
1548 OS_FALLTHROUGH;
1549
1550 case AUE_SEMOP:
1551 if (ARG_IS_VALID(kar, ARG_SVIPC_ID)) {
1552 tok = au_to_arg32(n: 1, text: "sem ID", v: ar->ar_arg_svipc_id);
1553 kau_write(rec, tok);
1554 if (ar->ar_errno != EINVAL) {
1555 tok = au_to_ipc(AT_IPC_SEM,
1556 id: ar->ar_arg_svipc_id);
1557 kau_write(rec, tok);
1558 }
1559 }
1560 break;
1561
1562 case AUE_SEMGET:
1563 if (ar->ar_errno == 0) {
1564 if (ARG_IS_VALID(kar, ARG_SVIPC_ID)) {
1565 tok = au_to_ipc(AT_IPC_SEM,
1566 id: ar->ar_arg_svipc_id);
1567 kau_write(rec, tok);
1568 }
1569 }
1570 break;
1571
1572 case AUE_SETEGID:
1573 if (ARG_IS_VALID(kar, ARG_EGID)) {
1574 tok = au_to_arg32(n: 1, text: "gid", v: ar->ar_arg_egid);
1575 kau_write(rec, tok);
1576 }
1577 break;
1578
1579 case AUE_SETEUID:
1580 if (ARG_IS_VALID(kar, ARG_EUID)) {
1581 tok = au_to_arg32(n: 1, text: "uid", v: ar->ar_arg_euid);
1582 kau_write(rec, tok);
1583 }
1584 break;
1585
1586 case AUE_SETREGID:
1587 if (ARG_IS_VALID(kar, ARG_RGID)) {
1588 tok = au_to_arg32(n: 1, text: "rgid", v: ar->ar_arg_rgid);
1589 kau_write(rec, tok);
1590 }
1591 if (ARG_IS_VALID(kar, ARG_EGID)) {
1592 tok = au_to_arg32(n: 2, text: "egid", v: ar->ar_arg_egid);
1593 kau_write(rec, tok);
1594 }
1595 break;
1596
1597 case AUE_SETREUID:
1598 if (ARG_IS_VALID(kar, ARG_RUID)) {
1599 tok = au_to_arg32(n: 1, text: "ruid", v: ar->ar_arg_ruid);
1600 kau_write(rec, tok);
1601 }
1602 if (ARG_IS_VALID(kar, ARG_EUID)) {
1603 tok = au_to_arg32(n: 2, text: "euid", v: ar->ar_arg_euid);
1604 kau_write(rec, tok);
1605 }
1606 break;
1607
1608 case AUE_SETGID:
1609 if (ARG_IS_VALID(kar, ARG_GID)) {
1610 tok = au_to_arg32(n: 1, text: "gid", v: ar->ar_arg_gid);
1611 kau_write(rec, tok);
1612 }
1613 break;
1614
1615 case AUE_SETUID:
1616 if (ARG_IS_VALID(kar, ARG_UID)) {
1617 tok = au_to_arg32(n: 1, text: "uid", v: ar->ar_arg_uid);
1618 kau_write(rec, tok);
1619 }
1620 break;
1621
1622 case AUE_SETGROUPS:
1623 if (ARG_IS_VALID(kar, ARG_GROUPSET)) {
1624 for (uctr = 0; uctr < ar->ar_arg_groups.gidset_size;
1625 uctr++) {
1626 tok = au_to_arg32(n: 1, text: "setgroups",
1627 v: ar->ar_arg_groups.gidset[uctr]);
1628 kau_write(rec, tok);
1629 }
1630 }
1631 break;
1632
1633 case AUE_SETLOGIN:
1634 if (ARG_IS_VALID(kar, ARG_TEXT)) {
1635 tok = au_to_text(text: ar->ar_arg_text);
1636 kau_write(rec, tok);
1637 }
1638 break;
1639
1640 case AUE_SETPRIORITY:
1641 if (ARG_IS_VALID(kar, ARG_CMD)) {
1642 tok = au_to_arg32(n: 1, text: "which", v: ar->ar_arg_cmd);
1643 kau_write(rec, tok);
1644 }
1645 if (ARG_IS_VALID(kar, ARG_UID)) {
1646 tok = au_to_arg32(n: 2, text: "who", v: ar->ar_arg_uid);
1647 kau_write(rec, tok);
1648 }
1649 if (ARG_IS_VALID(kar, ARG_VALUE32)) {
1650 tok = au_to_arg32(n: 2, text: "priority", v: ar->ar_arg_value32);
1651 kau_write(rec, tok);
1652 }
1653 break;
1654
1655 case AUE_SETPRIVEXEC:
1656 if (ARG_IS_VALID(kar, ARG_VALUE32)) {
1657 tok = au_to_arg32(n: 1, text: "flag", v: ar->ar_arg_value32);
1658 kau_write(rec, tok);
1659 }
1660 break;
1661
1662 /* AUE_SHMAT, AUE_SHMCTL, AUE_SHMDT and AUE_SHMGET are SysV IPC */
1663 case AUE_SHMAT:
1664 if (ARG_IS_VALID(kar, ARG_SVIPC_ID)) {
1665 tok = au_to_arg32(n: 1, text: "shmid", v: ar->ar_arg_svipc_id);
1666 kau_write(rec, tok);
1667 /* XXXAUDIT: Does having the ipc token make sense? */
1668 tok = au_to_ipc(AT_IPC_SHM, id: ar->ar_arg_svipc_id);
1669 kau_write(rec, tok);
1670 }
1671 if (ARG_IS_VALID(kar, ARG_SVIPC_ADDR)) {
1672 tok = au_to_arg64(n: 2, text: "shmaddr", v: ar->ar_arg_svipc_addr);
1673 kau_write(rec, tok);
1674 }
1675 if (ARG_IS_VALID(kar, ARG_SVIPC_PERM)) {
1676 tok = au_to_ipc_perm(perm: &ar->ar_arg_svipc_perm);
1677 kau_write(rec, tok);
1678 }
1679 break;
1680
1681 case AUE_SHMCTL:
1682 if (ARG_IS_VALID(kar, ARG_SVIPC_ID)) {
1683 tok = au_to_arg32(n: 1, text: "shmid", v: ar->ar_arg_svipc_id);
1684 kau_write(rec, tok);
1685 /* XXXAUDIT: Does having the ipc token make sense? */
1686 tok = au_to_ipc(AT_IPC_SHM, id: ar->ar_arg_svipc_id);
1687 kau_write(rec, tok);
1688 }
1689 switch (ar->ar_arg_svipc_cmd) {
1690 case IPC_STAT:
1691 ar->ar_event = AUE_SHMCTL_STAT;
1692 break;
1693 case IPC_RMID:
1694 ar->ar_event = AUE_SHMCTL_RMID;
1695 break;
1696 case IPC_SET:
1697 ar->ar_event = AUE_SHMCTL_SET;
1698 if (ARG_IS_VALID(kar, ARG_SVIPC_PERM)) {
1699 tok = au_to_ipc_perm(perm: &ar->ar_arg_svipc_perm);
1700 kau_write(rec, tok);
1701 }
1702 break;
1703 default:
1704 break; /* We will audit a bad command */
1705 }
1706 break;
1707
1708 case AUE_SHMDT:
1709 if (ARG_IS_VALID(kar, ARG_SVIPC_ADDR)) {
1710 tok = au_to_arg64(n: 1, text: "shmaddr",
1711 v: (int)(uintptr_t)ar->ar_arg_svipc_addr);
1712 kau_write(rec, tok);
1713 }
1714 break;
1715
1716 case AUE_SHMGET:
1717 /* This is unusual; the return value is in an argument token */
1718 if (ARG_IS_VALID(kar, ARG_SVIPC_ID)) {
1719 tok = au_to_arg32(n: 0, text: "shmid", v: ar->ar_arg_svipc_id);
1720 kau_write(rec, tok);
1721 tok = au_to_ipc(AT_IPC_SHM, id: ar->ar_arg_svipc_id);
1722 kau_write(rec, tok);
1723 }
1724 if (ARG_IS_VALID(kar, ARG_SVIPC_PERM)) {
1725 tok = au_to_ipc_perm(perm: &ar->ar_arg_svipc_perm);
1726 kau_write(rec, tok);
1727 }
1728 break;
1729
1730 /* AUE_SHMOPEN, AUE_SHMUNLINK, AUE_SEMOPEN, AUE_SEMCLOSE
1731 * and AUE_SEMUNLINK are Posix IPC */
1732 case AUE_SHMOPEN:
1733 if (ARG_IS_VALID(kar, ARG_SVIPC_ADDR)) {
1734 tok = au_to_arg32(n: 2, text: "flags", v: ar->ar_arg_fflags);
1735 kau_write(rec, tok);
1736 }
1737 if (ARG_IS_VALID(kar, ARG_MODE)) {
1738 tok = au_to_arg32(n: 3, text: "mode", v: ar->ar_arg_mode);
1739 kau_write(rec, tok);
1740 }
1741 OS_FALLTHROUGH;
1742
1743 case AUE_SHMUNLINK:
1744 if (ARG_IS_VALID(kar, ARG_TEXT)) {
1745 tok = au_to_text(text: ar->ar_arg_text);
1746 kau_write(rec, tok);
1747 }
1748 if (ARG_IS_VALID(kar, ARG_POSIX_IPC_PERM)) {
1749 struct ipc_perm perm;
1750
1751 perm.uid = ar->ar_arg_pipc_perm.pipc_uid;
1752 perm.gid = ar->ar_arg_pipc_perm.pipc_gid;
1753 perm.cuid = ar->ar_arg_pipc_perm.pipc_uid;
1754 perm.cgid = ar->ar_arg_pipc_perm.pipc_gid;
1755 perm.mode = ar->ar_arg_pipc_perm.pipc_mode;
1756 perm._seq = 0;
1757 perm._key = 0;
1758 tok = au_to_ipc_perm(perm: &perm);
1759 kau_write(rec, tok);
1760 }
1761 break;
1762
1763 case AUE_SEMOPEN:
1764 if (ARG_IS_VALID(kar, ARG_FFLAGS)) {
1765 tok = au_to_arg32(n: 2, text: "flags", v: ar->ar_arg_fflags);
1766 kau_write(rec, tok);
1767 }
1768 if (ARG_IS_VALID(kar, ARG_MODE)) {
1769 tok = au_to_arg32(n: 3, text: "mode", v: ar->ar_arg_mode);
1770 kau_write(rec, tok);
1771 }
1772 if (ARG_IS_VALID(kar, ARG_VALUE32)) {
1773 tok = au_to_arg32(n: 4, text: "value", v: ar->ar_arg_value32);
1774 kau_write(rec, tok);
1775 }
1776 OS_FALLTHROUGH;
1777
1778 case AUE_SEMUNLINK:
1779 if (ARG_IS_VALID(kar, ARG_TEXT)) {
1780 tok = au_to_text(text: ar->ar_arg_text);
1781 kau_write(rec, tok);
1782 }
1783 if (ARG_IS_VALID(kar, ARG_POSIX_IPC_PERM)) {
1784 struct ipc_perm perm;
1785
1786 perm.uid = ar->ar_arg_pipc_perm.pipc_uid;
1787 perm.gid = ar->ar_arg_pipc_perm.pipc_gid;
1788 perm.cuid = ar->ar_arg_pipc_perm.pipc_uid;
1789 perm.cgid = ar->ar_arg_pipc_perm.pipc_gid;
1790 perm.mode = ar->ar_arg_pipc_perm.pipc_mode;
1791 perm._seq = 0;
1792 perm._key = 0;
1793 tok = au_to_ipc_perm(perm: &perm);
1794 kau_write(rec, tok);
1795 }
1796 break;
1797
1798 case AUE_SEMCLOSE:
1799 if (ARG_IS_VALID(kar, ARG_FD)) {
1800 tok = au_to_arg32(n: 1, text: "sem", v: ar->ar_arg_fd);
1801 kau_write(rec, tok);
1802 }
1803 break;
1804
1805 case AUE_SYMLINK:
1806 if (ARG_IS_VALID(kar, ARG_TEXT)) {
1807 tok = au_to_text(text: ar->ar_arg_text);
1808 kau_write(rec, tok);
1809 }
1810 UPATH1_VNODE1_TOKENS;
1811 break;
1812
1813 case AUE_SYSCTL:
1814 case AUE_SYSCTL_NONADMIN:
1815 if (ARG_IS_VALID(kar, ARG_CTLNAME | ARG_LEN)) {
1816 for (ctr = 0; ctr < (int)ar->ar_arg_len; ctr++) {
1817 tok = au_to_arg32(n: 1, text: "name",
1818 v: ar->ar_arg_ctlname[ctr]);
1819 kau_write(rec, tok);
1820 }
1821 }
1822 if (ARG_IS_VALID(kar, ARG_VALUE32)) {
1823 tok = au_to_arg32(n: 5, text: "newval", v: ar->ar_arg_value32);
1824 kau_write(rec, tok);
1825 }
1826 if (ARG_IS_VALID(kar, ARG_TEXT)) {
1827 tok = au_to_text(text: ar->ar_arg_text);
1828 kau_write(rec, tok);
1829 }
1830 break;
1831
1832 case AUE_UMASK_EXTENDED:
1833 /* ACL data */
1834 if (ARG_IS_VALID(kar, ARG_OPAQUE)) {
1835 tok = au_to_opaque(data: ar->ar_arg_opaque,
1836 bytes: ar->ar_arg_opq_size);
1837 kau_write(rec, tok);
1838 }
1839 OS_FALLTHROUGH;
1840
1841 case AUE_UMASK:
1842 if (ARG_IS_VALID(kar, ARG_MASK)) {
1843 tok = au_to_arg32(n: 1, text: "new mask", v: ar->ar_arg_mask);
1844 kau_write(rec, tok);
1845 }
1846 tok = au_to_arg32(n: 0, text: "prev mask", v: ar->ar_retval);
1847 kau_write(rec, tok);
1848 break;
1849
1850 case AUE_WAIT4:
1851#if 0 /* XXXss - new */
1852 case AUE_WAITID:
1853#endif
1854 if (ARG_IS_VALID(kar, ARG_PID)) {
1855 tok = au_to_arg32(n: 0, text: "pid", v: ar->ar_arg_pid);
1856 kau_write(rec, tok);
1857 }
1858 break;
1859
1860 case AUE_FSGETPATH_EXTENDED:
1861 case AUE_FSGETPATH:
1862 if (ARG_IS_VALID(kar, ARG_VALUE32)) {
1863 tok = au_to_arg32(n: 3, text: "volfsid", v: ar->ar_arg_value32);
1864 kau_write(rec, tok);
1865 }
1866 if (ARG_IS_VALID(kar, ARG_VALUE64)) {
1867 tok = au_to_arg64(n: 4, text: "objid", v: ar->ar_arg_value64);
1868 kau_write(rec, tok);
1869 }
1870 if (ARG_IS_VALID(kar, ARG_TEXT)) {
1871 tok = au_to_text(text: ar->ar_arg_text);
1872 kau_write(rec, tok);
1873 }
1874 break;
1875
1876 case AUE_SESSION_START:
1877 case AUE_SESSION_UPDATE:
1878 case AUE_SESSION_END:
1879 case AUE_SESSION_CLOSE:
1880 if (ARG_IS_VALID(kar, ARG_VALUE64)) {
1881 tok = au_to_arg64(n: 1, text: "sflags", v: ar->ar_arg_value64);
1882 kau_write(rec, tok);
1883 }
1884 if (ARG_IS_VALID(kar, ARG_AMASK)) {
1885 tok = au_to_arg32(n: 2, text: "am_success",
1886 v: ar->ar_arg_amask.am_success);
1887 kau_write(rec, tok);
1888 tok = au_to_arg32(n: 3, text: "am_failure",
1889 v: ar->ar_arg_amask.am_failure);
1890 kau_write(rec, tok);
1891 }
1892 break;
1893
1894 /************************
1895 * Mach system calls *
1896 ************************/
1897 case AUE_INITPROCESS:
1898 break;
1899
1900 case AUE_PIDFORTASK:
1901 if (ARG_IS_VALID(kar, ARG_MACHPORT1)) {
1902 tok = au_to_arg32(n: 1, text: "port",
1903 v: (u_int32_t)ar->ar_arg_mach_port1);
1904 kau_write(rec, tok);
1905 }
1906 if (ARG_IS_VALID(kar, ARG_PID)) {
1907 tok = au_to_arg32(n: 2, text: "pid", v: (u_int32_t)ar->ar_arg_pid);
1908 kau_write(rec, tok);
1909 }
1910 break;
1911
1912 case AUE_TASKFORPID:
1913 case AUE_TASKNAMEFORPID:
1914 if (ARG_IS_VALID(kar, ARG_MACHPORT1)) {
1915 tok = au_to_arg32(n: 1, text: "target port",
1916 v: (u_int32_t)ar->ar_arg_mach_port1);
1917 kau_write(rec, tok);
1918 }
1919 if (ARG_IS_VALID(kar, ARG_MACHPORT2)) {
1920 tok = au_to_arg32(n: 3, text: "task port",
1921 v: (u_int32_t)ar->ar_arg_mach_port2);
1922 kau_write(rec, tok);
1923 }
1924 PROCESS_PID_TOKENS(2);
1925 break;
1926
1927 case AUE_SWAPON:
1928 if (ARG_IS_VALID(kar, ARG_VALUE32)) {
1929 tok = au_to_arg32(n: 4, text: "priority",
1930 v: (u_int32_t)ar->ar_arg_value32);
1931 kau_write(rec, tok);
1932 }
1933 UPATH1_VNODE1_TOKENS;
1934 break;
1935
1936 case AUE_SWAPOFF:
1937 UPATH1_VNODE1_TOKENS;
1938 break;
1939
1940 case AUE_MAPFD:
1941 if (ARG_IS_VALID(kar, ARG_ADDR64)) {
1942 tok = au_to_arg64(n: 3, text: "va", v: ar->ar_arg_addr);
1943 kau_write(rec, tok);
1944 } else if (ARG_IS_VALID(kar, ARG_ADDR32)) {
1945 tok = au_to_arg32(n: 3, text: "va",
1946 v: (u_int32_t)ar->ar_arg_addr);
1947 kau_write(rec, tok);
1948 }
1949 FD_VNODE1_TOKENS;
1950 break;
1951
1952#if CONFIG_MACF
1953 case AUE_MAC_GET_FILE:
1954 case AUE_MAC_SET_FILE:
1955 case AUE_MAC_GET_LINK:
1956 case AUE_MAC_SET_LINK:
1957 case AUE_MAC_GET_MOUNT:
1958 UPATH1_VNODE1_TOKENS;
1959 PROCESS_MAC_TOKENS;
1960 break;
1961
1962 case AUE_MAC_GET_FD:
1963 case AUE_MAC_SET_FD:
1964 FD_VNODE1_TOKENS;
1965 PROCESS_MAC_TOKENS;
1966 break;
1967
1968 case AUE_MAC_SYSCALL:
1969 PROCESS_MAC_TOKENS;
1970 if (ARG_IS_VALID(kar, ARG_VALUE32)) {
1971 tok = au_to_arg32(n: 3, text: "call", v: ar->ar_arg_value32);
1972 kau_write(rec, tok);
1973 }
1974 break;
1975
1976 case AUE_MAC_EXECVE:
1977 UPATH1_VNODE1_TOKENS;
1978 PROCESS_MAC_TOKENS;
1979 break;
1980
1981 case AUE_MAC_GET_PID:
1982 if (ARG_IS_VALID(kar, ARG_PID)) {
1983 tok = au_to_arg32(n: 1, text: "pid", v: (u_int32_t)ar->ar_arg_pid);
1984 kau_write(rec, tok);
1985 }
1986 PROCESS_MAC_TOKENS;
1987 break;
1988
1989 case AUE_MAC_GET_LCID:
1990 if (ARG_IS_VALID(kar, ARG_VALUE32)) {
1991 tok = au_to_arg32(n: 1, text: "lcid",
1992 v: (u_int32_t)ar->ar_arg_value32);
1993 kau_write(rec, tok);
1994 }
1995 PROCESS_MAC_TOKENS;
1996 break;
1997
1998 case AUE_MAC_GET_PROC:
1999 case AUE_MAC_SET_PROC:
2000 PROCESS_MAC_TOKENS;
2001 break;
2002#endif
2003 case AUE_NULL:
2004 default:
2005#if DIAGNOSTIC
2006 printf("BSM conversion requested for unknown event %d\n",
2007 ar->ar_event);
2008#endif
2009
2010 /*
2011 * Write the subject token so it is properly freed here.
2012 */
2013 kau_write(rec, tok: subj_tok);
2014 kau_free(rec);
2015 return BSM_NOAUDIT;
2016 }
2017
2018#if CONFIG_MACF
2019 if (NULL != ar->ar_mac_records) {
2020 /* Convert the audit data from the MAC policies */
2021 struct mac_audit_record *mar;
2022
2023 LIST_FOREACH(mar, ar->ar_mac_records, records) {
2024 switch (mar->type) {
2025 case MAC_AUDIT_DATA_TYPE:
2026 tok = au_to_data(AUP_BINARY, AUR_BYTE,
2027 unit_count: mar->length,
2028 p: (const char *)mar->data);
2029 break;
2030 case MAC_AUDIT_TEXT_TYPE:
2031 tok = au_to_text(text: (char*) mar->data);
2032 break;
2033 default:
2034 /*
2035 * XXX: we can either continue,
2036 * skipping this particular entry,
2037 * or we can pre-verify the list and
2038 * abort before writing any records
2039 */
2040 printf("kaudit_to_bsm(): "
2041 "BSM conversion requested for"
2042 "unknown mac_audit data type %d\n",
2043 mar->type);
2044 }
2045
2046 kau_write(rec, tok);
2047 }
2048 }
2049#endif
2050
2051 kau_write(rec, tok: subj_tok);
2052
2053#if CONFIG_MACF
2054 if (ar->ar_cred_mac_labels != NULL &&
2055 strlen(s: ar->ar_cred_mac_labels) != 0) {
2056 tok = au_to_text(text: ar->ar_cred_mac_labels);
2057 kau_write(rec, tok);
2058 }
2059#endif
2060
2061 tok = au_to_return32(status: au_errno_to_bsm(local_errno: ar->ar_errno), ret: ar->ar_retval);
2062 kau_write(rec, tok); /* Every record gets a return token */
2063
2064 if (ARG_IS_VALID(kar, ARG_IDENTITY)) {
2065 struct au_identity_info *id = &ar->ar_arg_identity;
2066 tok = au_to_identity(signer_type: id->signer_type, signing_id: id->signing_id,
2067 signing_id_trunc: id->signing_id_trunc, team_id: id->team_id, team_id_trunc: id->team_id_trunc,
2068 cdhash: id->cdhash, cdhash_len: id->cdhash_len);
2069 kau_write(rec, tok);
2070 }
2071
2072 rv = kau_close(rec, ctime: &ar->ar_endtime, event: ar->ar_event);
2073 if (rv != 0) {
2074 kau_free(rec);
2075 return BSM_FAILURE;
2076 }
2077
2078 *pau = rec;
2079 return BSM_SUCCESS;
2080}
2081
2082/*
2083 * Verify that a record is a valid BSM record. Return 1 if the
2084 * record is good, 0 otherwise.
2085 */
2086int
2087bsm_rec_verify(void *rec, int length, boolean_t kern_events_allowed)
2088{
2089 /* Used to partially deserialize the buffer */
2090 struct hdr_tok_partial *hdr;
2091 struct trl_tok_partial *trl;
2092
2093 /* A record requires a complete header and trailer token */
2094 if (length < (AUDIT_HEADER_SIZE + AUDIT_TRAILER_SIZE)) {
2095 return 0;
2096 }
2097
2098 hdr = (struct hdr_tok_partial*)rec;
2099
2100 /* Ensure the provided length matches what the record shows */
2101 if ((uint32_t)length != ntohl(hdr->len)) {
2102 return 0;
2103 }
2104
2105 trl = (struct trl_tok_partial*)((uintptr_t)rec + (length - AUDIT_TRAILER_SIZE));
2106
2107 /* Ensure the buffer contains what look like header and trailer tokens */
2108 if (((hdr->type != AUT_HEADER32) && (hdr->type != AUT_HEADER32_EX) &&
2109 (hdr->type != AUT_HEADER64) && (hdr->type != AUT_HEADER64_EX)) ||
2110 (trl->type != AUT_TRAILER)) {
2111 return 0;
2112 }
2113
2114 /* Ensure the header and trailer agree on the length */
2115 if (hdr->len != trl->len) {
2116 return 0;
2117 }
2118
2119 /* Ensure the trailer token has a proper magic value */
2120 if (ntohs(trl->magic) != AUT_TRAILER_MAGIC) {
2121 return 0;
2122 }
2123
2124 if (!kern_events_allowed && AUE_IS_A_KEVENT(ntohs(hdr->e_type))) {
2125 return 0;
2126 }
2127
2128 return 1;
2129}
2130#endif /* CONFIG_AUDIT */
2131