Little feedback on this,
If you have good reasons to keep the ability to convert and/or check
(very) old ffs on-disk formats, speak up now.
-Otto
On Mon, Apr 18, 2011 at 12:03:38PM +0200, Otto Moerbeek wrote:
> Hi,
>
> this removes the support to check and convert (very) old incarnations
> of ffs. This old code makes diffing to fsck_ffs in freebsd harder.
>
> We use and old filesystem in one place (the vax boot image), but that
> image does not need checking, and even Miod is not sure it's actually
> needed for the vaxen we support.
>
> -Otto
>
> Index: dir.c
> ===================================================================
> RCS file: /cvs/src/sbin/fsck_ffs/dir.c,v
> retrieving revision 1.25
> diff -u -p -r1.25 dir.c
> --- dir.c 16 Apr 2011 16:37:21 -0000 1.25
> +++ dir.c 17 Apr 2011 11:19:00 -0000
> @@ -115,29 +115,8 @@ dirscan(struct inodesc *idesc)
> for (dp = fsck_readdir(idesc); dp != NULL; dp = fsck_readdir(idesc)) {
> dsize = dp->d_reclen;
> memcpy(dbuf, dp, (size_t)dsize);
> -# if (BYTE_ORDER == LITTLE_ENDIAN)
> - if (!newinofmt) {
> - struct direct *tdp = (struct direct *)dbuf;
> - u_char tmp;
> -
> - tmp = tdp->d_namlen;
> - tdp->d_namlen = tdp->d_type;
> - tdp->d_type = tmp;
> - }
> -# endif
> idesc->id_dirp = (struct direct *)dbuf;
> if ((n = (*idesc->id_func)(idesc)) & ALTERED) {
> -# if (BYTE_ORDER == LITTLE_ENDIAN)
> - if (!newinofmt && !doinglevel2) {
> - struct direct *tdp;
> - u_char tmp;
> -
> - tdp = (struct direct *)dbuf;
> - tmp = tdp->d_namlen;
> - tdp->d_namlen = tdp->d_type;
> - tdp->d_type = tmp;
> - }
> -# endif
> bp = getdirblk(idesc->id_blkno, blksiz);
> memcpy(bp->b_un.b_buf + idesc->id_loc - dsize, dbuf,
> (size_t)dsize);
> @@ -230,19 +209,9 @@ dircheck(struct inodesc *idesc, struct d
> return (0);
> if (dp->d_ino == 0)
> return (1);
> - size = DIRSIZ(!newinofmt, dp);
> -# if (BYTE_ORDER == LITTLE_ENDIAN)
> - if (!newinofmt) {
> - type = dp->d_namlen;
> - namlen = dp->d_type;
> - } else {
> - namlen = dp->d_namlen;
> - type = dp->d_type;
> - }
> -# else
> - namlen = dp->d_namlen;
> - type = dp->d_type;
> -# endif
> + size = DIRSIZ(0, dp);
> + namlen = dp->d_namlen;
> + type = dp->d_type;
> if (dp->d_reclen < size ||
> idesc->id_filesize < size ||
> type > 15)
> @@ -334,27 +303,9 @@ mkentry(struct inodesc *idesc)
> dirp = (struct direct *)(((char *)dirp) + oldlen);
> dirp->d_ino = idesc->id_parent; /* ino to be entered is in id_parent */
> dirp->d_reclen = newent.d_reclen;
> - if (newinofmt)
> - dirp->d_type = GET_ITYPE(idesc->id_parent);
> - else
> - dirp->d_type = 0;
> + dirp->d_type = GET_ITYPE(idesc->id_parent);
> dirp->d_namlen = newent.d_namlen;
> memcpy(dirp->d_name, idesc->id_name, (size_t)dirp->d_namlen + 1);
> -# if (BYTE_ORDER == LITTLE_ENDIAN)
> - /*
> - * If the entry was split, dirscan() will only reverse the byte
> - * order of the original entry, and not the new one, before
> - * writing it back out. So, we reverse the byte order here if
> - * necessary.
> - */
> - if (oldlen != 0 && !newinofmt && !doinglevel2) {
> - u_char tmp;
> -
> - tmp = dirp->d_namlen;
> - dirp->d_namlen = dirp->d_type;
> - dirp->d_type = tmp;
> - }
> -# endif
> return (ALTERED|STOP);
> }
>
> @@ -366,10 +317,7 @@ chgino(struct inodesc *idesc)
> if (memcmp(dirp->d_name, idesc->id_name, (int)dirp->d_namlen + 1))
> return (KEEPON);
> dirp->d_ino = idesc->id_parent;
> - if (newinofmt)
> - dirp->d_type = GET_ITYPE(idesc->id_parent);
> - else
> - dirp->d_type = 0;
> + dirp->d_type = GET_ITYPE(idesc->id_parent);
> return (ALTERED|STOP);
> }
>
> @@ -615,10 +563,7 @@ allocdir(ino_t parent, ino_t request, in
> struct inoinfo *inp;
>
> ino = allocino(request, IFDIR|mode);
> - if (newinofmt)
> - dirp = &dirhead;
> - else
> - dirp = (struct dirtemplate *)&odirhead;
> + dirp = &dirhead;
> dirp->dot_ino = ino;
> dirp->dotdot_ino = parent;
> dp = ginode(ino);
> Index: fsck.h
> ===================================================================
> RCS file: /cvs/src/sbin/fsck_ffs/fsck.h,v
> retrieving revision 1.24
> diff -u -p -r1.24 fsck.h
> --- fsck.h 16 Apr 2011 16:37:21 -0000 1.24
> +++ fsck.h 17 Apr 2011 11:16:15 -0000
> @@ -237,9 +237,6 @@ char yflag; /* assume a yes
> response *
> int bflag; /* location of alternate super block */
> int debug; /* output debugging info */
> int cvtlevel; /* convert to newer file system format */
> -int doinglevel1; /* converting to new cylinder group format */
> -int doinglevel2; /* converting to new inode format */
> -int newinofmt; /* filesystem has new inode format */
> char usedsoftdep; /* just fix soft dependency inconsistencies
> */
> int preen; /* just fix normal inconsistencies */
> char resolved; /* cleared if unresolved changes => not
> clean */
> Index: inode.c
> ===================================================================
> RCS file: /cvs/src/sbin/fsck_ffs/inode.c,v
> retrieving revision 1.34
> diff -u -p -r1.34 inode.c
> --- inode.c 16 Apr 2011 16:37:21 -0000 1.34
> +++ inode.c 17 Apr 2011 11:19:25 -0000
> @@ -650,8 +650,7 @@ allocino(ino_t request, int type)
> DIP_SET(dp, di_blocks, btodb(sblock.fs_fsize));
> n_files++;
> inodirty();
> - if (newinofmt)
> - SET_ITYPE(ino, IFTODT(type));
> + SET_ITYPE(ino, IFTODT(type));
> return (ino);
> }
>
> Index: main.c
> ===================================================================
> RCS file: /cvs/src/sbin/fsck_ffs/main.c,v
> retrieving revision 1.37
> diff -u -p -r1.37 main.c
> --- main.c 16 Apr 2011 16:37:21 -0000 1.37
> +++ main.c 18 Apr 2011 09:33:15 -0000
> @@ -76,6 +76,9 @@ main(int argc, char *argv[])
> case 'c':
> skipclean = 0;
> cvtlevel = argtoi('c', "conversion level", optarg, 10);
> + if (cvtlevel < 3)
> + errexit("cannot do level %d conversion\n",
> + cvtlevel);
> break;
>
> case 'd':
> Index: pass1.c
> ===================================================================
> RCS file: /cvs/src/sbin/fsck_ffs/pass1.c,v
> retrieving revision 1.34
> diff -u -p -r1.34 pass1.c
> --- pass1.c 16 Apr 2011 16:37:21 -0000 1.34
> +++ pass1.c 17 Apr 2011 11:20:38 -0000
> @@ -259,34 +259,6 @@ checkinode(ino_t inumber, struct inodesc
> ndb++;
> if (mode == IFLNK) {
> /*
> - * Note that the old fastlink format always had di_blocks set
> - * to 0. Other than that we no longer use the `spare' field
> - * (which is now the extended uid) for sanity checking, the
> - * new format is the same as the old. We simply ignore the
> - * conversion altogether. - mycroft, 19MAY1994
> - */
> - if (sblock.fs_magic == FS_UFS1_MAGIC && doinglevel2 &&
> - DIP(dp, di_size) > 0 &&
> - DIP(dp, di_size) < MAXSYMLINKLEN_UFS1 &&
> - DIP(dp, di_blocks) != 0) {
> - symbuf = alloca(secsize);
> - if (bread(fsreadfd, symbuf,
> - fsbtodb(&sblock, DIP(dp, di_db[0])),
> - (long)secsize) != 0)
> - errexit("cannot read symlink\n");
> - if (debug) {
> - symbuf[DIP(dp, di_size)] = 0;
> - printf("convert symlink %d(%s) of size %llu\n",
> - inumber, symbuf,
> - (unsigned long long)DIP(dp, di_size));
> - }
> - dp = ginode(inumber);
> - memcpy(dp->dp1.di_shortlink, symbuf,
> - (long)DIP(dp, di_size));
> - DIP_SET(dp, di_blocks, 0);
> - inodirty();
> - }
> - /*
> * Fake ndb value so direct/indirect block checks below
> * will detect any garbage after symlink string.
> */
> @@ -349,16 +321,6 @@ checkinode(ino_t inumber, struct inodesc
> } else
> SET_ISTATE(inumber, FSTATE);
> SET_ITYPE(inumber, IFTODT(mode));
> - if (sblock.fs_magic == FS_UFS1_MAGIC && doinglevel2 &&
> - (dp->dp1.di_ouid != (u_short)-1 ||
> - dp->dp1.di_ogid != (u_short)-1)) {
> - dp = ginode(inumber);
> - DIP_SET(dp, di_uid, dp->dp1.di_ouid);
> - dp->dp1.di_ouid = -1;
> - DIP_SET(dp, di_gid, dp->dp1.di_ogid);
> - dp->dp1.di_ogid = -1;
> - inodirty();
> - }
> badblk = dupblk = 0;
> idesc->id_number = inumber;
> (void)ckinode(dp, idesc);
> Index: pass2.c
> ===================================================================
> RCS file: /cvs/src/sbin/fsck_ffs/pass2.c,v
> retrieving revision 1.30
> diff -u -p -r1.30 pass2.c
> --- pass2.c 16 Apr 2011 16:37:21 -0000 1.30
> +++ pass2.c 17 Apr 2011 11:23:37 -0000
> @@ -259,13 +259,6 @@ pass2check(struct inodesc *idesc)
> char pathbuf[MAXPATHLEN + 1];
>
> /*
> - * If converting, set directory entry type.
> - */
> - if (doinglevel2 && dirp->d_ino > 0 && dirp->d_ino < maxino) {
> - dirp->d_type = GET_ITYPE(dirp->d_ino);
> - ret |= ALTERED;
> - }
> - /*
> * check for "."
> */
> if (idesc->id_entryno != 0)
> @@ -277,7 +270,7 @@ pass2check(struct inodesc *idesc)
> if (reply("FIX") == 1)
> ret |= ALTERED;
> }
> - if (newinofmt && dirp->d_type != DT_DIR) {
> + if (dirp->d_type != DT_DIR) {
> direrror(idesc->id_number, "BAD TYPE VALUE FOR '.'");
> dirp->d_type = DT_DIR;
> if (reply("FIX") == 1)
> @@ -287,21 +280,9 @@ pass2check(struct inodesc *idesc)
> }
> direrror(idesc->id_number, "MISSING '.'");
> proto.d_ino = idesc->id_number;
> - if (newinofmt)
> - proto.d_type = DT_DIR;
> - else
> - proto.d_type = 0;
> + proto.d_type = DT_DIR;
> proto.d_namlen = 1;
> (void)strlcpy(proto.d_name, ".", sizeof proto.d_name);
> -# if BYTE_ORDER == LITTLE_ENDIAN
> - if (!newinofmt) {
> - u_char tmp;
> -
> - tmp = proto.d_type;
> - proto.d_type = proto.d_namlen;
> - proto.d_namlen = tmp;
> - }
> -# endif
> entrysize = DIRSIZ(0, &proto);
> if (dirp->d_ino != 0 && strcmp(dirp->d_name, "..") != 0) {
> pfatal("CANNOT FIX, FIRST ENTRY IN DIRECTORY CONTAINS %s\n",
> @@ -330,21 +311,9 @@ chk1:
> goto chk2;
> inp = getinoinfo(idesc->id_number);
> proto.d_ino = inp->i_parent;
> - if (newinofmt)
> - proto.d_type = DT_DIR;
> - else
> - proto.d_type = 0;
> + proto.d_type = DT_DIR;
> proto.d_namlen = 2;
> (void)strlcpy(proto.d_name, "..", sizeof proto.d_name);
> -# if BYTE_ORDER == LITTLE_ENDIAN
> - if (!newinofmt) {
> - u_char tmp;
> -
> - tmp = proto.d_type;
> - proto.d_type = proto.d_namlen;
> - proto.d_namlen = tmp;
> - }
> -# endif
> entrysize = DIRSIZ(0, &proto);
> if (idesc->id_entryno == 0) {
> n = DIRSIZ(0, dirp);
> @@ -360,7 +329,7 @@ chk1:
> }
> if (dirp->d_ino != 0 && strcmp(dirp->d_name, "..") == 0) {
> inp->i_dotdot = dirp->d_ino;
> - if (newinofmt && dirp->d_type != DT_DIR) {
> + if (dirp->d_type != DT_DIR) {
> direrror(idesc->id_number, "BAD TYPE VALUE FOR '..'");
> dirp->d_type = DT_DIR;
> if (reply("FIX") == 1)
> @@ -473,8 +442,7 @@ again:
> /* FALLTHROUGH */
>
> case FSTATE:
> - if (newinofmt && dirp->d_type !=
> - GET_ITYPE(dirp->d_ino)) {
> + if (dirp->d_type != GET_ITYPE(dirp->d_ino)) {
> fileerror(idesc->id_number, dirp->d_ino,
> "BAD TYPE VALUE");
> dirp->d_type = GET_ITYPE(dirp->d_ino);
> Index: pass5.c
> ===================================================================
> RCS file: /cvs/src/sbin/fsck_ffs/pass5.c,v
> retrieving revision 1.40
> diff -u -p -r1.40 pass5.c
> --- pass5.c 16 Apr 2011 16:37:21 -0000 1.40
> +++ pass5.c 17 Apr 2011 11:24:38 -0000
> @@ -65,7 +65,7 @@ pass5(void)
> struct cg *cg = &cgrp;
> daddr64_t dbase, dmax;
> daddr64_t d;
> - long i, j, k;
> + long i, j, k, rewritecg = 0;
> struct csum *cs;
> struct csum_total cstotal;
> struct inodesc idesc[3];
> @@ -80,7 +80,7 @@ pass5(void)
> pwarn("DELETING CLUSTERING MAPS\n");
> if (preen || reply("DELETE CLUSTERING MAPS")) {
> fs->fs_contigsumsize = 0;
> - doinglevel1 = 1;
> + rewritecg = 1;
> sbdirty();
> }
> }
> @@ -107,7 +107,7 @@ pass5(void)
> doit);
> fs->fs_cgsize =
> fragroundup(fs, CGSIZE(fs));
> - doinglevel1 = 1;
> + rewritecg = 1;
> sbdirty();
> }
> }
> @@ -164,11 +164,8 @@ pass5(void)
> fs->fs_postblformat);
> }
> memset(&idesc[0], 0, sizeof idesc);
> - for (i = 0; i < 3; i++) {
> + for (i = 0; i < 3; i++)
> idesc[i].id_type = ADDR;
> - if (doinglevel2)
> - idesc[i].id_fix = FIX;
> - }
> memset(&cstotal, 0, sizeof(struct csum_total));
> dmax = blknum(fs, fs->fs_size + fs->fs_frag - 1);
> for (d = fs->fs_size; d < dmax; d++)
> @@ -320,7 +317,7 @@ pass5(void)
> memcpy(cs, &newcg->cg_cs, sizeof *cs);
> sbdirty();
> }
> - if (doinglevel1) {
> + if (rewritecg) {
> memcpy(cg, newcg, (size_t)fs->fs_cgsize);
> cgdirty();
> continue;
> Index: setup.c
> ===================================================================
> RCS file: /cvs/src/sbin/fsck_ffs/setup.c,v
> retrieving revision 1.47
> diff -u -p -r1.47 setup.c
> --- setup.c 16 Apr 2011 16:37:21 -0000 1.47
> +++ setup.c 17 Apr 2011 19:16:18 -0000
> @@ -260,96 +260,57 @@ found:
> dirty(&asblk);
> }
> }
> - if (sblock.fs_inodefmt >= FS_44INODEFMT) {
> - if (sblock.fs_maxfilesize != maxfilesize) {
> - pwarn("INCORRECT MAXFILESIZE=%llu IN SUPERBLOCK",
> - (unsigned long long)sblock.fs_maxfilesize);
> - sblock.fs_maxfilesize = maxfilesize;
> - if (preen)
> - printf(" (FIXED)\n");
> - if (preen || reply("FIX") == 1) {
> - sbdirty();
> - dirty(&asblk);
> - }
> - }
> - maxsymlinklen = sblock.fs_magic == FS_UFS1_MAGIC ?
> - MAXSYMLINKLEN_UFS1 : MAXSYMLINKLEN_UFS2;
> - if (sblock.fs_maxsymlinklen != maxsymlinklen) {
> - pwarn("INCORRECT MAXSYMLINKLEN=%d IN SUPERBLOCK",
> - sblock.fs_maxsymlinklen);
> - sblock.fs_maxsymlinklen = maxsymlinklen;
> - if (preen)
> - printf(" (FIXED)\n");
> - if (preen || reply("FIX") == 1) {
> - sbdirty();
> - dirty(&asblk);
> - }
> - }
> - if (sblock.fs_qbmask != ~sblock.fs_bmask) {
> - pwarn("INCORRECT QBMASK=%lx IN SUPERBLOCK",
> - (unsigned long)sblock.fs_qbmask);
> - sblock.fs_qbmask = ~sblock.fs_bmask;
> - if (preen)
> - printf(" (FIXED)\n");
> - if (preen || reply("FIX") == 1) {
> - sbdirty();
> - dirty(&asblk);
> - }
> - }
> - if (sblock.fs_qfmask != ~sblock.fs_fmask) {
> - pwarn("INCORRECT QFMASK=%lx IN SUPERBLOCK",
> - (unsigned long)sblock.fs_qfmask);
> - sblock.fs_qfmask = ~sblock.fs_fmask;
> - if (preen)
> - printf(" (FIXED)\n");
> - if (preen || reply("FIX") == 1) {
> - sbdirty();
> - dirty(&asblk);
> - }
> + if (sblock.fs_inodefmt < FS_44INODEFMT) {
> + pwarn("Format of filesystem is too old.\n");
> + pwarn("Must update to modern format using a version of fsck\n");
> + pfatal("from before release 5.0 with the command ``fsck -c
> 2''\n");
> + exit(8);
> + }
> + if (sblock.fs_maxfilesize != maxfilesize) {
> + pwarn("INCORRECT MAXFILESIZE=%llu IN SUPERBLOCK",
> + (unsigned long long)sblock.fs_maxfilesize);
> + sblock.fs_maxfilesize = maxfilesize;
> + if (preen)
> + printf(" (FIXED)\n");
> + if (preen || reply("FIX") == 1) {
> + sbdirty();
> + dirty(&asblk);
> }
> - newinofmt = 1;
> - } else {
> - sblock.fs_qbmask = ~sblock.fs_bmask;
> - sblock.fs_qfmask = ~sblock.fs_fmask;
> - newinofmt = 0;
> }
> - /*
> - * Convert to new inode format.
> - */
> - if (cvtlevel >= 2 && sblock.fs_inodefmt < FS_44INODEFMT) {
> + maxsymlinklen = sblock.fs_magic == FS_UFS1_MAGIC ?
> + MAXSYMLINKLEN_UFS1 : MAXSYMLINKLEN_UFS2;
> + if (sblock.fs_maxsymlinklen != maxsymlinklen) {
> + pwarn("INCORRECT MAXSYMLINKLEN=%d IN SUPERBLOCK",
> + sblock.fs_maxsymlinklen);
> + sblock.fs_maxsymlinklen = maxsymlinklen;
> if (preen)
> - pwarn("CONVERTING TO NEW INODE FORMAT\n");
> - else if (!reply("CONVERT TO NEW INODE FORMAT"))
> - return(0);
> - doinglevel2++;
> - sblock.fs_inodefmt = FS_44INODEFMT;
> - sblock.fs_maxfilesize = maxfilesize;
> - sblock.fs_maxsymlinklen = MAXSYMLINKLEN_UFS1;
> + printf(" (FIXED)\n");
> + if (preen || reply("FIX") == 1) {
> + sbdirty();
> + dirty(&asblk);
> + }
> + }
> + if (sblock.fs_qbmask != ~sblock.fs_bmask) {
> + pwarn("INCORRECT QBMASK=%lx IN SUPERBLOCK",
> + (unsigned long)sblock.fs_qbmask);
> sblock.fs_qbmask = ~sblock.fs_bmask;
> - sblock.fs_qfmask = ~sblock.fs_fmask;
> - sbdirty();
> - dirty(&asblk);
> + if (preen)
> + printf(" (FIXED)\n");
> + if (preen || reply("FIX") == 1) {
> + sbdirty();
> + dirty(&asblk);
> + }
> }
> - /*
> - * Convert to new cylinder group format.
> - */
> - if (cvtlevel >= 1 && sblock.fs_postblformat == FS_42POSTBLFMT) {
> + if (sblock.fs_qfmask != ~sblock.fs_fmask) {
> + pwarn("INCORRECT QFMASK=%lx IN SUPERBLOCK",
> + (unsigned long)sblock.fs_qfmask);
> + sblock.fs_qfmask = ~sblock.fs_fmask;
> if (preen)
> - pwarn("CONVERTING TO NEW CYLINDER GROUP FORMAT\n");
> - else if (!reply("CONVERT TO NEW CYLINDER GROUP FORMAT"))
> - return(0);
> - doinglevel1++;
> - sblock.fs_postblformat = FS_DYNAMICPOSTBLFMT;
> - sblock.fs_nrpos = 8;
> - sblock.fs_postbloff =
> - (char *)(&sblock.fs_maxbsize) -
> - (char *)(&sblock.fs_firstfield);
> - sblock.fs_rotbloff = &sblock.fs_space[0] -
> - (u_char *)(&sblock.fs_firstfield);
> - sblock.fs_cgsize =
> - fragroundup(&sblock, CGSIZE(&sblock));
> - sbdirty();
> - dirty(&asblk);
> + printf(" (FIXED)\n");
> + if (preen || reply("FIX") == 1) {
> + sbdirty();
> + dirty(&asblk);
> + }
> }
> if (sblock.fs_cgsize != fragroundup(&sblock, CGSIZE(&sblock))) {
> pwarn("INCONSISTENT CGSIZE=%d\n", sblock.fs_cgsize);
> Index: utilities.c
> ===================================================================
> RCS file: /cvs/src/sbin/fsck_ffs/utilities.c,v
> retrieving revision 1.38
> diff -u -p -r1.38 utilities.c
> --- utilities.c 16 Apr 2011 16:37:21 -0000 1.38
> +++ utilities.c 17 Apr 2011 11:26:48 -0000
> @@ -511,8 +511,7 @@ getpathname(char *namebuf, size_t namebu
> void
> catch(int signo)
> {
> - if (!doinglevel2)
> - ckfini(0); /* XXX signal race */
> + ckfini(0); /* XXX signal race */
> _exit(12);
> }