12926Sphk/*-
22926Sphk * SPDX-License-Identifier: BSD-3-Clause
32926Sphk *
493150Sphk * Copyright (c) 1980, 1986, 1993
52926Sphk *	The Regents of the University of California.  All rights reserved.
62926Sphk *
72926Sphk * Redistribution and use in source and binary forms, with or without
82926Sphk * modification, are permitted provided that the following conditions
950479Speter * are met:
102926Sphk * 1. Redistributions of source code must retain the above copyright
112926Sphk *    notice, this list of conditions and the following disclaimer.
122926Sphk * 2. Redistributions in binary form must reproduce the above copyright
132886Sphk *    notice, this list of conditions and the following disclaimer in the
142886Sphk *    documentation and/or other materials provided with the distribution.
152886Sphk * 3. Neither the name of the University nor the names of its contributors
162886Sphk *    may be used to endorse or promote products derived from this software
172886Sphk *    without specific prior written permission.
182886Sphk *
192886Sphk * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
202886Sphk * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
212886Sphk * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
222886Sphk * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
232886Sphk * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
242886Sphk * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
252886Sphk * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
262886Sphk * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
272886Sphk * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
282886Sphk * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
292886Sphk * SUCH DAMAGE.
302886Sphk */
312886Sphk
322886Sphk#include <sys/param.h>
332886Sphk#include <sys/stat.h>
342886Sphk
352886Sphk#include <ufs/ufs/dinode.h>
362886Sphk#include <ufs/ffs/fs.h>
372886Sphk
382886Sphk#include <err.h>
392886Sphk#include <stdint.h>
402886Sphk#include <string.h>
412886Sphk
422886Sphk#include "fsck.h"
432886Sphk
442886Sphkvoid
452886Sphkpass4(void)
462886Sphk{
472886Sphk	ino_t inumber;
482886Sphk	struct inode ip;
492886Sphk	struct inodesc idesc;
502886Sphk	int i, n, cg;
512886Sphk
522948Sphk	memset(&idesc, 0, sizeof(struct inodesc));
532948Sphk	idesc.id_func = freeblock;
542948Sphk	for (cg = 0; cg < sblock.fs_ncg; cg++) {
552948Sphk		if (got_siginfo) {
562886Sphk			printf("%s: phase 4: cyl group %d of %d (%d%%)\n",
572886Sphk			    cdevname, cg, sblock.fs_ncg,
582886Sphk			    cg * 100 / sblock.fs_ncg);
592948Sphk			got_siginfo = 0;
602948Sphk		}
612886Sphk		if (got_sigalarm) {
622886Sphk			setproctitle("%s p4 %d%%", cdevname,
632886Sphk			    cg * 100 / sblock.fs_ncg);
642886Sphk			got_sigalarm = 0;
652886Sphk		}
662886Sphk		inumber = cg * sblock.fs_ipg;
672886Sphk		for (i = 0; i < inostathead[cg].il_numalloced; i++, inumber++) {
682948Sphk			if (inumber < UFS_ROOTINO)
692886Sphk				continue;
702886Sphk			idesc.id_number = inumber;
712886Sphk			idesc.id_type = inoinfo(inumber)->ino_idtype;
722948Sphk			switch (inoinfo(inumber)->ino_state) {
732886Sphk
742886Sphk			case FZLINK:
752886Sphk			case DZLINK:
762886Sphk				if (inoinfo(inumber)->ino_linkcnt == 0) {
772948Sphk					clri(&idesc, "UNREF", 1);
782948Sphk					break;
792948Sphk				}
802886Sphk				/* fall through */
812886Sphk
822886Sphk			case FSTATE:
832886Sphk			case DFOUND:
842886Sphk				n = inoinfo(inumber)->ino_linkcnt;
852886Sphk				if (n) {
862886Sphk					adjust(&idesc, (short)n);
872886Sphk					break;
882886Sphk				}
892886Sphk				break;
902886Sphk
912886Sphk			case DSTATE:
922886Sphk				clri(&idesc, "UNREF", 1);
932886Sphk				break;
942886Sphk
952886Sphk			case DCLEAR:
962886Sphk				/* if on snapshot, already cleared */
972886Sphk				if (cursnapshot != 0)
982886Sphk					break;
992886Sphk				ginode(inumber, &ip);
1002886Sphk				if (DIP(ip.i_dp, di_size) == 0) {
1012886Sphk					clri(&idesc, "ZERO LENGTH", 1);
10213917Sphk					irelse(&ip);
10313917Sphk					break;
10413917Sphk				}
10513917Sphk				irelse(&ip);
10613917Sphk				/* fall through */
10713917Sphk			case FCLEAR:
10813917Sphk				clri(&idesc, "BAD/DUP", 1);
10913917Sphk				break;
11013917Sphk
11113917Sphk			case USTATE:
11213917Sphk				break;
11313917Sphk
11413917Sphk			default:
11513917Sphk				errx(EEXIT, "BAD STATE %d FOR INODE I=%ju",
11613917Sphk				    inoinfo(inumber)->ino_state,
11713917Sphk				    (uintmax_t)inumber);
11813917Sphk			}
11913917Sphk		}
12013917Sphk	}
12113917Sphk}
12213917Sphk