]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - sbin/fsck_ifs/pass4.c
This commit was generated by cvs2svn to compensate for changes in r37074,
[FreeBSD/FreeBSD.git] / sbin / fsck_ifs / pass4.c
1 /*
2  * Copyright (c) 1980, 1986, 1993
3  *      The Regents of the University of California.  All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions
7  * are met:
8  * 1. Redistributions of source code must retain the above copyright
9  *    notice, this list of conditions and the following disclaimer.
10  * 2. Redistributions in binary form must reproduce the above copyright
11  *    notice, this list of conditions and the following disclaimer in the
12  *    documentation and/or other materials provided with the distribution.
13  * 3. All advertising materials mentioning features or use of this software
14  *    must display the following acknowledgement:
15  *      This product includes software developed by the University of
16  *      California, Berkeley and its contributors.
17  * 4. Neither the name of the University nor the names of its contributors
18  *    may be used to endorse or promote products derived from this software
19  *    without specific prior written permission.
20  *
21  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
22  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
25  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
26  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
27  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
28  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
29  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
30  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
31  * SUCH DAMAGE.
32  */
33
34 #ifndef lint
35 #if 0
36 static const char sccsid[] = "@(#)pass4.c       8.4 (Berkeley) 4/28/95";
37 #endif
38 static const char rcsid[] =
39         "$Id$";
40 #endif /* not lint */
41
42 #include <sys/param.h>
43
44 #include <ufs/ufs/dinode.h>
45
46 #include <err.h>
47 #include <string.h>
48
49 #include "fsck.h"
50
51 void
52 pass4()
53 {
54         register ino_t inumber;
55         register struct zlncnt *zlnp;
56         struct dinode *dp;
57         struct inodesc idesc;
58         int n;
59
60         memset(&idesc, 0, sizeof(struct inodesc));
61         idesc.id_type = ADDR;
62         idesc.id_func = pass4check;
63         for (inumber = ROOTINO; inumber <= lastino; inumber++) {
64                 idesc.id_number = inumber;
65                 switch (statemap[inumber]) {
66
67                 case FSTATE:
68                 case DFOUND:
69                         n = lncntp[inumber];
70                         if (n)
71                                 adjust(&idesc, (short)n);
72                         else {
73                                 for (zlnp = zlnhead; zlnp; zlnp = zlnp->next)
74                                         if (zlnp->zlncnt == inumber) {
75                                                 zlnp->zlncnt = zlnhead->zlncnt;
76                                                 zlnp = zlnhead;
77                                                 zlnhead = zlnhead->next;
78                                                 free((char *)zlnp);
79                                                 clri(&idesc, "UNREF", 1);
80                                                 break;
81                                         }
82                         }
83                         break;
84
85                 case DSTATE:
86                         clri(&idesc, "UNREF", 1);
87                         break;
88
89                 case DCLEAR:
90                         dp = ginode(inumber);
91                         if (dp->di_size == 0) {
92                                 clri(&idesc, "ZERO LENGTH", 1);
93                                 break;
94                         }
95                         /* fall through */
96                 case FCLEAR:
97                         clri(&idesc, "BAD/DUP", 1);
98                         break;
99
100                 case USTATE:
101                         break;
102
103                 default:
104                         errx(EEXIT, "BAD STATE %d FOR INODE I=%d",
105                             statemap[inumber], inumber);
106                 }
107         }
108 }
109
110 int
111 pass4check(idesc)
112         register struct inodesc *idesc;
113 {
114         register struct dups *dlp;
115         int nfrags, res = KEEPON;
116         ufs_daddr_t blkno = idesc->id_blkno;
117
118         for (nfrags = idesc->id_numfrags; nfrags > 0; blkno++, nfrags--) {
119                 if (chkrange(blkno, 1)) {
120                         res = SKIP;
121                 } else if (testbmap(blkno)) {
122                         for (dlp = duplist; dlp; dlp = dlp->next) {
123                                 if (dlp->dup != blkno)
124                                         continue;
125                                 dlp->dup = duplist->dup;
126                                 dlp = duplist;
127                                 duplist = duplist->next;
128                                 free((char *)dlp);
129                                 break;
130                         }
131                         if (dlp == 0) {
132                                 clrbmap(blkno);
133                                 n_blks--;
134                         }
135                 }
136         }
137         return (res);
138 }