|
|
1.1 ! root 1: /* ! 2: * Copyright (c) 2000 Apple Computer, Inc. All rights reserved. ! 3: * ! 4: * @APPLE_LICENSE_HEADER_START@ ! 5: * ! 6: * The contents of this file constitute Original Code as defined in and ! 7: * are subject to the Apple Public Source License Version 1.1 (the ! 8: * "License"). You may not use this file except in compliance with the ! 9: * License. Please obtain a copy of the License at ! 10: * http://www.apple.com/publicsource and read it before using this file. ! 11: * ! 12: * This Original Code and all software distributed under the License are ! 13: * distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, EITHER ! 14: * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES, ! 15: * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY, ! 16: * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT. Please see the ! 17: * License for the specific language governing rights and limitations ! 18: * under the License. ! 19: * ! 20: * @APPLE_LICENSE_HEADER_END@ ! 21: */ ! 22: /* $NetBSD: cd9660_util.c,v 1.8 1994/12/13 22:33:25 mycroft Exp $ */ ! 23: ! 24: /*- ! 25: * Copyright (c) 1994 ! 26: * The Regents of the University of California. All rights reserved. ! 27: * ! 28: * This code is derived from software contributed to Berkeley ! 29: * by Pace Willisson ([email protected]). The Rock Ridge Extension ! 30: * Support code is derived from software contributed to Berkeley ! 31: * by Atsushi Murai ([email protected]). ! 32: * ! 33: * Redistribution and use in source and binary forms, with or without ! 34: * modification, are permitted provided that the following conditions ! 35: * are met: ! 36: * 1. Redistributions of source code must retain the above copyright ! 37: * notice, this list of conditions and the following disclaimer. ! 38: * 2. Redistributions in binary form must reproduce the above copyright ! 39: * notice, this list of conditions and the following disclaimer in the ! 40: * documentation and/or other materials provided with the distribution. ! 41: * 3. All advertising materials mentioning features or use of this software ! 42: * must display the following acknowledgement: ! 43: * This product includes software developed by the University of ! 44: * California, Berkeley and its contributors. ! 45: * 4. Neither the name of the University nor the names of its contributors ! 46: * may be used to endorse or promote products derived from this software ! 47: * without specific prior written permission. ! 48: * ! 49: * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND ! 50: * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE ! 51: * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ! 52: * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE ! 53: * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL ! 54: * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS ! 55: * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) ! 56: * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT ! 57: * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY ! 58: * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF ! 59: * SUCH DAMAGE. ! 60: * ! 61: * @(#)cd9660_util.c 8.3 (Berkeley) 12/5/94 ! 62: * ! 63: * HISTORY ! 64: * 7-Dec-98 Add ATTR_VOL_MOUNTFLAGS attribute support - djb ! 65: * 18-Nov-98 Add support for volfs - djb ! 66: */ ! 67: ! 68: #include <sys/param.h> ! 69: #include <sys/systm.h> ! 70: #include <sys/namei.h> ! 71: #include <sys/resourcevar.h> ! 72: #include <sys/kernel.h> ! 73: #include <sys/file.h> ! 74: #include <sys/stat.h> ! 75: #include <sys/buf.h> ! 76: #include <sys/proc.h> ! 77: #include <sys/conf.h> ! 78: #include <sys/mount.h> ! 79: #include <sys/vnode.h> ! 80: #include <miscfs/specfs/specdev.h> /* XXX */ ! 81: #include <miscfs/fifofs/fifo.h> /* XXX */ ! 82: #include <sys/malloc.h> ! 83: #include <sys/dir.h> ! 84: #include <sys/attr.h> ! 85: #include <kern/assert.h> ! 86: ! 87: #include <isofs/cd9660/iso.h> ! 88: #include <isofs/cd9660/cd9660_node.h> ! 89: #include <isofs/cd9660/iso_rrip.h> ! 90: ! 91: /* ! 92: * translate and compare a filename ! 93: * Note: Version number plus ';' may be omitted. ! 94: */ ! 95: int ! 96: isofncmp(fn, fnlen, isofn, isolen) ! 97: u_char *fn, *isofn; ! 98: int fnlen, isolen; ! 99: { ! 100: int i, j; ! 101: char c; ! 102: ! 103: while (--fnlen >= 0) { ! 104: if (--isolen < 0) ! 105: return *fn; ! 106: if ((c = *isofn++) == ';') { ! 107: switch (*fn++) { ! 108: default: ! 109: return *--fn; ! 110: case 0: ! 111: return 0; ! 112: case ';': ! 113: break; ! 114: } ! 115: for (i = 0; --fnlen >= 0; i = i * 10 + *fn++ - '0') { ! 116: if (*fn < '0' || *fn > '9') { ! 117: return -1; ! 118: } ! 119: } ! 120: for (j = 0; --isolen >= 0; j = j * 10 + *isofn++ - '0'); ! 121: return i - j; ! 122: } ! 123: if (c != *fn) { ! 124: if (c >= 'A' && c <= 'Z') { ! 125: if (c + ('a' - 'A') != *fn) { ! 126: if (*fn >= 'a' && *fn <= 'z') ! 127: return *fn - ('a' - 'A') - c; ! 128: else ! 129: return *fn - c; ! 130: } ! 131: } else ! 132: return *fn - c; ! 133: } ! 134: fn++; ! 135: } ! 136: if (isolen > 0) { ! 137: switch (*isofn) { ! 138: default: ! 139: return -1; ! 140: case '.': ! 141: if (isofn[1] != ';') ! 142: return -1; ! 143: case ';': ! 144: return 0; ! 145: } ! 146: } ! 147: return 0; ! 148: } ! 149: ! 150: /* ! 151: * translate a filename ! 152: */ ! 153: void ! 154: isofntrans(infn, infnlen, outfn, outfnlen, original, assoc) ! 155: u_char *infn, *outfn; ! 156: int infnlen; ! 157: u_short *outfnlen; ! 158: int original; ! 159: int assoc; ! 160: { ! 161: int fnidx = 0; ! 162: ! 163: if (assoc) { ! 164: *outfn++ = ASSOCCHAR; ! 165: fnidx++; ! 166: infnlen++; ! 167: } ! 168: for (; fnidx < infnlen; fnidx++) { ! 169: char c = *infn++; ! 170: ! 171: if (!original && c >= 'A' && c <= 'Z') ! 172: *outfn++ = c + ('a' - 'A'); ! 173: else if (!original && c == '.' && *infn == ';') ! 174: break; ! 175: else if (!original && c == ';') ! 176: break; ! 177: else ! 178: *outfn++ = c; ! 179: } ! 180: *outfnlen = fnidx; ! 181: } ! 182: ! 183: ! 184: int ! 185: attrcalcsize(struct attrlist *attrlist) ! 186: { ! 187: int size; ! 188: attrgroup_t a; ! 189: ! 190: #if ((ATTR_CMN_NAME | ATTR_CMN_DEVID | ATTR_CMN_FSID | ATTR_CMN_OBJTYPE | \ ! 191: ATTR_CMN_OBJTAG | ATTR_CMN_OBJID | ATTR_CMN_OBJPERMANENTID | ATTR_CMN_PAROBJID | \ ! 192: ATTR_CMN_SCRIPT | ATTR_CMN_CRTIME | ATTR_CMN_MODTIME | ATTR_CMN_CHGTIME | \ ! 193: ATTR_CMN_ACCTIME | ATTR_CMN_BKUPTIME | ATTR_CMN_FNDRINFO | ATTR_CMN_OWNERID | \ ! 194: ATTR_CMN_GRPID | ATTR_CMN_ACCESSMASK | ATTR_CMN_NAMEDATTRCOUNT | ATTR_CMN_NAMEDATTRLIST| \ ! 195: ATTR_CMN_FLAGS) != ATTR_CMN_VALIDMASK) ! 196: #warning AttributeBlockSize: Missing bits in common mask computation! ! 197: #endif ! 198: assert((attrlist->commonattr & ~ATTR_CMN_VALIDMASK) == 0); ! 199: ! 200: #if ((ATTR_VOL_FSTYPE | ATTR_VOL_SIGNATURE | ATTR_VOL_SIZE | ATTR_VOL_SPACEFREE | \ ! 201: ATTR_VOL_SPACEAVAIL | ATTR_VOL_MINALLOCATION | ATTR_VOL_ALLOCATIONCLUMP | ATTR_VOL_IOBLOCKSIZE | \ ! 202: ATTR_VOL_OBJCOUNT | ATTR_VOL_FILECOUNT | ATTR_VOL_DIRCOUNT | ATTR_VOL_MAXOBJCOUNT | \ ! 203: ATTR_VOL_MOUNTPOINT | ATTR_VOL_NAME | ATTR_VOL_MOUNTFLAGS | ATTR_VOL_INFO) != ATTR_VOL_VALIDMASK) ! 204: #warning AttributeBlockSize: Missing bits in volume mask computation! ! 205: #endif ! 206: assert((attrlist->volattr & ~ATTR_VOL_VALIDMASK) == 0); ! 207: ! 208: #if ((ATTR_DIR_LINKCOUNT | ATTR_DIR_ENTRYCOUNT) != ATTR_DIR_VALIDMASK) ! 209: #warning AttributeBlockSize: Missing bits in directory mask computation! ! 210: #endif ! 211: assert((attrlist->dirattr & ~ATTR_DIR_VALIDMASK) == 0); ! 212: #if ((ATTR_FILE_LINKCOUNT | ATTR_FILE_TOTALSIZE | ATTR_FILE_ALLOCSIZE | ATTR_FILE_IOBLOCKSIZE | \ ! 213: ATTR_FILE_CLUMPSIZE | ATTR_FILE_DEVTYPE | ATTR_FILE_FILETYPE | ATTR_FILE_FORKCOUNT | \ ! 214: ATTR_FILE_FORKLIST | ATTR_FILE_DATALENGTH | ATTR_FILE_DATAALLOCSIZE | ATTR_FILE_DATAEXTENTS | \ ! 215: ATTR_FILE_RSRCLENGTH | ATTR_FILE_RSRCALLOCSIZE | ATTR_FILE_RSRCEXTENTS) != ATTR_FILE_VALIDMASK) ! 216: #warning AttributeBlockSize: Missing bits in file mask computation! ! 217: #endif ! 218: assert((attrlist->fileattr & ~ATTR_FILE_VALIDMASK) == 0); ! 219: ! 220: #if ((ATTR_FORK_TOTALSIZE | ATTR_FORK_ALLOCSIZE) != ATTR_FORK_VALIDMASK) ! 221: #warning AttributeBlockSize: Missing bits in fork mask computation! ! 222: #endif ! 223: assert((attrlist->forkattr & ~ATTR_FORK_VALIDMASK) == 0); ! 224: ! 225: size = 0; ! 226: ! 227: if ((a = attrlist->commonattr) != 0) { ! 228: if (a & ATTR_CMN_NAME) size += sizeof(struct attrreference); ! 229: if (a & ATTR_CMN_DEVID) size += sizeof(dev_t); ! 230: if (a & ATTR_CMN_FSID) size += sizeof(fsid_t); ! 231: if (a & ATTR_CMN_OBJTYPE) size += sizeof(fsobj_type_t); ! 232: if (a & ATTR_CMN_OBJTAG) size += sizeof(fsobj_tag_t); ! 233: if (a & ATTR_CMN_OBJID) size += sizeof(fsobj_id_t); ! 234: if (a & ATTR_CMN_OBJPERMANENTID) size += sizeof(fsobj_id_t); ! 235: if (a & ATTR_CMN_PAROBJID) size += sizeof(fsobj_id_t); ! 236: if (a & ATTR_CMN_SCRIPT) size += sizeof(text_encoding_t); ! 237: if (a & ATTR_CMN_CRTIME) size += sizeof(struct timespec); ! 238: if (a & ATTR_CMN_MODTIME) size += sizeof(struct timespec); ! 239: if (a & ATTR_CMN_CHGTIME) size += sizeof(struct timespec); ! 240: if (a & ATTR_CMN_ACCTIME) size += sizeof(struct timespec); ! 241: if (a & ATTR_CMN_BKUPTIME) size += sizeof(struct timespec); ! 242: if (a & ATTR_CMN_FNDRINFO) size += 32 * sizeof(u_int8_t); ! 243: if (a & ATTR_CMN_OWNERID) size += sizeof(uid_t); ! 244: if (a & ATTR_CMN_GRPID) size += sizeof(gid_t); ! 245: if (a & ATTR_CMN_ACCESSMASK) size += sizeof(u_long); ! 246: if (a & ATTR_CMN_NAMEDATTRCOUNT) size += sizeof(u_long); ! 247: if (a & ATTR_CMN_NAMEDATTRLIST) size += sizeof(struct attrreference); ! 248: if (a & ATTR_CMN_FLAGS) size += sizeof(u_long); ! 249: }; ! 250: if ((a = attrlist->volattr) != 0) { ! 251: if (a & ATTR_VOL_FSTYPE) size += sizeof(u_long); ! 252: if (a & ATTR_VOL_SIGNATURE) size += sizeof(u_long); ! 253: if (a & ATTR_VOL_SIZE) size += sizeof(off_t); ! 254: if (a & ATTR_VOL_SPACEFREE) size += sizeof(off_t); ! 255: if (a & ATTR_VOL_SPACEAVAIL) size += sizeof(off_t); ! 256: if (a & ATTR_VOL_MINALLOCATION) size += sizeof(off_t); ! 257: if (a & ATTR_VOL_ALLOCATIONCLUMP) size += sizeof(off_t); ! 258: if (a & ATTR_VOL_IOBLOCKSIZE) size += sizeof(size_t); ! 259: if (a & ATTR_VOL_OBJCOUNT) size += sizeof(u_long); ! 260: if (a & ATTR_VOL_FILECOUNT) size += sizeof(u_long); ! 261: if (a & ATTR_VOL_DIRCOUNT) size += sizeof(u_long); ! 262: if (a & ATTR_VOL_MAXOBJCOUNT) size += sizeof(u_long); ! 263: if (a & ATTR_VOL_MOUNTPOINT) size += sizeof(struct attrreference); ! 264: if (a & ATTR_VOL_NAME) size += sizeof(struct attrreference); ! 265: if (a & ATTR_VOL_MOUNTFLAGS) size += sizeof(u_long); ! 266: }; ! 267: if ((a = attrlist->dirattr) != 0) { ! 268: if (a & ATTR_DIR_LINKCOUNT) size += sizeof(u_long); ! 269: if (a & ATTR_DIR_ENTRYCOUNT) size += sizeof(u_long); ! 270: }; ! 271: if ((a = attrlist->fileattr) != 0) { ! 272: if (a & ATTR_FILE_LINKCOUNT) size += sizeof(u_long); ! 273: if (a & ATTR_FILE_TOTALSIZE) size += sizeof(off_t); ! 274: if (a & ATTR_FILE_ALLOCSIZE) size += sizeof(off_t); ! 275: if (a & ATTR_FILE_IOBLOCKSIZE) size += sizeof(size_t); ! 276: if (a & ATTR_FILE_CLUMPSIZE) size += sizeof(off_t); ! 277: if (a & ATTR_FILE_DEVTYPE) size += sizeof(u_long); ! 278: if (a & ATTR_FILE_FILETYPE) size += sizeof(u_long); ! 279: if (a & ATTR_FILE_FORKCOUNT) size += sizeof(u_long); ! 280: if (a & ATTR_FILE_FORKLIST) size += sizeof(struct attrreference); ! 281: if (a & ATTR_FILE_DATALENGTH) size += sizeof(off_t); ! 282: if (a & ATTR_FILE_DATAALLOCSIZE) size += sizeof(off_t); ! 283: if (a & ATTR_FILE_DATAEXTENTS) size += sizeof(extentrecord); ! 284: if (a & ATTR_FILE_RSRCLENGTH) size += sizeof(off_t); ! 285: if (a & ATTR_FILE_RSRCALLOCSIZE) size += sizeof(off_t); ! 286: if (a & ATTR_FILE_RSRCEXTENTS) size += sizeof(extentrecord); ! 287: }; ! 288: if ((a = attrlist->forkattr) != 0) { ! 289: if (a & ATTR_FORK_TOTALSIZE) size += sizeof(off_t); ! 290: if (a & ATTR_FORK_ALLOCSIZE) size += sizeof(off_t); ! 291: }; ! 292: ! 293: return size; ! 294: } ! 295: ! 296: ! 297: ! 298: void ! 299: packvolattr (struct attrlist *alist, ! 300: struct iso_node *ip, /* ip for root directory */ ! 301: void **attrbufptrptr, ! 302: void **varbufptrptr) ! 303: { ! 304: void *attrbufptr; ! 305: void *varbufptr; ! 306: struct iso_mnt *imp; ! 307: attrgroup_t a; ! 308: u_long attrlength; ! 309: ! 310: attrbufptr = *attrbufptrptr; ! 311: varbufptr = *varbufptrptr; ! 312: imp = ip->i_mnt; ! 313: ! 314: if ((a = alist->commonattr) != 0) { ! 315: if (a & ATTR_CMN_NAME) { ! 316: attrlength = strlen( imp->volume_id ) + 1; ! 317: ((struct attrreference *)attrbufptr)->attr_dataoffset = varbufptr - attrbufptr; ! 318: ((struct attrreference *)attrbufptr)->attr_length = attrlength; ! 319: (void) strncpy((unsigned char *)varbufptr, imp->volume_id, attrlength); ! 320: ! 321: /* Advance beyond the space just allocated and round up to the next 4-byte boundary: */ ! 322: varbufptr += attrlength + ((4 - (attrlength & 3)) & 3); ! 323: ++((struct attrreference *)attrbufptr); ! 324: }; ! 325: if (a & ATTR_CMN_DEVID) *((dev_t *)attrbufptr)++ = imp->im_devvp->v_rdev; ! 326: if (a & ATTR_CMN_FSID) *((fsid_t *)attrbufptr)++ = ITOV(ip)->v_mount->mnt_stat.f_fsid; ! 327: if (a & ATTR_CMN_OBJTYPE) *((fsobj_type_t *)attrbufptr)++ = 0; ! 328: if (a & ATTR_CMN_OBJTAG) *((fsobj_tag_t *)attrbufptr)++ = VT_ISOFS; ! 329: if (a & ATTR_CMN_OBJID) { ! 330: ((fsobj_id_t *)attrbufptr)->fid_objno = 0; ! 331: ((fsobj_id_t *)attrbufptr)->fid_generation = 0; ! 332: ++((fsobj_id_t *)attrbufptr); ! 333: }; ! 334: if (a & ATTR_CMN_OBJPERMANENTID) { ! 335: ((fsobj_id_t *)attrbufptr)->fid_objno = 0; ! 336: ((fsobj_id_t *)attrbufptr)->fid_generation = 0; ! 337: ++((fsobj_id_t *)attrbufptr); ! 338: }; ! 339: if (a & ATTR_CMN_PAROBJID) { ! 340: ((fsobj_id_t *)attrbufptr)->fid_objno = 0; ! 341: ((fsobj_id_t *)attrbufptr)->fid_generation = 0; ! 342: ++((fsobj_id_t *)attrbufptr); ! 343: }; ! 344: if (a & ATTR_CMN_SCRIPT) *((text_encoding_t *)attrbufptr)++ = 0; ! 345: if (a & ATTR_CMN_CRTIME) *((struct timespec *)attrbufptr)++ = imp->creation_date; ! 346: if (a & ATTR_CMN_MODTIME) *((struct timespec *)attrbufptr)++ = imp->modification_date; ! 347: if (a & ATTR_CMN_CHGTIME) *((struct timespec *)attrbufptr)++ = imp->modification_date; ! 348: if (a & ATTR_CMN_ACCTIME) *((struct timespec *)attrbufptr)++ = imp->modification_date; ! 349: if (a & ATTR_CMN_BKUPTIME) { ! 350: ((struct timespec *)attrbufptr)->tv_sec = 0; ! 351: ((struct timespec *)attrbufptr)->tv_nsec = 0; ! 352: ++((struct timespec *)attrbufptr); ! 353: }; ! 354: if (a & ATTR_CMN_FNDRINFO) { ! 355: bzero (attrbufptr, 32 * sizeof(u_int8_t)); ! 356: attrbufptr += 32 * sizeof(u_int8_t); ! 357: }; ! 358: if (a & ATTR_CMN_OWNERID) *((uid_t *)attrbufptr)++ = ip->inode.iso_uid; ! 359: if (a & ATTR_CMN_GRPID) *((gid_t *)attrbufptr)++ = ip->inode.iso_gid; ! 360: if (a & ATTR_CMN_ACCESSMASK) *((u_long *)attrbufptr)++ = (u_long)ip->inode.iso_mode; ! 361: if (a & ATTR_CMN_FLAGS) *((u_long *)attrbufptr)++ = 0; ! 362: }; ! 363: ! 364: if ((a = alist->volattr) != 0) { ! 365: off_t blocksize = (off_t)imp->logical_block_size; ! 366: ! 367: if (a & ATTR_VOL_FSTYPE) *((u_long *)attrbufptr)++ = (u_long)imp->im_mountp->mnt_vfc->vfc_typenum; ! 368: if (a & ATTR_VOL_SIGNATURE) *((u_long *)attrbufptr)++ = (u_long)ISO9660SIGNATURE; ! 369: if (a & ATTR_VOL_SIZE) *((off_t *)attrbufptr)++ = (off_t)imp->volume_space_size * blocksize; ! 370: if (a & ATTR_VOL_SPACEFREE) *((off_t *)attrbufptr)++ = 0; ! 371: if (a & ATTR_VOL_SPACEAVAIL) *((off_t *)attrbufptr)++ = 0; ! 372: if (a & ATTR_VOL_MINALLOCATION) *((off_t *)attrbufptr)++ = blocksize; ! 373: if (a & ATTR_VOL_ALLOCATIONCLUMP) *((off_t *)attrbufptr)++ = blocksize; ! 374: if (a & ATTR_VOL_IOBLOCKSIZE) *((size_t *)attrbufptr)++ = blocksize; ! 375: if (a & ATTR_VOL_OBJCOUNT) *((u_long *)attrbufptr)++ = 0; ! 376: if (a & ATTR_VOL_FILECOUNT) *((u_long *)attrbufptr)++ = 0; ! 377: if (a & ATTR_VOL_DIRCOUNT) *((u_long *)attrbufptr)++ = 0; ! 378: if (a & ATTR_VOL_MAXOBJCOUNT) *((u_long *)attrbufptr)++ = 0xFFFFFFFF; ! 379: if (a & ATTR_VOL_NAME) { ! 380: attrlength = strlen( imp->volume_id ) + 1; ! 381: ((struct attrreference *)attrbufptr)->attr_dataoffset = varbufptr - attrbufptr; ! 382: ((struct attrreference *)attrbufptr)->attr_length = attrlength; ! 383: (void) strncpy((unsigned char *)varbufptr, imp->volume_id, attrlength); ! 384: ! 385: /* Advance beyond the space just allocated and round up to the next 4-byte boundary: */ ! 386: varbufptr += attrlength + ((4 - (attrlength & 3)) & 3); ! 387: ++((struct attrreference *)attrbufptr); ! 388: }; ! 389: if (a & ATTR_VOL_MOUNTFLAGS) *((u_long *)attrbufptr)++ = (u_long)imp->im_mountp->mnt_flag; ! 390: }; ! 391: ! 392: *attrbufptrptr = attrbufptr; ! 393: *varbufptrptr = varbufptr; ! 394: } ! 395: ! 396: ! 397: void ! 398: packcommonattr (struct attrlist *alist, ! 399: struct iso_node *ip, ! 400: void **attrbufptrptr, ! 401: void **varbufptrptr) ! 402: { ! 403: void *attrbufptr; ! 404: void *varbufptr; ! 405: attrgroup_t a; ! 406: u_long attrlength; ! 407: ! 408: attrbufptr = *attrbufptrptr; ! 409: varbufptr = *varbufptrptr; ! 410: ! 411: if ((a = alist->commonattr) != 0) { ! 412: struct iso_mnt *imp = ip->i_mnt; ! 413: ! 414: if (a & ATTR_CMN_NAME) { ! 415: /* special case root since we know how to get it's name */ ! 416: if (ITOV(ip)->v_flag & VROOT) { ! 417: attrlength = strlen( imp->volume_id ) + 1; ! 418: (void) strncpy((unsigned char *)varbufptr, imp->volume_id, attrlength); ! 419: } else { ! 420: attrlength = strlen(ip->i_name) + 1; ! 421: (void) strncpy((unsigned char *)varbufptr, ip->i_name, attrlength); ! 422: } ! 423: ! 424: ((struct attrreference *)attrbufptr)->attr_dataoffset = varbufptr - attrbufptr; ! 425: ((struct attrreference *)attrbufptr)->attr_length = attrlength; ! 426: /* Advance beyond the space just allocated and round up to the next 4-byte boundary: */ ! 427: varbufptr += attrlength + ((4 - (attrlength & 3)) & 3); ! 428: ++((struct attrreference *)attrbufptr); ! 429: }; ! 430: if (a & ATTR_CMN_DEVID) *((dev_t *)attrbufptr)++ = ip->i_dev; ! 431: if (a & ATTR_CMN_FSID) *((fsid_t *)attrbufptr)++ = ITOV(ip)->v_mount->mnt_stat.f_fsid; ! 432: if (a & ATTR_CMN_OBJTYPE) *((fsobj_type_t *)attrbufptr)++ = ITOV(ip)->v_type; ! 433: if (a & ATTR_CMN_OBJTAG) *((fsobj_tag_t *)attrbufptr)++ = ITOV(ip)->v_tag; ! 434: if (a & ATTR_CMN_OBJID) { ! 435: if (ITOV(ip)->v_flag & VROOT) ! 436: ((fsobj_id_t *)attrbufptr)->fid_objno = 2; /* force root to be 2 */ ! 437: else ! 438: ((fsobj_id_t *)attrbufptr)->fid_objno = ip->i_number; ! 439: ((fsobj_id_t *)attrbufptr)->fid_generation = 0; ! 440: ++((fsobj_id_t *)attrbufptr); ! 441: }; ! 442: if (a & ATTR_CMN_OBJPERMANENTID) { ! 443: if (ITOV(ip)->v_flag & VROOT) ! 444: ((fsobj_id_t *)attrbufptr)->fid_objno = 2; /* force root to be 2 */ ! 445: else ! 446: ((fsobj_id_t *)attrbufptr)->fid_objno = ip->i_number; ! 447: ((fsobj_id_t *)attrbufptr)->fid_generation = 0; ! 448: ++((fsobj_id_t *)attrbufptr); ! 449: }; ! 450: if (a & ATTR_CMN_PAROBJID) { ! 451: struct iso_directory_record *dp = (struct iso_directory_record *)imp->root; ! 452: ino_t rootino = isodirino(dp, imp); ! 453: ! 454: if (ip->i_number == rootino) ! 455: ((fsobj_id_t *)attrbufptr)->fid_objno = 1; /* force root parent to be 1 */ ! 456: else if (ip->i_parent == rootino) ! 457: ((fsobj_id_t *)attrbufptr)->fid_objno = 2; /* force root to be 2 */ ! 458: else ! 459: ((fsobj_id_t *)attrbufptr)->fid_objno = ip->i_parent; ! 460: ((fsobj_id_t *)attrbufptr)->fid_generation = 0; ! 461: ++((fsobj_id_t *)attrbufptr); ! 462: }; ! 463: if (a & ATTR_CMN_SCRIPT) *((text_encoding_t *)attrbufptr)++ = 0; ! 464: if (a & ATTR_CMN_CRTIME) *((struct timespec *)attrbufptr)++ = ip->inode.iso_mtime; ! 465: if (a & ATTR_CMN_MODTIME) *((struct timespec *)attrbufptr)++ = ip->inode.iso_mtime; ! 466: if (a & ATTR_CMN_CHGTIME) *((struct timespec *)attrbufptr)++ = ip->inode.iso_ctime; ! 467: if (a & ATTR_CMN_ACCTIME) *((struct timespec *)attrbufptr)++ = ip->inode.iso_atime; ! 468: if (a & ATTR_CMN_BKUPTIME) { ! 469: ((struct timespec *)attrbufptr)->tv_sec = 0; ! 470: ((struct timespec *)attrbufptr)->tv_nsec = 0; ! 471: ++((struct timespec *)attrbufptr); ! 472: }; ! 473: if (a & ATTR_CMN_FNDRINFO) { ! 474: struct finder_info finfo = {0}; ! 475: ! 476: finfo.fdFlags = ip->i_FinderFlags; ! 477: if (ITOV(ip)->v_type == VREG) { ! 478: finfo.fdType = ip->i_FileType; ! 479: finfo.fdCreator = ip->i_Creator; ! 480: } ! 481: bcopy (&finfo, attrbufptr, sizeof(finfo)); ! 482: attrbufptr += sizeof(finfo); ! 483: bzero (attrbufptr, EXTFNDRINFOSIZE); ! 484: attrbufptr += EXTFNDRINFOSIZE; ! 485: }; ! 486: if (a & ATTR_CMN_OWNERID) *((uid_t *)attrbufptr)++ = ip->inode.iso_uid; ! 487: if (a & ATTR_CMN_GRPID) *((gid_t *)attrbufptr)++ = ip->inode.iso_gid; ! 488: if (a & ATTR_CMN_ACCESSMASK) *((u_long *)attrbufptr)++ = (u_long)ip->inode.iso_mode; ! 489: if (a & ATTR_CMN_FLAGS) *((u_long *)attrbufptr)++ = 0; /* could also use ip->i_flag */ ! 490: }; ! 491: ! 492: *attrbufptrptr = attrbufptr; ! 493: *varbufptrptr = varbufptr; ! 494: } ! 495: ! 496: ! 497: void ! 498: packdirattr(struct attrlist *alist, ! 499: struct iso_node *ip, ! 500: void **attrbufptrptr, ! 501: void **varbufptrptr) ! 502: { ! 503: void *attrbufptr; ! 504: attrgroup_t a; ! 505: ! 506: attrbufptr = *attrbufptrptr; ! 507: ! 508: a = alist->dirattr; ! 509: if ((ITOV(ip)->v_type == VDIR) && (a != 0)) { ! 510: if (a & ATTR_DIR_LINKCOUNT) *((u_long *)attrbufptr)++ = ip->inode.iso_links; ! 511: if (a & ATTR_DIR_ENTRYCOUNT) *((u_long *)attrbufptr)++ = 2; /* XXX */ ! 512: }; ! 513: ! 514: *attrbufptrptr = attrbufptr; ! 515: } ! 516: ! 517: ! 518: void ! 519: packfileattr(struct attrlist *alist, ! 520: struct iso_node *ip, ! 521: void **attrbufptrptr, ! 522: void **varbufptrptr) ! 523: { ! 524: void *attrbufptr = *attrbufptrptr; ! 525: void *varbufptr = *varbufptrptr; ! 526: attrgroup_t a = alist->fileattr; ! 527: ! 528: if ((ITOV(ip)->v_type == VREG) && (a != 0)) { ! 529: if (a & ATTR_FILE_LINKCOUNT) *((u_long *)attrbufptr)++ = ip->inode.iso_links; ! 530: if (a & ATTR_FILE_TOTALSIZE) *((off_t *)attrbufptr)++ = (off_t)ip->i_size; ! 531: if (a & ATTR_FILE_ALLOCSIZE) *((off_t *)attrbufptr)++ = (off_t)ip->i_size; ! 532: if (a & ATTR_FILE_IOBLOCKSIZE) *((u_long *)attrbufptr)++ = ip->i_mnt->logical_block_size; ! 533: if (a & ATTR_FILE_CLUMPSIZE) *((u_long *)attrbufptr)++ = ip->i_mnt->logical_block_size; ! 534: if (a & ATTR_FILE_DEVTYPE) *((u_long *)attrbufptr)++ = (u_long)ip->inode.iso_rdev; ! 535: if (0 /* XXX associated file */) { ! 536: if (a & ATTR_FILE_RSRCLENGTH) *((off_t *)attrbufptr)++ = ip->i_size; ! 537: if (a & ATTR_FILE_RSRCALLOCSIZE) *((off_t *)attrbufptr)++ = ip->i_size; ! 538: if (a & ATTR_FILE_DATALENGTH) *((off_t *)attrbufptr)++ = (off_t)0; ! 539: if (a & ATTR_FILE_DATAALLOCSIZE) *((off_t *)attrbufptr)++ = (off_t)0; ! 540: } else { ! 541: if (a & ATTR_FILE_DATALENGTH) *((off_t *)attrbufptr)++ = (off_t)ip->i_size; ! 542: if (a & ATTR_FILE_DATAALLOCSIZE) *((off_t *)attrbufptr)++ = (off_t)ip->i_size; ! 543: if (a & ATTR_FILE_RSRCLENGTH) *((off_t *)attrbufptr)++ = (off_t)0; ! 544: if (a & ATTR_FILE_RSRCALLOCSIZE) *((off_t *)attrbufptr)++ = (off_t)0; ! 545: }; ! 546: }; ! 547: ! 548: *attrbufptrptr = attrbufptr; ! 549: *varbufptrptr = varbufptr; ! 550: } ! 551: ! 552: ! 553: void ! 554: packattrblk(struct attrlist *alist, ! 555: struct vnode *vp, ! 556: void **attrbufptrptr, ! 557: void **varbufptrptr) ! 558: { ! 559: struct iso_node *ip = VTOI(vp); ! 560: ! 561: if (alist->volattr != 0) { ! 562: packvolattr(alist, ip, attrbufptrptr, varbufptrptr); ! 563: } else { ! 564: packcommonattr(alist, ip, attrbufptrptr, varbufptrptr); ! 565: ! 566: switch (ITOV(ip)->v_type) { ! 567: case VDIR: ! 568: packdirattr(alist, ip, attrbufptrptr, varbufptrptr); ! 569: break; ! 570: ! 571: case VREG: ! 572: packfileattr(alist, ip, attrbufptrptr, varbufptrptr); ! 573: break; ! 574: ! 575: #if 0 /* XXX PPD TBC */ ! 576: case VFORK: ! 577: packforkattr(alist, ip, attrbufptrptr, varbufptrptr); ! 578: break; ! 579: #endif ! 580: ! 581: /* Without this the compiler complains about VNON,VBLK,VCHR,VLNK,VSOCK,VFIFO,VBAD and VSTR ! 582: not being handled... ! 583: */ ! 584: default: ! 585: /* XXX PPD - Panic? */ ! 586: break; ! 587: }; ! 588: }; ! 589: };
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.