xref: /freebsd/contrib/openbsm/libbsm/bsm_token.c (revision bc168a6cdd45ba809a5580b6e67ebc6806b5aeb3)
1ca0716f5SRobert Watson /*
2ca0716f5SRobert Watson  * Copyright (c) 2004 Apple Computer, Inc.
3ca0716f5SRobert Watson  * Copyright (c) 2005 SPARTA, Inc.
4ca0716f5SRobert Watson  * All rights reserved.
5ca0716f5SRobert Watson  *
6ca0716f5SRobert Watson  * This code was developed in part by Robert N. M. Watson, Senior Principal
7ca0716f5SRobert Watson  * Scientist, SPARTA, Inc.
8ca0716f5SRobert Watson  *
9ca0716f5SRobert Watson  * Redistribution and use in source and binary forms, with or without
10ca0716f5SRobert Watson  * modification, are permitted provided that the following conditions
11ca0716f5SRobert Watson  * are met:
12ca0716f5SRobert Watson  * 1.  Redistributions of source code must retain the above copyright
13ca0716f5SRobert Watson  *     notice, this list of conditions and the following disclaimer.
14ca0716f5SRobert Watson  * 2.  Redistributions in binary form must reproduce the above copyright
15ca0716f5SRobert Watson  *     notice, this list of conditions and the following disclaimer in the
16ca0716f5SRobert Watson  *     documentation and/or other materials provided with the distribution.
17ca0716f5SRobert Watson  * 3.  Neither the name of Apple Computer, Inc. ("Apple") nor the names of
18ca0716f5SRobert Watson  *     its contributors may be used to endorse or promote products derived
19ca0716f5SRobert Watson  *     from this software without specific prior written permission.
20ca0716f5SRobert Watson  *
21ca0716f5SRobert Watson  * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND
22ca0716f5SRobert Watson  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23ca0716f5SRobert Watson  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24ca0716f5SRobert Watson  * ARE DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR
25ca0716f5SRobert Watson  * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
26ca0716f5SRobert Watson  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
27ca0716f5SRobert Watson  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
28ca0716f5SRobert Watson  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
29ca0716f5SRobert Watson  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
30ca0716f5SRobert Watson  * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
31ca0716f5SRobert Watson  * POSSIBILITY OF SUCH DAMAGE.
32ca0716f5SRobert Watson  *
33bc168a6cSRobert Watson  * $P4: //depot/projects/trustedbsd/openbsm/libbsm/bsm_token.c#62 $
34ca0716f5SRobert Watson  */
35ca0716f5SRobert Watson 
36ca0716f5SRobert Watson #include <sys/types.h>
373b97a967SRobert Watson 
383b97a967SRobert Watson #include <config/config.h>
393b97a967SRobert Watson #ifdef HAVE_SYS_ENDIAN_H
40ca0716f5SRobert Watson #include <sys/endian.h>
413b97a967SRobert Watson #else /* !HAVE_SYS_ENDIAN_H */
423b97a967SRobert Watson #ifdef HAVE_MACHINE_ENDIAN_H
433b97a967SRobert Watson #include <machine/endian.h>
443b97a967SRobert Watson #else /* !HAVE_MACHINE_ENDIAN_H */
453b97a967SRobert Watson #ifdef HAVE_ENDIAN_H
463b97a967SRobert Watson #include <endian.h>
473b97a967SRobert Watson #else /* !HAVE_ENDIAN_H */
483b97a967SRobert Watson #error "No supported endian.h"
493b97a967SRobert Watson #endif /* !HAVE_ENDIAN_H */
503b97a967SRobert Watson #endif /* !HAVE_MACHINE_ENDIAN_H */
513b97a967SRobert Watson #include <compat/endian.h>
523b97a967SRobert Watson #endif /* !HAVE_SYS_ENDIAN_H */
533b97a967SRobert Watson #ifdef HAVE_FULL_QUEUE_H
543b97a967SRobert Watson #include <sys/queue.h>
553b97a967SRobert Watson #else /* !HAVE_FULL_QUEUE_H */
563b97a967SRobert Watson #include <compat/queue.h>
573b97a967SRobert Watson #endif /* !HAVE_FULL_QUEUE_H */
583b97a967SRobert Watson 
59ca0716f5SRobert Watson #include <sys/socket.h>
60ca0716f5SRobert Watson #include <sys/time.h>
61ca0716f5SRobert Watson #include <sys/un.h>
62ca0716f5SRobert Watson 
63ca0716f5SRobert Watson #include <sys/ipc.h>
64ca0716f5SRobert Watson 
65ca0716f5SRobert Watson #include <netinet/in.h>
66ca0716f5SRobert Watson #include <netinet/in_systm.h>
67ca0716f5SRobert Watson #include <netinet/ip.h>
68ca0716f5SRobert Watson 
69ca0716f5SRobert Watson #include <assert.h>
70ca0716f5SRobert Watson #include <errno.h>
71ca0716f5SRobert Watson #include <string.h>
72ca0716f5SRobert Watson #include <stdlib.h>
73ca0716f5SRobert Watson #include <unistd.h>
74ca0716f5SRobert Watson 
75ca0716f5SRobert Watson #include <bsm/audit_internal.h>
76ca0716f5SRobert Watson #include <bsm/libbsm.h>
77ca0716f5SRobert Watson 
78ca0716f5SRobert Watson #define	GET_TOKEN_AREA(t, dptr, length) do {				\
79ca0716f5SRobert Watson 	(t) = malloc(sizeof(token_t));					\
80ca0716f5SRobert Watson 	if ((t) != NULL) {						\
81ca0716f5SRobert Watson 		(t)->len = (length);					\
82ca0716f5SRobert Watson 		(dptr) = (t->t_data) = malloc((length) * sizeof(u_char)); \
83ca0716f5SRobert Watson 		if ((dptr) == NULL) {					\
84ca0716f5SRobert Watson 			free(t);					\
85ca0716f5SRobert Watson 			(t) = NULL;					\
86ca0716f5SRobert Watson 		} else							\
87ca0716f5SRobert Watson 			memset((dptr), 0, (length));			\
88ca0716f5SRobert Watson 	} else								\
89ca0716f5SRobert Watson 		(dptr) = NULL;						\
90ca0716f5SRobert Watson 	assert(t == NULL || dptr != NULL);				\
91ca0716f5SRobert Watson } while (0)
92ca0716f5SRobert Watson 
93ca0716f5SRobert Watson /*
94ca0716f5SRobert Watson  * token ID                1 byte
95ca0716f5SRobert Watson  * argument #              1 byte
96ca0716f5SRobert Watson  * argument value          4 bytes/8 bytes (32-bit/64-bit value)
97ca0716f5SRobert Watson  * text length             2 bytes
98ca0716f5SRobert Watson  * text                    N bytes + 1 terminating NULL byte
99ca0716f5SRobert Watson  */
100ca0716f5SRobert Watson token_t *
101ca0716f5SRobert Watson au_to_arg32(char n, char *text, u_int32_t v)
102ca0716f5SRobert Watson {
103ca0716f5SRobert Watson 	token_t *t;
104ca0716f5SRobert Watson 	u_char *dptr = NULL;
105ca0716f5SRobert Watson 	u_int16_t textlen;
106ca0716f5SRobert Watson 
107ca0716f5SRobert Watson 	textlen = strlen(text);
108ca0716f5SRobert Watson 	textlen += 1;
109ca0716f5SRobert Watson 
110ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, 2 * sizeof(u_char) + sizeof(u_int32_t) +
111ca0716f5SRobert Watson 	    sizeof(u_int16_t) + textlen);
112ca0716f5SRobert Watson 	if (t == NULL)
113ca0716f5SRobert Watson 		return (NULL);
114ca0716f5SRobert Watson 
115ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_ARG32);
116ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, n);
117ca0716f5SRobert Watson 	ADD_U_INT32(dptr, v);
118ca0716f5SRobert Watson 	ADD_U_INT16(dptr, textlen);
119ca0716f5SRobert Watson 	ADD_STRING(dptr, text, textlen);
120ca0716f5SRobert Watson 
121ca0716f5SRobert Watson 	return (t);
122ca0716f5SRobert Watson 
123ca0716f5SRobert Watson }
124ca0716f5SRobert Watson 
125ca0716f5SRobert Watson token_t *
126ca0716f5SRobert Watson au_to_arg64(char n, char *text, u_int64_t v)
127ca0716f5SRobert Watson {
128ca0716f5SRobert Watson 	token_t *t;
129ca0716f5SRobert Watson 	u_char *dptr = NULL;
130ca0716f5SRobert Watson 	u_int16_t textlen;
131ca0716f5SRobert Watson 
132ca0716f5SRobert Watson 	textlen = strlen(text);
133ca0716f5SRobert Watson 	textlen += 1;
134ca0716f5SRobert Watson 
135ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, 2 * sizeof(u_char) + sizeof(u_int64_t) +
136ca0716f5SRobert Watson 	    sizeof(u_int16_t) + textlen);
137ca0716f5SRobert Watson 	if (t == NULL)
138ca0716f5SRobert Watson 		return (NULL);
139ca0716f5SRobert Watson 
140ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_ARG64);
141ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, n);
142ca0716f5SRobert Watson 	ADD_U_INT64(dptr, v);
143ca0716f5SRobert Watson 	ADD_U_INT16(dptr, textlen);
144ca0716f5SRobert Watson 	ADD_STRING(dptr, text, textlen);
145ca0716f5SRobert Watson 
146ca0716f5SRobert Watson 	return (t);
147ca0716f5SRobert Watson 
148ca0716f5SRobert Watson }
149ca0716f5SRobert Watson 
150ca0716f5SRobert Watson token_t *
151ca0716f5SRobert Watson au_to_arg(char n, char *text, u_int32_t v)
152ca0716f5SRobert Watson {
153ca0716f5SRobert Watson 
154ca0716f5SRobert Watson 	return (au_to_arg32(n, text, v));
155ca0716f5SRobert Watson }
156ca0716f5SRobert Watson 
157ca0716f5SRobert Watson #if defined(_KERNEL) || defined(KERNEL)
158ca0716f5SRobert Watson /*
159ca0716f5SRobert Watson  * token ID                1 byte
160ca0716f5SRobert Watson  * file access mode        4 bytes
161ca0716f5SRobert Watson  * owner user ID           4 bytes
162ca0716f5SRobert Watson  * owner group ID          4 bytes
163ca0716f5SRobert Watson  * file system ID          4 bytes
164ca0716f5SRobert Watson  * node ID                 8 bytes
165ca0716f5SRobert Watson  * device                  4 bytes/8 bytes (32-bit/64-bit)
166ca0716f5SRobert Watson  */
167ca0716f5SRobert Watson token_t *
168ca0716f5SRobert Watson au_to_attr32(struct vnode_au_info *vni)
169ca0716f5SRobert Watson {
170ca0716f5SRobert Watson 	token_t *t;
171ca0716f5SRobert Watson 	u_char *dptr = NULL;
172ca0716f5SRobert Watson 	u_int16_t pad0_16 = 0;
173ca0716f5SRobert Watson 	u_int16_t pad0_32 = 0;
174ca0716f5SRobert Watson 
175ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + 2 * sizeof(u_int16_t) +
176ca0716f5SRobert Watson 	    3 * sizeof(u_int32_t) + sizeof(u_int64_t) + sizeof(u_int32_t));
177ca0716f5SRobert Watson 	if (t == NULL)
178ca0716f5SRobert Watson 		return (NULL);
179ca0716f5SRobert Watson 
180ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_ATTR32);
181ca0716f5SRobert Watson 
182ca0716f5SRobert Watson 	/*
183ca0716f5SRobert Watson 	 * Darwin defines the size for the file mode
184ca0716f5SRobert Watson 	 * as 2 bytes; BSM defines 4 so pad with 0
185ca0716f5SRobert Watson 	 */
186ca0716f5SRobert Watson 	ADD_U_INT16(dptr, pad0_16);
187ca0716f5SRobert Watson 	ADD_U_INT16(dptr, vni->vn_mode);
188ca0716f5SRobert Watson 
189ca0716f5SRobert Watson 	ADD_U_INT32(dptr, vni->vn_uid);
190ca0716f5SRobert Watson 	ADD_U_INT32(dptr, vni->vn_gid);
191ca0716f5SRobert Watson 	ADD_U_INT32(dptr, vni->vn_fsid);
192ca0716f5SRobert Watson 
193ca0716f5SRobert Watson 	/*
194ca0716f5SRobert Watson 	 * Some systems use 32-bit file ID's, other's use 64-bit file IDs.
195ca0716f5SRobert Watson 	 * Attempt to handle both, and let the compiler sort it out.  If we
196ca0716f5SRobert Watson 	 * could pick this out at compile-time, it would be better, so as to
197ca0716f5SRobert Watson 	 * avoid the else case below.
198ca0716f5SRobert Watson 	 */
199ca0716f5SRobert Watson 	if (sizeof(vni->vn_fileid) == sizeof(uint32_t)) {
200ca0716f5SRobert Watson 		ADD_U_INT32(dptr, pad0_32);
201ca0716f5SRobert Watson 		ADD_U_INT32(dptr, vni->vn_fileid);
202ca0716f5SRobert Watson 	} else if (sizeof(vni->vn_fileid) == sizeof(uint64_t))
203ca0716f5SRobert Watson 		ADD_U_INT64(dptr, vni->vn_fileid);
204ca0716f5SRobert Watson 	else
205ca0716f5SRobert Watson 		ADD_U_INT64(dptr, 0LL);
206ca0716f5SRobert Watson 
207ca0716f5SRobert Watson 	ADD_U_INT32(dptr, vni->vn_dev);
208ca0716f5SRobert Watson 
209ca0716f5SRobert Watson 	return (t);
210ca0716f5SRobert Watson }
211ca0716f5SRobert Watson 
212ca0716f5SRobert Watson token_t *
213ca0716f5SRobert Watson au_to_attr64(struct vnode_au_info *vni)
214ca0716f5SRobert Watson {
215bc168a6cSRobert Watson 	token_t *t;
216bc168a6cSRobert Watson 	u_char *dptr = NULL;
217bc168a6cSRobert Watson 	u_int16_t pad0_16 = 0;
218bc168a6cSRobert Watson 	u_int16_t pad0_32 = 0;
219ca0716f5SRobert Watson 
220bc168a6cSRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + 2 * sizeof(u_int16_t) +
221bc168a6cSRobert Watson 	    3 * sizeof(u_int32_t) + sizeof(u_int64_t) * 2);
222bc168a6cSRobert Watson 	if (t == NULL)
223ca0716f5SRobert Watson 		return (NULL);
224bc168a6cSRobert Watson 
225bc168a6cSRobert Watson 	ADD_U_CHAR(dptr, AUT_ATTR64);
226bc168a6cSRobert Watson 
227bc168a6cSRobert Watson 	/*
228bc168a6cSRobert Watson 	 * Darwin defines the size for the file mode
229bc168a6cSRobert Watson 	 * as 2 bytes; BSM defines 4 so pad with 0
230bc168a6cSRobert Watson 	 */
231bc168a6cSRobert Watson 	ADD_U_INT16(dptr, pad0_16);
232bc168a6cSRobert Watson 	ADD_U_INT16(dptr, vni->vn_mode);
233bc168a6cSRobert Watson 
234bc168a6cSRobert Watson 	ADD_U_INT32(dptr, vni->vn_uid);
235bc168a6cSRobert Watson 	ADD_U_INT32(dptr, vni->vn_gid);
236bc168a6cSRobert Watson 	ADD_U_INT32(dptr, vni->vn_fsid);
237bc168a6cSRobert Watson 
238bc168a6cSRobert Watson 	/*
239bc168a6cSRobert Watson 	 * Some systems use 32-bit file ID's, other's use 64-bit file IDs.
240bc168a6cSRobert Watson 	 * Attempt to handle both, and let the compiler sort it out.  If we
241bc168a6cSRobert Watson 	 * could pick this out at compile-time, it would be better, so as to
242bc168a6cSRobert Watson 	 * avoid the else case below.
243bc168a6cSRobert Watson 	 */
244bc168a6cSRobert Watson 	if (sizeof(vni->vn_fileid) == sizeof(uint32_t)) {
245bc168a6cSRobert Watson 		ADD_U_INT32(dptr, pad0_32);
246bc168a6cSRobert Watson 		ADD_U_INT32(dptr, vni->vn_fileid);
247bc168a6cSRobert Watson 	} else if (sizeof(vni->vn_fileid) == sizeof(uint64_t))
248bc168a6cSRobert Watson 		ADD_U_INT64(dptr, vni->vn_fileid);
249bc168a6cSRobert Watson 	else
250bc168a6cSRobert Watson 		ADD_U_INT64(dptr, 0LL);
251bc168a6cSRobert Watson 
252bc168a6cSRobert Watson 	ADD_U_INT64(dptr, vni->vn_dev);
253bc168a6cSRobert Watson 
254bc168a6cSRobert Watson 	return (t);
255ca0716f5SRobert Watson }
256ca0716f5SRobert Watson 
257ca0716f5SRobert Watson token_t *
258ca0716f5SRobert Watson au_to_attr(struct vnode_au_info *vni)
259ca0716f5SRobert Watson {
260ca0716f5SRobert Watson 
261ca0716f5SRobert Watson 	return (au_to_attr32(vni));
262ca0716f5SRobert Watson }
263ca0716f5SRobert Watson #endif /* !(defined(_KERNEL) || defined(KERNEL) */
264ca0716f5SRobert Watson 
265ca0716f5SRobert Watson /*
266ca0716f5SRobert Watson  * token ID                1 byte
267ca0716f5SRobert Watson  * how to print            1 byte
268ca0716f5SRobert Watson  * basic unit              1 byte
269ca0716f5SRobert Watson  * unit count              1 byte
270ca0716f5SRobert Watson  * data items              (depends on basic unit)
271ca0716f5SRobert Watson  */
272ca0716f5SRobert Watson token_t *
273ca0716f5SRobert Watson au_to_data(char unit_print, char unit_type, char unit_count, char *p)
274ca0716f5SRobert Watson {
275ca0716f5SRobert Watson 	token_t *t;
276ca0716f5SRobert Watson 	u_char *dptr = NULL;
277ca0716f5SRobert Watson 	size_t datasize, totdata;
278ca0716f5SRobert Watson 
279ca0716f5SRobert Watson 	/* Determine the size of the basic unit. */
280ca0716f5SRobert Watson 	switch (unit_type) {
281ca0716f5SRobert Watson 	case AUR_BYTE:
282506764c6SRobert Watson 	/* case AUR_CHAR: */
283ca0716f5SRobert Watson 		datasize = AUR_BYTE_SIZE;
284ca0716f5SRobert Watson 		break;
285ca0716f5SRobert Watson 
286ca0716f5SRobert Watson 	case AUR_SHORT:
287ca0716f5SRobert Watson 		datasize = AUR_SHORT_SIZE;
288ca0716f5SRobert Watson 		break;
289ca0716f5SRobert Watson 
290506764c6SRobert Watson 	case AUR_INT32:
291506764c6SRobert Watson 	/* case AUR_INT: */
292506764c6SRobert Watson 		datasize = AUR_INT32_SIZE;
293506764c6SRobert Watson 		break;
294506764c6SRobert Watson 
295506764c6SRobert Watson 	case AUR_INT64:
296506764c6SRobert Watson 		datasize = AUR_INT64_SIZE;
297ca0716f5SRobert Watson 		break;
298ca0716f5SRobert Watson 
299ca0716f5SRobert Watson 	default:
300ca0716f5SRobert Watson 		errno = EINVAL;
301ca0716f5SRobert Watson  		return (NULL);
302ca0716f5SRobert Watson 	}
303ca0716f5SRobert Watson 
304ca0716f5SRobert Watson 	totdata = datasize * unit_count;
305ca0716f5SRobert Watson 
306506764c6SRobert Watson 	GET_TOKEN_AREA(t, dptr, 4 * sizeof(u_char) + totdata);
307ca0716f5SRobert Watson 	if (t == NULL)
308ca0716f5SRobert Watson 		return (NULL);
309ca0716f5SRobert Watson 
310ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_DATA);
311ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, unit_print);
312ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, unit_type);
313ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, unit_count);
314ca0716f5SRobert Watson 	ADD_MEM(dptr, p, totdata);
315ca0716f5SRobert Watson 
316ca0716f5SRobert Watson 	return (t);
317ca0716f5SRobert Watson }
318ca0716f5SRobert Watson 
319ca0716f5SRobert Watson 
320ca0716f5SRobert Watson /*
321ca0716f5SRobert Watson  * token ID                1 byte
322ca0716f5SRobert Watson  * status		   4 bytes
323ca0716f5SRobert Watson  * return value            4 bytes
324ca0716f5SRobert Watson  */
325ca0716f5SRobert Watson token_t *
326ca0716f5SRobert Watson au_to_exit(int retval, int err)
327ca0716f5SRobert Watson {
328ca0716f5SRobert Watson 	token_t *t;
329ca0716f5SRobert Watson 	u_char *dptr = NULL;
330ca0716f5SRobert Watson 
331ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + 2 * sizeof(u_int32_t));
332ca0716f5SRobert Watson 	if (t == NULL)
333ca0716f5SRobert Watson 		return (NULL);
334ca0716f5SRobert Watson 
335ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_EXIT);
336ca0716f5SRobert Watson 	ADD_U_INT32(dptr, err);
337ca0716f5SRobert Watson 	ADD_U_INT32(dptr, retval);
338ca0716f5SRobert Watson 
339ca0716f5SRobert Watson 	return (t);
340ca0716f5SRobert Watson }
341ca0716f5SRobert Watson 
342ca0716f5SRobert Watson /*
343ca0716f5SRobert Watson  */
344ca0716f5SRobert Watson token_t *
345ca0716f5SRobert Watson au_to_groups(int *groups)
346ca0716f5SRobert Watson {
347ca0716f5SRobert Watson 
348bc168a6cSRobert Watson 	return (au_to_newgroups(AUDIT_MAX_GROUPS, (gid_t*)groups));
349ca0716f5SRobert Watson }
350ca0716f5SRobert Watson 
351ca0716f5SRobert Watson /*
352ca0716f5SRobert Watson  * token ID                1 byte
353ca0716f5SRobert Watson  * number groups           2 bytes
354ca0716f5SRobert Watson  * group list              count * 4 bytes
355ca0716f5SRobert Watson  */
356ca0716f5SRobert Watson token_t *
357ca0716f5SRobert Watson au_to_newgroups(u_int16_t n, gid_t *groups)
358ca0716f5SRobert Watson {
359ca0716f5SRobert Watson 	token_t *t;
360ca0716f5SRobert Watson 	u_char *dptr = NULL;
361ca0716f5SRobert Watson 	int i;
362ca0716f5SRobert Watson 
363ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + sizeof(u_int16_t) +
364ca0716f5SRobert Watson 	    n * sizeof(u_int32_t));
365ca0716f5SRobert Watson 	if (t == NULL)
366ca0716f5SRobert Watson 		return (NULL);
367ca0716f5SRobert Watson 
368ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_NEWGROUPS);
369ca0716f5SRobert Watson 	ADD_U_INT16(dptr, n);
370ca0716f5SRobert Watson 	for (i = 0; i < n; i++)
371ca0716f5SRobert Watson 		ADD_U_INT32(dptr, groups[i]);
372ca0716f5SRobert Watson 
373ca0716f5SRobert Watson 	return (t);
374ca0716f5SRobert Watson }
375ca0716f5SRobert Watson 
376ca0716f5SRobert Watson /*
377ca0716f5SRobert Watson  * token ID                1 byte
378ca0716f5SRobert Watson  * internet address        4 bytes
379ca0716f5SRobert Watson  */
380ca0716f5SRobert Watson token_t *
381ca0716f5SRobert Watson au_to_in_addr(struct in_addr *internet_addr)
382ca0716f5SRobert Watson {
383ca0716f5SRobert Watson 	token_t *t;
384ca0716f5SRobert Watson 	u_char *dptr = NULL;
385ca0716f5SRobert Watson 
386506764c6SRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + sizeof(uint32_t));
387ca0716f5SRobert Watson 	if (t == NULL)
388ca0716f5SRobert Watson 		return (NULL);
389ca0716f5SRobert Watson 
390ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_IN_ADDR);
391506764c6SRobert Watson 	ADD_MEM(dptr, &internet_addr->s_addr, sizeof(uint32_t));
392ca0716f5SRobert Watson 
393ca0716f5SRobert Watson 	return (t);
394ca0716f5SRobert Watson }
395ca0716f5SRobert Watson 
396ca0716f5SRobert Watson /*
397ca0716f5SRobert Watson  * token ID                1 byte
398ca0716f5SRobert Watson  * address type/length     4 bytes
399ca0716f5SRobert Watson  * Address                16 bytes
400ca0716f5SRobert Watson  */
401ca0716f5SRobert Watson token_t *
402ca0716f5SRobert Watson au_to_in_addr_ex(struct in6_addr *internet_addr)
403ca0716f5SRobert Watson {
404ca0716f5SRobert Watson 	token_t *t;
405ca0716f5SRobert Watson 	u_char *dptr = NULL;
406ca0716f5SRobert Watson 	u_int32_t type = AF_INET6;
407ca0716f5SRobert Watson 
408506764c6SRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + 5 * sizeof(uint32_t));
409ca0716f5SRobert Watson 	if (t == NULL)
410ca0716f5SRobert Watson 		return (NULL);
411ca0716f5SRobert Watson 
412ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_IN_ADDR_EX);
413ca0716f5SRobert Watson 	ADD_U_INT32(dptr, type);
414506764c6SRobert Watson 	ADD_MEM(dptr, internet_addr, 5 * sizeof(uint32_t));
415ca0716f5SRobert Watson 
416ca0716f5SRobert Watson 	return (t);
417ca0716f5SRobert Watson }
418ca0716f5SRobert Watson 
419ca0716f5SRobert Watson /*
420ca0716f5SRobert Watson  * token ID                1 byte
421ca0716f5SRobert Watson  * ip header		   20 bytes
422bc168a6cSRobert Watson  *
423bc168a6cSRobert Watson  * The IP header should be submitted in network byte order.
424ca0716f5SRobert Watson  */
425ca0716f5SRobert Watson token_t *
426ca0716f5SRobert Watson au_to_ip(struct ip *ip)
427ca0716f5SRobert Watson {
428ca0716f5SRobert Watson 	token_t *t;
429ca0716f5SRobert Watson 	u_char *dptr = NULL;
430ca0716f5SRobert Watson 
431ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + sizeof(struct ip));
432ca0716f5SRobert Watson 	if (t == NULL)
433ca0716f5SRobert Watson 		return (NULL);
434ca0716f5SRobert Watson 
435ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_IP);
436ca0716f5SRobert Watson 	ADD_MEM(dptr, ip, sizeof(struct ip));
437ca0716f5SRobert Watson 
438ca0716f5SRobert Watson 	return (t);
439ca0716f5SRobert Watson }
440ca0716f5SRobert Watson 
441ca0716f5SRobert Watson /*
442ca0716f5SRobert Watson  * token ID                1 byte
443ca0716f5SRobert Watson  * object ID type          1 byte
444ca0716f5SRobert Watson  * object ID               4 bytes
445ca0716f5SRobert Watson  */
446ca0716f5SRobert Watson token_t *
447ca0716f5SRobert Watson au_to_ipc(char type, int id)
448ca0716f5SRobert Watson {
449ca0716f5SRobert Watson 	token_t *t;
450ca0716f5SRobert Watson 	u_char *dptr = NULL;
451ca0716f5SRobert Watson 
452ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, 2 * sizeof(u_char) + sizeof(u_int32_t));
453ca0716f5SRobert Watson 	if (t == NULL)
454ca0716f5SRobert Watson 		return (NULL);
455ca0716f5SRobert Watson 
456ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_IPC);
457ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, type);
458ca0716f5SRobert Watson 	ADD_U_INT32(dptr, id);
459ca0716f5SRobert Watson 
460ca0716f5SRobert Watson 	return (t);
461ca0716f5SRobert Watson }
462ca0716f5SRobert Watson 
463ca0716f5SRobert Watson /*
464ca0716f5SRobert Watson  * token ID                1 byte
465ca0716f5SRobert Watson  * owner user ID           4 bytes
466ca0716f5SRobert Watson  * owner group ID          4 bytes
467ca0716f5SRobert Watson  * creator user ID         4 bytes
468ca0716f5SRobert Watson  * creator group ID        4 bytes
469ca0716f5SRobert Watson  * access mode             4 bytes
470ca0716f5SRobert Watson  * slot sequence #         4 bytes
471ca0716f5SRobert Watson  * key                     4 bytes
472ca0716f5SRobert Watson  */
473ca0716f5SRobert Watson token_t *
474ca0716f5SRobert Watson au_to_ipc_perm(struct ipc_perm *perm)
475ca0716f5SRobert Watson {
476ca0716f5SRobert Watson 	token_t *t;
477ca0716f5SRobert Watson 	u_char *dptr = NULL;
478ca0716f5SRobert Watson 	u_int16_t pad0 = 0;
479ca0716f5SRobert Watson 
480ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, 12 * sizeof(u_int16_t) + sizeof(u_int32_t));
481ca0716f5SRobert Watson 	if (t == NULL)
482ca0716f5SRobert Watson 		return (NULL);
483ca0716f5SRobert Watson 
484ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_IPC_PERM);
485ca0716f5SRobert Watson 
486ca0716f5SRobert Watson 	/*
487ca0716f5SRobert Watson 	 * Darwin defines the sizes for ipc_perm members
488ca0716f5SRobert Watson 	 * as 2 bytes; BSM defines 4 so pad with 0
489ca0716f5SRobert Watson 	 */
490ca0716f5SRobert Watson 	ADD_U_INT16(dptr, pad0);
491ca0716f5SRobert Watson 	ADD_U_INT16(dptr, perm->uid);
492ca0716f5SRobert Watson 
493ca0716f5SRobert Watson 	ADD_U_INT16(dptr, pad0);
494ca0716f5SRobert Watson 	ADD_U_INT16(dptr, perm->gid);
495ca0716f5SRobert Watson 
496ca0716f5SRobert Watson 	ADD_U_INT16(dptr, pad0);
497ca0716f5SRobert Watson 	ADD_U_INT16(dptr, perm->cuid);
498ca0716f5SRobert Watson 
499ca0716f5SRobert Watson 	ADD_U_INT16(dptr, pad0);
500ca0716f5SRobert Watson 	ADD_U_INT16(dptr, perm->cgid);
501ca0716f5SRobert Watson 
502ca0716f5SRobert Watson 	ADD_U_INT16(dptr, pad0);
503ca0716f5SRobert Watson 	ADD_U_INT16(dptr, perm->mode);
504ca0716f5SRobert Watson 
505ca0716f5SRobert Watson 	ADD_U_INT16(dptr, pad0);
506ca0716f5SRobert Watson 
5073b97a967SRobert Watson #ifdef HAVE_IPC_PERM___SEQ
5083b97a967SRobert Watson 	ADD_U_INT16(dptr, perm->__seq);
5093b97a967SRobert Watson #else
5103b97a967SRobert Watson 	ADD_U_INT16(dptr, perm->seq);
5113b97a967SRobert Watson #endif
5123b97a967SRobert Watson 
5133b97a967SRobert Watson #ifdef HAVE_IPC_PERM___KEY
5143b97a967SRobert Watson 	ADD_U_INT32(dptr, perm->__key);
5153b97a967SRobert Watson #else
516ca0716f5SRobert Watson 	ADD_U_INT32(dptr, perm->key);
5173b97a967SRobert Watson #endif
518ca0716f5SRobert Watson 
519ca0716f5SRobert Watson 	return (t);
520ca0716f5SRobert Watson }
521ca0716f5SRobert Watson 
522ca0716f5SRobert Watson /*
523ca0716f5SRobert Watson  * token ID                1 byte
524ca0716f5SRobert Watson  * port IP address         2 bytes
525ca0716f5SRobert Watson  */
526ca0716f5SRobert Watson token_t *
527ca0716f5SRobert Watson au_to_iport(u_int16_t iport)
528ca0716f5SRobert Watson {
529ca0716f5SRobert Watson 	token_t *t;
530ca0716f5SRobert Watson 	u_char *dptr = NULL;
531ca0716f5SRobert Watson 
532ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + sizeof(u_int16_t));
533ca0716f5SRobert Watson 	if (t == NULL)
534ca0716f5SRobert Watson 		return (NULL);
535ca0716f5SRobert Watson 
536ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_IPORT);
537ca0716f5SRobert Watson 	ADD_U_INT16(dptr, iport);
538ca0716f5SRobert Watson 
539ca0716f5SRobert Watson 	return (t);
540ca0716f5SRobert Watson }
541ca0716f5SRobert Watson 
542ca0716f5SRobert Watson /*
543ca0716f5SRobert Watson  * token ID                1 byte
544ca0716f5SRobert Watson  * size                    2 bytes
545ca0716f5SRobert Watson  * data                    size bytes
546ca0716f5SRobert Watson  */
547ca0716f5SRobert Watson token_t *
548ca0716f5SRobert Watson au_to_opaque(char *data, u_int16_t bytes)
549ca0716f5SRobert Watson {
550ca0716f5SRobert Watson 	token_t *t;
551ca0716f5SRobert Watson 	u_char *dptr = NULL;
552ca0716f5SRobert Watson 
553ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + sizeof(u_int16_t) + bytes);
554ca0716f5SRobert Watson 	if (t == NULL)
555ca0716f5SRobert Watson 		return (NULL);
556ca0716f5SRobert Watson 
557ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_OPAQUE);
558ca0716f5SRobert Watson 	ADD_U_INT16(dptr, bytes);
559ca0716f5SRobert Watson 	ADD_MEM(dptr, data, bytes);
560ca0716f5SRobert Watson 
561ca0716f5SRobert Watson 	return (t);
562ca0716f5SRobert Watson }
563ca0716f5SRobert Watson 
564ca0716f5SRobert Watson /*
565ca0716f5SRobert Watson  * token ID                1 byte
566ca0716f5SRobert Watson  * seconds of time         4 bytes
567ca0716f5SRobert Watson  * milliseconds of time    4 bytes
568ca0716f5SRobert Watson  * file name len           2 bytes
569ca0716f5SRobert Watson  * file pathname           N bytes + 1 terminating NULL byte
570ca0716f5SRobert Watson  */
571ca0716f5SRobert Watson token_t *
572ca0716f5SRobert Watson au_to_file(char *file, struct timeval tm)
573ca0716f5SRobert Watson {
574ca0716f5SRobert Watson 	token_t *t;
575ca0716f5SRobert Watson 	u_char *dptr = NULL;
576ca0716f5SRobert Watson 	u_int16_t filelen;
577ca0716f5SRobert Watson 	u_int32_t timems;
578ca0716f5SRobert Watson 
579ca0716f5SRobert Watson 	filelen = strlen(file);
580ca0716f5SRobert Watson 	filelen += 1;
581ca0716f5SRobert Watson 
582ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + 2 * sizeof(u_int32_t) +
583ca0716f5SRobert Watson 	    sizeof(u_int16_t) + filelen);
584ca0716f5SRobert Watson 	if (t == NULL)
585ca0716f5SRobert Watson 		return (NULL);
586ca0716f5SRobert Watson 
587ca0716f5SRobert Watson 	timems = tm.tv_usec/1000;
588ca0716f5SRobert Watson 
589ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_OTHER_FILE32);
590ca0716f5SRobert Watson 	ADD_U_INT32(dptr, tm.tv_sec);
591ca0716f5SRobert Watson 	ADD_U_INT32(dptr, timems);	/* We need time in ms. */
592ca0716f5SRobert Watson 	ADD_U_INT16(dptr, filelen);
593ca0716f5SRobert Watson 	ADD_STRING(dptr, file, filelen);
594ca0716f5SRobert Watson 
595ca0716f5SRobert Watson 	return (t);
596ca0716f5SRobert Watson }
597ca0716f5SRobert Watson 
598ca0716f5SRobert Watson /*
599ca0716f5SRobert Watson  * token ID                1 byte
600ca0716f5SRobert Watson  * text length             2 bytes
601ca0716f5SRobert Watson  * text                    N bytes + 1 terminating NULL byte
602ca0716f5SRobert Watson  */
603ca0716f5SRobert Watson token_t *
604ca0716f5SRobert Watson au_to_text(char *text)
605ca0716f5SRobert Watson {
606ca0716f5SRobert Watson 	token_t *t;
607ca0716f5SRobert Watson 	u_char *dptr = NULL;
608ca0716f5SRobert Watson 	u_int16_t textlen;
609ca0716f5SRobert Watson 
610ca0716f5SRobert Watson 	textlen = strlen(text);
611ca0716f5SRobert Watson 	textlen += 1;
612ca0716f5SRobert Watson 
613ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + sizeof(u_int16_t) + textlen);
614ca0716f5SRobert Watson 	if (t == NULL)
615ca0716f5SRobert Watson 		return (NULL);
616ca0716f5SRobert Watson 
617ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_TEXT);
618ca0716f5SRobert Watson 	ADD_U_INT16(dptr, textlen);
619ca0716f5SRobert Watson 	ADD_STRING(dptr, text, textlen);
620ca0716f5SRobert Watson 
621ca0716f5SRobert Watson 	return (t);
622ca0716f5SRobert Watson }
623ca0716f5SRobert Watson 
624ca0716f5SRobert Watson /*
625ca0716f5SRobert Watson  * token ID                1 byte
626ca0716f5SRobert Watson  * path length             2 bytes
627ca0716f5SRobert Watson  * path                    N bytes + 1 terminating NULL byte
628ca0716f5SRobert Watson  */
629ca0716f5SRobert Watson token_t *
630ca0716f5SRobert Watson au_to_path(char *text)
631ca0716f5SRobert Watson {
632ca0716f5SRobert Watson 	token_t *t;
633ca0716f5SRobert Watson 	u_char *dptr = NULL;
634ca0716f5SRobert Watson 	u_int16_t textlen;
635ca0716f5SRobert Watson 
636ca0716f5SRobert Watson 	textlen = strlen(text);
637ca0716f5SRobert Watson 	textlen += 1;
638ca0716f5SRobert Watson 
639ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + sizeof(u_int16_t) + textlen);
640ca0716f5SRobert Watson 	if (t == NULL)
641ca0716f5SRobert Watson 		return (NULL);
642ca0716f5SRobert Watson 
643ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_PATH);
644ca0716f5SRobert Watson 	ADD_U_INT16(dptr, textlen);
645ca0716f5SRobert Watson 	ADD_STRING(dptr, text, textlen);
646ca0716f5SRobert Watson 
647ca0716f5SRobert Watson 	return (t);
648ca0716f5SRobert Watson }
649ca0716f5SRobert Watson 
650ca0716f5SRobert Watson /*
651ca0716f5SRobert Watson  * token ID                1 byte
652ca0716f5SRobert Watson  * audit ID                4 bytes
653ca0716f5SRobert Watson  * effective user ID       4 bytes
654ca0716f5SRobert Watson  * effective group ID      4 bytes
655ca0716f5SRobert Watson  * real user ID            4 bytes
656ca0716f5SRobert Watson  * real group ID           4 bytes
657ca0716f5SRobert Watson  * process ID              4 bytes
658ca0716f5SRobert Watson  * session ID              4 bytes
659ca0716f5SRobert Watson  * terminal ID
660ca0716f5SRobert Watson  *   port ID               4 bytes/8 bytes (32-bit/64-bit value)
661ca0716f5SRobert Watson  *   machine address       4 bytes
662ca0716f5SRobert Watson  */
663ca0716f5SRobert Watson token_t *
664ca0716f5SRobert Watson au_to_process32(au_id_t auid, uid_t euid, gid_t egid, uid_t ruid, gid_t rgid,
665ca0716f5SRobert Watson     pid_t pid, au_asid_t sid, au_tid_t *tid)
666ca0716f5SRobert Watson {
667ca0716f5SRobert Watson 	token_t *t;
668ca0716f5SRobert Watson 	u_char *dptr = NULL;
669ca0716f5SRobert Watson 
670ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + 9 * sizeof(u_int32_t));
671ca0716f5SRobert Watson 	if (t == NULL)
672ca0716f5SRobert Watson 		return (NULL);
673ca0716f5SRobert Watson 
674ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_PROCESS32);
675ca0716f5SRobert Watson 	ADD_U_INT32(dptr, auid);
676ca0716f5SRobert Watson 	ADD_U_INT32(dptr, euid);
677ca0716f5SRobert Watson 	ADD_U_INT32(dptr, egid);
678ca0716f5SRobert Watson 	ADD_U_INT32(dptr, ruid);
679ca0716f5SRobert Watson 	ADD_U_INT32(dptr, rgid);
680ca0716f5SRobert Watson 	ADD_U_INT32(dptr, pid);
681ca0716f5SRobert Watson 	ADD_U_INT32(dptr, sid);
682ca0716f5SRobert Watson 	ADD_U_INT32(dptr, tid->port);
683506764c6SRobert Watson 	ADD_MEM(dptr, &tid->machine, sizeof(u_int32_t));
684ca0716f5SRobert Watson 
685ca0716f5SRobert Watson 	return (t);
686ca0716f5SRobert Watson }
687ca0716f5SRobert Watson 
688ca0716f5SRobert Watson token_t *
689bc168a6cSRobert Watson au_to_process64(au_id_t auid, uid_t euid, gid_t egid, uid_t ruid, gid_t rgid,
690bc168a6cSRobert Watson     pid_t pid, au_asid_t sid, au_tid_t *tid)
691ca0716f5SRobert Watson {
692bc168a6cSRobert Watson 	token_t *t;
693bc168a6cSRobert Watson 	u_char *dptr = NULL;
694ca0716f5SRobert Watson 
695bc168a6cSRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + 8 * sizeof(u_int32_t) +
696bc168a6cSRobert Watson 	    sizeof(u_int64_t));
697bc168a6cSRobert Watson 	if (t == NULL)
698ca0716f5SRobert Watson 		return (NULL);
699bc168a6cSRobert Watson 
700bc168a6cSRobert Watson 	ADD_U_CHAR(dptr, AUT_PROCESS64);
701bc168a6cSRobert Watson 	ADD_U_INT32(dptr, auid);
702bc168a6cSRobert Watson 	ADD_U_INT32(dptr, euid);
703bc168a6cSRobert Watson 	ADD_U_INT32(dptr, egid);
704bc168a6cSRobert Watson 	ADD_U_INT32(dptr, ruid);
705bc168a6cSRobert Watson 	ADD_U_INT32(dptr, rgid);
706bc168a6cSRobert Watson 	ADD_U_INT32(dptr, pid);
707bc168a6cSRobert Watson 	ADD_U_INT32(dptr, sid);
708bc168a6cSRobert Watson 	ADD_U_INT64(dptr, tid->port);
709bc168a6cSRobert Watson 	ADD_MEM(dptr, &tid->machine, sizeof(u_int32_t));
710bc168a6cSRobert Watson 
711bc168a6cSRobert Watson 	return (t);
712ca0716f5SRobert Watson }
713ca0716f5SRobert Watson 
714ca0716f5SRobert Watson token_t *
715bc168a6cSRobert Watson au_to_process(au_id_t auid, uid_t euid, gid_t egid, uid_t ruid, gid_t rgid,
716bc168a6cSRobert Watson     pid_t pid, au_asid_t sid, au_tid_t *tid)
717ca0716f5SRobert Watson {
718ca0716f5SRobert Watson 
719ca0716f5SRobert Watson 	return (au_to_process32(auid, euid, egid, ruid, rgid, pid, sid,
720ca0716f5SRobert Watson 	    tid));
721ca0716f5SRobert Watson }
722ca0716f5SRobert Watson 
723ca0716f5SRobert Watson /*
724ca0716f5SRobert Watson  * token ID                1 byte
725ca0716f5SRobert Watson  * audit ID                4 bytes
726ca0716f5SRobert Watson  * effective user ID       4 bytes
727ca0716f5SRobert Watson  * effective group ID      4 bytes
728ca0716f5SRobert Watson  * real user ID            4 bytes
729ca0716f5SRobert Watson  * real group ID           4 bytes
730ca0716f5SRobert Watson  * process ID              4 bytes
731ca0716f5SRobert Watson  * session ID              4 bytes
732ca0716f5SRobert Watson  * terminal ID
733ca0716f5SRobert Watson  *   port ID               4 bytes/8 bytes (32-bit/64-bit value)
734ca0716f5SRobert Watson  *   address type-len      4 bytes
735ca0716f5SRobert Watson  *   machine address      16 bytes
736ca0716f5SRobert Watson  */
737ca0716f5SRobert Watson token_t *
738ca0716f5SRobert Watson au_to_process32_ex(au_id_t auid, uid_t euid, gid_t egid, uid_t ruid,
739ca0716f5SRobert Watson     gid_t rgid, pid_t pid, au_asid_t sid, au_tid_addr_t *tid)
740ca0716f5SRobert Watson {
741ca0716f5SRobert Watson 	token_t *t;
742ca0716f5SRobert Watson 	u_char *dptr = NULL;
743ca0716f5SRobert Watson 
744d9af45c4SRobert Watson 	if (tid->at_type == AU_IPv4)
745d9af45c4SRobert Watson 		GET_TOKEN_AREA(t, dptr, sizeof(u_char) +
746d9af45c4SRobert Watson 		    10 * sizeof(u_int32_t));
747d9af45c4SRobert Watson 	else if (tid->at_type == AU_IPv6)
748d9af45c4SRobert Watson 		GET_TOKEN_AREA(t, dptr, sizeof(u_char) +
749d9af45c4SRobert Watson 		    13 * sizeof(u_int32_t));
750d9af45c4SRobert Watson 	else {
751d9af45c4SRobert Watson 		errno = EINVAL;
752d9af45c4SRobert Watson 		return (NULL);
753d9af45c4SRobert Watson 	}
754ca0716f5SRobert Watson 	if (t == NULL)
755ca0716f5SRobert Watson 		return (NULL);
756ca0716f5SRobert Watson 
757ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_PROCESS32_EX);
758ca0716f5SRobert Watson 	ADD_U_INT32(dptr, auid);
759ca0716f5SRobert Watson 	ADD_U_INT32(dptr, euid);
760ca0716f5SRobert Watson 	ADD_U_INT32(dptr, egid);
761ca0716f5SRobert Watson 	ADD_U_INT32(dptr, ruid);
762ca0716f5SRobert Watson 	ADD_U_INT32(dptr, rgid);
763ca0716f5SRobert Watson 	ADD_U_INT32(dptr, pid);
764ca0716f5SRobert Watson 	ADD_U_INT32(dptr, sid);
765ca0716f5SRobert Watson 	ADD_U_INT32(dptr, tid->at_port);
766ca0716f5SRobert Watson 	ADD_U_INT32(dptr, tid->at_type);
767bc168a6cSRobert Watson 	ADD_MEM(dptr, &tid->at_addr[0], sizeof(u_int32_t));
768d9af45c4SRobert Watson 	if (tid->at_type == AU_IPv6) {
769bc168a6cSRobert Watson 		ADD_MEM(dptr, &tid->at_addr[1], sizeof(u_int32_t));
770bc168a6cSRobert Watson 		ADD_MEM(dptr, &tid->at_addr[2], sizeof(u_int32_t));
771bc168a6cSRobert Watson 		ADD_MEM(dptr, &tid->at_addr[3], sizeof(u_int32_t));
772d9af45c4SRobert Watson 	}
773ca0716f5SRobert Watson 
774ca0716f5SRobert Watson 	return (t);
775ca0716f5SRobert Watson }
776ca0716f5SRobert Watson 
777ca0716f5SRobert Watson token_t *
778ca0716f5SRobert Watson au_to_process64_ex(au_id_t auid, uid_t euid, gid_t egid, uid_t ruid,
779ca0716f5SRobert Watson     gid_t rgid, pid_t pid, au_asid_t sid, au_tid_addr_t *tid)
780ca0716f5SRobert Watson {
781bc168a6cSRobert Watson 	token_t *t;
782bc168a6cSRobert Watson 	u_char *dptr = NULL;
783ca0716f5SRobert Watson 
784bc168a6cSRobert Watson 	if (tid->at_type == AU_IPv4)
785bc168a6cSRobert Watson 		GET_TOKEN_AREA(t, dptr, sizeof(u_char) +
786bc168a6cSRobert Watson 		    7 * sizeof(u_int32_t) + sizeof(u_int64_t) +
787bc168a6cSRobert Watson 		    2 * sizeof(u_int32_t));
788bc168a6cSRobert Watson 	else if (tid->at_type == AU_IPv6)
789bc168a6cSRobert Watson 		GET_TOKEN_AREA(t, dptr, sizeof(u_char) +
790bc168a6cSRobert Watson 		    7 * sizeof(u_int32_t) + sizeof(u_int64_t) +
791bc168a6cSRobert Watson 		    5 * sizeof(u_int32_t));
792bc168a6cSRobert Watson 	else {
793bc168a6cSRobert Watson 		errno = EINVAL;
794ca0716f5SRobert Watson 		return (NULL);
795ca0716f5SRobert Watson 	}
796bc168a6cSRobert Watson 	if (t == NULL)
797bc168a6cSRobert Watson 		return (NULL);
798bc168a6cSRobert Watson 
799bc168a6cSRobert Watson 	ADD_U_CHAR(dptr, AUT_PROCESS64_EX);
800bc168a6cSRobert Watson 	ADD_U_INT32(dptr, auid);
801bc168a6cSRobert Watson 	ADD_U_INT32(dptr, euid);
802bc168a6cSRobert Watson 	ADD_U_INT32(dptr, egid);
803bc168a6cSRobert Watson 	ADD_U_INT32(dptr, ruid);
804bc168a6cSRobert Watson 	ADD_U_INT32(dptr, rgid);
805bc168a6cSRobert Watson 	ADD_U_INT32(dptr, pid);
806bc168a6cSRobert Watson 	ADD_U_INT32(dptr, sid);
807bc168a6cSRobert Watson 	ADD_U_INT64(dptr, tid->at_port);
808bc168a6cSRobert Watson 	ADD_U_INT32(dptr, tid->at_type);
809bc168a6cSRobert Watson 	ADD_MEM(dptr, &tid->at_addr[0], sizeof(u_int32_t));
810bc168a6cSRobert Watson 	if (tid->at_type == AU_IPv6) {
811bc168a6cSRobert Watson 		ADD_MEM(dptr, &tid->at_addr[1], sizeof(u_int32_t));
812bc168a6cSRobert Watson 		ADD_MEM(dptr, &tid->at_addr[2], sizeof(u_int32_t));
813bc168a6cSRobert Watson 		ADD_MEM(dptr, &tid->at_addr[3], sizeof(u_int32_t));
814bc168a6cSRobert Watson 	}
815bc168a6cSRobert Watson 
816bc168a6cSRobert Watson 	return (t);
817bc168a6cSRobert Watson }
818ca0716f5SRobert Watson 
819ca0716f5SRobert Watson token_t *
820ca0716f5SRobert Watson au_to_process_ex(au_id_t auid, uid_t euid, gid_t egid, uid_t ruid,
821ca0716f5SRobert Watson     gid_t rgid, pid_t pid, au_asid_t sid, au_tid_addr_t *tid)
822ca0716f5SRobert Watson {
823ca0716f5SRobert Watson 
824ca0716f5SRobert Watson 	return (au_to_process32_ex(auid, euid, egid, ruid, rgid, pid, sid,
825ca0716f5SRobert Watson 	    tid));
826ca0716f5SRobert Watson }
827ca0716f5SRobert Watson 
828ca0716f5SRobert Watson /*
829ca0716f5SRobert Watson  * token ID                1 byte
830ca0716f5SRobert Watson  * error status            1 byte
831ca0716f5SRobert Watson  * return value            4 bytes/8 bytes (32-bit/64-bit value)
832ca0716f5SRobert Watson  */
833ca0716f5SRobert Watson token_t *
834ca0716f5SRobert Watson au_to_return32(char status, u_int32_t ret)
835ca0716f5SRobert Watson {
836ca0716f5SRobert Watson 	token_t *t;
837ca0716f5SRobert Watson 	u_char *dptr = NULL;
838ca0716f5SRobert Watson 
839ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, 2 * sizeof(u_char) + sizeof(u_int32_t));
840ca0716f5SRobert Watson 	if (t == NULL)
841ca0716f5SRobert Watson 		return (NULL);
842ca0716f5SRobert Watson 
843ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_RETURN32);
844ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, status);
845ca0716f5SRobert Watson 	ADD_U_INT32(dptr, ret);
846ca0716f5SRobert Watson 
847ca0716f5SRobert Watson 	return (t);
848ca0716f5SRobert Watson }
849ca0716f5SRobert Watson 
850ca0716f5SRobert Watson token_t *
851ca0716f5SRobert Watson au_to_return64(char status, u_int64_t ret)
852ca0716f5SRobert Watson {
853ca0716f5SRobert Watson 	token_t *t;
854ca0716f5SRobert Watson 	u_char *dptr = NULL;
855ca0716f5SRobert Watson 
856ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, 2 * sizeof(u_char) + sizeof(u_int64_t));
857ca0716f5SRobert Watson 	if (t == NULL)
858ca0716f5SRobert Watson 		return (NULL);
859ca0716f5SRobert Watson 
860ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_RETURN64);
861ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, status);
862ca0716f5SRobert Watson 	ADD_U_INT64(dptr, ret);
863ca0716f5SRobert Watson 
864ca0716f5SRobert Watson 	return (t);
865ca0716f5SRobert Watson }
866ca0716f5SRobert Watson 
867ca0716f5SRobert Watson token_t *
868ca0716f5SRobert Watson au_to_return(char status, u_int32_t ret)
869ca0716f5SRobert Watson {
870ca0716f5SRobert Watson 
871ca0716f5SRobert Watson 	return (au_to_return32(status, ret));
872ca0716f5SRobert Watson }
873ca0716f5SRobert Watson 
874ca0716f5SRobert Watson /*
875ca0716f5SRobert Watson  * token ID                1 byte
876ca0716f5SRobert Watson  * sequence number         4 bytes
877ca0716f5SRobert Watson  */
878ca0716f5SRobert Watson token_t *
879ca0716f5SRobert Watson au_to_seq(long audit_count)
880ca0716f5SRobert Watson {
881ca0716f5SRobert Watson 	token_t *t;
882ca0716f5SRobert Watson 	u_char *dptr = NULL;
883ca0716f5SRobert Watson 
884ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + sizeof(u_int32_t));
885ca0716f5SRobert Watson 	if (t == NULL)
886ca0716f5SRobert Watson 		return (NULL);
887ca0716f5SRobert Watson 
888ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_SEQ);
889ca0716f5SRobert Watson 	ADD_U_INT32(dptr, audit_count);
890ca0716f5SRobert Watson 
891ca0716f5SRobert Watson 	return (t);
892ca0716f5SRobert Watson }
893ca0716f5SRobert Watson 
894ca0716f5SRobert Watson /*
895ca0716f5SRobert Watson  * token ID                1 byte
896ca0716f5SRobert Watson  * socket family           2 bytes
897ca0716f5SRobert Watson  * path                    104 bytes
898ca0716f5SRobert Watson  */
899ca0716f5SRobert Watson token_t *
900ca0716f5SRobert Watson au_to_sock_unix(struct sockaddr_un *so)
901ca0716f5SRobert Watson {
902ca0716f5SRobert Watson 	token_t *t;
903ca0716f5SRobert Watson 	u_char *dptr;
904ca0716f5SRobert Watson 
905ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, 3 * sizeof(u_char) + strlen(so->sun_path) + 1);
906ca0716f5SRobert Watson 	if (t == NULL)
907ca0716f5SRobert Watson 		return (NULL);
908ca0716f5SRobert Watson 
909ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AU_SOCK_UNIX_TOKEN);
910ca0716f5SRobert Watson 	/* BSM token has two bytes for family */
911ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, 0);
912ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, so->sun_family);
913ca0716f5SRobert Watson 	ADD_STRING(dptr, so->sun_path, strlen(so->sun_path) + 1);
914ca0716f5SRobert Watson 
915ca0716f5SRobert Watson 	return (t);
916ca0716f5SRobert Watson }
917ca0716f5SRobert Watson 
918ca0716f5SRobert Watson /*
919ca0716f5SRobert Watson  * token ID                1 byte
920ca0716f5SRobert Watson  * socket family           2 bytes
921ca0716f5SRobert Watson  * local port              2 bytes
922ca0716f5SRobert Watson  * socket address          4 bytes
923ca0716f5SRobert Watson  */
924ca0716f5SRobert Watson token_t *
925ca0716f5SRobert Watson au_to_sock_inet32(struct sockaddr_in *so)
926ca0716f5SRobert Watson {
927ca0716f5SRobert Watson 	token_t *t;
928ca0716f5SRobert Watson 	u_char *dptr = NULL;
929506764c6SRobert Watson 	uint16_t family;
930ca0716f5SRobert Watson 
931506764c6SRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + 2 * sizeof(uint16_t) +
932506764c6SRobert Watson 	    sizeof(uint32_t));
933ca0716f5SRobert Watson 	if (t == NULL)
934ca0716f5SRobert Watson 		return (NULL);
935ca0716f5SRobert Watson 
936ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_SOCKINET32);
937ca0716f5SRobert Watson 	/*
938506764c6SRobert Watson 	 * BSM defines the family field as 16 bits, but many operating
939506764c6SRobert Watson 	 * systems have an 8-bit sin_family field.  Extend to 16 bits before
940506764c6SRobert Watson 	 * writing into the token.  Assume that both the port and the address
941506764c6SRobert Watson 	 * in the sockaddr_in are already in network byte order, but family
942506764c6SRobert Watson 	 * is in local byte order.
943506764c6SRobert Watson 	 *
944506764c6SRobert Watson 	 * XXXRW: Should a name space conversion be taking place on the value
945506764c6SRobert Watson 	 * of sin_family?
946ca0716f5SRobert Watson  	 */
947506764c6SRobert Watson 	family = so->sin_family;
948506764c6SRobert Watson 	ADD_U_INT16(dptr, family);
949506764c6SRobert Watson 	ADD_MEM(dptr, &so->sin_port, sizeof(uint16_t));
950506764c6SRobert Watson 	ADD_MEM(dptr, &so->sin_addr.s_addr, sizeof(uint32_t));
951ca0716f5SRobert Watson 
952ca0716f5SRobert Watson 	return (t);
953ca0716f5SRobert Watson 
954ca0716f5SRobert Watson }
955ca0716f5SRobert Watson 
956ca0716f5SRobert Watson token_t *
957ca0716f5SRobert Watson au_to_sock_inet128(struct sockaddr_in6 *so)
958ca0716f5SRobert Watson {
959ca0716f5SRobert Watson 	token_t *t;
960ca0716f5SRobert Watson 	u_char *dptr = NULL;
961ca0716f5SRobert Watson 
962ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, 3 * sizeof(u_char) + sizeof(u_int16_t) +
963ca0716f5SRobert Watson 	    4 * sizeof(u_int32_t));
964ca0716f5SRobert Watson 	if (t == NULL)
965ca0716f5SRobert Watson 		return (NULL);
966ca0716f5SRobert Watson 
967ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_SOCKINET128);
968ca0716f5SRobert Watson 	/*
969ca0716f5SRobert Watson 	 * In Darwin, sin6_family is one octet, but BSM defines the token
970ca0716f5SRobert Watson  	 * to store two. So we copy in a 0 first.
971ca0716f5SRobert Watson  	 */
972ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, 0);
973ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, so->sin6_family);
974ca0716f5SRobert Watson 
975ca0716f5SRobert Watson 	ADD_U_INT16(dptr, so->sin6_port);
976506764c6SRobert Watson 	ADD_MEM(dptr, &so->sin6_addr, 4 * sizeof(uint32_t));
977ca0716f5SRobert Watson 
978ca0716f5SRobert Watson 	return (t);
979ca0716f5SRobert Watson 
980ca0716f5SRobert Watson }
981ca0716f5SRobert Watson 
982ca0716f5SRobert Watson token_t *
983ca0716f5SRobert Watson au_to_sock_inet(struct sockaddr_in *so)
984ca0716f5SRobert Watson {
985ca0716f5SRobert Watson 
986ca0716f5SRobert Watson 	return (au_to_sock_inet32(so));
987ca0716f5SRobert Watson }
988ca0716f5SRobert Watson 
989ca0716f5SRobert Watson /*
990ca0716f5SRobert Watson  * token ID                1 byte
991ca0716f5SRobert Watson  * audit ID                4 bytes
992ca0716f5SRobert Watson  * effective user ID       4 bytes
993ca0716f5SRobert Watson  * effective group ID      4 bytes
994ca0716f5SRobert Watson  * real user ID            4 bytes
995ca0716f5SRobert Watson  * real group ID           4 bytes
996ca0716f5SRobert Watson  * process ID              4 bytes
997ca0716f5SRobert Watson  * session ID              4 bytes
998ca0716f5SRobert Watson  * terminal ID
999ca0716f5SRobert Watson  *   port ID               4 bytes/8 bytes (32-bit/64-bit value)
1000ca0716f5SRobert Watson  *   machine address       4 bytes
1001ca0716f5SRobert Watson  */
1002ca0716f5SRobert Watson token_t *
1003ca0716f5SRobert Watson au_to_subject32(au_id_t auid, uid_t euid, gid_t egid, uid_t ruid, gid_t rgid,
1004ca0716f5SRobert Watson     pid_t pid, au_asid_t sid, au_tid_t *tid)
1005ca0716f5SRobert Watson {
1006ca0716f5SRobert Watson 	token_t *t;
1007ca0716f5SRobert Watson 	u_char *dptr = NULL;
1008ca0716f5SRobert Watson 
1009ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + 9 * sizeof(u_int32_t));
1010ca0716f5SRobert Watson 	if (t == NULL)
1011ca0716f5SRobert Watson 		return (NULL);
1012ca0716f5SRobert Watson 
1013ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_SUBJECT32);
1014ca0716f5SRobert Watson 	ADD_U_INT32(dptr, auid);
1015ca0716f5SRobert Watson 	ADD_U_INT32(dptr, euid);
1016ca0716f5SRobert Watson 	ADD_U_INT32(dptr, egid);
1017ca0716f5SRobert Watson 	ADD_U_INT32(dptr, ruid);
1018ca0716f5SRobert Watson 	ADD_U_INT32(dptr, rgid);
1019ca0716f5SRobert Watson 	ADD_U_INT32(dptr, pid);
1020ca0716f5SRobert Watson 	ADD_U_INT32(dptr, sid);
1021ca0716f5SRobert Watson 	ADD_U_INT32(dptr, tid->port);
1022506764c6SRobert Watson 	ADD_MEM(dptr, &tid->machine, sizeof(u_int32_t));
1023ca0716f5SRobert Watson 
1024ca0716f5SRobert Watson 	return (t);
1025ca0716f5SRobert Watson }
1026ca0716f5SRobert Watson 
1027ca0716f5SRobert Watson token_t *
1028ca0716f5SRobert Watson au_to_subject64(au_id_t auid, uid_t euid, gid_t egid, uid_t ruid, gid_t rgid,
1029ca0716f5SRobert Watson     pid_t pid, au_asid_t sid, au_tid_t *tid)
1030ca0716f5SRobert Watson {
1031bc168a6cSRobert Watson 	token_t *t;
1032bc168a6cSRobert Watson 	u_char *dptr = NULL;
1033ca0716f5SRobert Watson 
1034bc168a6cSRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + 7 * sizeof(u_int32_t) +
1035bc168a6cSRobert Watson 	    sizeof(u_int64_t) + sizeof(u_int32_t));
1036bc168a6cSRobert Watson 	if (t == NULL)
1037ca0716f5SRobert Watson 		return (NULL);
1038bc168a6cSRobert Watson 
1039bc168a6cSRobert Watson 	ADD_U_CHAR(dptr, AUT_SUBJECT64);
1040bc168a6cSRobert Watson 	ADD_U_INT32(dptr, auid);
1041bc168a6cSRobert Watson 	ADD_U_INT32(dptr, euid);
1042bc168a6cSRobert Watson 	ADD_U_INT32(dptr, egid);
1043bc168a6cSRobert Watson 	ADD_U_INT32(dptr, ruid);
1044bc168a6cSRobert Watson 	ADD_U_INT32(dptr, rgid);
1045bc168a6cSRobert Watson 	ADD_U_INT32(dptr, pid);
1046bc168a6cSRobert Watson 	ADD_U_INT32(dptr, sid);
1047bc168a6cSRobert Watson 	ADD_U_INT64(dptr, tid->port);
1048bc168a6cSRobert Watson 	ADD_MEM(dptr, &tid->machine, sizeof(u_int32_t));
1049bc168a6cSRobert Watson 
1050bc168a6cSRobert Watson 	return (t);
1051ca0716f5SRobert Watson }
1052ca0716f5SRobert Watson 
1053ca0716f5SRobert Watson token_t *
1054ca0716f5SRobert Watson au_to_subject(au_id_t auid, uid_t euid, gid_t egid, uid_t ruid, gid_t rgid,
1055ca0716f5SRobert Watson     pid_t pid, au_asid_t sid, au_tid_t *tid)
1056ca0716f5SRobert Watson {
1057ca0716f5SRobert Watson 
1058ca0716f5SRobert Watson 	return (au_to_subject32(auid, euid, egid, ruid, rgid, pid, sid,
1059ca0716f5SRobert Watson 	    tid));
1060ca0716f5SRobert Watson }
1061ca0716f5SRobert Watson 
1062ca0716f5SRobert Watson /*
1063ca0716f5SRobert Watson  * token ID                1 byte
1064ca0716f5SRobert Watson  * audit ID                4 bytes
1065ca0716f5SRobert Watson  * effective user ID       4 bytes
1066ca0716f5SRobert Watson  * effective group ID      4 bytes
1067ca0716f5SRobert Watson  * real user ID            4 bytes
1068ca0716f5SRobert Watson  * real group ID           4 bytes
1069ca0716f5SRobert Watson  * process ID              4 bytes
1070ca0716f5SRobert Watson  * session ID              4 bytes
1071ca0716f5SRobert Watson  * terminal ID
1072ca0716f5SRobert Watson  *   port ID               4 bytes/8 bytes (32-bit/64-bit value)
1073ca0716f5SRobert Watson  *   address type/length   4 bytes
1074ca0716f5SRobert Watson  *   machine address      16 bytes
1075ca0716f5SRobert Watson  */
1076ca0716f5SRobert Watson token_t *
1077ca0716f5SRobert Watson au_to_subject32_ex(au_id_t auid, uid_t euid, gid_t egid, uid_t ruid,
1078ca0716f5SRobert Watson     gid_t rgid, pid_t pid, au_asid_t sid, au_tid_addr_t *tid)
1079ca0716f5SRobert Watson {
1080ca0716f5SRobert Watson 	token_t *t;
1081ca0716f5SRobert Watson 	u_char *dptr = NULL;
1082ca0716f5SRobert Watson 
1083d9af45c4SRobert Watson 	if (tid->at_type == AU_IPv4)
1084d9af45c4SRobert Watson 		GET_TOKEN_AREA(t, dptr, sizeof(u_char) + 10 *
1085d9af45c4SRobert Watson 		    sizeof(u_int32_t));
1086d9af45c4SRobert Watson 	else if (tid->at_type == AU_IPv6)
1087d9af45c4SRobert Watson 		GET_TOKEN_AREA(t, dptr, sizeof(u_char) + 13 *
1088d9af45c4SRobert Watson 		    sizeof(u_int32_t));
1089d9af45c4SRobert Watson 	else {
1090d9af45c4SRobert Watson 		errno = EINVAL;
1091d9af45c4SRobert Watson 		return (NULL);
1092d9af45c4SRobert Watson 	}
1093ca0716f5SRobert Watson 	if (t == NULL)
1094ca0716f5SRobert Watson 		return (NULL);
1095ca0716f5SRobert Watson 
1096ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_SUBJECT32_EX);
1097ca0716f5SRobert Watson 	ADD_U_INT32(dptr, auid);
1098ca0716f5SRobert Watson 	ADD_U_INT32(dptr, euid);
1099ca0716f5SRobert Watson 	ADD_U_INT32(dptr, egid);
1100ca0716f5SRobert Watson 	ADD_U_INT32(dptr, ruid);
1101ca0716f5SRobert Watson 	ADD_U_INT32(dptr, rgid);
1102ca0716f5SRobert Watson 	ADD_U_INT32(dptr, pid);
1103ca0716f5SRobert Watson 	ADD_U_INT32(dptr, sid);
1104ca0716f5SRobert Watson 	ADD_U_INT32(dptr, tid->at_port);
1105ca0716f5SRobert Watson 	ADD_U_INT32(dptr, tid->at_type);
1106bc168a6cSRobert Watson 	if (tid->at_type == AU_IPv6)
1107bc168a6cSRobert Watson 		ADD_MEM(dptr, &tid->at_addr[0], 4 * sizeof(u_int32_t));
1108bc168a6cSRobert Watson 	else
1109bc168a6cSRobert Watson 		ADD_MEM(dptr, &tid->at_addr[0], sizeof(u_int32_t));
1110ca0716f5SRobert Watson 
1111ca0716f5SRobert Watson 	return (t);
1112ca0716f5SRobert Watson }
1113ca0716f5SRobert Watson 
1114ca0716f5SRobert Watson token_t *
1115ca0716f5SRobert Watson au_to_subject64_ex(au_id_t auid, uid_t euid, gid_t egid, uid_t ruid,
1116ca0716f5SRobert Watson     gid_t rgid, pid_t pid, au_asid_t sid, au_tid_addr_t *tid)
1117ca0716f5SRobert Watson {
1118bc168a6cSRobert Watson 	token_t *t;
1119bc168a6cSRobert Watson 	u_char *dptr = NULL;
1120ca0716f5SRobert Watson 
1121bc168a6cSRobert Watson 	if (tid->at_type == AU_IPv4)
1122bc168a6cSRobert Watson 		GET_TOKEN_AREA(t, dptr, sizeof(u_char) +
1123bc168a6cSRobert Watson 		    7 * sizeof(u_int32_t) + sizeof(u_int64_t) +
1124bc168a6cSRobert Watson 		    2 * sizeof(u_int32_t));
1125bc168a6cSRobert Watson 	else if (tid->at_type == AU_IPv6)
1126bc168a6cSRobert Watson 		GET_TOKEN_AREA(t, dptr, sizeof(u_char) +
1127bc168a6cSRobert Watson 		    7 * sizeof(u_int32_t) + sizeof(u_int64_t) +
1128bc168a6cSRobert Watson 		    5 * sizeof(u_int32_t));
1129bc168a6cSRobert Watson 	else {
1130bc168a6cSRobert Watson 		errno = EINVAL;
1131ca0716f5SRobert Watson 		return (NULL);
1132ca0716f5SRobert Watson 	}
1133bc168a6cSRobert Watson 	if (t == NULL)
1134bc168a6cSRobert Watson 		return (NULL);
1135bc168a6cSRobert Watson 
1136bc168a6cSRobert Watson 	ADD_U_CHAR(dptr, AUT_SUBJECT64_EX);
1137bc168a6cSRobert Watson 	ADD_U_INT32(dptr, auid);
1138bc168a6cSRobert Watson 	ADD_U_INT32(dptr, euid);
1139bc168a6cSRobert Watson 	ADD_U_INT32(dptr, egid);
1140bc168a6cSRobert Watson 	ADD_U_INT32(dptr, ruid);
1141bc168a6cSRobert Watson 	ADD_U_INT32(dptr, rgid);
1142bc168a6cSRobert Watson 	ADD_U_INT32(dptr, pid);
1143bc168a6cSRobert Watson 	ADD_U_INT32(dptr, sid);
1144bc168a6cSRobert Watson 	ADD_U_INT64(dptr, tid->at_port);
1145bc168a6cSRobert Watson 	ADD_U_INT32(dptr, tid->at_type);
1146bc168a6cSRobert Watson 	if (tid->at_type == AU_IPv6)
1147bc168a6cSRobert Watson 		ADD_MEM(dptr, &tid->at_addr[0], 4 * sizeof(u_int32_t));
1148bc168a6cSRobert Watson 	else
1149bc168a6cSRobert Watson 		ADD_MEM(dptr, &tid->at_addr[0], sizeof(u_int32_t));
1150bc168a6cSRobert Watson 
1151bc168a6cSRobert Watson 	return (t);
1152bc168a6cSRobert Watson }
1153ca0716f5SRobert Watson 
1154ca0716f5SRobert Watson token_t *
1155ca0716f5SRobert Watson au_to_subject_ex(au_id_t auid, uid_t euid, gid_t egid, uid_t ruid,
1156ca0716f5SRobert Watson     gid_t rgid, pid_t pid, au_asid_t sid, au_tid_addr_t *tid)
1157ca0716f5SRobert Watson {
1158ca0716f5SRobert Watson 
1159ca0716f5SRobert Watson 	return (au_to_subject32_ex(auid, euid, egid, ruid, rgid, pid, sid,
1160ca0716f5SRobert Watson 	    tid));
1161ca0716f5SRobert Watson }
1162ca0716f5SRobert Watson 
11633b97a967SRobert Watson #if !defined(_KERNEL) && !defined(KERNEL) && defined(HAVE_AUDIT_SYSCALLS)
1164ca0716f5SRobert Watson /*
1165ca0716f5SRobert Watson  * Collects audit information for the current process
1166ca0716f5SRobert Watson  * and creates a subject token from it
1167ca0716f5SRobert Watson  */
1168ca0716f5SRobert Watson token_t *
1169ca0716f5SRobert Watson au_to_me(void)
1170ca0716f5SRobert Watson {
1171ca0716f5SRobert Watson 	auditinfo_t auinfo;
1172ca0716f5SRobert Watson 
1173ca0716f5SRobert Watson 	if (getaudit(&auinfo) != 0)
1174ca0716f5SRobert Watson 		return (NULL);
1175ca0716f5SRobert Watson 
1176ca0716f5SRobert Watson 	return (au_to_subject32(auinfo.ai_auid, geteuid(), getegid(),
1177ca0716f5SRobert Watson 	    getuid(), getgid(), getpid(), auinfo.ai_asid, &auinfo.ai_termid));
1178ca0716f5SRobert Watson }
1179ca0716f5SRobert Watson #endif
1180ca0716f5SRobert Watson 
1181ca0716f5SRobert Watson /*
1182ca0716f5SRobert Watson  * token ID				1 byte
1183ca0716f5SRobert Watson  * count				4 bytes
1184ca0716f5SRobert Watson  * text					count null-terminated strings
1185ca0716f5SRobert Watson  */
1186ca0716f5SRobert Watson token_t *
118785feadf6SRobert Watson au_to_exec_args(char **argv)
1188ca0716f5SRobert Watson {
1189ca0716f5SRobert Watson 	token_t *t;
1190ca0716f5SRobert Watson 	u_char *dptr = NULL;
1191ca0716f5SRobert Watson 	const char *nextarg;
1192ca0716f5SRobert Watson 	int i, count = 0;
1193ca0716f5SRobert Watson 	size_t totlen = 0;
1194ca0716f5SRobert Watson 
119522ccb20dSRobert Watson 	nextarg = *argv;
1196ca0716f5SRobert Watson 
1197ca0716f5SRobert Watson 	while (nextarg != NULL) {
1198ca0716f5SRobert Watson 		int nextlen;
1199ca0716f5SRobert Watson 
1200ca0716f5SRobert Watson 		nextlen = strlen(nextarg);
1201ca0716f5SRobert Watson 		totlen += nextlen + 1;
1202ca0716f5SRobert Watson 		count++;
120322ccb20dSRobert Watson 		nextarg = *(argv + count);
1204ca0716f5SRobert Watson 	}
1205ca0716f5SRobert Watson 
1206ca0716f5SRobert Watson 	totlen += count * sizeof(char);	/* nul terminations. */
1207ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + sizeof(u_int32_t) + totlen);
1208ca0716f5SRobert Watson 	if (t == NULL)
1209ca0716f5SRobert Watson 		return (NULL);
1210ca0716f5SRobert Watson 
1211ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_EXEC_ARGS);
1212ca0716f5SRobert Watson 	ADD_U_INT32(dptr, count);
1213ca0716f5SRobert Watson 
1214ca0716f5SRobert Watson 	for (i = 0; i < count; i++) {
121522ccb20dSRobert Watson 		nextarg = *(argv + i);
1216ca0716f5SRobert Watson 		ADD_MEM(dptr, nextarg, strlen(nextarg) + 1);
1217ca0716f5SRobert Watson 	}
1218ca0716f5SRobert Watson 
1219ca0716f5SRobert Watson 	return (t);
1220ca0716f5SRobert Watson }
1221ca0716f5SRobert Watson 
1222ca0716f5SRobert Watson /*
1223ca0716f5SRobert Watson  * token ID                1 byte
1224bc168a6cSRobert Watson  * zonename length         2 bytes
1225bc168a6cSRobert Watson  * zonename                N bytes + 1 terminating NULL byte
1226bc168a6cSRobert Watson  */
1227bc168a6cSRobert Watson token_t *
1228bc168a6cSRobert Watson au_to_zonename(char *zonename)
1229bc168a6cSRobert Watson {
1230bc168a6cSRobert Watson 	u_char *dptr = NULL;
1231bc168a6cSRobert Watson 	u_int16_t textlen;
1232bc168a6cSRobert Watson 	token_t *t;
1233bc168a6cSRobert Watson 
1234bc168a6cSRobert Watson 	textlen = strlen(zonename);
1235bc168a6cSRobert Watson 	textlen += 1;
1236bc168a6cSRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + sizeof(u_int16_t) + textlen);
1237bc168a6cSRobert Watson 	ADD_U_CHAR(dptr, AUT_ZONENAME);
1238bc168a6cSRobert Watson 	ADD_U_INT16(dptr, textlen);
1239bc168a6cSRobert Watson 	ADD_STRING(dptr, zonename, textlen);
1240bc168a6cSRobert Watson 	return (t);
1241bc168a6cSRobert Watson }
1242bc168a6cSRobert Watson 
1243bc168a6cSRobert Watson /*
1244bc168a6cSRobert Watson  * token ID				1 byte
1245ca0716f5SRobert Watson  * count				4 bytes
1246ca0716f5SRobert Watson  * text					count null-terminated strings
1247ca0716f5SRobert Watson  */
1248ca0716f5SRobert Watson token_t *
124985feadf6SRobert Watson au_to_exec_env(char **envp)
1250ca0716f5SRobert Watson {
1251ca0716f5SRobert Watson 	token_t *t;
1252ca0716f5SRobert Watson 	u_char *dptr = NULL;
1253ca0716f5SRobert Watson 	int i, count = 0;
1254ca0716f5SRobert Watson 	size_t totlen = 0;
1255ca0716f5SRobert Watson 	const char *nextenv;
1256ca0716f5SRobert Watson 
125722ccb20dSRobert Watson 	nextenv = *envp;
1258ca0716f5SRobert Watson 
1259ca0716f5SRobert Watson 	while (nextenv != NULL) {
1260ca0716f5SRobert Watson 		int nextlen;
1261ca0716f5SRobert Watson 
1262ca0716f5SRobert Watson 		nextlen = strlen(nextenv);
1263ca0716f5SRobert Watson 		totlen += nextlen + 1;
1264ca0716f5SRobert Watson 		count++;
126522ccb20dSRobert Watson 		nextenv = *(envp + count);
1266ca0716f5SRobert Watson 	}
1267ca0716f5SRobert Watson 
1268ca0716f5SRobert Watson 	totlen += sizeof(char) * count;
1269ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + sizeof(u_int32_t) + totlen);
1270ca0716f5SRobert Watson 	if (t == NULL)
1271ca0716f5SRobert Watson 		return (NULL);
1272ca0716f5SRobert Watson 
1273ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_EXEC_ENV);
1274ca0716f5SRobert Watson 	ADD_U_INT32(dptr, count);
1275ca0716f5SRobert Watson 
1276ca0716f5SRobert Watson 	for (i = 0; i < count; i++) {
127722ccb20dSRobert Watson 		nextenv = *(envp + i);
1278ca0716f5SRobert Watson 		ADD_MEM(dptr, nextenv, strlen(nextenv) + 1);
1279ca0716f5SRobert Watson 	}
1280ca0716f5SRobert Watson 
1281ca0716f5SRobert Watson 	return (t);
1282ca0716f5SRobert Watson }
1283ca0716f5SRobert Watson 
1284ca0716f5SRobert Watson /*
1285ca0716f5SRobert Watson  * token ID                1 byte
1286ca0716f5SRobert Watson  * record byte count       4 bytes
1287ca0716f5SRobert Watson  * version #               1 byte    [2]
1288ca0716f5SRobert Watson  * event type              2 bytes
1289ca0716f5SRobert Watson  * event modifier          2 bytes
1290ca0716f5SRobert Watson  * seconds of time         4 bytes/8 bytes (32-bit/64-bit value)
1291ca0716f5SRobert Watson  * milliseconds of time    4 bytes/8 bytes (32-bit/64-bit value)
1292ca0716f5SRobert Watson  */
1293ca0716f5SRobert Watson token_t *
1294506764c6SRobert Watson au_to_header32_tm(int rec_size, au_event_t e_type, au_emod_t e_mod,
1295ca0716f5SRobert Watson     struct timeval tm)
1296ca0716f5SRobert Watson {
1297ca0716f5SRobert Watson 	token_t *t;
1298ca0716f5SRobert Watson 	u_char *dptr = NULL;
1299ca0716f5SRobert Watson 	u_int32_t timems;
1300ca0716f5SRobert Watson 
1301ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + sizeof(u_int32_t) +
1302ca0716f5SRobert Watson 	    sizeof(u_char) + 2 * sizeof(u_int16_t) + 2 * sizeof(u_int32_t));
1303ca0716f5SRobert Watson 	if (t == NULL)
1304ca0716f5SRobert Watson 		return (NULL);
1305ca0716f5SRobert Watson 
1306ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_HEADER32);
1307ca0716f5SRobert Watson 	ADD_U_INT32(dptr, rec_size);
130822ccb20dSRobert Watson 	ADD_U_CHAR(dptr, AUDIT_HEADER_VERSION_OPENBSM);
1309ca0716f5SRobert Watson 	ADD_U_INT16(dptr, e_type);
1310ca0716f5SRobert Watson 	ADD_U_INT16(dptr, e_mod);
1311ca0716f5SRobert Watson 
1312ca0716f5SRobert Watson 	timems = tm.tv_usec/1000;
1313ca0716f5SRobert Watson 	/* Add the timestamp */
1314ca0716f5SRobert Watson 	ADD_U_INT32(dptr, tm.tv_sec);
1315ca0716f5SRobert Watson 	ADD_U_INT32(dptr, timems);	/* We need time in ms. */
1316ca0716f5SRobert Watson 
1317ca0716f5SRobert Watson 	return (t);
1318ca0716f5SRobert Watson }
1319ca0716f5SRobert Watson 
1320bc168a6cSRobert Watson token_t *
1321bc168a6cSRobert Watson au_to_header64_tm(int rec_size, au_event_t e_type, au_emod_t e_mod,
1322bc168a6cSRobert Watson     struct timeval tm)
1323bc168a6cSRobert Watson {
1324bc168a6cSRobert Watson 	token_t *t;
1325bc168a6cSRobert Watson 	u_char *dptr = NULL;
1326bc168a6cSRobert Watson 	u_int32_t timems;
1327bc168a6cSRobert Watson 
1328bc168a6cSRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + sizeof(u_int32_t) +
1329bc168a6cSRobert Watson 	    sizeof(u_char) + 2 * sizeof(u_int16_t) + 2 * sizeof(u_int64_t));
1330bc168a6cSRobert Watson 	if (t == NULL)
1331bc168a6cSRobert Watson 		return (NULL);
1332bc168a6cSRobert Watson 
1333bc168a6cSRobert Watson 	ADD_U_CHAR(dptr, AUT_HEADER64);
1334bc168a6cSRobert Watson 	ADD_U_INT32(dptr, rec_size);
1335bc168a6cSRobert Watson 	ADD_U_CHAR(dptr, AUDIT_HEADER_VERSION_OPENBSM);
1336bc168a6cSRobert Watson 	ADD_U_INT16(dptr, e_type);
1337bc168a6cSRobert Watson 	ADD_U_INT16(dptr, e_mod);
1338bc168a6cSRobert Watson 
1339bc168a6cSRobert Watson 	timems = tm.tv_usec/1000;
1340bc168a6cSRobert Watson 	/* Add the timestamp */
1341bc168a6cSRobert Watson 	ADD_U_INT64(dptr, tm.tv_sec);
1342bc168a6cSRobert Watson 	ADD_U_INT64(dptr, timems);	/* We need time in ms. */
1343bc168a6cSRobert Watson 
1344bc168a6cSRobert Watson 	return (t);
1345bc168a6cSRobert Watson }
1346bc168a6cSRobert Watson 
1347506764c6SRobert Watson #if !defined(KERNEL) && !defined(_KERNEL)
1348506764c6SRobert Watson token_t *
1349506764c6SRobert Watson au_to_header32(int rec_size, au_event_t e_type, au_emod_t e_mod)
1350506764c6SRobert Watson {
1351506764c6SRobert Watson 	struct timeval tm;
1352506764c6SRobert Watson 
1353506764c6SRobert Watson 	if (gettimeofday(&tm, NULL) == -1)
1354506764c6SRobert Watson 		return (NULL);
1355506764c6SRobert Watson 	return (au_to_header32_tm(rec_size, e_type, e_mod, tm));
1356506764c6SRobert Watson }
1357506764c6SRobert Watson 
1358ca0716f5SRobert Watson token_t *
1359ca0716f5SRobert Watson au_to_header64(__unused int rec_size, __unused au_event_t e_type,
1360ca0716f5SRobert Watson     __unused au_emod_t e_mod)
1361ca0716f5SRobert Watson {
1362bc168a6cSRobert Watson 	struct timeval tm;
1363ca0716f5SRobert Watson 
1364bc168a6cSRobert Watson 	if (gettimeofday(&tm, NULL) == -1)
1365ca0716f5SRobert Watson 		return (NULL);
1366bc168a6cSRobert Watson 	return (au_to_header64_tm(rec_size, e_type, e_mod, tm));
1367ca0716f5SRobert Watson }
1368ca0716f5SRobert Watson 
1369ca0716f5SRobert Watson token_t *
1370ca0716f5SRobert Watson au_to_header(int rec_size, au_event_t e_type, au_emod_t e_mod)
1371ca0716f5SRobert Watson {
1372ca0716f5SRobert Watson 
1373ca0716f5SRobert Watson 	return (au_to_header32(rec_size, e_type, e_mod));
1374ca0716f5SRobert Watson }
1375506764c6SRobert Watson #endif
1376ca0716f5SRobert Watson 
1377ca0716f5SRobert Watson /*
1378ca0716f5SRobert Watson  * token ID                1 byte
1379ca0716f5SRobert Watson  * trailer magic number    2 bytes
1380ca0716f5SRobert Watson  * record byte count       4 bytes
1381ca0716f5SRobert Watson  */
1382ca0716f5SRobert Watson token_t *
1383ca0716f5SRobert Watson au_to_trailer(int rec_size)
1384ca0716f5SRobert Watson {
1385ca0716f5SRobert Watson 	token_t *t;
1386ca0716f5SRobert Watson 	u_char *dptr = NULL;
1387ca0716f5SRobert Watson 	u_int16_t magic = TRAILER_PAD_MAGIC;
1388ca0716f5SRobert Watson 
1389ca0716f5SRobert Watson 	GET_TOKEN_AREA(t, dptr, sizeof(u_char) + sizeof(u_int16_t) +
1390ca0716f5SRobert Watson 	    sizeof(u_int32_t));
1391ca0716f5SRobert Watson 	if (t == NULL)
1392ca0716f5SRobert Watson 		return (NULL);
1393ca0716f5SRobert Watson 
1394ca0716f5SRobert Watson 	ADD_U_CHAR(dptr, AUT_TRAILER);
1395ca0716f5SRobert Watson 	ADD_U_INT16(dptr, magic);
1396ca0716f5SRobert Watson 	ADD_U_INT32(dptr, rec_size);
1397ca0716f5SRobert Watson 
1398ca0716f5SRobert Watson 	return (t);
1399ca0716f5SRobert Watson }
1400