Annotation of XNU/bsd/isofs/cd9660/cd9660_vfsops.c, revision 1.1

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_vfsops.c,v 1.18 1995/03/09 12:05:36 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_vfsops.c     8.9 (Berkeley) 12/5/94
        !            62: 
        !            63: 
        !            64: 
        !            65:  * HISTORY
        !            66:  * 18-Nov-98   Add support for volfs - djb
        !            67:  * 22-Jan-98   radar 1669467 - ISO 9660 CD support - jwc
        !            68: 
        !            69:  */
        !            70: 
        !            71: #include <sys/param.h>
        !            72: #include <sys/systm.h>
        !            73: #include <sys/namei.h>
        !            74: #include <sys/proc.h>
        !            75: #include <sys/kernel.h>
        !            76: #include <sys/vnode.h>
        !            77: #include <miscfs/specfs/specdev.h>
        !            78: #include <sys/mount.h>
        !            79: #include <sys/buf.h>
        !            80: #include <sys/file.h>
        !            81: #include <sys/disklabel.h>
        !            82: #include <sys/ioctl.h>
        !            83: #include <sys/errno.h>
        !            84: #include <sys/malloc.h>
        !            85: #include <sys/stat.h>
        !            86: 
        !            87: #include <isofs/cd9660/iso.h>
        !            88: #include <isofs/cd9660/iso_rrip.h>
        !            89: #include <isofs/cd9660/cd9660_node.h>
        !            90: #include <isofs/cd9660/cd9660_mount.h>
        !            91: 
        !            92: extern int enodev ();
        !            93: 
        !            94: struct vfsops cd9660_vfsops = {
        !            95:        cd9660_mount,
        !            96:        cd9660_start,
        !            97:        cd9660_unmount,
        !            98:        cd9660_root,
        !            99:        cd9660_quotactl,
        !           100:        cd9660_statfs,
        !           101:        cd9660_sync,
        !           102:        cd9660_vget,
        !           103:        cd9660_fhtovp,
        !           104:        cd9660_vptofh,
        !           105:        cd9660_init,
        !           106:        cd9660_sysctl
        !           107: };
        !           108: 
        !           109: /*
        !           110:  * Called by vfs_mountroot when iso is going to be mounted as root.
        !           111:  *
        !           112:  * Name is updated by mount(8) after booting.
        !           113:  */
        !           114: #define ROOTNAME       "root_device"
        !           115: 
        !           116: static int iso_mountfs __P((struct vnode *devvp, struct mount *mp,
        !           117:                struct proc *p, struct iso_args *argp));
        !           118: #if 1 // radar 1669467
        !           119: static void    DRGetTypeCreatorAndFlags(       struct iso_mnt * theMountPointPtr,
        !           120:                                                                                        struct iso_directory_record * theDirRecPtr, 
        !           121:                                                                                        u_int32_t * theTypePtr, 
        !           122:                                                                                        u_int32_t * theCreatorPtr, 
        !           123:                                                                                        u_int16_t * theFlagsPtr ); // radar 1669467
        !           124: 
        !           125: int                            cd9660_vget_internal(   struct mount *mp, 
        !           126:                                                                                ino_t ino, 
        !           127:                                                                                struct vnode **vpp, 
        !           128:                                                                                int relocated, 
        !           129:                                                                                struct iso_directory_record *isodir, 
        !           130:                                                                                struct proc *p );
        !           131: #endif // radar 1669467
        !           132: 
        !           133: 
        !           134: int
        !           135: cd9660_mountroot()
        !           136: {
        !           137:        register struct mount *mp;
        !           138:        extern struct vnode *rootvp;
        !           139:        struct proc *p = current_proc();        /* XXX */
        !           140:        struct iso_mnt *imp;
        !           141:        //register struct fs *fs;   radar 1669467 - get rid of warning
        !           142:        size_t size;
        !           143:        int error;
        !           144:        struct iso_args args;
        !           145:        
        !           146:        
        !           147:        /*
        !           148:         * Get vnodes for swapdev and rootdev.
        !           149:         */
        !           150: #if 0
        !           151:        if (bdevvp(swapdev, &swapdev_vp) || bdevvp(rootdev, &rootvp))
        !           152:                panic("cd9660_mountroot: can't setup bdevvp's");
        !           153: #else
        !           154:        if ( bdevvp(rootdev, &rootvp))
        !           155:                panic("cd9660_mountroot: can't setup bdevvp's");
        !           156: 
        !           157: #endif
        !           158: 
        !           159:        MALLOC_ZONE(mp, struct mount *,
        !           160:                        sizeof(struct mount), M_MOUNT, M_WAITOK);
        !           161:        bzero((char *)mp, (u_long)sizeof(struct mount));
        !           162:        mp->mnt_op = &cd9660_vfsops;
        !           163:        mp->mnt_flag = MNT_RDONLY;
        !           164:        LIST_INIT(&mp->mnt_vnodelist);
        !           165:        args.flags = ISOFSMNT_ROOT;
        !           166:        if ((error = iso_mountfs(rootvp, mp, p, &args))) {
        !           167:                FREE_ZONE(mp, sizeof (struct mount), M_MOUNT);
        !           168:                return (error);
        !           169:        }
        !           170:        simple_lock(&mountlist_slock);
        !           171:     #if 0
        !           172:        if (error = VFS_LOCK(mp)) {
        !           173:                (void)cd9660_unmount(mp, 0, p);
        !           174:                FREE_ZONE(mp, sizeof (struct mount), M_MOUNT);
        !           175:                return (error);
        !           176:        }
        !           177:     #endif
        !           178:        CIRCLEQ_INSERT_TAIL(&mountlist, mp, mnt_list);
        !           179:        simple_unlock(&mountlist_slock);
        !           180:        mp->mnt_vnodecovered = NULLVP;
        !           181:        imp = VFSTOISOFS(mp);
        !           182:        (void) copystr("/", mp->mnt_stat.f_mntonname, MNAMELEN - 1,
        !           183:            &size);
        !           184:        bzero(mp->mnt_stat.f_mntonname + size, MNAMELEN - size);
        !           185:        (void) copystr(ROOTNAME, mp->mnt_stat.f_mntfromname, MNAMELEN - 1,
        !           186:            &size);
        !           187:        bzero(mp->mnt_stat.f_mntfromname + size, MNAMELEN - size);
        !           188:        (void)cd9660_statfs(mp, &mp->mnt_stat, p);
        !           189: //     VFS_UNLOCK(mp);
        !           190:        return (0);
        !           191: }
        !           192: 
        !           193: /*
        !           194:  * VFS Operations.
        !           195:  *
        !           196:  * mount system call
        !           197:  */
        !           198: int
        !           199: cd9660_mount(mp, path, data, ndp, p)
        !           200:        register struct mount *mp;
        !           201:        char *path;
        !           202:        caddr_t data;
        !           203:        struct nameidata *ndp;
        !           204:        struct proc *p;
        !           205: {
        !           206:        struct vnode *devvp;
        !           207:        struct iso_args args;
        !           208:        size_t size;
        !           209:        int error;
        !           210:        struct iso_mnt *imp;
        !           211:        
        !           212:        if ( (error = copyin(data, (caddr_t)&args, sizeof (struct iso_args))) ) // radar 1669467 - fix compiler warning
        !           213:                return (error);
        !           214:        
        !           215:        if ((mp->mnt_flag & MNT_RDONLY) == 0)
        !           216:                return (EROFS);
        !           217:        
        !           218:        imp = VFSTOISOFS(mp); // radar 1669467 - imp could be used with out getting set up.
        !           219: 
        !           220:        /*
        !           221:         * If updating, check whether changing from read-only to
        !           222:         * read/write; if there is no device name, that's all we do.
        !           223:         */
        !           224:        if (mp->mnt_flag & MNT_UPDATE) {
        !           225:                //imp = VFSTOISOFS(mp);  radar 1669467 - we do this above now
        !           226:                if (args.fspec == 0)
        !           227:                        return (vfs_export(mp, &imp->im_export, &args.export));
        !           228:        }
        !           229:        /*
        !           230:         * Not an update, or updating the name: look up the name
        !           231:         * and verify that it refers to a sensible block device.
        !           232:         */
        !           233:        NDINIT(ndp, LOOKUP, FOLLOW, UIO_USERSPACE, args.fspec, p);
        !           234:        if ( (error = namei(ndp)) )
        !           235:                return (error);
        !           236:        devvp = ndp->ni_vp;
        !           237: 
        !           238:        if (devvp->v_type != VBLK) {
        !           239:                vrele(devvp);
        !           240:                return ENOTBLK;
        !           241:        }
        !           242:        if (major(devvp->v_rdev) >= nblkdev) {
        !           243:                vrele(devvp);
        !           244:                return ENXIO;
        !           245:        }
        !           246:        if ((mp->mnt_flag & MNT_UPDATE) == 0)
        !           247:                error = iso_mountfs(devvp, mp, p, &args);
        !           248:        else {
        !           249:                if (devvp != imp->im_devvp)
        !           250:                        error = EINVAL; /* needs translation */
        !           251:                else
        !           252:                        vrele(devvp);
        !           253:        }
        !           254:        if (error) {
        !           255:                vrele(devvp);
        !           256:                return error;
        !           257:        }
        !           258: 
        !           259:        /* Set the mount flag to indicate that we support volfs  */
        !           260:     mp->mnt_flag |= MNT_DOVOLFS;
        !           261: 
        !           262:        //imp = VFSTOISOFS(mp); radar 1669467 - we do this above now
        !           263:        (void) copyinstr(path, mp->mnt_stat.f_mntonname, MNAMELEN - 1, &size);
        !           264:        bzero(mp->mnt_stat.f_mntonname + size, MNAMELEN - size);
        !           265:        (void) copyinstr(args.fspec, mp->mnt_stat.f_mntfromname, MNAMELEN - 1,
        !           266:            &size);
        !           267:        bzero(mp->mnt_stat.f_mntfromname + size, MNAMELEN - size);
        !           268:        return 0;
        !           269: }
        !           270: 
        !           271: /*
        !           272:  * Common code for mount and mountroot
        !           273:  */
        !           274: static int
        !           275: iso_mountfs(devvp, mp, p, argp)
        !           276:        register struct vnode *devvp;
        !           277:        struct mount *mp;
        !           278:        struct proc *p;
        !           279:        struct iso_args *argp;
        !           280: {
        !           281:        register struct iso_mnt *isomp = (struct iso_mnt *)0;
        !           282:        struct buf *bp = NULL;
        !           283:        dev_t dev = devvp->v_rdev;
        !           284:        int error = EINVAL;
        !           285:        //int i, size;
        !           286:        int needclose = 0;
        !           287:        int ronly = (mp->mnt_flag & MNT_RDONLY) != 0;
        !           288:        extern struct vnode *rootvp;
        !           289:        int iso_bsize;
        !           290:        int iso_blknum;
        !           291:        struct iso_volume_descriptor *vdp;
        !           292:        struct iso_primary_descriptor *pri;
        !           293:        struct iso_directory_record *rootp;
        !           294:        int logical_block_size;
        !           295: #ifdef 0
        !           296:        int devBlockSize=0;
        !           297: #endif /* NeXT */
        !           298:        
        !           299:        if (!ronly)
        !           300:                return EROFS;
        !           301:        
        !           302:        /*
        !           303:         * Disallow multiple mounts of the same device.
        !           304:         * Disallow mounting of a device that is currently in use
        !           305:         * (except for root, which might share swap device for miniroot).
        !           306:         * Flush out any old buffers remaining from a previous use.
        !           307:         */
        !           308:        if ( (error = vfs_mountedon(devvp)) )
        !           309:                return error;
        !           310:        if ( vcount(devvp) > 1 && devvp != rootvp )
        !           311:                return EBUSY;
        !           312:        if ( (error = vinvalbuf(devvp, V_SAVE, p->p_ucred, p, 0, 0)) )
        !           313:                return (error);
        !           314: 
        !           315:        if ( (error = VOP_OPEN(devvp, ronly ? FREAD : FREAD|FWRITE, FSCRED, p)) )
        !           316:                return error;
        !           317:        needclose = 1;
        !           318:        
        !           319:        /* This is the "logical sector size".  The standard says this
        !           320:         * should be 2048 or the physical sector size on the device,
        !           321:         * whichever is greater.  For now, we'll just use a constant.
        !           322:         */
        !           323:        iso_bsize = ISO_DEFAULT_BLOCK_SIZE;
        !           324:        
        !           325:        for (iso_blknum = 16; iso_blknum < 100; iso_blknum++) {
        !           326: 
        !           327: #if 1 // radar 1669467
        !           328:                if ( (error = bread(devvp, iso_blknum, iso_bsize, NOCRED, &bp)) )
        !           329:                {
        !           330:                        goto out;
        !           331:                };
        !           332: #else 
        !           333:                /* Old code that used incorrect block - btodb is wrong - we should read the iso_blknum */
        !           334:                if (error = bread(devvp, iso_blknum * btodb(iso_bsize),
        !           335:                                  iso_bsize, NOCRED, &bp)) {
        !           336:             #ifdef DEBUG
        !           337:                printf("cd9660_vfsops.c: iso_mountfs: bread() returned %d.\n", error);
        !           338:             #endif
        !           339:                        goto out;
        !           340:                };
        !           341: #endif // radar 1669467
        !           342: 
        !           343:                vdp = (struct iso_volume_descriptor *)bp->b_data;
        !           344:                if (bcmp (vdp->volume_desc_id, ISO_STANDARD_ID, sizeof vdp->volume_desc_id) != 0) {
        !           345:                         #ifdef DEBUG
        !           346:                        printf("cd9660_vfsops.c: iso_mountfs: Invalid ID in volume desciptor.\n");
        !           347:                         #endif
        !           348:                        error = EINVAL;
        !           349:                        goto out;
        !           350:                }
        !           351:                
        !           352:                if (isonum_711 (vdp->type) == ISO_VD_END) {
        !           353:                         #ifdef DEBUG
        !           354:                        printf("cd9660_vfsops.c: iso_mountfs: isonum_711() != ISO_VD_END.\n");
        !           355:                         #endif
        !           356:                        error = EINVAL;
        !           357:                        goto out;
        !           358:                }
        !           359:                
        !           360:                if (isonum_711 (vdp->type) == ISO_VD_PRIMARY)
        !           361:                        break;
        !           362:                brelse(bp);
        !           363:        }
        !           364:        
        !           365:        if (isonum_711 (vdp->type) != ISO_VD_PRIMARY) {
        !           366:                 #ifdef DEBUG
        !           367:                printf("cd9660_vfsops.c: iso_mountfs: isnum_711() != ISO_VD_PRIMARY.\n");
        !           368:                #endif
        !           369:                error = EINVAL;
        !           370:                goto out;
        !           371:        }
        !           372:        
        !           373:        pri = (struct iso_primary_descriptor *)vdp;
        !           374:        
        !           375:        logical_block_size = isonum_723 (pri->logical_block_size);
        !           376:        
        !           377:        if (logical_block_size < DEV_BSIZE || logical_block_size > MAXBSIZE
        !           378:            || (logical_block_size & (logical_block_size - 1)) != 0) {
        !           379:                error = EINVAL;
        !           380:                goto out;
        !           381:        }
        !           382:        
        !           383:        rootp = (struct iso_directory_record *)pri->root_directory_record;
        !           384:        
        !           385: //     isomp = malloc(sizeof *isomp, M_ISOFSMNT, M_WAITOK);
        !           386:        MALLOC(isomp, struct iso_mnt *, sizeof *isomp, M_ISOFSMNT, M_WAITOK);
        !           387:        bzero((caddr_t)isomp, sizeof *isomp);
        !           388:        isomp->logical_block_size = logical_block_size;
        !           389:        isomp->volume_space_size = isonum_733 (pri->volume_space_size);
        !           390:        bcopy (rootp, isomp->root, sizeof isomp->root);
        !           391:        isomp->root_extent = isonum_733 (rootp->extent);
        !           392:        isomp->root_size = isonum_733 (rootp->size);
        !           393: 
        !           394:        /*
        !           395:         * getattrlist wants the volume name, create date and modify date
        !           396:         */
        !           397: 
        !           398:     /* Remove any trailing white space */
        !           399:     if ( strlen(pri->volume_id) ) {
        !           400:        char            *myPtr;
        !           401:        
        !           402:                myPtr = pri->volume_id + strlen( pri->volume_id ) - 1;
        !           403:                while ( *myPtr == ' ' && myPtr >= pri->volume_id ) {
        !           404:                *myPtr = 0x00;
        !           405:                myPtr--;
        !           406:                }
        !           407:     }
        !           408:        /* YYY need to use secondary volume descriptor name for kanji disks */
        !           409:        bcopy(pri->volume_id, isomp->volume_id, sizeof(isomp->volume_id));
        !           410:        cd9660_tstamp_conv17(pri->creation_date, &isomp->creation_date);
        !           411:        cd9660_tstamp_conv17(pri->modification_date, &isomp->modification_date);
        !           412: 
        !           413: #if 0
        !           414:        kprintf("\n************************************************************************* \n");
        !           415:        kprintf( "iso_mountfs - pri->primary_desc_id is \"%c%c%c%c%c\" \n",
        !           416:                        pri->primary_desc_id[0], pri->primary_desc_id[1], pri->primary_desc_id[2], 
        !           417:                        pri->primary_desc_id[3], pri->primary_desc_id[4] );
        !           418:        kprintf( "iso_mountfs - pri->CDXASignature is \"%c%c%c%c%c%c%c%c\" \n",
        !           419:                        pri->CDXASignature[0], pri->CDXASignature[1], pri->CDXASignature[2], 
        !           420:                        pri->CDXASignature[3], pri->CDXASignature[4], pri->CDXASignature[5],
        !           421:                        pri->CDXASignature[6], pri->CDXASignature[7] );
        !           422: #endif
        !           423: 
        !           424: #if 1 // radar 1669467
        !           425:        /* See if this is a CD-XA volume */
        !           426:        if ( bcmp( pri->CDXASignature, ISO_XA_ID, sizeof(pri->CDXASignature) ) == 0 ) 
        !           427:                isomp->im_flags2 |= IMF2_IS_CDXA;
        !           428: #endif // radar 1669467
        !           429:                        
        !           430:        isomp->im_bmask = logical_block_size - 1;
        !           431:        isomp->im_bshift = 0;
        !           432:        while ((1 << isomp->im_bshift) < isomp->logical_block_size)
        !           433:                isomp->im_bshift++;
        !           434: 
        !           435:        bp->b_flags |= B_AGE;
        !           436:        brelse(bp);
        !           437:        bp = NULL;
        !           438: 
        !           439:        mp->mnt_data = (qaddr_t)isomp;
        !           440:        mp->mnt_stat.f_fsid.val[0] = (long)dev;
        !           441:        mp->mnt_stat.f_fsid.val[1] = mp->mnt_vfc->vfc_typenum;
        !           442:        mp->mnt_maxsymlinklen = 0;
        !           443:        mp->mnt_flag |= MNT_LOCAL;
        !           444:        isomp->im_mountp = mp;
        !           445:        isomp->im_dev = dev;
        !           446:        isomp->im_devvp = devvp;        
        !           447:        devvp->v_specflags |= SI_MOUNTEDON;
        !           448:        
        !           449:        /* Check the Rock Ridge Extention support */
        !           450:        if (!(argp->flags & ISOFSMNT_NORRIP)) {
        !           451:                if ( (error = bread(isomp->im_devvp,
        !           452: #if 1 // radar 1669467
        !           453:                                  (isomp->root_extent + isonum_711(rootp->ext_attr_length)),
        !           454: #else
        !           455:                                  (isomp->root_extent + isonum_711(rootp->ext_attr_length)) <<
        !           456:                                  (isomp->im_bshift - DEV_BSHIFT),
        !           457: #endif // radar 1669467
        !           458:                                  isomp->logical_block_size, NOCRED, &bp)) )
        !           459:                    goto out;
        !           460:                
        !           461:                rootp = (struct iso_directory_record *)bp->b_data;
        !           462:                
        !           463:                if ((isomp->rr_skip = cd9660_rrip_offset(rootp,isomp)) < 0) {
        !           464:                    argp->flags  |= ISOFSMNT_NORRIP;
        !           465:                } else {
        !           466:                    argp->flags  &= ~ISOFSMNT_GENS;
        !           467:                }
        !           468:                
        !           469:                /*
        !           470:                 * The contents are valid,
        !           471:                 * but they will get reread as part of another vnode, so...
        !           472:                 */
        !           473:                bp->b_flags |= B_AGE;
        !           474:                brelse(bp);
        !           475:                bp = NULL;
        !           476:        }
        !           477:        isomp->im_flags = argp->flags&(ISOFSMNT_NORRIP|ISOFSMNT_GENS|ISOFSMNT_EXTATT);
        !           478:        switch (isomp->im_flags&(ISOFSMNT_NORRIP|ISOFSMNT_GENS)) {
        !           479:        default:
        !           480:            isomp->iso_ftype = ISO_FTYPE_DEFAULT;
        !           481:            break;
        !           482:        case ISOFSMNT_GENS|ISOFSMNT_NORRIP:
        !           483:            isomp->iso_ftype = ISO_FTYPE_9660;
        !           484:            break;
        !           485:        case 0:
        !           486:            isomp->iso_ftype = ISO_FTYPE_RRIP;
        !           487:            break;
        !           488:        }
        !           489:        
        !           490:        return 0;
        !           491: out:
        !           492:        if (bp)
        !           493:                brelse(bp);
        !           494:        if (needclose)
        !           495:                (void)VOP_CLOSE(devvp, ronly ? FREAD : FREAD|FWRITE, NOCRED, p);
        !           496:        if (isomp) {
        !           497:                FREE((caddr_t)isomp, M_ISOFSMNT);
        !           498:                mp->mnt_data = (qaddr_t)0;
        !           499:        }
        !           500: 
        !           501:        /* Clear the mounted on bit in the devvp If it   */
        !           502:        /* not set, this is a nop and there is no way to */
        !           503:        /* get here with it set unless we did it.  If you*/
        !           504:        /* are making code changes which makes the above */
        !           505:        /* assumption not true, change this code.        */
        !           506: 
        !           507:        devvp->v_specflags &= ~SI_MOUNTEDON;
        !           508: 
        !           509:        return error;
        !           510: }
        !           511: 
        !           512: /*
        !           513:  * Make a filesystem operational.
        !           514:  * Nothing to do at the moment.
        !           515:  */
        !           516: /* ARGSUSED */
        !           517: int
        !           518: cd9660_start(mp, flags, p)
        !           519:        struct mount *mp;
        !           520:        int flags;
        !           521:        struct proc *p;
        !           522: {
        !           523:        return 0;
        !           524: }
        !           525: 
        !           526: 
        !           527: /*
        !           528:  * unmount system call
        !           529:  */
        !           530: int
        !           531: cd9660_unmount(mp, mntflags, p)
        !           532:        struct mount *mp;
        !           533:        int mntflags;
        !           534:        struct proc *p;
        !           535: {
        !           536:        register struct iso_mnt *isomp;
        !           537:        int error, flags = 0;
        !           538:        
        !           539:        if ( (mntflags & MNT_FORCE) )
        !           540:                flags |= FORCECLOSE;
        !           541: #if 0
        !           542:        mntflushbuf(mp, 0);
        !           543:        if (mntinvalbuf(mp))
        !           544:                return EBUSY;
        !           545: #endif
        !           546:        if ( (error = vflush(mp, NULLVP, flags)) )
        !           547:                return (error);
        !           548: 
        !           549:        isomp = VFSTOISOFS(mp);
        !           550: 
        !           551: #ifdef ISODEVMAP
        !           552:        if (isomp->iso_ftype == ISO_FTYPE_RRIP)
        !           553:                iso_dunmap(isomp->im_dev);
        !           554: #endif
        !           555:        
        !           556:        isomp->im_devvp->v_specflags &= ~SI_MOUNTEDON;
        !           557:        error = VOP_CLOSE(isomp->im_devvp, FREAD, NOCRED, p);
        !           558:        vrele(isomp->im_devvp);
        !           559:        FREE((caddr_t)isomp, M_ISOFSMNT);
        !           560:        mp->mnt_data = (qaddr_t)0;
        !           561:        mp->mnt_flag &= ~MNT_LOCAL;
        !           562: 
        !           563:        return (error);
        !           564: }
        !           565: 
        !           566: /*
        !           567:  * Return root of a filesystem
        !           568:  */
        !           569: int
        !           570: cd9660_root(mp, vpp)
        !           571:        struct mount *mp;
        !           572:        struct vnode **vpp;
        !           573: {
        !           574:        struct iso_mnt *imp = VFSTOISOFS(mp);
        !           575:        struct iso_directory_record *dp =
        !           576:            (struct iso_directory_record *)imp->root;
        !           577:        ino_t ino = isodirino(dp, imp);
        !           578:        
        !           579:        /*
        !           580:         * With RRIP we must use the `.' entry of the root directory.
        !           581:         * Simply tell vget, that it's a relocated directory.
        !           582:         */
        !           583:        return (cd9660_vget_internal(mp, ino, vpp,
        !           584:            imp->iso_ftype == ISO_FTYPE_RRIP, dp, current_proc()));
        !           585: }
        !           586: 
        !           587: /*
        !           588:  * Do operations associated with quotas, not supported
        !           589:  */
        !           590: /* ARGSUSED */
        !           591: int
        !           592: cd9660_quotactl(mp, cmd, uid, arg, p)
        !           593:        struct mount *mp;
        !           594:        int cmd;
        !           595:        uid_t uid;
        !           596:        caddr_t arg;
        !           597:        struct proc *p;
        !           598: {
        !           599: 
        !           600:        return (EOPNOTSUPP);
        !           601: }
        !           602: 
        !           603: /*
        !           604:  * Get file system statistics.
        !           605:  */
        !           606: int
        !           607: cd9660_statfs(mp, sbp, p)
        !           608:        struct mount *mp;
        !           609:        register struct statfs *sbp;
        !           610:        struct proc *p;
        !           611: {
        !           612:        register struct iso_mnt *isomp;
        !           613:        
        !           614:        isomp = VFSTOISOFS(mp);
        !           615: 
        !           616: #ifdef COMPAT_09
        !           617:        sbp->f_type = 5;
        !           618: #else
        !           619:        sbp->f_type = 0;
        !           620: #endif
        !           621:        sbp->f_bsize = isomp->logical_block_size;
        !           622:        sbp->f_iosize = sbp->f_bsize;   /* XXX */
        !           623:        sbp->f_blocks = isomp->volume_space_size;
        !           624:        sbp->f_bfree = 0; /* total free blocks */
        !           625:        sbp->f_bavail = 0; /* blocks free for non superuser */
        !           626:        sbp->f_files =  0; /* total files */
        !           627:        sbp->f_ffree = 0; /* free file nodes */
        !           628:        if (sbp != &mp->mnt_stat) {
        !           629:                bcopy(mp->mnt_stat.f_mntonname, sbp->f_mntonname, MNAMELEN);
        !           630:                bcopy(mp->mnt_stat.f_mntfromname, sbp->f_mntfromname, MNAMELEN);
        !           631:        }
        !           632: 
        !           633: #if 1 // radar 1669467
        !           634:        strncpy( sbp->f_fstypename, mp->mnt_vfc->vfc_name, (MFSNAMELEN - 1) );
        !           635:        sbp->f_fstypename[(MFSNAMELEN - 1)] = '\0';
        !           636: #else
        !           637:        strncpy(sbp->f_fstypename, mp->mnt_vfc->vfc_name, MFSNAMELEN);
        !           638:        sbp->f_fstypename[MFSNAMELEN] = '\0';
        !           639: #endif // radar 1669467
        !           640: 
        !           641:        /* Use the first spare for flags: */
        !           642:        sbp->f_spare[0] = isomp->im_flags;
        !           643: 
        !           644:        return 0;
        !           645: }
        !           646: 
        !           647: /* ARGSUSED */
        !           648: int
        !           649: cd9660_sync(mp, waitfor, cred, p)
        !           650:        struct mount *mp;
        !           651:        int waitfor;
        !           652:        struct ucred *cred;
        !           653:        struct proc *p;
        !           654: {
        !           655: 
        !           656:        return (0);
        !           657: }
        !           658: 
        !           659: /*
        !           660:  * File handle to vnode
        !           661:  *
        !           662:  * Have to be really careful about stale file handles:
        !           663:  * - check that the inode number is in range
        !           664:  * - call iget() to get the locked inode
        !           665:  * - check for an unallocated inode (i_mode == 0)
        !           666:  * - check that the generation number matches
        !           667:  */
        !           668: 
        !           669: struct ifid {
        !           670:        ushort  ifid_len;
        !           671:        ushort  ifid_pad;
        !           672:        int     ifid_ino;
        !           673:        long    ifid_start;
        !           674: };
        !           675: 
        !           676: /* ARGSUSED */
        !           677: int
        !           678: cd9660_fhtovp(mp, fhp, nam, vpp, exflagsp, credanonp)
        !           679:        register struct mount *mp;
        !           680:        struct fid *fhp;
        !           681:        struct mbuf *nam;
        !           682:        struct vnode **vpp;
        !           683:        int *exflagsp;
        !           684:        struct ucred **credanonp;
        !           685: {
        !           686:        struct ifid *ifhp = (struct ifid *)fhp;
        !           687:        register struct iso_node *ip;
        !           688:        register struct netcred *np;
        !           689:        register struct iso_mnt *imp = VFSTOISOFS(mp);
        !           690:        struct vnode *nvp;
        !           691:        int error;
        !           692:        
        !           693: #ifdef ISOFS_DBG
        !           694:        printf("fhtovp: ino %d, start %ld\n",
        !           695:               ifhp->ifid_ino, ifhp->ifid_start);
        !           696: #endif
        !           697:        
        !           698:        /*
        !           699:         * Get the export permission structure for this <mp, client> tuple.
        !           700:         */
        !           701:        np = vfs_export_lookup(mp, &imp->im_export, nam);
        !           702:        if (np == NULL)
        !           703:                return (EACCES);
        !           704: 
        !           705:        if ( (error = VFS_VGET(mp, &ifhp->ifid_ino, &nvp)) ) {
        !           706:                *vpp = NULLVP;
        !           707:                return (error);
        !           708:        }
        !           709:        ip = VTOI(nvp);
        !           710:        if (ip->inode.iso_mode == 0) {
        !           711:                vput(nvp);
        !           712:                *vpp = NULLVP;
        !           713:                return (ESTALE);
        !           714:        }
        !           715:        *vpp = nvp;
        !           716:        *exflagsp = np->netc_exflags;
        !           717:        *credanonp = &np->netc_anon;
        !           718:        return (0);
        !           719: }
        !           720: 
        !           721: int
        !           722: cd9660_vget(mp, ino, vpp)
        !           723:        struct mount *mp;
        !           724:        void *ino;
        !           725:        struct vnode **vpp;
        !           726: {
        !           727:        /*
        !           728:         * XXXX
        !           729:         * It would be nice if we didn't always set the `relocated' flag
        !           730:         * and force the extra read, but I don't want to think about fixing
        !           731:         * that right now.
        !           732:         */
        !           733: 
        !           734: #if 1 // radar 1669467 - fix compiler warning
        !           735: 
        !           736:        return ( cd9660_vget_internal( mp, *(ino_t*)ino, vpp, 0, 
        !           737:                                                                   (struct iso_directory_record *) 0,
        !           738:                                                                   current_proc()) );
        !           739: 
        !           740: #else // radar 1669467
        !           741: 
        !           742:        return (cd9660_vget_internal(mp, *(ino_t*)ino, vpp,
        !           743: #if 0
        !           744:            VFSTOISOFS(mp)->iso_ftype == ISO_FTYPE_RRIP,
        !           745: #else
        !           746:            0,
        !           747: #endif
        !           748:            (struct iso_directory_entry *)0));
        !           749: #endif // radar 1669467
        !           750: }
        !           751: 
        !           752: int
        !           753: cd9660_vget_internal(mp, ino, vpp, relocated, isodir, p)
        !           754:        struct mount *mp;
        !           755:        ino_t ino;
        !           756:        struct vnode **vpp;
        !           757:        int relocated;
        !           758:        struct iso_directory_record *isodir;
        !           759:     struct proc *p;
        !           760: {
        !           761:        register struct iso_mnt *imp;
        !           762:        struct iso_node *ip;
        !           763:        struct buf *bp;
        !           764:        struct vnode *vp, *nvp;
        !           765:        dev_t dev;
        !           766:        int error;
        !           767: 
        !           768:        imp = VFSTOISOFS(mp);
        !           769:        dev = imp->im_dev;
        !           770:        if ((*vpp = cd9660_ihashget(dev, ino, p)) != NULLVP)
        !           771:                return (0);
        !           772: 
        !           773:        MALLOC(ip, struct iso_node *, sizeof(struct iso_node), M_ISOFSNODE,
        !           774:            M_WAITOK);
        !           775:        /* Allocate a new vnode/iso_node. */
        !           776:        if ( (error = getnewvnode(VT_ISOFS, mp, cd9660_vnodeop_p, &vp)) ) {
        !           777:                FREE(ip, M_ISOFSNODE);
        !           778:                *vpp = NULLVP;
        !           779:                return (error);
        !           780:        }
        !           781:        bzero((caddr_t)ip, sizeof(struct iso_node));
        !           782: 
        !           783: // radar 1669467 - chw initialize the lock structure now that we are using
        !           784: //                the lock manager
        !           785: 
        !           786:        lockinit(&ip->i_lock, PINOD,"inode",0,0);
        !           787:        vp->v_data = ip;
        !           788:        ip->i_vnode = vp;
        !           789:        ip->i_dev = dev;
        !           790:        ip->i_number = ino;
        !           791: 
        !           792:        /*
        !           793:         * Put it onto its hash chain and lock it so that other requests for
        !           794:         * this inode will block if they arrive while we are sleeping waiting
        !           795:         * for old data structures to be purged or for the contents of the
        !           796:         * disk portion of this inode to be read.
        !           797:         */
        !           798:        cd9660_ihashins(ip);
        !           799: 
        !           800:        if (isodir == 0) {
        !           801:                int lbn, off;
        !           802: 
        !           803:                lbn = lblkno(imp, ino);
        !           804:                if (lbn >= imp->volume_space_size) {
        !           805:                        vput(vp);
        !           806:                        printf("fhtovp: lbn exceed volume space %d\n", lbn);
        !           807:                        return (ESTALE);
        !           808:                }
        !           809:        
        !           810:                off = blkoff(imp, ino);
        !           811:                if (off + ISO_DIRECTORY_RECORD_SIZE > imp->logical_block_size) {
        !           812:                        vput(vp);
        !           813:                        printf("fhtovp: crosses block boundary %d\n",
        !           814:                               off + ISO_DIRECTORY_RECORD_SIZE);
        !           815:                        return (ESTALE);
        !           816:                }
        !           817:        
        !           818:                error = bread(imp->im_devvp,
        !           819: #if 1 // radar 1669467
        !           820:                              lbn,
        !           821: #else
        !           822:                              lbn << (imp->im_bshift - DEV_BSHIFT),
        !           823: #endif // radar 1669467
        !           824:                              imp->logical_block_size, NOCRED, &bp);
        !           825:                if (error) {
        !           826:                        vput(vp);
        !           827:                        brelse(bp);
        !           828:                        printf("fhtovp: bread error %d\n",error);
        !           829:                        return (error);
        !           830:                }
        !           831:                isodir = (struct iso_directory_record *)(bp->b_data + off);
        !           832: 
        !           833:                if (off + isonum_711(isodir->length) >
        !           834:                    imp->logical_block_size) {
        !           835:                        vput(vp);
        !           836:                        if (bp != 0)
        !           837:                                brelse(bp);
        !           838:                        printf("fhtovp: directory crosses block boundary %d[off=%d/len=%d]\n",
        !           839:                               off +isonum_711(isodir->length), off,
        !           840:                               isonum_711(isodir->length));
        !           841:                        return (ESTALE);
        !           842:                }
        !           843: 
        !           844:                /*
        !           845:                 * for directories we can get parentID from adjacent parent directory record
        !           846:                 */
        !           847:                if ((isonum_711(isodir->flags) & directoryBit) && (isodir->name[0] == 0)) {
        !           848:                        struct iso_directory_record *pdp;
        !           849:                        
        !           850:                        pdp = (struct iso_directory_record *) ((char *)bp->b_data + isonum_711(isodir->length));
        !           851:                        if ((isonum_711(pdp->flags) & directoryBit) && (pdp->name[0] == 1))
        !           852:                                ip->i_parent = isodirino(pdp, imp);
        !           853:                        
        !           854:                }
        !           855: #if 0
        !           856:                if (isonum_733(isodir->extent) +
        !           857:                    isonum_711(isodir->ext_attr_length) != ifhp->ifid_start) {
        !           858:                        if (bp != 0)
        !           859:                                brelse(bp);
        !           860:                        printf("fhtovp: file start miss %d vs %d\n",
        !           861:                               isonum_733(isodir->extent) + isonum_711(isodir->ext_attr_length),
        !           862:                               ifhp->ifid_start);
        !           863:                        return (ESTALE);
        !           864:                }
        !           865: #endif
        !           866:        } else
        !           867:                bp = 0;
        !           868: 
        !           869:        ip->i_mnt = imp;
        !           870:        ip->i_devvp = imp->im_devvp;
        !           871:        VREF(ip->i_devvp);
        !           872: 
        !           873:        if (relocated) {
        !           874:                /*
        !           875:                 * On relocated directories we must
        !           876:                 * read the `.' entry out of a dir.
        !           877:                 */
        !           878:                ip->iso_start = ino >> imp->im_bshift;
        !           879:                if (bp != 0)
        !           880:                        brelse(bp);
        !           881:                if ( (error = VOP_BLKATOFF(vp, (off_t)0, NULL, &bp)) ) {
        !           882:                        vput(vp);
        !           883:                        return (error);
        !           884:                }
        !           885:                isodir = (struct iso_directory_record *)bp->b_data;
        !           886:        }
        !           887: 
        !           888: #if 1 // radar 1669467
        !           889: 
        !           890:        /* go get apple extensions to ISO directory record or use defaults when there are no apple */
        !           891:        /* extensions.   */
        !           892:        if ( (isonum_711( isodir->flags ) & directoryBit) == 0 )
        !           893:        {
        !           894:                /* This is an ISO directory record for a file */
        !           895:                DRGetTypeCreatorAndFlags( imp, isodir, &ip->i_FileType, 
        !           896:                                                                  &ip->i_Creator, &ip->i_FinderFlags );
        !           897:        }
        !           898: 
        !           899: #endif // radar 1669467
        !           900: 
        !           901:        ip->iso_extent = isonum_733(isodir->extent);
        !           902:        ip->i_size = isonum_733(isodir->size);
        !           903:        ip->iso_start = isonum_711(isodir->ext_attr_length) + ip->iso_extent;
        !           904: 
        !           905:        /*
        !           906:         * if we have a valid name, fill in i_name
        !           907:         */
        !           908:        if (((u_char)isodir->name[0]) > 1) {
        !           909:                u_short namelen;
        !           910: 
        !           911:                if (imp->iso_ftype == ISO_FTYPE_RRIP) {
        !           912:                        ino_t inump = 0;
        !           913:        
        !           914:                        cd9660_rrip_getname(isodir, ip->i_name, &namelen, &inump, imp);
        !           915:                } else {
        !           916:                        isofntrans (isodir->name, isonum_711(isodir->name_len),
        !           917:                                        ip->i_name, &namelen,
        !           918:                                        imp->iso_ftype == ISO_FTYPE_9660,
        !           919:                                        isonum_711(isodir->flags) & associatedBit);
        !           920:                }
        !           921:        
        !           922:                if (namelen > (sizeof(ip->i_name) - 1))
        !           923:                        namelen = sizeof(ip->i_name) - 1;
        !           924:                ip->i_name[namelen] = '\0';
        !           925:        }
        !           926:        
        !           927:        /*
        !           928:         * Setup time stamp, attribute
        !           929:         */
        !           930:        vp->v_type = VNON;
        !           931:        switch (imp->iso_ftype) {
        !           932:        default:        /* ISO_FTYPE_9660 */
        !           933:            {
        !           934:                struct buf *bp2;
        !           935:                int off;
        !           936:                if ((imp->im_flags & ISOFSMNT_EXTATT)
        !           937:                    && (off = isonum_711(isodir->ext_attr_length)))
        !           938:                        VOP_BLKATOFF(vp, (off_t)-(off << imp->im_bshift), NULL,
        !           939:                                     &bp2);
        !           940:                else
        !           941:                        bp2 = NULL;
        !           942:                cd9660_defattr(isodir, ip, bp2);
        !           943:                cd9660_deftstamp(isodir, ip, bp2);
        !           944:                if (bp2)
        !           945:                        brelse(bp2);
        !           946:                break;
        !           947:            }
        !           948:        case ISO_FTYPE_RRIP:
        !           949:                cd9660_rrip_analyze(isodir, ip, imp);
        !           950:                break;
        !           951:        }
        !           952: 
        !           953:        if (bp != 0)
        !           954:                brelse(bp);
        !           955: 
        !           956:        /*
        !           957:         * Initialize the associated vnode
        !           958:         */
        !           959:        switch (vp->v_type = IFTOVT(ip->inode.iso_mode)) {
        !           960:        case VFIFO:
        !           961: #if    FIFO
        !           962:                vp->v_op = cd9660_fifoop_p;
        !           963:                break;
        !           964: #else
        !           965:                vput(vp);
        !           966:                return (EOPNOTSUPP);
        !           967: #endif /* FIFO */
        !           968:        case VCHR:
        !           969:        case VBLK:
        !           970:                /*
        !           971:                 * if device, look at device number table for translation
        !           972:                 */
        !           973: #ifdef ISODEVMAP
        !           974:                if (dp = iso_dmap(dev, ino, 0))
        !           975:                        ip->inode.iso_rdev = dp->d_dev;
        !           976: #endif
        !           977:                vp->v_op = cd9660_specop_p;
        !           978:                if ( (nvp = checkalias(vp, ip->inode.iso_rdev, mp)) ) {
        !           979:                        /*
        !           980:                         * Discard unneeded vnode, but save its iso_node.
        !           981:                         */
        !           982:                        cd9660_ihashrem(ip);
        !           983:                        VOP_UNLOCK(vp, 0, p);
        !           984:                        nvp->v_data = vp->v_data;
        !           985:                        vp->v_data = NULL;
        !           986:                        vp->v_op = spec_vnodeop_p;
        !           987:                        vrele(vp);
        !           988:                        vgone(vp);
        !           989:                        /*
        !           990:                         * Reinitialize aliased inode.
        !           991:                         */
        !           992:                        vp = nvp;
        !           993:                        ip->i_vnode = vp;
        !           994:                        cd9660_ihashins(ip);
        !           995:                }
        !           996:                break;
        !           997:        default:                // radar 1669467 - fix compiler warning
        !           998:                break;
        !           999:        }
        !          1000:        
        !          1001:        if (ip->iso_extent == imp->root_extent) {
        !          1002:                vp->v_flag |= VROOT;
        !          1003:                ip->i_parent = 1;       /* root's parent is always 1 by convention */
        !          1004:        }
        !          1005:        /*
        !          1006:         * XXX need generation number?
        !          1007:         */
        !          1008: 
        !          1009:        *vpp = vp;
        !          1010: 
        !          1011:        return (0);
        !          1012: }
        !          1013: 
        !          1014: 
        !          1015: /************************************************************************
        !          1016:  *
        !          1017:  *  Function:  DRGetTypeCreatorAndFlags
        !          1018:  *
        !          1019:  *  Purpose:   Set up the fileType, fileCreator and fileFlags
        !          1020:  *
        !          1021:  *  Returns:   none
        !          1022:  *
        !          1023:  *  Side Effects:      sets *theTypePtr, *theCreatorPtr, and *theFlagsPtr
        !          1024:  *
        !          1025:  *  Description:
        !          1026:  *
        !          1027:  *  Revision History:
        !          1028:  *     28 Jul 88       BL�B    Added a new extension type of 6, which allows
        !          1029:  *                                             the specification of four of the finder flags.
        !          1030:  *                                             We let the creator of the disk just copy over
        !          1031:  *                                             the finder flags, but we only look at always
        !          1032:  *                                             switch launch, system, bundle, and locked bits.
        !          1033:  *     15 Aug 88       BL�B    The Apple extensions to ISO 9660 implemented the
        !          1034:  *                                             padding field at the end of a directory record
        !          1035:  *                                             incorrectly.
        !          1036:  *     19 Jul 89       BG              Rewrote routine to handle the "new" Apple
        !          1037:  *                                             Extensions definition, as well as take into
        !          1038:  *                                             account the possibility of "other" definitions.
        !          1039:  *     02 Nov 89       BG              Corrected the 'AA' SystemUseID processing to
        !          1040:  *                                             check for SystemUseID == 2 (HFS).  Was incorrectly
        !          1041:  *                                             checking for SystemUseID == 1 (ProDOS) before.
        !          1042:  *     18 Mar 92       CMP             Fixed the check for whether len_fi was odd or even.
        !          1043:  *                                             Before it would always assume even for an XA record.
        !          1044:  *     26 Dec 97       jwc             Swiped from MacOS implementation of ISO 9660 CD-ROM support
        !          1045:  *                                             and modified to work in MacOSX file system.
        !          1046:  *
        !          1047:  *********************************************************************** */
        !          1048:  
        !          1049: static void DRGetTypeCreatorAndFlags(  struct iso_mnt * theMountPointPtr,
        !          1050:                                                                                struct iso_directory_record * theDirRecPtr, 
        !          1051:                                                                                u_int32_t * theTypePtr, 
        !          1052:                                                                                u_int32_t * theCreatorPtr, 
        !          1053:                                                                                u_int16_t * theFlagsPtr )
        !          1054: {
        !          1055:        int                                     foundStuff;
        !          1056:        u_int32_t                       myType;
        !          1057:        u_int32_t                       myCreator;
        !          1058:        AppleExtension          *myAppleExtPtr;
        !          1059:        NewAppleExtension       *myNewAppleExtPtr;
        !          1060:        u_int16_t                       myFinderFlags;
        !          1061:        char                            *myPtr;
        !          1062: 
        !          1063:        foundStuff = 1;
        !          1064:        myType = 0L;
        !          1065:        myCreator = 0L;
        !          1066:        myFinderFlags = 0;
        !          1067:        *theFlagsPtr = 0x0000;
        !          1068: 
        !          1069:        /* handle the fact that our original apple extensions didn't take
        !          1070:           into account the padding byte on a file name */
        !          1071: 
        !          1072:        myPtr = &theDirRecPtr->name[ (isonum_711(theDirRecPtr->name_len)) ];
        !          1073:        
        !          1074:        /* if string length is even, bump myPtr for padding byte */
        !          1075:        if ( ((isonum_711(theDirRecPtr->name_len)) & 0x01) == 0 )
        !          1076:                myPtr++;
        !          1077:        myAppleExtPtr = (AppleExtension *) myPtr;
        !          1078: 
        !          1079:        /* checking for whether or not the new 'AA' code is being called (and if so, correctly) */
        !          1080:        if ( (isonum_711(theDirRecPtr->length)) <= 
        !          1081:                 ISO_DIRECTORY_RECORD_SIZE + (isonum_711(theDirRecPtr->name_len)) )
        !          1082:        {
        !          1083:                foundStuff = 0;
        !          1084:                goto DoneLooking;
        !          1085:        }
        !          1086: 
        !          1087:        if ( myAppleExtPtr->signature[0] == 'B' && myAppleExtPtr->signature[1] == 'A' )
        !          1088:        {
        !          1089:                int             i;
        !          1090: 
        !          1091:                switch ( isonum_711(myAppleExtPtr->systemUseID) )
        !          1092:                {
        !          1093:                        case 0x00:      /* nothing there.  use default */
        !          1094:                                foundStuff = 0;
        !          1095:                                break;
        !          1096:                        case 0x02:      /* no icon */
        !          1097:                        case 0x04:      /* icon, no bundle bit */
        !          1098:                                for ( i = 0; i < 4; i++ )
        !          1099:                                        myType = (myType << 8) | myAppleExtPtr->fileType[i];
        !          1100:                                        
        !          1101:                                for ( i = 0; i < 4; i++ )
        !          1102:                                        myCreator = (myCreator << 8) | myAppleExtPtr->fileCreator[i];
        !          1103:                                        
        !          1104:                                *theFlagsPtr |= fInitedBit;
        !          1105:                                break;
        !          1106:                        case 0x03:      /* no icon, bundle bit */
        !          1107:                        case 0x05:      /* icon and bundle bit */
        !          1108:                                for ( i = 0; i < 4; i++ )
        !          1109:                                        myType = (myType << 8) | myAppleExtPtr->fileType[i];
        !          1110:                                        
        !          1111:                                for ( i = 0; i < 4; i++ )
        !          1112:                                        myCreator = (myCreator << 8) | myAppleExtPtr->fileCreator[i];
        !          1113:                                        
        !          1114:                                *theFlagsPtr |= fInitedBit | fHasBundleBit;
        !          1115:                                break;
        !          1116:                        case 0x06:      /* finder flags in word at end */
        !          1117:                                for ( i = 0; i < 4; i++ )
        !          1118:                                        myType = (myType << 8) | myAppleExtPtr->fileType[i];
        !          1119:                                        
        !          1120:                                for ( i = 0; i < 4; i++ )
        !          1121:                                        myCreator = (myCreator << 8) | myAppleExtPtr->fileCreator[i];
        !          1122:                                        
        !          1123:                                myFinderFlags = 
        !          1124:                                        (myAppleExtPtr->finderFlags[0] << 8) | myAppleExtPtr->finderFlags[1];
        !          1125:                                        
        !          1126:                                /* just check the following four bits--all others always set to 0 */
        !          1127:                                myFinderFlags &= (fAlwaysBit | fSystemBit | fHasBundleBit | fLockedBit);
        !          1128:                                *theFlagsPtr |= (fInitedBit | myFinderFlags);
        !          1129:                                break;
        !          1130:                        default:
        !          1131:                                foundStuff = 0;
        !          1132:                }
        !          1133:                goto DoneLooking;
        !          1134:        }
        !          1135:        
        !          1136:        /*
        !          1137:         *              If signature[]s != 'BA', then (1) this is not an old-style disc and we
        !          1138:         *              need to look at ALL available SystemUse possibilities;  (2)  this could
        !          1139:         *              possibly be a CD-XA style disc and our offset calculations need to
        !          1140:         *              take this into account.
        !          1141:         */
        !          1142: 
        !          1143:        foundStuff = 0; /* now we default to *false* until we find a good one */
        !          1144:        myPtr = (char *) myAppleExtPtr;
        !          1145: 
        !          1146:        if ( (theMountPointPtr->im_flags2 & IMF2_IS_CDXA) != 0 )
        !          1147:                myPtr += 14;/* add in CD-XA fixed record offset (tnx, Phillips) */
        !          1148:        myNewAppleExtPtr = (NewAppleExtension *) myPtr;
        !          1149: 
        !          1150:        /* calculate the "real" end of the directory record information */
        !          1151:        myPtr = ((char *) theDirRecPtr) + (isonum_711(theDirRecPtr->length));
        !          1152:        while( (char *) myNewAppleExtPtr < myPtr )      /* end of directory buffer */
        !          1153:        {
        !          1154:                /*
        !          1155:                 *      If we get here, we can assume that ALL further entries in this
        !          1156:                 *      directory record are of the form:
        !          1157:                 *
        !          1158:                 *              struct OptionalSystemUse
        !          1159:                 *              {
        !          1160:                 *                      byte    Signature[2];
        !          1161:                 *                      byte    systemUseID;
        !          1162:                 *                      byte    OSULength;
        !          1163:                 *                      byte    fileType[4];            # only if HFS
        !          1164:                 *                      byte    fileCreator[4];         # only if HFS
        !          1165:                 *                      byte    finderFlags[2];         # only if HFS
        !          1166:                 *              };
        !          1167:                 *
        !          1168:                 *      This means that we can examine the Signature bytes to see if they are 'AA'
        !          1169:                 *      (the NEW Apple extension signature).  If they are, deal with them.  If they
        !          1170:                 *      aren't, the OSULength field will tell us how long this extension info is
        !          1171:                 *      (including the signature and length bytes) and that will allow us to walk
        !          1172:                 *      the OptionalSystemUse records until we hit the end of them or run off the
        !          1173:                 *      end of the directory record.
        !          1174:                 */
        !          1175:                u_char                          *myFromPtr, *myToPtr;
        !          1176:                union
        !          1177:                {
        !          1178:                        u_int32_t               fourchars;
        !          1179:                        u_char                  chars[4];
        !          1180:                } myChars;
        !          1181: 
        !          1182:                if ( myNewAppleExtPtr->signature[0] == 'A' && myNewAppleExtPtr->signature[1] == 'A' )
        !          1183:                {
        !          1184:                        if ( isonum_711(myNewAppleExtPtr->systemUseID) == 2 )   /* HFS */
        !          1185:                        {
        !          1186:                                foundStuff = 1;                 /* we got one! */
        !          1187: 
        !          1188:                                myFromPtr = &myNewAppleExtPtr->fileType[0]; 
        !          1189:                                myToPtr = &myChars.chars[0];
        !          1190:                                *myToPtr++ = *myFromPtr++; 
        !          1191:                                *myToPtr++ = *myFromPtr++; 
        !          1192:                                *myToPtr++ = *myFromPtr++; 
        !          1193:                                *myToPtr = *myFromPtr;
        !          1194:                                myType = myChars.fourchars;             /* copy file type to user var */
        !          1195: 
        !          1196:                                myFromPtr = &myNewAppleExtPtr->fileCreator[0]; 
        !          1197:                                myToPtr = &myChars.chars[0];
        !          1198:                                *myToPtr++ = *myFromPtr++; 
        !          1199:                                *myToPtr++ = *myFromPtr++; 
        !          1200:                                *myToPtr++ = *myFromPtr++; 
        !          1201:                                *myToPtr = *myFromPtr;
        !          1202:                                myCreator = myChars.fourchars;  /* copy creator to user var */
        !          1203: 
        !          1204:                                myFromPtr = &myNewAppleExtPtr->finderFlags[0]; 
        !          1205:                                myToPtr = &myChars.chars[2];    /* *flags* is a short */
        !          1206:                                myChars.fourchars = 0; 
        !          1207:                                *myToPtr++ = *myFromPtr++; 
        !          1208:                                *myToPtr = *myFromPtr;
        !          1209:                                myFinderFlags = myChars.fourchars;
        !          1210:                                myFinderFlags &= ( fAlwaysBit | fSystemBit | fHasBundleBit | fLockedBit );
        !          1211:                                *theFlagsPtr = (myFinderFlags | fInitedBit); /* return Finder flags to user var */
        !          1212: 
        !          1213:                                break;          /* exit the loop */
        !          1214:                        }
        !          1215:                }
        !          1216: 
        !          1217:                /*
        !          1218:                 *      Check to see if we have a reasonable OSULength value.
        !          1219:                 *      ZERO is not an acceptable value.  Nor is any value less than 4.
        !          1220:                 */
        !          1221: 
        !          1222:                if ( (isonum_711(myNewAppleExtPtr->OSULength)) < 4 ) 
        !          1223:                        break;  /* not acceptable - get out! */
        !          1224: 
        !          1225:                /* otherwise, step past this SystemUse record */
        !          1226:                (char *)myNewAppleExtPtr += (isonum_711(myNewAppleExtPtr->OSULength));
        !          1227:                
        !          1228:        } // end of while loop
        !          1229: 
        !          1230: DoneLooking:
        !          1231:        if ( foundStuff != 0 )
        !          1232:        {
        !          1233:                *theTypePtr    = myType;
        !          1234:                *theCreatorPtr = myCreator;
        !          1235:        }
        !          1236:        else
        !          1237:        {
        !          1238:                *theTypePtr = DEFAULTTYPE;
        !          1239:                *theCreatorPtr = DEFAULTCREATOR;
        !          1240:                *theFlagsPtr |= fInitedBit;
        !          1241:        }
        !          1242:        
        !          1243:        return;
        !          1244:        
        !          1245: } /* DRGetTypeCreatorAndFlags */
        !          1246: 
        !          1247: 
        !          1248: /*
        !          1249:  * Vnode pointer to File handle
        !          1250:  */
        !          1251: /* ARGSUSED */
        !          1252: int
        !          1253: cd9660_vptofh(vp, fhp)
        !          1254:        struct vnode *vp;
        !          1255:        struct fid *fhp;
        !          1256: {
        !          1257:        register struct iso_node *ip = VTOI(vp);
        !          1258:        register struct ifid *ifhp;
        !          1259:        
        !          1260:        ifhp = (struct ifid *)fhp;
        !          1261:        ifhp->ifid_len = sizeof(struct ifid);
        !          1262:        
        !          1263:        ifhp->ifid_ino = ip->i_number;
        !          1264:        ifhp->ifid_start = ip->iso_start;
        !          1265:        
        !          1266: #ifdef ISOFS_DBG
        !          1267:        printf("vptofh: ino %d, start %ld\n",
        !          1268:               ifhp->ifid_ino,ifhp->ifid_start);
        !          1269: #endif
        !          1270:        return 0;
        !          1271: }
        !          1272: 
        !          1273: /*
        !          1274:  * Fast-FileSystem only?
        !          1275:  */
        !          1276: int
        !          1277: cd9660_sysctl(name, namelen, oldp, oldlenp, newp, newlen, p)
        !          1278:      int * name;
        !          1279:      u_int namelen;
        !          1280:      void* oldp;
        !          1281:      size_t * oldlenp;
        !          1282:      void * newp;
        !          1283:      size_t newlen;
        !          1284:      struct proc * p;
        !          1285: {
        !          1286:      return EOPNOTSUPP;
        !          1287: }
        !          1288: 

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.