X-Git-Url: https://git.saurik.com/apple/xnu.git/blobdiff_plain/1c79356b52d46aa6b508fb032f5ae709b1f2897b..c0fea4742e91338fffdcf79f86a7c1d5e2b97eb1:/bsd/isofs/cd9660/cd9660_bmap.c diff --git a/bsd/isofs/cd9660/cd9660_bmap.c b/bsd/isofs/cd9660/cd9660_bmap.c index f031630e2..53cbb55d9 100644 --- a/bsd/isofs/cd9660/cd9660_bmap.c +++ b/bsd/isofs/cd9660/cd9660_bmap.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2000 Apple Computer, Inc. All rights reserved. + * Copyright (c) 2000-2003 Apple Computer, Inc. All rights reserved. * * @APPLE_LICENSE_HEADER_START@ * @@ -65,76 +65,18 @@ #include #include #include -#include #include #include #include -/* - * Bmap converts the logical block number of a file to its physical block - * number on the disk. The conversion is done by using the logical block - * number to index into the data block (extent) for the file. - */ -int -cd9660_bmap(ap) - struct vop_bmap_args /* { - struct vnode *a_vp; - daddr_t a_bn; - struct vnode **a_vpp; - daddr_t *a_bnp; - int *a_runp; - } */ *ap; -{ - struct iso_node *ip = VTOI(ap->a_vp); - daddr_t lblkno = ap->a_bn; - int bshift; - - /* - * Check for underlying vnode requests and ensure that logical - * to physical mapping is requested. - */ - if (ap->a_vpp != NULL) - *ap->a_vpp = ip->i_devvp; - if (ap->a_bnp == NULL) - return (0); - - /* - * Compute the requested block number - */ - bshift = ip->i_mnt->im_bshift; - *ap->a_bnp = (ip->iso_start + lblkno); - - /* - * Determine maximum number of readahead blocks following the - * requested block. - */ - if (ap->a_runp) { - int nblk; - - nblk = (ip->i_size >> bshift) - (lblkno + 1); - if (nblk <= 0) - *ap->a_runp = 0; - else if (nblk >= (MAXBSIZE >> bshift)) - *ap->a_runp = (MAXBSIZE >> bshift) - 1; - else - *ap->a_runp = nblk; - } - - return (0); -} /* blktooff converts a logical block number to a file offset */ int -cd9660_blktooff(ap) - struct vop_blktooff_args /* { - struct vnode *a_vp; - daddr_t a_lblkno; - off_t *a_offset; - } */ *ap; +cd9660_blktooff(struct vnop_blktooff_args *ap) { register struct iso_node *ip; - register struct iso_mnt *imp; + register struct iso_mnt *imp; if (ap->a_vp == NULL) return (EINVAL); @@ -148,12 +90,7 @@ cd9660_blktooff(ap) /* offtoblk converts a file offset to a logical block number */ int -cd9660_offtoblk(ap) -struct vop_offtoblk_args /* { - struct vnode *a_vp; - off_t a_offset; - daddr_t *a_lblkno; - } */ *ap; +cd9660_offtoblk(struct vnop_offtoblk_args *ap) { register struct iso_node *ip; register struct iso_mnt *imp; @@ -164,24 +101,17 @@ struct vop_offtoblk_args /* { ip = VTOI(ap->a_vp); imp = ip->i_mnt; - *ap->a_lblkno = (daddr_t)lblkno(imp, ap->a_offset); + *ap->a_lblkno = (daddr64_t)lblkno(imp, ap->a_offset); return (0); } int -cd9660_cmap(ap) -struct vop_cmap_args /* { - struct vnode *a_vp; - off_t a_offset; - size_t a_size; - daddr_t *a_bpn; - size_t *a_run; - void *a_poff; -} */ *ap; +cd9660_blockmap(struct vnop_blockmap_args *ap) { struct iso_node *ip = VTOI(ap->a_vp); size_t cbytes; int devBlockSize = 0; + off_t offset = ap->a_foffset; /* * Check for underlying vnode requests and ensure that logical @@ -190,17 +120,31 @@ struct vop_cmap_args /* { if (ap->a_bpn == NULL) return (0); - VOP_DEVBLOCKSIZE(ip->i_devvp, &devBlockSize); + devBlockSize = vfs_devblocksize(vnode_mount(ap->a_vp)); - *ap->a_bpn = (daddr_t)(ip->iso_start + lblkno(ip->i_mnt, ap->a_foffset)); + /* + * Associated files have an Apple Double header + */ + if (ip->i_flag & ISO_ASSOCIATED) { + if (offset < ADH_SIZE) { + if (ap->a_run) + *ap->a_run = 0; + *ap->a_bpn = (daddr64_t)-1; + goto out; + } else { + offset -= ADH_SIZE; + } + } + + *ap->a_bpn = (daddr64_t)(ip->iso_start + lblkno(ip->i_mnt, offset)); /* * Determine maximum number of contiguous bytes following the * requested offset. */ if (ap->a_run) { - if (ip->i_size > ap->a_foffset) - cbytes = ip->i_size - ap->a_foffset; + if (ip->i_size > offset) + cbytes = ip->i_size - offset; else cbytes = 0; @@ -208,9 +152,9 @@ struct vop_cmap_args /* { *ap->a_run = MIN(cbytes, ap->a_size); }; - +out: if (ap->a_poff) - *(int *)ap->a_poff = (long)ap->a_foffset & (devBlockSize - 1); + *(int *)ap->a_poff = (long)offset & (devBlockSize - 1); return (0); }