dmake: do not set MAKEFLAGS=k
[unleashed/tickless.git] / kernel / fs / nfs / nfs4_attr.c
blob95f606b9e67f2994a38d77a53ee677e60e1a0c75
1 /*
2 * CDDL HEADER START
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.
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.
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]
19 * CDDL HEADER END
22 * Copyright 2009 Sun Microsystems, Inc. All rights reserved.
23 * Use is subject to license terms.
26 #include <sys/time.h>
27 #include <sys/systm.h>
29 #include <nfs/nfs.h>
30 #include <nfs/nfs4.h>
31 #include <nfs/rnode4.h>
32 #include <nfs/nfs4_clnt.h>
33 #include <sys/cmn_err.h>
35 static int
36 timestruc_to_settime4(timestruc_t *tt, settime4 *tt4, int flags)
38 int error = 0;
40 if (flags & ATTR_UTIME) {
41 tt4->set_it = SET_TO_CLIENT_TIME4;
42 error = nfs4_time_vton(tt, &tt4->time);
43 } else {
44 tt4->set_it = SET_TO_SERVER_TIME4;
46 return (error);
51 * nfs4_ver_fattr4_attr translates a vattr attribute into a fattr4 attribute
52 * for use by nfsv4 verify. For setting atime or mtime use the entry for
53 * time_XX (XX == access or modify).
54 * Return TRUE if arg was set (even if there was an error) and FALSE
55 * otherwise. Also set error code. The caller should not continue
56 * if error was set, whether or not the return is TRUE or FALSE. Returning
57 * FALSE does not mean there was an error, only that the attr was not set.
59 * Note: For now we only have the options used by setattr. In the future
60 * the switch statement below should cover all vattr attrs and possibly
61 * sys attrs as well.
63 /* ARGSUSED */
64 static bool_t
65 nfs4_ver_fattr4_attr(vattr_t *vap, struct nfs4_ntov_map *ntovp,
66 union nfs4_attr_u *nap, int flags, int *errorp)
68 bool_t retval = TRUE;
71 * Special case for time set: if setting the
72 * time, ignore entry for time access/modify set (setattr)
73 * and instead use that of time access/modify.
75 *errorp = 0;
77 * Bit matches the mask
79 switch (ntovp->vbit & vap->va_mask) {
80 case AT_SIZE:
81 nap->size = vap->va_size;
82 break;
83 case AT_MODE:
84 nap->mode = vap->va_mode;
85 break;
86 case AT_UID:
88 * if no mapping, uid could be mapped to a numeric string,
89 * e.g. 12345->"12345"
91 if (*errorp = nfs_idmap_uid_str(vap->va_uid, &nap->owner,
92 FALSE))
93 retval = FALSE;
94 break;
95 case AT_GID:
97 * if no mapping, gid will be mapped to a number string,
98 * e.g. "12345"
100 if (*errorp = nfs_idmap_gid_str(vap->va_gid, &nap->owner_group,
101 FALSE))
102 retval = FALSE;
103 break;
104 case AT_ATIME:
105 if ((ntovp->nval != FATTR4_TIME_ACCESS) ||
106 (*errorp = nfs4_time_vton(&vap->va_ctime,
107 &nap->time_access))) {
109 * either asked for FATTR4_TIME_ACCESS_SET -
110 * not used for setattr
111 * or system time invalid for otw transfers
113 retval = FALSE;
115 break;
116 case AT_MTIME:
117 if ((ntovp->nval != FATTR4_TIME_MODIFY) ||
118 (*errorp = nfs4_time_vton(&vap->va_mtime,
119 &nap->time_modify))) {
121 * either asked for FATTR4_TIME_MODIFY_SET -
122 * not used for setattr
123 * or system time invalid for otw transfers
125 retval = FALSE;
127 break;
128 case AT_CTIME:
129 if (*errorp = nfs4_time_vton(&vap->va_ctime,
130 &nap->time_metadata)) {
132 * system time invalid for otw transfers
134 retval = FALSE;
136 break;
137 default:
138 retval = FALSE;
140 return (retval);
144 * nfs4_set_fattr4_attr translates a vattr attribute into a fattr4 attribute
145 * for use by nfs4_setattr. For setting atime or mtime use the entry for
146 * time_XX_set rather than time_XX (XX == access or modify).
147 * Return TRUE if arg was set (even if there was an error) and FALSE
148 * otherwise. Also set error code. The caller should not continue
149 * if error was set, whether or not the return is TRUE or FALSE. Returning
150 * FALSE does not mean there was an error, only that the attr was not set.
152 static bool_t
153 nfs4_set_fattr4_attr(vattr_t *vap, vsecattr_t *vsap,
154 struct nfs4_ntov_map *ntovp, union nfs4_attr_u *nap, int flags,
155 int *errorp)
157 bool_t retval = TRUE;
160 * Special case for time set: if setting the
161 * time, ignore entry for time access/modify
162 * and instead use that of time access/modify set.
164 *errorp = 0;
166 * Bit matches the mask
168 switch (ntovp->vbit & vap->va_mask) {
169 case AT_SIZE:
170 nap->size = vap->va_size;
171 break;
172 case AT_MODE:
173 nap->mode = vap->va_mode;
174 break;
175 case AT_UID:
177 * if no mapping, uid will be mapped to a number string,
178 * e.g. "12345"
180 if (*errorp = nfs_idmap_uid_str(vap->va_uid, &nap->owner,
181 FALSE))
182 retval = FALSE;
183 break;
184 case AT_GID:
186 * if no mapping, gid will be mapped to a number string,
187 * e.g. "12345"
189 if (*errorp = nfs_idmap_gid_str(vap->va_gid, &nap->owner_group,
190 FALSE))
191 retval = FALSE;
192 break;
193 case AT_ATIME:
194 if ((ntovp->nval != FATTR4_TIME_ACCESS_SET) ||
195 (*errorp = timestruc_to_settime4(&vap->va_atime,
196 &nap->time_access_set, flags))) {
197 /* FATTR4_TIME_ACCESS - not used for verify */
198 retval = FALSE;
200 break;
201 case AT_MTIME:
202 if ((ntovp->nval != FATTR4_TIME_MODIFY_SET) ||
203 (*errorp = timestruc_to_settime4(&vap->va_mtime,
204 &nap->time_modify_set, flags))) {
205 /* FATTR4_TIME_MODIFY - not used for verify */
206 retval = FALSE;
208 break;
209 default:
211 * If the ntovp->vbit == 0 this is most likely the ACL.
213 if (ntovp->vbit == 0 && ntovp->fbit == FATTR4_ACL_MASK) {
214 ASSERT(vsap->vsa_mask == (VSA_ACE | VSA_ACECNT));
215 nap->acl.fattr4_acl_len = vsap->vsa_aclcnt;
216 nap->acl.fattr4_acl_val = vsap->vsa_aclentp;
217 } else
218 retval = FALSE;
221 return (retval);
225 * XXX - This is a shorter version of vattr_to_fattr4 which only takes care
226 * of setattr args - size, mode, uid/gid, times. Eventually we should generalize
227 * by using nfs4_ntov_map and the same functions used by the server.
228 * Here we just hardcoded the setattr attributes. Note that the order is
229 * important - it should follow the order of the bits in the mask.
232 vattr_to_fattr4(vattr_t *vap, vsecattr_t *vsap, fattr4 *fattrp, int flags,
233 enum nfs_opnum4 op, bitmap4 supp)
235 int i, j;
236 union nfs4_attr_u *na = NULL;
237 int attrcnt;
238 int uid_attr = -1;
239 int gid_attr = -1;
240 int acl_attr = -1;
241 XDR xdr;
242 ulong_t xdr_size;
243 char *xdr_attrs;
244 int error = 0;
245 uint8_t amap[NFS4_MAXNUM_ATTRS];
246 uint_t va_mask = vap->va_mask;
247 bool_t (*attrfunc)();
250 * Make sure that maximum attribute number can be expressed as an
251 * 8 bit quantity.
253 ASSERT(NFS4_MAXNUM_ATTRS <= (UINT8_MAX + 1));
254 fattrp->attrmask = 0;
255 fattrp->attrlist4_len = 0;
256 fattrp->attrlist4 = NULL;
257 na = kmem_zalloc(sizeof (union nfs4_attr_u) * nfs4_ntov_map_size,
258 KM_SLEEP);
260 if (op == OP_SETATTR || op == OP_CREATE || op == OP_OPEN) {
262 * Note we need to set the attrmask for set operations.
263 * In particular mtime and atime will be set to the
264 * servers time.
266 nfs4_vmask_to_nmask_set(va_mask, &fattrp->attrmask);
267 if (vsap != NULL)
268 fattrp->attrmask |= FATTR4_ACL_MASK;
269 attrfunc = nfs4_set_fattr4_attr;
270 } else { /* verify/nverify */
272 * Verfy/nverify use the "normal vmask_to_nmask
273 * this routine knows how to handle all vmask bits
275 nfs4_vmask_to_nmask(va_mask, &fattrp->attrmask);
277 * XXX verify/nverify only works for a subset of attrs that
278 * directly map to vattr_t attrs. So, verify/nverify is
279 * broken for servers that only support mandatory attrs.
280 * Mask out change attr for now and fix verify op to
281 * work with mandonly servers later. nfs4_vmask_to_nmask
282 * sets change whenever it sees request for ctime/mtime,
283 * so we must turn off change because nfs4_ver_fattr4_attr
284 * will not generate args for change. This is a bug
285 * that will be fixed later.
286 * XXX
288 fattrp->attrmask &= ~FATTR4_CHANGE_MASK;
289 attrfunc = nfs4_ver_fattr4_attr;
292 /* Mask out any rec attrs unsupported by server */
293 fattrp->attrmask &= supp;
295 attrcnt = 0;
296 xdr_size = 0;
297 for (i = 0; i < nfs4_ntov_map_size; i++) {
299 * In the case of FATTR4_ACL_MASK, the vbit will be 0 (zero)
300 * so we must also check if the fbit is FATTR4_ACL_MASK before
301 * skipping over this attribute.
303 if (!(nfs4_ntov_map[i].vbit & vap->va_mask)) {
304 if (nfs4_ntov_map[i].fbit != FATTR4_ACL_MASK)
305 continue;
306 if (vsap == NULL)
307 continue;
310 if (attrfunc == nfs4_set_fattr4_attr) {
311 if (!(*attrfunc)(vap, vsap, &nfs4_ntov_map[i],
312 &na[attrcnt], flags, &error))
313 continue;
314 } else if (attrfunc == nfs4_ver_fattr4_attr) {
315 if (!(*attrfunc)(vap, &nfs4_ntov_map[i], &na[attrcnt],
316 flags, &error))
317 continue;
320 if (error)
321 goto done; /* Exit! */
324 * Calculate XDR size
326 if (nfs4_ntov_map[i].xdr_size != 0) {
328 * If we are setting attributes (attrfunc is
329 * nfs4_set_fattr4_attr) and are setting the
330 * mtime or atime, adjust the xdr size down by
331 * 3 words, since we are using the server's
332 * time as the current time. Exception: if
333 * ATTR_UTIME is set, the client sends the
334 * time, so leave the xdr size alone.
336 xdr_size += nfs4_ntov_map[i].xdr_size;
337 if ((nfs4_ntov_map[i].nval == FATTR4_TIME_ACCESS_SET ||
338 nfs4_ntov_map[i].nval == FATTR4_TIME_MODIFY_SET) &&
339 attrfunc == nfs4_set_fattr4_attr &&
340 !(flags & ATTR_UTIME)) {
341 xdr_size -= 3 * BYTES_PER_XDR_UNIT;
343 } else {
345 * The only zero xdr_sizes we should see
346 * are AT_UID, AT_GID and FATTR4_ACL_MASK
348 ASSERT(nfs4_ntov_map[i].vbit == AT_UID ||
349 nfs4_ntov_map[i].vbit == AT_GID ||
350 nfs4_ntov_map[i].fbit == FATTR4_ACL_MASK);
351 if (nfs4_ntov_map[i].vbit == AT_UID) {
352 uid_attr = attrcnt;
353 xdr_size += BYTES_PER_XDR_UNIT; /* length */
354 xdr_size +=
355 RNDUP(na[attrcnt].owner.utf8string_len);
356 } else if (nfs4_ntov_map[i].vbit == AT_GID) {
357 gid_attr = attrcnt;
358 xdr_size += BYTES_PER_XDR_UNIT; /* length */
359 xdr_size +=
360 RNDUP(
361 na[attrcnt].owner_group.utf8string_len);
362 } else if (nfs4_ntov_map[i].fbit == FATTR4_ACL_MASK) {
363 nfsace4 *tmpacl = (nfsace4 *)vsap->vsa_aclentp;
365 acl_attr = attrcnt;
366 /* fattr4_acl_len */
367 xdr_size += BYTES_PER_XDR_UNIT;
368 /* fattr4_acl_val */
369 xdr_size += RNDUP((vsap->vsa_aclcnt *
370 (sizeof (acetype4) + sizeof (aceflag4)
371 + sizeof (acemask4))));
373 for (j = 0; j < vsap->vsa_aclcnt; j++) {
374 /* who - utf8string_len */
375 xdr_size += BYTES_PER_XDR_UNIT;
376 /* who - utf8string_val */
377 xdr_size +=
378 RNDUP(tmpacl[j].who.utf8string_len);
384 * This attr is going otw
386 amap[attrcnt] = (uint8_t)nfs4_ntov_map[i].nval;
387 attrcnt++;
390 * Clear this bit from test mask so we stop
391 * as soon as all requested attrs are done.
393 va_mask &= ~nfs4_ntov_map[i].vbit;
394 if (va_mask == 0 &&
395 (vsap == NULL || (vsap != NULL && acl_attr != -1)))
396 break;
399 if (attrcnt == 0) {
400 goto done;
403 fattrp->attrlist4 = xdr_attrs = kmem_alloc(xdr_size, KM_SLEEP);
404 fattrp->attrlist4_len = xdr_size;
405 xdrmem_create(&xdr, xdr_attrs, xdr_size, XDR_ENCODE);
406 for (i = 0; i < attrcnt; i++) {
407 if ((*nfs4_ntov_map[amap[i]].xfunc)(&xdr, &na[i]) == FALSE) {
408 cmn_err(CE_WARN, "vattr_to_fattr4: xdr encode of "
409 "attribute failed\n");
410 error = EINVAL;
411 break;
414 done:
416 * Free any malloc'd attrs, can only be uid or gid
418 if (uid_attr != -1 && na[uid_attr].owner.utf8string_val != NULL) {
419 kmem_free(na[uid_attr].owner.utf8string_val,
420 na[uid_attr].owner.utf8string_len);
422 if (gid_attr != -1 && na[gid_attr].owner_group.utf8string_val != NULL) {
423 kmem_free(na[gid_attr].owner_group.utf8string_val,
424 na[gid_attr].owner_group.utf8string_len);
427 /* xdrmem_destroy(&xdrs); */ /* NO-OP */
428 kmem_free(na, sizeof (union nfs4_attr_u) * nfs4_ntov_map_size);
429 if (error)
430 nfs4_fattr4_free(fattrp);
431 return (error);
434 void
435 nfs4_fattr4_free(fattr4 *attrp)
438 * set attrlist4val/len to 0 because...
440 * op_readdir resfree function could call us again
441 * for last entry4 if it was able to encode the name
442 * and cookie but couldn't encode the attrs because
443 * of maxcount violation (from rddir args). In that
444 * case, the last/partial entry4's fattr4 has already
445 * been free'd, but the entry4 remains on the end of
446 * the list.
448 attrp->attrmask = 0;
450 if (attrp->attrlist4) {
451 kmem_free(attrp->attrlist4, attrp->attrlist4_len);
452 attrp->attrlist4 = NULL;
453 attrp->attrlist4_len = 0;
458 * Translate a vattr_t mask to a fattr4 type bitmap, caller is
459 * responsible for zeroing bitsval if needed.
461 void
462 nfs4_vmask_to_nmask(uint_t vmask, bitmap4 *bitsval)
464 if (vmask == AT_ALL || vmask == NFS4_VTON_ATTR_MASK) {
465 *bitsval |= NFS4_NTOV_ATTR_MASK;
466 return;
469 vmask &= NFS4_VTON_ATTR_MASK;
470 if (vmask == 0) {
471 return;
474 if (vmask & AT_TYPE)
475 *bitsval |= FATTR4_TYPE_MASK;
476 if (vmask & AT_MODE)
477 *bitsval |= FATTR4_MODE_MASK;
478 if (vmask & AT_UID)
479 *bitsval |= FATTR4_OWNER_MASK;
480 if (vmask & AT_GID)
481 *bitsval |= FATTR4_OWNER_GROUP_MASK;
482 if (vmask & AT_FSID)
483 *bitsval |= FATTR4_FSID_MASK;
484 /* set mounted_on_fileid when AT_NODEID requested */
485 if (vmask & AT_NODEID)
486 *bitsval |= FATTR4_FILEID_MASK | FATTR4_MOUNTED_ON_FILEID_MASK;
487 if (vmask & AT_NLINK)
488 *bitsval |= FATTR4_NUMLINKS_MASK;
489 if (vmask & AT_SIZE)
490 *bitsval |= FATTR4_SIZE_MASK;
491 if (vmask & AT_ATIME)
492 *bitsval |= FATTR4_TIME_ACCESS_MASK;
493 if (vmask & AT_MTIME)
494 *bitsval |= FATTR4_TIME_MODIFY_MASK;
495 /* also set CHANGE whenever AT_CTIME requested */
496 if (vmask & AT_CTIME)
497 *bitsval |= FATTR4_TIME_METADATA_MASK | FATTR4_CHANGE_MASK;
498 if (vmask & AT_NBLOCKS)
499 *bitsval |= FATTR4_SPACE_USED_MASK;
500 if (vmask & AT_RDEV)
501 *bitsval |= FATTR4_RAWDEV_MASK;
505 * nfs4_vmask_to_nmask_set is used for setattr. A separate function needed
506 * because of special treatment to timeset.
508 void
509 nfs4_vmask_to_nmask_set(uint_t vmask, bitmap4 *bitsval)
511 vmask &= NFS4_VTON_ATTR_MASK_SET;
513 if (vmask == 0) {
514 return;
517 if (vmask & AT_MODE)
518 *bitsval |= FATTR4_MODE_MASK;
519 if (vmask & AT_UID)
520 *bitsval |= FATTR4_OWNER_MASK;
521 if (vmask & AT_GID)
522 *bitsval |= FATTR4_OWNER_GROUP_MASK;
523 if (vmask & AT_SIZE)
524 *bitsval |= FATTR4_SIZE_MASK;
525 if (vmask & AT_ATIME)
526 *bitsval |= FATTR4_TIME_ACCESS_SET_MASK;
527 if (vmask & AT_MTIME)
528 *bitsval |= FATTR4_TIME_MODIFY_SET_MASK;
532 * Convert NFS Version 4 over the network attributes to the local
533 * virtual attributes.
535 vtype_t nf4_to_vt[] = {
536 VBAD, VREG, VDIR, VBLK, VCHR, VLNK, VSOCK, VFIFO, VDIR, VREG
541 * { fbit, vbit, vfsstat, mandatory,
542 * nval, xdr_size, xfunc,
543 * sv_getit, prtstr },
545 struct nfs4_ntov_map nfs4_ntov_map[] = {
546 { FATTR4_SUPPORTED_ATTRS_MASK, 0, FALSE, TRUE,
547 FATTR4_SUPPORTED_ATTRS, 2 * BYTES_PER_XDR_UNIT, xdr_bitmap4,
548 NULL, "fattr4_supported_attrs" },
550 { FATTR4_TYPE_MASK, AT_TYPE, FALSE, TRUE,
551 FATTR4_TYPE, BYTES_PER_XDR_UNIT, xdr_int,
552 NULL, "fattr4_type" },
554 { FATTR4_FH_EXPIRE_TYPE_MASK, 0, FALSE, TRUE,
555 FATTR4_FH_EXPIRE_TYPE, BYTES_PER_XDR_UNIT, xdr_u_int,
556 NULL, "fattr4_fh_expire_type" },
558 { FATTR4_CHANGE_MASK, 0, FALSE, TRUE,
559 FATTR4_CHANGE, 2 * BYTES_PER_XDR_UNIT, xdr_u_longlong_t,
560 NULL, "fattr4_change" },
562 { FATTR4_SIZE_MASK, AT_SIZE, FALSE, TRUE,
563 FATTR4_SIZE, 2 * BYTES_PER_XDR_UNIT, xdr_u_longlong_t,
564 NULL, "fattr4_size" },
566 { FATTR4_LINK_SUPPORT_MASK, 0, FALSE, TRUE,
567 FATTR4_LINK_SUPPORT, BYTES_PER_XDR_UNIT, xdr_bool,
568 NULL, "fattr4_link_support" },
570 { FATTR4_SYMLINK_SUPPORT_MASK, 0, FALSE, TRUE,
571 FATTR4_SYMLINK_SUPPORT, BYTES_PER_XDR_UNIT, xdr_bool,
572 NULL, "fattr4_symlink_support" },
574 { FATTR4_NAMED_ATTR_MASK, 0, FALSE, TRUE,
575 FATTR4_NAMED_ATTR, BYTES_PER_XDR_UNIT, xdr_bool,
576 NULL, "fattr4_named_attr" },
578 { FATTR4_FSID_MASK, AT_FSID, FALSE, TRUE,
579 FATTR4_FSID, 4 * BYTES_PER_XDR_UNIT, xdr_fattr4_fsid,
580 NULL, "fattr4_fsid" },
582 { FATTR4_UNIQUE_HANDLES_MASK, 0, FALSE, TRUE,
583 FATTR4_UNIQUE_HANDLES, BYTES_PER_XDR_UNIT, xdr_bool,
584 NULL, "fattr4_unique_handles" },
586 { FATTR4_LEASE_TIME_MASK, 0, FALSE, TRUE,
587 FATTR4_LEASE_TIME, BYTES_PER_XDR_UNIT, xdr_u_int,
588 NULL, "fattr4_lease_time" },
590 { FATTR4_RDATTR_ERROR_MASK, 0, FALSE, TRUE,
591 FATTR4_RDATTR_ERROR, BYTES_PER_XDR_UNIT, xdr_int,
592 NULL, "fattr4_rdattr_error" },
594 { FATTR4_ACL_MASK, 0, FALSE, FALSE,
595 FATTR4_ACL, 0, xdr_fattr4_acl,
596 NULL, "fattr4_acl" },
598 { FATTR4_ACLSUPPORT_MASK, 0, FALSE, FALSE,
599 FATTR4_ACLSUPPORT, BYTES_PER_XDR_UNIT, xdr_u_int,
600 NULL, "fattr4_aclsupport" },
602 { FATTR4_ARCHIVE_MASK, 0, FALSE, FALSE,
603 FATTR4_ARCHIVE, BYTES_PER_XDR_UNIT, xdr_bool,
604 NULL, "fattr4_archive" },
606 { FATTR4_CANSETTIME_MASK, 0, FALSE, FALSE,
607 FATTR4_CANSETTIME, BYTES_PER_XDR_UNIT, xdr_bool,
608 NULL, "fattr4_cansettime" },
610 { FATTR4_CASE_INSENSITIVE_MASK, 0, FALSE, FALSE,
611 FATTR4_CASE_INSENSITIVE, BYTES_PER_XDR_UNIT, xdr_bool,
612 NULL, "fattr4_case_insensitive" },
614 { FATTR4_CASE_PRESERVING_MASK, 0, FALSE, FALSE,
615 FATTR4_CASE_PRESERVING, BYTES_PER_XDR_UNIT, xdr_bool,
616 NULL, "fattr4_case_preserving" },
618 { FATTR4_CHOWN_RESTRICTED_MASK, 0, FALSE, FALSE,
619 FATTR4_CHOWN_RESTRICTED, BYTES_PER_XDR_UNIT, xdr_bool,
620 NULL, "fattr4_chown_restricted" },
622 { FATTR4_FILEHANDLE_MASK, 0, FALSE, TRUE,
623 FATTR4_FILEHANDLE, 0, xdr_nfs_fh4,
624 NULL, "fattr4_filehandle" },
626 { FATTR4_FILEID_MASK, AT_NODEID, FALSE, FALSE,
627 FATTR4_FILEID, 2 * BYTES_PER_XDR_UNIT, xdr_u_longlong_t,
628 NULL, "fattr4_fileid" },
630 { FATTR4_FILES_AVAIL_MASK, 0, TRUE, FALSE,
631 FATTR4_FILES_AVAIL, 2 * BYTES_PER_XDR_UNIT, xdr_u_longlong_t,
632 NULL, "fattr4_files_avail" },
634 { FATTR4_FILES_FREE_MASK, 0, TRUE, FALSE,
635 FATTR4_FILES_FREE, 2 * BYTES_PER_XDR_UNIT, xdr_u_longlong_t,
636 NULL, "fattr4_files_free" },
638 { FATTR4_FILES_TOTAL_MASK, 0, TRUE, FALSE,
639 FATTR4_FILES_TOTAL, 2 * BYTES_PER_XDR_UNIT, xdr_u_longlong_t,
640 NULL, "fattr4_files_total" },
642 { FATTR4_FS_LOCATIONS_MASK, 0, FALSE, FALSE,
643 FATTR4_FS_LOCATIONS, 0, xdr_fattr4_fs_locations,
644 NULL, "fattr4_fs_locations" },
646 { FATTR4_HIDDEN_MASK, 0, FALSE, FALSE,
647 FATTR4_HIDDEN, BYTES_PER_XDR_UNIT, xdr_bool,
648 NULL, "fattr4_hidden" },
650 { FATTR4_HOMOGENEOUS_MASK, 0, FALSE, FALSE,
651 FATTR4_HOMOGENEOUS, BYTES_PER_XDR_UNIT, xdr_bool,
652 NULL, "fattr4_homogeneous" },
654 { FATTR4_MAXFILESIZE_MASK, 0, FALSE, FALSE,
655 FATTR4_MAXFILESIZE, 2 * BYTES_PER_XDR_UNIT, xdr_u_longlong_t,
656 NULL, "fattr4_maxfilesize" },
658 { FATTR4_MAXLINK_MASK, 0, FALSE, FALSE,
659 FATTR4_MAXLINK, BYTES_PER_XDR_UNIT, xdr_u_int,
660 NULL, "fattr4_maxlink" },
662 { FATTR4_MAXNAME_MASK, 0, FALSE, FALSE,
663 FATTR4_MAXNAME, BYTES_PER_XDR_UNIT, xdr_u_int,
664 NULL, "fattr4_maxname" },
666 { FATTR4_MAXREAD_MASK, 0, FALSE, FALSE,
667 FATTR4_MAXREAD, 2 * BYTES_PER_XDR_UNIT, xdr_u_longlong_t,
668 NULL, "fattr4_maxread" },
670 { FATTR4_MAXWRITE_MASK, 0, FALSE, FALSE,
671 FATTR4_MAXWRITE, 2 * BYTES_PER_XDR_UNIT, xdr_u_longlong_t,
672 NULL, "fattr4_maxwrite" },
674 { FATTR4_MIMETYPE_MASK, 0, FALSE, FALSE,
675 FATTR4_MIMETYPE, 0, xdr_utf8string,
676 NULL, "fattr4_mimetype" },
678 { FATTR4_MODE_MASK, AT_MODE, FALSE, FALSE,
679 FATTR4_MODE, BYTES_PER_XDR_UNIT, xdr_u_int,
680 NULL, "fattr4_mode" },
682 { FATTR4_NO_TRUNC_MASK, 0, FALSE, FALSE,
683 FATTR4_NO_TRUNC, BYTES_PER_XDR_UNIT, xdr_bool,
684 NULL, "fattr4_no_trunc" },
686 { FATTR4_NUMLINKS_MASK, AT_NLINK, FALSE, FALSE,
687 FATTR4_NUMLINKS, BYTES_PER_XDR_UNIT, xdr_u_int,
688 NULL, "fattr4_numlinks" },
690 { FATTR4_OWNER_MASK, AT_UID, FALSE, FALSE,
691 FATTR4_OWNER, 0, xdr_utf8string,
692 NULL, "fattr4_owner" },
694 { FATTR4_OWNER_GROUP_MASK, AT_GID, FALSE, FALSE,
695 FATTR4_OWNER_GROUP, 0, xdr_utf8string,
696 NULL, "fattr4_owner_group" },
698 { FATTR4_QUOTA_AVAIL_HARD_MASK, 0, FALSE, FALSE,
699 FATTR4_QUOTA_AVAIL_HARD, 2 * BYTES_PER_XDR_UNIT,
700 xdr_u_longlong_t,
701 NULL, "fattr4_quota_avail_hard" },
703 { FATTR4_QUOTA_AVAIL_SOFT_MASK, 0, FALSE, FALSE,
704 FATTR4_QUOTA_AVAIL_SOFT, 2 * BYTES_PER_XDR_UNIT,
705 xdr_u_longlong_t,
706 NULL, "fattr4_quota_avail_soft" },
708 { FATTR4_QUOTA_USED_MASK, 0, FALSE, FALSE,
709 FATTR4_QUOTA_USED, 2 * BYTES_PER_XDR_UNIT, xdr_u_longlong_t,
710 NULL, "fattr4_quota_used" },
712 { FATTR4_RAWDEV_MASK, AT_RDEV, FALSE, FALSE,
713 FATTR4_RAWDEV, 2 * BYTES_PER_XDR_UNIT, xdr_fattr4_rawdev,
714 NULL, "fattr4_rawdev" },
716 { FATTR4_SPACE_AVAIL_MASK, 0, TRUE, FALSE,
717 FATTR4_SPACE_AVAIL, 2 * BYTES_PER_XDR_UNIT, xdr_u_longlong_t,
718 NULL, "fattr4_space_avail" },
720 { FATTR4_SPACE_FREE_MASK, 0, TRUE, FALSE,
721 FATTR4_SPACE_FREE, 2 * BYTES_PER_XDR_UNIT, xdr_u_longlong_t,
722 NULL, "fattr4_space_free" },
724 { FATTR4_SPACE_TOTAL_MASK, 0, TRUE, FALSE,
725 FATTR4_SPACE_TOTAL, 2 * BYTES_PER_XDR_UNIT, xdr_u_longlong_t,
726 NULL, "fattr4_space_total" },
728 { FATTR4_SPACE_USED_MASK, AT_NBLOCKS, FALSE, FALSE,
729 FATTR4_SPACE_USED, 2 * BYTES_PER_XDR_UNIT, xdr_u_longlong_t,
730 NULL, "fattr4_space_used" },
732 { FATTR4_SYSTEM_MASK, 0, FALSE, FALSE,
733 FATTR4_SYSTEM, BYTES_PER_XDR_UNIT, xdr_bool,
734 NULL, "fattr4_system" },
736 { FATTR4_TIME_ACCESS_MASK, AT_ATIME, FALSE, FALSE,
737 FATTR4_TIME_ACCESS, 3 * BYTES_PER_XDR_UNIT, xdr_nfstime4,
738 NULL, "fattr4_time_access" },
740 { FATTR4_TIME_ACCESS_SET_MASK, AT_ATIME, FALSE, FALSE,
741 FATTR4_TIME_ACCESS_SET, 4 * BYTES_PER_XDR_UNIT, xdr_settime4,
742 NULL, "fattr4_time_access_set" },
744 { FATTR4_TIME_BACKUP_MASK, 0, FALSE, FALSE,
745 FATTR4_TIME_BACKUP, 3 * BYTES_PER_XDR_UNIT, xdr_nfstime4,
746 NULL, "fattr4_time_backup" },
748 { FATTR4_TIME_CREATE_MASK, 0, FALSE, FALSE,
749 FATTR4_TIME_CREATE, 3 * BYTES_PER_XDR_UNIT, xdr_nfstime4,
750 NULL, "fattr4_time_create" },
752 { FATTR4_TIME_DELTA_MASK, 0, FALSE, FALSE,
753 FATTR4_TIME_DELTA, 3 * BYTES_PER_XDR_UNIT, xdr_nfstime4,
754 NULL, "fattr4_time_delta" },
756 { FATTR4_TIME_METADATA_MASK, AT_CTIME, FALSE, FALSE,
757 FATTR4_TIME_METADATA, 3 * BYTES_PER_XDR_UNIT, xdr_nfstime4,
758 NULL, "fattr4_time_metadata" },
760 { FATTR4_TIME_MODIFY_MASK, AT_MTIME, FALSE, FALSE,
761 FATTR4_TIME_MODIFY, 3 * BYTES_PER_XDR_UNIT, xdr_nfstime4,
762 NULL, "fattr4_time_modify" },
764 { FATTR4_TIME_MODIFY_SET_MASK, AT_MTIME, FALSE, FALSE,
765 FATTR4_TIME_MODIFY_SET, 4 * BYTES_PER_XDR_UNIT, xdr_settime4,
766 NULL, "fattr4_time_modify_set" },
768 { FATTR4_MOUNTED_ON_FILEID_MASK, AT_NODEID, FALSE, FALSE,
769 FATTR4_MOUNTED_ON_FILEID, 2 * BYTES_PER_XDR_UNIT,
770 xdr_u_longlong_t,
771 NULL, "fattr4_mounted_on_fileid" },
775 uint_t nfs4_ntov_map_size = sizeof (nfs4_ntov_map) /
776 sizeof (struct nfs4_ntov_map);