1: #
   2: #include "../param.h"
   3: #include "../systm.h"
   4: #include "../user.h"
   5: #include "../inode.h"
   6: #include "../filsys.h"
   7: #include "../conf.h"
   8: #include "../buf.h"
   9: 
  10: /*
  11:  * Look up an inode by device,inumber.
  12:  * If it is in core (in the inode structure),
  13:  * honor the locking protocol.
  14:  * If it is not in core, read it in from the
  15:  * specified device.
  16:  * If the inode is mounted on, perform
  17:  * the indicated indirection.
  18:  * In all cases, a pointer to a locked
  19:  * inode structure is returned.
  20:  *
  21:  * printf warning: no inodes -- if the inode
  22:  *	structure is full
  23:  * panic: no imt -- if the mounted file
  24:  *	system is not in the mount table.
  25:  *	"cannot happen"
  26:  */
  27: iget(dev, ino)
  28: {
  29:     register struct inode *p;
  30:     register *ip2;
  31:     int *ip1;
  32:     register struct mount *ip;
  33: 
  34: loop:
  35:     ip = NULL;
  36:     for(p = &inode[0]; p < &inode[NINODE]; p++) {
  37:         if(dev==p->i_dev && ino==p->i_number) {
  38:             if((p->i_flag&ILOCK) != 0) {
  39:                 p->i_flag =| IWANT;
  40:                 sleep(p, PINOD);
  41:                 goto loop;
  42:             }
  43:             if((p->i_flag&IMOUNT) != 0) {
  44:                 for(ip = &mount[0]; ip < &mount[NMOUNT]; ip++)
  45:                 if(ip->m_inodp == p) {
  46:                     dev = ip->m_dev;
  47:                     ino = ROOTINO;
  48:                     goto loop;
  49:                 }
  50:                 panic("no imt");
  51:             }
  52:             p->i_count++;
  53:             p->i_flag =| ILOCK;
  54:             return(p);
  55:         }
  56:         if(ip==NULL && p->i_count==0)
  57:             ip = p;
  58:     }
  59:     if((p=ip) == NULL) {
  60:         printf("Inode table overflow\n");
  61:         u.u_error = ENFILE;
  62:         return(NULL);
  63:     }
  64:     p->i_dev = dev;
  65:     p->i_number = ino;
  66:     p->i_flag = ILOCK;
  67:     p->i_count++;
  68:     p->i_lastr = -1;
  69:     ip = bread(dev, ldiv(ino+31,16));
  70:     /*
  71: 	 * Check I/O errors
  72: 	 */
  73:     if (ip->b_flags&B_ERROR) {
  74:         brelse(ip);
  75:         iput(p);
  76:         return(NULL);
  77:     }
  78:     ip1 = ip->b_addr + 32*lrem(ino+31, 16);
  79:     ip2 = &p->i_mode;
  80:     while(ip2 < &p->i_addr[8])
  81:         *ip2++ = *ip1++;
  82:     brelse(ip);
  83:     return(p);
  84: }
  85: 
  86: /*
  87:  * Decrement reference count of
  88:  * an inode structure.
  89:  * On the last reference,
  90:  * write the inode out and if necessary,
  91:  * truncate and deallocate the file.
  92:  */
  93: iput(p)
  94: struct inode *p;
  95: {
  96:     register *rp;
  97: 
  98:     rp = p;
  99:     if(rp->i_count == 1) {
 100:         rp->i_flag =| ILOCK;
 101:         if(rp->i_nlink <= 0) {
 102:             itrunc(rp);
 103:             rp->i_mode = 0;
 104:             ifree(rp->i_dev, rp->i_number);
 105:         }
 106:         iupdat(rp, time);
 107:         prele(rp);
 108:         rp->i_flag = 0;
 109:         rp->i_number = 0;
 110:     }
 111:     rp->i_count--;
 112:     prele(rp);
 113: }
 114: 
 115: /*
 116:  * Check accessed and update flags on
 117:  * an inode structure.
 118:  * If either is on, update the inode
 119:  * with the corresponding dates
 120:  * set to the argument tm.
 121:  */
 122: iupdat(p, tm)
 123: int *p;
 124: int *tm;
 125: {
 126:     register *ip1, *ip2, *rp;
 127:     int *bp, i;
 128: 
 129:     rp = p;
 130:     if((rp->i_flag&(IUPD|IACC)) != 0) {
 131:         if(getfs(rp->i_dev)->s_ronly)
 132:             return;
 133:         i = rp->i_number+31;
 134:         bp = bread(rp->i_dev, ldiv(i,16));
 135:         ip1 = bp->b_addr + 32*lrem(i, 16);
 136:         ip2 = &rp->i_mode;
 137:         while(ip2 < &rp->i_addr[8])
 138:             *ip1++ = *ip2++;
 139:         if(rp->i_flag&IACC) {
 140:             *ip1++ = time[0];
 141:             *ip1++ = time[1];
 142:         } else
 143:             ip1 =+ 2;
 144:         if(rp->i_flag&IUPD) {
 145:             *ip1++ = *tm++;
 146:             *ip1++ = *tm;
 147:         }
 148:         bwrite(bp);
 149:     }
 150: }
 151: 
 152: /*
 153:  * Free all the disk blocks associated
 154:  * with the specified inode structure.
 155:  * The blocks of the file are removed
 156:  * in reverse order. This FILO
 157:  * algorithm will tend to maintain
 158:  * a contiguous free list much longer
 159:  * than FIFO.
 160:  */
 161: itrunc(ip)
 162: int *ip;
 163: {
 164:     register *rp, *bp, *cp;
 165:     int *dp, *ep;
 166: 
 167:     rp = ip;
 168:     if((rp->i_mode&(IFCHR&IFBLK)) != 0)
 169:         return;
 170:     for(ip = &rp->i_addr[7]; ip >= &rp->i_addr[0]; ip--)
 171:     if(*ip) {
 172:         if((rp->i_mode&ILARG) != 0) {
 173:             bp = bread(rp->i_dev, *ip);
 174:             for(cp = bp->b_addr+512; cp >= bp->b_addr; cp--)
 175:             if(*cp) {
 176:                 if(ip == &rp->i_addr[7]) {
 177:                     dp = bread(rp->i_dev, *cp);
 178:                     for(ep = dp->b_addr+512; ep >= dp->b_addr; ep--)
 179:                     if(*ep)
 180:                         free(rp->i_dev, *ep);
 181:                     brelse(dp);
 182:                 }
 183:                 free(rp->i_dev, *cp);
 184:             }
 185:             brelse(bp);
 186:         }
 187:         free(rp->i_dev, *ip);
 188:         *ip = 0;
 189:     }
 190:     rp->i_mode =& ~ILARG;
 191:     rp->i_size0 = 0;
 192:     rp->i_size1 = 0;
 193:     rp->i_flag =| IUPD;
 194: }
 195: 
 196: /*
 197:  * Make a new file.
 198:  */
 199: maknode(mode)
 200: {
 201:     register *ip;
 202: 
 203:     ip = ialloc(u.u_pdir->i_dev);
 204:     if (ip==NULL)
 205:         return(NULL);
 206:     ip->i_flag =| IACC|IUPD;
 207:     ip->i_mode = mode|IALLOC;
 208:     ip->i_nlink = 1;
 209:     ip->i_uid = u.u_uid;
 210:     ip->i_gid = u.u_gid;
 211:     wdir(ip);
 212:     return(ip);
 213: }
 214: 
 215: /*
 216:  * Write a directory entry with
 217:  * parameters left as side effects
 218:  * to a call to namei.
 219:  */
 220: wdir(ip)
 221: int *ip;
 222: {
 223:     register char *cp1, *cp2;
 224: 
 225:     u.u_dent.u_ino = ip->i_number;
 226:     cp1 = &u.u_dent.u_name[0];
 227:     for(cp2 = &u.u_dbuf[0]; cp2 < &u.u_dbuf[DIRSIZ];)
 228:         *cp1++ = *cp2++;
 229:     u.u_count = DIRSIZ+2;
 230:     u.u_segflg = 1;
 231:     u.u_base = &u.u_dent;
 232:     writei(u.u_pdir);
 233:     iput(u.u_pdir);
 234: }

Defined functions

iget defined in line 27; used 6 times
iput defined in line 93; used 28 times
itrunc defined in line 161; used 3 times
iupdat defined in line 122; used 3 times
maknode defined in line 199; used 3 times
wdir defined in line 220; used 2 times
Last modified: 1975-07-18
Generated: 2016-12-26
Generated by src2html V0.67
page hit count: 1080
Valid CSS Valid XHTML 1.0 Strict