1 /* 2 * Copyright (c) 1980, 1986 The Regents of the University of California. 3 * All rights reserved. 4 * 5 * %sccs.include.redist.c% 6 */ 7 8 #ifndef lint 9 static char sccsid[] = "@(#)pass4.c 5.11 (Berkeley) 11/04/91"; 10 #endif /* not lint */ 11 12 #include <sys/param.h> 13 #include <ufs/ufs/dinode.h> 14 #include <ufs/ffs/fs.h> 15 #include <stdlib.h> 16 #include <string.h> 17 #include "fsck.h" 18 19 int pass4check(); 20 21 pass4() 22 { 23 register ino_t inumber; 24 register struct zlncnt *zlnp; 25 struct dinode *dp; 26 struct inodesc idesc; 27 int n; 28 29 bzero((char *)&idesc, sizeof(struct inodesc)); 30 idesc.id_type = ADDR; 31 idesc.id_func = pass4check; 32 for (inumber = ROOTINO; inumber <= lastino; inumber++) { 33 idesc.id_number = inumber; 34 switch (statemap[inumber]) { 35 36 case FSTATE: 37 case DFOUND: 38 n = lncntp[inumber]; 39 if (n) 40 adjust(&idesc, (short)n); 41 else { 42 for (zlnp = zlnhead; zlnp; zlnp = zlnp->next) 43 if (zlnp->zlncnt == inumber) { 44 zlnp->zlncnt = zlnhead->zlncnt; 45 zlnp = zlnhead; 46 zlnhead = zlnhead->next; 47 free((char *)zlnp); 48 clri(&idesc, "UNREF", 1); 49 break; 50 } 51 } 52 break; 53 54 case DSTATE: 55 clri(&idesc, "UNREF", 1); 56 break; 57 58 case DCLEAR: 59 dp = ginode(inumber); 60 if (dp->di_size == 0) { 61 clri(&idesc, "ZERO LENGTH", 1); 62 break; 63 } 64 /* fall through */ 65 case FCLEAR: 66 clri(&idesc, "BAD/DUP", 1); 67 break; 68 69 case USTATE: 70 break; 71 72 default: 73 errexit("BAD STATE %d FOR INODE I=%d", 74 statemap[inumber], inumber); 75 } 76 } 77 } 78 79 pass4check(idesc) 80 register struct inodesc *idesc; 81 { 82 register struct dups *dlp; 83 int nfrags, res = KEEPON; 84 daddr_t blkno = idesc->id_blkno; 85 86 for (nfrags = idesc->id_numfrags; nfrags > 0; blkno++, nfrags--) { 87 if (chkrange(blkno, 1)) { 88 res = SKIP; 89 } else if (testbmap(blkno)) { 90 for (dlp = duplist; dlp; dlp = dlp->next) { 91 if (dlp->dup != blkno) 92 continue; 93 dlp->dup = duplist->dup; 94 dlp = duplist; 95 duplist = duplist->next; 96 free((char *)dlp); 97 break; 98 } 99 if (dlp == 0) { 100 clrbmap(blkno); 101 n_blks--; 102 } 103 } 104 } 105 return (res); 106 } 107