|
|
1.1 ! root 1: /* ! 2: * Copyright (c) 1999 Apple Computer, Inc. All rights reserved. ! 3: * ! 4: * @APPLE_LICENSE_HEADER_START@ ! 5: * ! 6: * Portions Copyright (c) 1999 Apple Computer, Inc. All Rights ! 7: * Reserved. This file contains Original Code and/or Modifications of ! 8: * Original Code as defined in and that are subject to the Apple Public ! 9: * Source License Version 1.1 (the "License"). You may not use this file ! 10: * except in compliance with the License. Please obtain a copy of the ! 11: * License at http://www.apple.com/publicsource and read it before using ! 12: * this file. ! 13: * ! 14: * The Original Code and all software distributed under the License are ! 15: * distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, EITHER ! 16: * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES, ! 17: * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY, ! 18: * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT. Please see the ! 19: * License for the specific language governing rights and limitations ! 20: * under the License. ! 21: * ! 22: * @APPLE_LICENSE_HEADER_END@ ! 23: */ ! 24: ! 25: /* $NetBSD: lfs_subr.c,v 1.2 1994/06/29 06:47:00 cgd Exp $ */ ! 26: ! 27: /* ! 28: * Copyright (c) 1991, 1993 ! 29: * The Regents of the University of California. All rights reserved. ! 30: * ! 31: * Redistribution and use in source and binary forms, with or without ! 32: * modification, are permitted provided that the following conditions ! 33: * are met: ! 34: * 1. Redistributions of source code must retain the above copyright ! 35: * notice, this list of conditions and the following disclaimer. ! 36: * 2. Redistributions in binary form must reproduce the above copyright ! 37: * notice, this list of conditions and the following disclaimer in the ! 38: * documentation and/or other materials provided with the distribution. ! 39: * 3. All advertising materials mentioning features or use of this software ! 40: * must display the following acknowledgement: ! 41: * This product includes software developed by the University of ! 42: * California, Berkeley and its contributors. ! 43: * 4. Neither the name of the University nor the names of its contributors ! 44: * may be used to endorse or promote products derived from this software ! 45: * without specific prior written permission. ! 46: * ! 47: * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND ! 48: * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE ! 49: * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ! 50: * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE ! 51: * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL ! 52: * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS ! 53: * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) ! 54: * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT ! 55: * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY ! 56: * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF ! 57: * SUCH DAMAGE. ! 58: * ! 59: * @(#)lfs_subr.c 8.2 (Berkeley) 9/21/93 ! 60: */ ! 61: ! 62: #include <sys/param.h> ! 63: #include <sys/namei.h> ! 64: #include <sys/vnode.h> ! 65: #include <sys/buf.h> ! 66: #include <sys/mount.h> ! 67: #include <sys/malloc.h> ! 68: #include <sys/proc.h> ! 69: ! 70: #include <ufs/ufs/quota.h> ! 71: #include <ufs/ufs/inode.h> ! 72: #include <ufs/lfs/lfs.h> ! 73: #include <ufs/lfs/lfs_extern.h> ! 74: ! 75: /* ! 76: * Return buffer with the contents of block "offset" from the beginning of ! 77: * directory "ip". If "res" is non-zero, fill it in with a pointer to the ! 78: * remaining space in the directory. ! 79: */ ! 80: int ! 81: lfs_blkatoff(ap) ! 82: struct vop_blkatoff_args /* { ! 83: struct vnode *a_vp; ! 84: off_t a_offset; ! 85: char **a_res; ! 86: struct buf **a_bpp; ! 87: } */ *ap; ! 88: { ! 89: register struct lfs *fs; ! 90: struct inode *ip; ! 91: struct buf *bp; ! 92: daddr_t lbn; ! 93: int bsize, error; ! 94: ! 95: ip = VTOI(ap->a_vp); ! 96: fs = ip->i_lfs; ! 97: lbn = lblkno(fs, ap->a_offset); ! 98: bsize = blksize(fs); ! 99: ! 100: *ap->a_bpp = NULL; ! 101: if (error = bread(ap->a_vp, lbn, bsize, NOCRED, &bp)) { ! 102: brelse(bp); ! 103: return (error); ! 104: } ! 105: if (ap->a_res) ! 106: *ap->a_res = (char *)bp->b_data + blkoff(fs, ap->a_offset); ! 107: *ap->a_bpp = bp; ! 108: return (0); ! 109: } ! 110: ! 111: ! 112: /* ! 113: * lfs_seglock -- ! 114: * Single thread the segment writer. ! 115: */ ! 116: void ! 117: lfs_seglock(fs, flags) ! 118: struct lfs *fs; ! 119: unsigned long flags; ! 120: { ! 121: struct segment *sp; ! 122: int s; ! 123: ! 124: if (fs->lfs_seglock) ! 125: if (fs->lfs_lockpid == curproc->p_pid) { ! 126: ++fs->lfs_seglock; ! 127: fs->lfs_sp->seg_flags |= flags; ! 128: return; ! 129: } else while (fs->lfs_seglock) ! 130: (void)tsleep(&fs->lfs_seglock, PRIBIO + 1, ! 131: "lfs seglock", 0); ! 132: ! 133: fs->lfs_seglock = 1; ! 134: fs->lfs_lockpid = curproc->p_pid; ! 135: ! 136: // sp = fs->lfs_sp = malloc(sizeof(struct segment), M_SEGMENT, M_WAITOK); ! 137: MALLOC(fs->lfs_sp, struct segment *, sizeof(struct segment), M_SEGMENT, M_WAITOK); ! 138: sp = fs->lfs_sp; ! 139: // sp->bpp = malloc(((LFS_SUMMARY_SIZE - sizeof(SEGSUM)) / ! 140: // sizeof(daddr_t) + 1) * sizeof(struct buf *), M_SEGMENT, M_WAITOK); ! 141: MALLOC(sp->bpp, caddr_t, ((LFS_SUMMARY_SIZE - sizeof(SEGSUM)) / ! 142: sizeof(daddr_t) + 1) * sizeof(struct buf *), M_SEGMENT, M_WAITOK); ! 143: sp->seg_flags = flags; ! 144: sp->vp = NULL; ! 145: (void) lfs_initseg(fs); ! 146: ! 147: /* ! 148: * Keep a cumulative count of the outstanding I/O operations. If the ! 149: * disk drive catches up with us it could go to zero before we finish, ! 150: * so we artificially increment it by one until we've scheduled all of ! 151: * the writes we intend to do. ! 152: */ ! 153: s = splbio(); ! 154: ++fs->lfs_iocount; ! 155: splx(s); ! 156: } ! 157: /* ! 158: * lfs_segunlock -- ! 159: * Single thread the segment writer. ! 160: */ ! 161: void ! 162: lfs_segunlock(fs) ! 163: struct lfs *fs; ! 164: { ! 165: struct segment *sp; ! 166: unsigned long sync, ckp; ! 167: int s; ! 168: ! 169: if (fs->lfs_seglock == 1) { ! 170: ! 171: sp = fs->lfs_sp; ! 172: sync = sp->seg_flags & SEGM_SYNC; ! 173: ckp = sp->seg_flags & SEGM_CKP; ! 174: if (sp->bpp != sp->cbpp) { ! 175: /* Free allocated segment summary */ ! 176: fs->lfs_offset -= LFS_SUMMARY_SIZE / DEV_BSIZE; ! 177: brelvp(*sp->bpp); ! 178: free((*sp->bpp)->b_data, M_SEGMENT); ! 179: free(*sp->bpp, M_SEGMENT); ! 180: } else ! 181: printf ("unlock to 0 with no summary"); ! 182: free(sp->bpp, M_SEGMENT); ! 183: free(sp, M_SEGMENT); ! 184: ! 185: /* ! 186: * If the I/O count is non-zero, sleep until it reaches zero. ! 187: * At the moment, the user's process hangs around so we can ! 188: * sleep. ! 189: */ ! 190: s = splbio(); ! 191: --fs->lfs_iocount; ! 192: /* ! 193: * We let checkpoints happen asynchronously. That means ! 194: * that during recovery, we have to roll forward between ! 195: * the two segments described by the first and second ! 196: * superblocks to make sure that the checkpoint described ! 197: * by a superblock completed. ! 198: */ ! 199: if (sync && fs->lfs_iocount) ! 200: (void)tsleep(&fs->lfs_iocount, PRIBIO + 1, "lfs vflush", 0); ! 201: splx(s); ! 202: if (ckp) { ! 203: fs->lfs_nactive = 0; ! 204: lfs_writesuper(fs); ! 205: } ! 206: --fs->lfs_seglock; ! 207: fs->lfs_lockpid = 0; ! 208: wakeup(&fs->lfs_seglock); ! 209: } else if (fs->lfs_seglock == 0) { ! 210: panic ("Seglock not held"); ! 211: } else { ! 212: --fs->lfs_seglock; ! 213: } ! 214: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.