Skip site navigation (1)Skip section navigation (2)
Date:      Mon, 26 Apr 2021 23:44:44 GMT
From:      Kirk McKusick <mckusick@FreeBSD.org>
To:        src-committers@FreeBSD.org, dev-commits-src-all@FreeBSD.org, dev-commits-src-main@FreeBSD.org
Subject:   git: 84a0e3f95700 - main - Make fsck_ffs more persistent in creating a lost+found directory.
Message-ID:  <202104262344.13QNiiJr051683@gitrepo.freebsd.org>

next in thread | raw e-mail | index | archive | help
The branch main has been updated by mckusick:

URL: https://cgit.FreeBSD.org/src/commit/?id=84a0e3f95700733695115fb2a9d84d6666efe5d9

commit 84a0e3f95700733695115fb2a9d84d6666efe5d9
Author:     Kirk McKusick <mckusick@FreeBSD.org>
AuthorDate: 2021-04-26 23:47:27 +0000
Commit:     Kirk McKusick <mckusick@FreeBSD.org>
CommitDate: 2021-04-26 23:48:30 +0000

    Make fsck_ffs more persistent in creating a lost+found directory.
    
    When fsck_ffs is running in interactive mode and finds unlinked files,
    it offers to either unlink them or place them in a lost+found directory.
    If the lost+found directory option is requested and no lost+found
    directory exists, fsck_ffs offers to create one. When creating one,
    it must allocate an inode and a filesystem block. It attempts to
    allocate them from the first cylinder group. If the first cylinder
    group has a bad check hash, it gives up.
    
    This change expands the search into later cylinder groups when the
    first one fails with a bad check hash.
    
    Reported by:  Chuck Silvers
    Tested by:    Chuck Silvers
    MFC after:    1 week
    Sponsored by: Netflix
---
 sbin/fsck_ffs/dir.c    |  2 ++
 sbin/fsck_ffs/fsutil.c |  6 ++++--
 sbin/fsck_ffs/inode.c  | 19 +++++++++++++------
 3 files changed, 19 insertions(+), 8 deletions(-)

diff --git a/sbin/fsck_ffs/dir.c b/sbin/fsck_ffs/dir.c
index e88d1650ce5a..e806f113ff16 100644
--- a/sbin/fsck_ffs/dir.c
+++ b/sbin/fsck_ffs/dir.c
@@ -801,6 +801,8 @@ allocdir(ino_t parent, ino_t request, int mode)
 	struct dirtemplate *dirp;
 
 	ino = allocino(request, IFDIR|mode);
+	if (ino == 0)
+		return (0);
 	dirp = &dirhead;
 	dirp->dot_ino = ino;
 	dirp->dotdot_ino = parent;
diff --git a/sbin/fsck_ffs/fsutil.c b/sbin/fsck_ffs/fsutil.c
index ca19f6726af5..276d543dedc6 100644
--- a/sbin/fsck_ffs/fsutil.c
+++ b/sbin/fsck_ffs/fsutil.c
@@ -1048,8 +1048,10 @@ allocblk(long frags)
 			cg = dtog(&sblock, i + j);
 			cgbp = cglookup(cg);
 			cgp = cgbp->b_un.b_cg;
-			if (!check_cgmagic(cg, cgbp, 0))
-				return (0);
+			if (!check_cgmagic(cg, cgbp, 0)) {
+				i = (cg + 1) * sblock.fs_fpg - sblock.fs_frag;
+				continue;
+			}
 			baseblk = dtogd(&sblock, i + j);
 			for (k = 0; k < frags; k++) {
 				setbmap(i + j + k);
diff --git a/sbin/fsck_ffs/inode.c b/sbin/fsck_ffs/inode.c
index 020a69dd72f8..d4e5723f559f 100644
--- a/sbin/fsck_ffs/inode.c
+++ b/sbin/fsck_ffs/inode.c
@@ -902,22 +902,29 @@ allocino(ino_t request, int type)
 	union dinode *dp;
 	struct bufarea *cgbp;
 	struct cg *cgp;
-	int cg;
+	int cg, anyino;
 
-	if (request == 0)
+	anyino = 0;
+	if (request == 0) {
 		request = UFS_ROOTINO;
-	else if (inoinfo(request)->ino_state != USTATE)
+		anyino = 1;
+	} else if (inoinfo(request)->ino_state != USTATE)
 		return (0);
+retry:
 	for (ino = request; ino < maxino; ino++)
 		if (inoinfo(ino)->ino_state == USTATE)
 			break;
-	if (ino == maxino)
+	if (ino >= maxino)
 		return (0);
 	cg = ino_to_cg(&sblock, ino);
 	cgbp = cglookup(cg);
 	cgp = cgbp->b_un.b_cg;
-	if (!check_cgmagic(cg, cgbp, 0))
-		return (0);
+	if (!check_cgmagic(cg, cgbp, 0)) {
+		if (anyino == 0)
+			return (0);
+		request = (cg + 1) * sblock.fs_ipg;
+		goto retry;
+	}
 	setbit(cg_inosused(cgp), ino % sblock.fs_ipg);
 	cgp->cg_cs.cs_nifree--;
 	switch (type & IFMT) {



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?202104262344.13QNiiJr051683>