|
|
1.1 ! root 1: /* ! 2: * linux/fs/truncate.c ! 3: * ! 4: * (C) 1991 Linus Torvalds ! 5: */ ! 6: ! 7: #include <linux/sched.h> ! 8: #include <linux/minix_fs.h> ! 9: #include <linux/tty.h> ! 10: ! 11: #include <errno.h> ! 12: #include <fcntl.h> ! 13: #include <sys/stat.h> ! 14: ! 15: static int minix_free_ind(int dev,int block) ! 16: { ! 17: struct buffer_head * bh; ! 18: unsigned short * p; ! 19: int i; ! 20: int block_busy; ! 21: ! 22: if (!block) ! 23: return 1; ! 24: block_busy = 0; ! 25: if (bh=bread(dev,block)) { ! 26: p = (unsigned short *) bh->b_data; ! 27: for (i=0;i<512;i++,p++) ! 28: if (*p) ! 29: if (minix_free_block(dev,*p)) { ! 30: *p = 0; ! 31: bh->b_dirt = 1; ! 32: } else ! 33: block_busy = 1; ! 34: brelse(bh); ! 35: } ! 36: if (block_busy) ! 37: return 0; ! 38: else ! 39: return minix_free_block(dev,block); ! 40: } ! 41: ! 42: static int minix_free_dind(int dev,int block) ! 43: { ! 44: struct buffer_head * bh; ! 45: unsigned short * p; ! 46: int i; ! 47: int block_busy; ! 48: ! 49: if (!block) ! 50: return 1; ! 51: block_busy = 0; ! 52: if (bh=bread(dev,block)) { ! 53: p = (unsigned short *) bh->b_data; ! 54: for (i=0;i<512;i++,p++) ! 55: if (*p) ! 56: if (minix_free_ind(dev,*p)) { ! 57: *p = 0; ! 58: bh->b_dirt = 1; ! 59: } else ! 60: block_busy = 1; ! 61: brelse(bh); ! 62: } ! 63: if (block_busy) ! 64: return 0; ! 65: else ! 66: return minix_free_block(dev,block); ! 67: } ! 68: ! 69: void minix_truncate(struct inode * inode) ! 70: { ! 71: int i; ! 72: int block_busy; ! 73: ! 74: if (!(S_ISREG(inode->i_mode) || S_ISDIR(inode->i_mode) || ! 75: S_ISLNK(inode->i_mode))) ! 76: return; ! 77: repeat: ! 78: block_busy = 0; ! 79: for (i=0;i<7;i++) ! 80: if (inode->i_data[i]) { ! 81: if (minix_free_block(inode->i_dev,inode->i_data[i])) ! 82: inode->i_data[i]=0; ! 83: else ! 84: block_busy = 1; ! 85: } ! 86: if (minix_free_ind(inode->i_dev,inode->i_data[7])) ! 87: inode->i_data[7] = 0; ! 88: else ! 89: block_busy = 1; ! 90: if (minix_free_dind(inode->i_dev,inode->i_data[8])) ! 91: inode->i_data[8] = 0; ! 92: else ! 93: block_busy = 1; ! 94: inode->i_dirt = 1; ! 95: if (block_busy) { ! 96: current->counter = 0; ! 97: schedule(); ! 98: goto repeat; ! 99: } ! 100: inode->i_size = 0; ! 101: inode->i_mtime = inode->i_ctime = CURRENT_TIME; ! 102: } ! 103: ! 104: /* ! 105: * Called when a inode is released. Note that this is different ! 106: * from minix_open: open gets called at every open, but release ! 107: * gets called only when /all/ the files are closed. ! 108: */ ! 109: void minix_release(struct inode * inode, struct file * filp) ! 110: { ! 111: printk("minix_release not implemented\n"); ! 112: } ! 113: ! 114: static int check_char_dev(struct inode * inode, struct file * filp) ! 115: { ! 116: struct tty_struct *tty; ! 117: int min, dev; ! 118: ! 119: dev = inode->i_rdev; ! 120: if (MAJOR(dev) == 4 || MAJOR(dev) == 5) { ! 121: if (MAJOR(dev) == 5) ! 122: min = current->tty; ! 123: else ! 124: min = MINOR(dev); ! 125: if (min < 0) ! 126: return -1; ! 127: if ((IS_A_PTY_MASTER(min)) && (inode->i_count>1)) ! 128: return -1; ! 129: tty = TTY_TABLE(min); ! 130: if (!(filp->f_flags & O_NOCTTY) && ! 131: current->leader && ! 132: current->tty<0 && ! 133: tty->session==0) { ! 134: current->tty = min; ! 135: tty->session= current->session; ! 136: tty->pgrp = current->pgrp; ! 137: } ! 138: } ! 139: return 0; ! 140: } ! 141: ! 142: /* ! 143: * Called every time a minix-file is opened ! 144: */ ! 145: int minix_open(struct inode * inode, struct file * filp) ! 146: { ! 147: if (S_ISCHR(inode->i_mode)) { ! 148: if (check_char_dev(inode,filp)) ! 149: return -EAGAIN; ! 150: } else if (S_ISBLK(inode->i_mode)) ! 151: check_disk_change(inode->i_rdev); ! 152: filp->f_op = &minix_file_operations; ! 153: return 0; ! 154: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.