Home | History | Annotate | Download | only in c2
      1 /*
      2  * CDDL HEADER START
      3  *
      4  * The contents of this file are subject to the terms of the
      5  * Common Development and Distribution License (the "License").
      6  * You may not use this file except in compliance with the License.
      7  *
      8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
      9  * or http://www.opensolaris.org/os/licensing.
     10  * See the License for the specific language governing permissions
     11  * and limitations under the License.
     12  *
     13  * When distributing Covered Code, include this CDDL HEADER in each
     14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
     15  * If applicable, add the following below this CDDL HEADER, with the
     16  * fields enclosed by brackets "[]" replaced with your own identifying
     17  * information: Portions Copyright [yyyy] [name of copyright owner]
     18  *
     19  * CDDL HEADER END
     20  */
     21 /*
     22  * Copyright 2008 Sun Microsystems, Inc.  All rights reserved.
     23  * Use is subject to license terms.
     24  */
     25 
     26 /*
     27  * Support routines for building audit records.
     28  */
     29 
     30 #include <sys/param.h>
     31 #include <sys/systm.h>		/* for rval */
     32 #include <sys/time.h>
     33 #include <sys/types.h>
     34 #include <sys/vnode.h>
     35 #include <sys/mode.h>
     36 #include <sys/user.h>
     37 #include <sys/session.h>
     38 #include <sys/acl.h>
     39 #include <sys/ipc_impl.h>
     40 #include <netinet/in_systm.h>
     41 #include <netinet/in.h>
     42 #include <netinet/ip.h>
     43 #include <sys/socket.h>
     44 #include <net/route.h>
     45 #include <netinet/in_pcb.h>
     46 #include <c2/audit.h>
     47 #include <c2/audit_kernel.h>
     48 #include <c2/audit_record.h>
     49 #include <sys/model.h>		/* for model_t */
     50 #include <sys/vmparam.h>	/* for USRSTACK/USRSTACK32 */
     51 #include <sys/vfs.h>		/* for sonode */
     52 #include <sys/socketvar.h>	/* for sonode */
     53 #include <sys/zone.h>
     54 #include <sys/tsol/label.h>
     55 
     56 /*
     57  * These are the control tokens
     58  */
     59 
     60 /*
     61  * au_to_header
     62  * returns:
     63  *	pointer to au_membuf chain containing a header token.
     64  */
     65 token_t *
     66 au_to_header(int byte_count, au_event_t e_type, au_emod_t e_mod)
     67 {
     68 	adr_t adr;			/* adr memory stream header */
     69 	token_t *m;			/* au_membuf pointer */
     70 #ifdef _LP64
     71 	char data_header = AUT_HEADER64;	/* header for this token */
     72 	static int64_t zerotime[2];
     73 #else
     74 	char data_header = AUT_HEADER32;
     75 	static int32_t zerotime[2];
     76 #endif
     77 	char version = TOKEN_VERSION;	/* version of token family */
     78 
     79 	m = au_getclr();
     80 
     81 	adr_start(&adr, memtod(m, char *));
     82 	adr_char(&adr, &data_header, 1);	/* token ID */
     83 	adr_int32(&adr, (int32_t *)&byte_count, 1);	/* length of */
     84 							/* audit record */
     85 	adr_char(&adr, &version, 1);		/* version of audit tokens */
     86 	adr_ushort(&adr, &e_type, 1);		/* event ID */
     87 	adr_ushort(&adr, &e_mod, 1);		/* event ID modifier */
     88 #ifdef _LP64
     89 	adr_int64(&adr, zerotime, 2);		/* time & date space */
     90 #else
     91 	adr_int32(&adr, zerotime, 2);
     92 #endif
     93 	m->len = adr_count(&adr);
     94 
     95 	return (m);
     96 }
     97 
     98 token_t *
     99 au_to_header_ex(int byte_count, au_event_t e_type, au_emod_t e_mod)
    100 {
    101 	adr_t adr;			/* adr memory stream header */
    102 	token_t *m;			/* au_membuf pointer */
    103 	au_kcontext_t	*kctx = GET_KCTX_PZ;
    104 
    105 #ifdef _LP64
    106 	char data_header = AUT_HEADER64_EX;	/* header for this token */
    107 	static int64_t zerotime[2];
    108 #else
    109 	char data_header = AUT_HEADER32_EX;
    110 	static int32_t zerotime[2];
    111 #endif
    112 	char version = TOKEN_VERSION;	/* version of token family */
    113 
    114 	m = au_getclr();
    115 
    116 	adr_start(&adr, memtod(m, char *));
    117 	adr_char(&adr, &data_header, 1);	/* token ID */
    118 	adr_int32(&adr, (int32_t *)&byte_count, 1);	/* length of */
    119 							/* audit record */
    120 	adr_char(&adr, &version, 1);		/* version of audit tokens */
    121 	adr_ushort(&adr, &e_type, 1);		/* event ID */
    122 	adr_ushort(&adr, &e_mod, 1);		/* event ID modifier */
    123 	adr_uint32(&adr, &kctx->auk_info.ai_termid.at_type, 1);
    124 	adr_char(&adr, (char *)&kctx->auk_info.ai_termid.at_addr[0],
    125 	    (int)kctx->auk_info.ai_termid.at_type);
    126 #ifdef _LP64
    127 	adr_int64(&adr, zerotime, 2);		/* time & date */
    128 #else
    129 	adr_int32(&adr, zerotime, 2);
    130 #endif
    131 	m->len = adr_count(&adr);
    132 
    133 	return (m);
    134 }
    135 
    136 /*
    137  * au_to_trailer
    138  * returns:
    139  *	pointer to au_membuf chain containing a trailer token.
    140  */
    141 token_t *
    142 au_to_trailer(int byte_count)
    143 {
    144 	adr_t adr;				/* adr memory stream header */
    145 	token_t *m;				/* au_membuf pointer */
    146 	char data_header = AUT_TRAILER;		/* header for this token */
    147 	short magic = (short)AUT_TRAILER_MAGIC; /* trailer magic number */
    148 
    149 	m = au_getclr();
    150 
    151 	adr_start(&adr, memtod(m, char *));
    152 	adr_char(&adr, &data_header, 1);		/* token ID */
    153 	adr_short(&adr, &magic, 1);			/* magic number */
    154 	adr_int32(&adr, (int32_t *)&byte_count, 1);	/* length of */
    155 							/* audit record */
    156 
    157 	m->len = adr_count(&adr);
    158 
    159 	return (m);
    160 }
    161 /*
    162  * These are the data tokens
    163  */
    164 
    165 /*
    166  * au_to_data
    167  * returns:
    168  *	pointer to au_membuf chain containing a data token.
    169  */
    170 token_t *
    171 au_to_data(char unit_print, char unit_type, char unit_count, char *p)
    172 {
    173 	adr_t adr;			/* adr memory stream header */
    174 	token_t *m;			/* au_membuf pointer */
    175 	char data_header = AUT_DATA;	/* header for this token */
    176 
    177 	ASSERT(p != NULL);
    178 	ASSERT(unit_count != 0);
    179 
    180 	switch (unit_type) {
    181 	case AUR_SHORT:
    182 		if (sizeof (short) * unit_count >= AU_BUFSIZE)
    183 			return (au_to_text("au_to_data: unit count too big"));
    184 		break;
    185 	case AUR_INT32:
    186 		if (sizeof (int32_t) * unit_count >= AU_BUFSIZE)
    187 			return (au_to_text("au_to_data: unit count too big"));
    188 		break;
    189 	case AUR_INT64:
    190 		if (sizeof (int64_t) * unit_count >= AU_BUFSIZE)
    191 			return (au_to_text("au_to_data: unit count too big"));
    192 		break;
    193 	case AUR_BYTE:
    194 	default:
    195 #ifdef _CHAR_IS_UNSIGNED
    196 		if (sizeof (char) * unit_count >= AU_BUFSIZE)
    197 			return (au_to_text("au_to_data: unit count too big"));
    198 #endif
    199 		/*
    200 		 * we used to check for this:
    201 		 * sizeof (char) * (int)unit_count >= AU_BUFSIZE).
    202 		 * but the compiler is smart enough to see that
    203 		 * will never be >= AU_BUFSIZE, since that's 128
    204 		 * and unit_count maxes out at 127 (signed char),
    205 		 * and complain.
    206 		 */
    207 		break;
    208 	}
    209 
    210 	m = au_getclr();
    211 
    212 	adr_start(&adr, memtod(m, char *));
    213 	adr_char(&adr, &data_header, 1);
    214 	adr_char(&adr, &unit_print, 1);
    215 	adr_char(&adr, &unit_type, 1);
    216 	adr_char(&adr, &unit_count, 1);
    217 
    218 	switch (unit_type) {
    219 	case AUR_SHORT:
    220 		adr_short(&adr, (short *)p, unit_count);
    221 		break;
    222 	case AUR_INT32:
    223 		adr_int32(&adr, (int32_t *)p, unit_count);
    224 		break;
    225 	case AUR_INT64:
    226 		adr_int64(&adr, (int64_t *)p, unit_count);
    227 		break;
    228 	case AUR_BYTE:
    229 	default:
    230 		adr_char(&adr, p, unit_count);
    231 		break;
    232 	}
    233 
    234 	m->len = adr_count(&adr);
    235 
    236 	return (m);
    237 }
    238 
    239 /*
    240  * au_to_process
    241  * au_to_subject
    242  * returns:
    243  *	pointer to au_membuf chain containing a process token.
    244  */
    245 static token_t *au_to_any_process(char, uid_t, gid_t, uid_t, gid_t,
    246     pid_t, au_id_t, au_asid_t, const au_tid_addr_t *atid);
    247 
    248 token_t *
    249 au_to_process(uid_t uid, gid_t gid, uid_t ruid, gid_t rgid, pid_t pid,
    250     au_id_t auid, au_asid_t asid, const au_tid_addr_t *atid)
    251 {
    252 	char data_header;
    253 
    254 #ifdef _LP64
    255 	if (atid->at_type == AU_IPv6)
    256 		data_header = AUT_PROCESS64_EX;
    257 	else
    258 		data_header = AUT_PROCESS64;
    259 #else
    260 	if (atid->at_type == AU_IPv6)
    261 		data_header = AUT_PROCESS32_EX;
    262 	else
    263 		data_header = AUT_PROCESS32;
    264 #endif
    265 
    266 	return (au_to_any_process(data_header, uid, gid, ruid,
    267 	    rgid, pid, auid, asid, atid));
    268 }
    269 
    270 token_t *
    271 au_to_subject(uid_t uid, gid_t gid, uid_t ruid, gid_t rgid, pid_t pid,
    272     au_id_t auid, au_asid_t asid, const au_tid_addr_t *atid)
    273 {
    274 	char data_header;
    275 
    276 #ifdef _LP64
    277 	if (atid->at_type == AU_IPv6)
    278 		data_header = AUT_SUBJECT64_EX;
    279 	else
    280 		data_header = AUT_SUBJECT64;
    281 #else
    282 	if (atid->at_type == AU_IPv6)
    283 		data_header = AUT_SUBJECT32_EX;
    284 	else
    285 		data_header = AUT_SUBJECT32;
    286 #endif
    287 	return (au_to_any_process(data_header, uid, gid, ruid,
    288 	    rgid, pid, auid, asid, atid));
    289 }
    290 
    291 
    292 static token_t *
    293 au_to_any_process(char data_header,
    294     uid_t uid, gid_t gid, uid_t ruid, gid_t rgid, pid_t pid,
    295     au_id_t auid, au_asid_t asid, const au_tid_addr_t *atid)
    296 {
    297 	token_t *m;	/* local au_membuf */
    298 	adr_t adr;	/* adr memory stream header */
    299 	int32_t value;
    300 
    301 	m = au_getclr();
    302 
    303 	adr_start(&adr, memtod(m, char *));
    304 	adr_char(&adr, &data_header, 1);
    305 	value = (int32_t)auid;
    306 	adr_int32(&adr, &value, 1);
    307 	value = (int32_t)uid;
    308 	adr_int32(&adr, &value, 1);
    309 	value = (int32_t)gid;
    310 	adr_int32(&adr, &value, 1);
    311 	value = (int32_t)ruid;
    312 	adr_int32(&adr, &value, 1);
    313 	value = (int32_t)rgid;
    314 	adr_int32(&adr, &value, 1);
    315 	value = (int32_t)pid;
    316 	adr_int32(&adr, &value, 1);
    317 	value = (int32_t)asid;
    318 	adr_int32(&adr, &value, 1);
    319 #ifdef _LP64
    320 	adr_int64(&adr, (int64_t *)&(atid->at_port), 1);
    321 #else
    322 	adr_int32(&adr, (int32_t *)&(atid->at_port), 1);
    323 #endif
    324 	if (atid->at_type == AU_IPv6) {
    325 		adr_uint32(&adr, (uint_t *)&atid->at_type, 1);
    326 		adr_char(&adr, (char *)&atid->at_addr[0], 16);
    327 	} else {
    328 		adr_char(&adr, (char *)&(atid->at_addr[0]), 4);
    329 	}
    330 
    331 	m->len = adr_count(&adr);
    332 
    333 	return (m);
    334 }
    335 
    336 /*
    337  * au_to_text
    338  * returns:
    339  *	pointer to au_membuf chain containing a text token.
    340  */
    341 token_t *
    342 au_to_text(const char *text)
    343 {
    344 	token_t *token;			/* local au_membuf */
    345 	adr_t adr;			/* adr memory stream header */
    346 	char data_header = AUT_TEXT;	/* header for this token */
    347 	short bytes;			/* length of string */
    348 
    349 	token = au_getclr();
    350 
    351 	bytes = (short)strlen(text) + 1;
    352 	adr_start(&adr, memtod(token, char *));
    353 	adr_char(&adr, &data_header, 1);
    354 	adr_short(&adr, &bytes, 1);
    355 
    356 	token->len = (char)adr_count(&adr);
    357 	/*
    358 	 * Now attach the text
    359 	 */
    360 	(void) au_append_buf(text, bytes, token);
    361 
    362 	return (token);
    363 }
    364 
    365 /*
    366  * au_zonename_length
    367  * returns:
    368  * -	length of zonename token to be generated
    369  * -	zone name up to ZONENAME_MAX + 1 in length
    370  */
    371 #define	ZONE_TOKEN_OVERHEAD 3
    372 	/*
    373 	 * the zone token is
    374 	 * token id (1 byte)
    375 	 * string length (2 bytes)
    376 	 * the string (strlen(zonename) + 1)
    377 	 */
    378 size_t
    379 au_zonename_length(zone_t *zone)
    380 {
    381 	if (zone == NULL)
    382 		zone = curproc->p_zone;
    383 	return (strlen(zone->zone_name) + 1 +
    384 	    ZONE_TOKEN_OVERHEAD);
    385 }
    386 
    387 /*
    388  * au_to_zonename
    389  *
    390  * A length of zero input to au_to_zonename means the length is not
    391  * pre-calculated.
    392  *
    393  * The caller is responsible for checking the AUDIT_ZONENAME policy
    394  * before calling au_zonename_length() and au_to_zonename().  If
    395  * the policy changes between the calls, no harm is done, so the
    396  * policy only needs to be checked once.
    397  *
    398  * returns:
    399  *	pointer to au_membuf chain containing a zonename token; NULL if
    400  *	policy is off.
    401  *
    402  *	if the zonename token is generated at token generation close time,
    403  *	the length of the token is already known and it is ASSERTed that
    404  *	it has not changed.  If not precalculated, zone_length must be
    405  *	zero.
    406  */
    407 token_t *
    408 au_to_zonename(size_t zone_length, zone_t *zone)
    409 {
    410 	token_t *token;			/* local au_membuf */
    411 	adr_t adr;			/* adr memory stream header */
    412 	char data_header = AUT_ZONENAME;	/* header for this token */
    413 	short bytes;			/* length of string */
    414 
    415 	token = au_getclr();
    416 
    417 	if (zone == NULL)
    418 		zone = curproc->p_zone;
    419 	bytes = (short)strlen(zone->zone_name) + 1;
    420 	/*
    421 	 * If zone_length != 0, it was precalculated and is
    422 	 * the token length, not the string length.
    423 	 */
    424 	ASSERT((zone_length == 0) ||
    425 	    (zone_length == (bytes + ZONE_TOKEN_OVERHEAD)));
    426 
    427 	adr_start(&adr, memtod(token, char *));
    428 	adr_char(&adr, &data_header, 1);
    429 	adr_short(&adr, &bytes, 1);
    430 
    431 	token->len = (char)adr_count(&adr);
    432 	(void) au_append_buf(zone->zone_name, bytes, token);
    433 
    434 	return (token);
    435 }
    436 
    437 /*
    438  * au_to_strings
    439  * returns:
    440  *	pointer to au_membuf chain containing a strings array token.
    441  */
    442 token_t *
    443 au_to_strings(
    444 	char header,		/* token type */
    445 	const char *kstrp,	/* kernel string pointer */
    446 	ssize_t count)		/* count of arguments */
    447 {
    448 	token_t *token;			/* local au_membuf */
    449 	token_t *m;			/* local au_membuf */
    450 	adr_t adr;			/* adr memory stream header */
    451 	size_t len;
    452 	int32_t tlen;
    453 
    454 	token = au_getclr();
    455 
    456 	adr_start(&adr, memtod(token, char *));
    457 	adr_char(&adr, &header, 1);
    458 	tlen = (int32_t)count;
    459 	adr_int32(&adr, &tlen, 1);
    460 
    461 	token->len = (char)adr_count(&adr);
    462 
    463 	while (count-- > 0) {
    464 		m = au_getclr();
    465 		len = strlen(kstrp) + 1;
    466 		(void) au_append_buf(kstrp, len, m);
    467 		(void) au_append_rec((token_t *)token, (token_t *)m, AU_PACK);
    468 		kstrp += len;
    469 	}
    470 
    471 	return (token);
    472 }
    473 
    474 /*
    475  * au_to_exec_args
    476  * returns:
    477  *	pointer to au_membuf chain containing a argv token.
    478  */
    479 token_t *
    480 au_to_exec_args(const char *kstrp, ssize_t argc)
    481 {
    482 	return (au_to_strings(AUT_EXEC_ARGS, kstrp, argc));
    483 }
    484 
    485 /*
    486  * au_to_exec_env
    487  * returns:
    488  *	pointer to au_membuf chain containing a arge token.
    489  */
    490 token_t *
    491 au_to_exec_env(const char *kstrp, ssize_t envc)
    492 {
    493 	return (au_to_strings(AUT_EXEC_ENV, kstrp, envc));
    494 }
    495 
    496 /*
    497  * au_to_arg32
    498  *	char   n;	argument # being used
    499  *	char  *text;	text describing argument
    500  *	uint32_t v;	argument value
    501  * returns:
    502  *	pointer to au_membuf chain containing an argument token.
    503  */
    504 token_t *
    505 au_to_arg32(char n, char *text, uint32_t v)
    506 {
    507 	token_t *token;			/* local au_membuf */
    508 	adr_t adr;			/* adr memory stream header */
    509 	char data_header = AUT_ARG32;	/* header for this token */
    510 	short bytes;			/* length of string */
    511 
    512 	token = au_getclr();
    513 
    514 	bytes = strlen(text) + 1;
    515 	adr_start(&adr, memtod(token, char *));
    516 	adr_char(&adr, &data_header, 1);	/* token type */
    517 	adr_char(&adr, &n, 1);			/* argument id */
    518 	adr_uint32(&adr, &v, 1);		/* argument value */
    519 	adr_short(&adr, &bytes, 1);
    520 
    521 	token->len = adr_count(&adr);
    522 	/*
    523 	 * Now add the description
    524 	 */
    525 	(void) au_append_buf(text, bytes, token);
    526 
    527 	return (token);
    528 }
    529 
    530 
    531 /*
    532  * au_to_arg64
    533  *	char		n;	argument # being used
    534  *	char		*text;	text describing argument
    535  *	uint64_t	v;	argument value
    536  * returns:
    537  *	pointer to au_membuf chain containing an argument token.
    538  */
    539 token_t *
    540 au_to_arg64(char n, char *text, uint64_t v)
    541 {
    542 	token_t *token;			/* local au_membuf */
    543 	adr_t adr;			/* adr memory stream header */
    544 	char data_header = AUT_ARG64;	/* header for this token */
    545 	short bytes;			/* length of string */
    546 
    547 	token = au_getclr();
    548 
    549 	bytes = strlen(text) + 1;
    550 	adr_start(&adr, memtod(token, char *));
    551 	adr_char(&adr, &data_header, 1);	/* token type */
    552 	adr_char(&adr, &n, 1);			/* argument id */
    553 	adr_uint64(&adr, &v, 1);		/* argument value */
    554 	adr_short(&adr, &bytes, 1);
    555 
    556 	token->len = adr_count(&adr);
    557 	/*
    558 	 * Now the description
    559 	 */
    560 	(void) au_append_buf(text, bytes, token);
    561 
    562 	return (token);
    563 }
    564 
    565 
    566 /*
    567  * au_to_path
    568  * returns:
    569  *	pointer to au_membuf chain containing a path token.
    570  */
    571 token_t *
    572 au_to_path(struct audit_path *app)
    573 {
    574 	token_t *token;			/* local au_membuf */
    575 	token_t *m;			/* local au_membuf */
    576 	adr_t adr;			/* adr memory stream header */
    577 	char data_header = AUT_PATH;	/* header for this token */
    578 	short bytes;			/* length of string */
    579 	char *path = app->audp_sect[0];
    580 
    581 	bytes = (short)(app->audp_sect[1] - app->audp_sect[0]);
    582 
    583 	/*
    584 	 * generate path token header
    585 	 */
    586 	m = au_getclr();
    587 	adr_start(&adr, memtod(m, char *));
    588 	adr_char(&adr, &data_header, 1);
    589 	adr_short(&adr, &bytes, 1);
    590 	m->len = adr_count(&adr);
    591 
    592 	/* append path string */
    593 	token = m;
    594 	(void) au_append_buf(path, bytes, token);
    595 
    596 	if (app->audp_cnt > 1) {
    597 		/* generate attribute path strings token */
    598 		m = au_to_strings(AUT_XATPATH, app->audp_sect[1],
    599 		    app->audp_cnt - 1);
    600 
    601 		token = au_append_token(token, m);
    602 	}
    603 
    604 	return (token);
    605 }
    606 
    607 /*
    608  * au_to_ipc
    609  * returns:
    610  *	pointer to au_membuf chain containing a System V IPC token.
    611  */
    612 token_t *
    613 au_to_ipc(char type, int id)
    614 {
    615 	token_t *m;			/* local au_membuf */
    616 	adr_t adr;			/* adr memory stream header */
    617 	char data_header = AUT_IPC;	/* header for this token */
    618 
    619 	m = au_getclr();
    620 
    621 	adr_start(&adr, memtod(m, char *));
    622 	adr_char(&adr, &data_header, 1);
    623 	adr_char(&adr, &type, 1);		/* type of IPC object */
    624 	adr_int32(&adr, (int32_t *)&id, 1);
    625 
    626 	m->len = adr_count(&adr);
    627 
    628 	return (m);
    629 }
    630 
    631 /*
    632  * au_to_return32
    633  * returns:
    634  *	pointer to au_membuf chain containing a return value token.
    635  */
    636 token_t *
    637 au_to_return32(int error, int32_t rv)
    638 {
    639 	token_t *m;			/* local au_membuf */
    640 	adr_t adr;			/* adr memory stream header */
    641 	char data_header = AUT_RETURN32; /* header for this token */
    642 	int32_t val;
    643 	char ed = error;
    644 
    645 	m = au_getclr();
    646 
    647 	adr_start(&adr, memtod(m, char *));
    648 	adr_char(&adr, &data_header, 1);
    649 	adr_char(&adr, &ed, 1);
    650 
    651 	if (error) {
    652 		val = -1;
    653 		adr_int32(&adr, &val, 1);
    654 	} else {
    655 		adr_int32(&adr, &rv, 1);
    656 	}
    657 	m->len = adr_count(&adr);
    658 
    659 	return (m);
    660 }
    661 
    662 /*
    663  * au_to_return64
    664  * returns:
    665  *	pointer to au_membuf chain containing a return value token.
    666  */
    667 token_t *
    668 au_to_return64(int error, int64_t rv)
    669 {
    670 	token_t *m;			/* local au_membuf */
    671 	adr_t adr;			/* adr memory stream header */
    672 	char data_header = AUT_RETURN64; /* header for this token */
    673 	int64_t val;
    674 	char ed = error;
    675 
    676 	m = au_getclr();
    677 
    678 	adr_start(&adr, memtod(m, char *));
    679 	adr_char(&adr, &data_header, 1);
    680 	adr_char(&adr, &ed, 1);
    681 
    682 	if (error) {
    683 		val = -1;
    684 		adr_int64(&adr, &val, 1);
    685 	} else {
    686 		adr_int64(&adr, &rv, 1);
    687 	}
    688 	m->len = adr_count(&adr);
    689 
    690 	return (m);
    691 }
    692 
    693 #ifdef	AU_MAY_USE_SOMEDAY
    694 /*
    695  * au_to_opaque
    696  * returns:
    697  *	pointer to au_membuf chain containing a opaque token.
    698  */
    699 token_t *
    700 au_to_opaque(short bytes, char *opaque)
    701 {
    702 	token_t *token;			/* local au_membuf */
    703 	adr_t adr;			/* adr memory stream header */
    704 	char data_header = AUT_OPAQUE;	/* header for this token */
    705 
    706 	token = au_getclr();
    707 
    708 	adr_start(&adr, memtod(token, char *));
    709 	adr_char(&adr, &data_header, 1);
    710 	adr_short(&adr, &bytes, 1);
    711 
    712 	token->len = adr_count(&adr);
    713 
    714 	/*
    715 	 * Now attach the data
    716 	 */
    717 	(void) au_append_buf(opaque, bytes, token);
    718 
    719 	return (token);
    720 }
    721 #endif	/* AU_MAY_USE_SOMEDAY */
    722 
    723 /*
    724  * au_to_ip
    725  * returns:
    726  *	pointer to au_membuf chain containing a ip header token
    727  */
    728 token_t *
    729 au_to_ip(struct ip *ipp)
    730 {
    731 	token_t *m;			/* local au_membuf */
    732 	adr_t adr;			/* adr memory stream header */
    733 	char data_header = AUT_IP;	/* header for this token */
    734 
    735 	m = au_getclr();
    736 
    737 	adr_start(&adr, memtod(m, char *));
    738 	adr_char(&adr, &data_header, 1);
    739 	adr_char(&adr, (char *)ipp, 2);
    740 	adr_short(&adr, (short *)&(ipp->ip_len), 3);
    741 	adr_char(&adr, (char *)&(ipp->ip_ttl), 2);
    742 	adr_short(&adr, (short *)&(ipp->ip_sum), 1);
    743 	adr_int32(&adr, (int32_t *)&(ipp->ip_src), 2);
    744 
    745 	m->len = adr_count(&adr);
    746 
    747 	return (m);
    748 }
    749 
    750 /*
    751  * au_to_iport
    752  * returns:
    753  *	pointer to au_membuf chain containing a ip path token
    754  */
    755 token_t *
    756 au_to_iport(ushort_t iport)
    757 {
    758 	token_t *m;			/* local au_membuf */
    759 	adr_t adr;			/* adr memory stream header */
    760 	char data_header = AUT_IPORT;	/* header for this token */
    761 
    762 	m = au_getclr();
    763 
    764 	adr_start(&adr, memtod(m, char *));
    765 	adr_char(&adr, &data_header, 1);
    766 	adr_ushort(&adr, &iport, 1);
    767 
    768 	m->len = adr_count(&adr);
    769 
    770 	return (m);
    771 }
    772 
    773 /*
    774  * au_to_in_addr
    775  * returns:
    776  *	pointer to au_membuf chain containing a ip path token
    777  */
    778 token_t *
    779 au_to_in_addr(struct in_addr *internet_addr)
    780 {
    781 	token_t *m;			/* local au_membuf */
    782 	adr_t adr;			/* adr memory stream header */
    783 	char data_header = AUT_IN_ADDR;	/* header for this token */
    784 
    785 	m = au_getclr();
    786 
    787 	adr_start(&adr, memtod(m, char *));
    788 	adr_char(&adr, &data_header, 1);
    789 	adr_char(&adr, (char *)internet_addr, sizeof (struct in_addr));
    790 
    791 	m->len = adr_count(&adr);
    792 
    793 	return (m);
    794 }
    795 
    796 /*
    797  * au_to_in_addr_ex
    798  * returns:
    799  *	pointer to au_membuf chain containing an ipv6 token
    800  */
    801 token_t *
    802 au_to_in_addr_ex(int32_t *internet_addr)
    803 {
    804 	token_t *m;			/* local au_membuf */
    805 	adr_t adr;			/* adr memory stream header */
    806 	char data_header_v4 = AUT_IN_ADDR;	/* header for v4 token */
    807 	char data_header_v6 = AUT_IN_ADDR_EX;	/* header for v6 token */
    808 	int32_t type = AU_IPv6;
    809 
    810 	m = au_getclr();
    811 	adr_start(&adr, memtod(m, char *));
    812 
    813 	if (IN6_IS_ADDR_V4MAPPED((in6_addr_t *)internet_addr)) {
    814 		ipaddr_t in4;
    815 
    816 		/*
    817 		 * An IPv4-mapped IPv6 address is really an IPv4 address
    818 		 * in IPv6 format.
    819 		 */
    820 		IN6_V4MAPPED_TO_IPADDR((in6_addr_t *)internet_addr, in4);
    821 
    822 		adr_char(&adr, &data_header_v4, 1);
    823 		adr_char(&adr, (char *)&in4, sizeof (ipaddr_t));
    824 	} else {
    825 		adr_char(&adr, &data_header_v6, 1);
    826 		adr_int32(&adr, &type, 1);
    827 		adr_char(&adr, (char *)internet_addr, sizeof (struct in6_addr));
    828 	}
    829 
    830 	m->len = adr_count(&adr);
    831 
    832 	return (m);
    833 }
    834 
    835 /*
    836  * The Modifier tokens
    837  */
    838 
    839 /*
    840  * au_to_attr
    841  * returns:
    842  *	pointer to au_membuf chain containing an attribute token.
    843  */
    844 token_t *
    845 au_to_attr(struct vattr *attr)
    846 {
    847 	token_t *m;			/* local au_membuf */
    848 	adr_t adr;			/* adr memory stream header */
    849 #ifdef _LP64
    850 	char data_header = AUT_ATTR64;	/* header for this token */
    851 #else
    852 	char data_header = AUT_ATTR32;
    853 #endif
    854 	int32_t value;
    855 
    856 	m = au_getclr();
    857 
    858 	adr_start(&adr, memtod(m, char *));
    859 	adr_char(&adr, &data_header, 1);
    860 	value = (int32_t)attr->va_mode;
    861 	value |= (int32_t)(VTTOIF(attr->va_type));
    862 	adr_int32(&adr, &value, 1);
    863 	value = (int32_t)attr->va_uid;
    864 	adr_int32(&adr, &value, 1);
    865 	value = (int32_t)attr->va_gid;
    866 	adr_int32(&adr, &value, 1);
    867 	adr_int32(&adr, (int32_t *)&(attr->va_fsid), 1);
    868 	adr_int64(&adr, (int64_t *)&(attr->va_nodeid), 1);
    869 #ifdef _LP64
    870 	adr_int64(&adr, (int64_t *)&(attr->va_rdev), 1);
    871 #else
    872 	adr_int32(&adr, (int32_t *)&(attr->va_rdev), 1);
    873 #endif
    874 
    875 	m->len = adr_count(&adr);
    876 
    877 	return (m);
    878 }
    879 
    880 token_t *
    881 au_to_acl(struct acl *aclp)
    882 {
    883 	token_t *m;				/* local au_membuf */
    884 	adr_t adr;				/* adr memory stream header */
    885 	char data_header = AUT_ACL;		/* header for this token */
    886 	int32_t value;
    887 
    888 	m = au_getclr();
    889 
    890 	adr_start(&adr, memtod(m, char *));
    891 	adr_char(&adr, &data_header, 1);
    892 
    893 	value = (int32_t)aclp->a_type;
    894 	adr_int32(&adr, &value, 1);
    895 	value = (int32_t)aclp->a_id;
    896 	adr_int32(&adr, &value, 1);
    897 	value = (int32_t)aclp->a_perm;
    898 	adr_int32(&adr, &value, 1);
    899 
    900 	m->len = adr_count(&adr);
    901 	return (m);
    902 }
    903 
    904 token_t *
    905 au_to_ace(ace_t *acep)
    906 {
    907 	token_t *m;				/* local au_membuf */
    908 	adr_t adr;				/* adr memory stream header */
    909 	char data_header = AUT_ACE;		/* header for this token */
    910 
    911 	m = au_getclr();
    912 
    913 	adr_start(&adr, memtod(m, char *));
    914 	adr_char(&adr, &data_header, 1);
    915 
    916 	adr_uint32(&adr, &(acep->a_who), 1);
    917 	adr_uint32(&adr, &(acep->a_access_mask), 1);
    918 	adr_ushort(&adr, &(acep->a_flags), 1);
    919 	adr_ushort(&adr, &(acep->a_type), 1);
    920 
    921 	m->len = adr_count(&adr);
    922 	return (m);
    923 }
    924 
    925 /*
    926  * au_to_ipc_perm
    927  * returns:
    928  *	pointer to au_membuf chain containing a System V IPC attribute token.
    929  */
    930 token_t *
    931 au_to_ipc_perm(struct kipc_perm *perm)
    932 {
    933 	token_t *m;				/* local au_membuf */
    934 	adr_t adr;				/* adr memory stream header */
    935 	char data_header = AUT_IPC_PERM;	/* header for this token */
    936 	int32_t value;
    937 
    938 	m = au_getclr();
    939 
    940 	adr_start(&adr, memtod(m, char *));
    941 	adr_char(&adr, &data_header, 1);
    942 	value = (int32_t)perm->ipc_uid;
    943 	adr_int32(&adr, &value, 1);
    944 	value = (int32_t)perm->ipc_gid;
    945 	adr_int32(&adr, &value, 1);
    946 	value = (int32_t)perm->ipc_cuid;
    947 	adr_int32(&adr, &value, 1);
    948 	value = (int32_t)perm->ipc_cgid;
    949 	adr_int32(&adr, &value, 1);
    950 	value = (int32_t)perm->ipc_mode;
    951 	adr_int32(&adr, &value, 1);
    952 	value = 0;			/* seq is now obsolete */
    953 	adr_int32(&adr, &value, 1);
    954 	value = (int32_t)perm->ipc_key;
    955 	adr_int32(&adr, &value, 1);
    956 
    957 	m->len = adr_count(&adr);
    958 
    959 	return (m);
    960 }
    961 
    962 token_t *
    963 au_to_groups(const gid_t *crgroups, uint_t crngroups)
    964 {
    965 	token_t *m;			/* local au_membuf */
    966 	adr_t adr;			/* adr memory stream header */
    967 	char data_header = AUT_NEWGROUPS;	/* header for this token */
    968 	short n_groups;
    969 
    970 	m = au_getclr();
    971 
    972 	adr_start(&adr, memtod(m, char *));
    973 	adr_char(&adr, &data_header, 1);
    974 	n_groups = (short)crngroups;
    975 	adr_short(&adr, &n_groups, 1);
    976 	adr_int32(&adr, (int32_t *)crgroups, (int)crngroups);
    977 
    978 	m->len = adr_count(&adr);
    979 
    980 	return (m);
    981 }
    982 
    983 /*
    984  * au_to_socket_ex
    985  * returns:
    986  *	pointer to au_membuf chain containing a socket token.
    987  */
    988 token_t *
    989 au_to_socket_ex(short dom, short type, char *l, char *f)
    990 {
    991 	adr_t adr;
    992 	token_t *m;
    993 	char data_header = AUT_SOCKET_EX;
    994 	struct sockaddr_in6 *addr6;
    995 	struct sockaddr_in  *addr4;
    996 	short size;
    997 
    998 	m = au_getclr();
    999 
   1000 	adr_start(&adr, memtod(m, char *));
   1001 	adr_char(&adr, &data_header, 1);
   1002 	adr_short(&adr, &dom, 1);		/* dom of socket */
   1003 	adr_short(&adr, &type, 1);		/* type of socket */
   1004 
   1005 	if (dom == AF_INET6) {
   1006 		size = AU_IPv6;
   1007 		adr_short(&adr, &size, 1);	/* type of addresses */
   1008 		addr6 = (struct sockaddr_in6 *)l;
   1009 		adr_short(&adr, (short *)&addr6->sin6_port, 1);
   1010 		adr_char(&adr, (char *)&addr6->sin6_addr, size);
   1011 		addr6 = (struct sockaddr_in6 *)f;
   1012 		adr_short(&adr, (short *)&addr6->sin6_port, 1);
   1013 		adr_char(&adr, (char *)&addr6->sin6_addr, size);
   1014 	} else if (dom == AF_INET) {
   1015 		size = AU_IPv4;
   1016 		adr_short(&adr, &size, 1);	/* type of addresses */
   1017 		addr4 = (struct sockaddr_in *)l;
   1018 		adr_short(&adr, (short *)&addr4->sin_port, 1);
   1019 		adr_char(&adr, (char *)&addr4->sin_addr, size);
   1020 		addr4 = (struct sockaddr_in *)f;
   1021 		adr_short(&adr, (short *)&addr4->sin_port, 1);
   1022 		adr_char(&adr, (char *)&addr4->sin_addr, size);
   1023 	}
   1024 
   1025 
   1026 	m->len = adr_count(&adr);
   1027 
   1028 	return (m);
   1029 }
   1030 
   1031 /*
   1032  * au_to_seq
   1033  * returns:
   1034  *	pointer to au_membuf chain containing a sequence token.
   1035  */
   1036 token_t *
   1037 au_to_seq()
   1038 {
   1039 	adr_t adr;
   1040 	token_t *m;
   1041 	char data_header = AUT_SEQ;
   1042 	static int32_t zerocount;
   1043 
   1044 	m = au_getclr();
   1045 
   1046 	adr_start(&adr, memtod(m, char *));
   1047 
   1048 	adr_char(&adr, &data_header, 1);
   1049 
   1050 	adr_int32(&adr, &zerocount, 1);
   1051 
   1052 	m->len = adr_count(&adr);
   1053 
   1054 	return (m);
   1055 }
   1056 
   1057 token_t *
   1058 au_to_sock_inet(struct sockaddr_in *s_inet)
   1059 {
   1060 	adr_t adr;
   1061 	token_t *m;
   1062 	char data_header = AUT_SOCKET;
   1063 
   1064 	m = au_getclr();
   1065 
   1066 	adr_start(&adr, memtod(m, char *));
   1067 	adr_char(&adr, &data_header, 1);
   1068 	adr_short(&adr, (short *)&s_inet->sin_family, 1);
   1069 	adr_short(&adr, (short *)&s_inet->sin_port, 1);
   1070 
   1071 	/* remote addr */
   1072 	adr_int32(&adr, (int32_t *)&s_inet->sin_addr.