[Ocfs2-tools-commits] zab commits r493 - in trunk/fsck.ocfs2: . include

svn-commits at oss.oracle.com svn-commits at oss.oracle.com
Tue Dec 14 19:22:16 CST 2004


Author: zab
Date: 2004-12-14 19:22:14 -0600 (Tue, 14 Dec 2004)
New Revision: 493

Modified:
   trunk/fsck.ocfs2/Makefile
   trunk/fsck.ocfs2/extent.c
   trunk/fsck.ocfs2/fsck.ocfs2.checks.8.in
   trunk/fsck.ocfs2/include/problem.h
   trunk/fsck.ocfs2/pass0.c
   trunk/fsck.ocfs2/pass1.c
   trunk/fsck.ocfs2/pass2.c
   trunk/fsck.ocfs2/pass3.c
   trunk/fsck.ocfs2/pass4.c
   trunk/fsck.ocfs2/problem.c
Log:
o identify the errors fsck addresses with symbolic names instead of numbers
o make it irritating to compile a prompt() call without an error name
o go wild documenting errors for the existing prompt() calls


Modified: trunk/fsck.ocfs2/Makefile
===================================================================
--- trunk/fsck.ocfs2/Makefile	2004-12-15 01:14:30 UTC (rev 492)
+++ trunk/fsck.ocfs2/Makefile	2004-12-15 01:22:14 UTC (rev 493)
@@ -49,6 +49,7 @@
 		include/strings.h	\
 		include/util.h
 
+
 OBJS = $(subst .c,.o,$(CFILES))
 MANS = fsck.ocfs2.8 fsck.ocfs2.checks.8
 
@@ -61,6 +62,22 @@
 fsck.ocfs2: $(OBJS) $(LIBOCFS2_DEPS)
 	$(LINK) $(LIBOCFS2_LIBS) $(COM_ERR_LIBS)
 
+$(OBJS): prompt-codes.h
+
+# make it hard to add a prompt call
+# without documenting what it does
+prompt-codes.h: fsck.ocfs2.checks.8.in
+	@echo generating $@ by parsing $^
+	@rm -f .$@.tmp
+	@(	echo '#ifndef __PROMPT_CODES_H__';			\
+		echo '#define __PROMPT_CODES_H__';			\
+		for a in `grep '^.SS ".*"' $^ | awk -F\" '{print $$2}'`; do\
+			echo '#define PR_'$$a' \';			\
+			echo '	(struct prompt_code){ .str = "'$$a'" }';\
+		done;							\
+		echo '#endif';						\
+	 ) > $@
+
 .PHONY: check-prompt-dups
 check-prompt-dups: fsck.ocfs2
 	@rm -f .$@.tmp
@@ -70,4 +87,9 @@
 	@cat .$@.tmp
 	@test ! -s .$@.tmp
 
+CLEAN_RULES += o2fsck-clean
+.PHONY: o2fsck-clean
+o2fsck-clean:
+	rm -f prompt-codes.h
+
 include $(TOPDIR)/Postamble.make

Modified: trunk/fsck.ocfs2/extent.c
===================================================================
--- trunk/fsck.ocfs2/extent.c	2004-12-15 01:14:30 UTC (rev 492)
+++ trunk/fsck.ocfs2/extent.c	2004-12-15 01:22:14 UTC (rev 493)
@@ -92,7 +92,8 @@
 	eb = (ocfs2_extent_block *)buf;
 
 	if (eb->h_blkno != blkno &&
-	    prompt(ost, PY, 0, "An extent block at %"PRIu64" in inode %"PRIu64" "
+	    prompt(ost, PY, PR_EB_BLKNO,
+		   "An extent block at %"PRIu64" in inode %"PRIu64" "
 		   "claims to be located at block %"PRIu64".  Update the "
 		   "extent block's location?", blkno, di->i_blkno,
 		   eb->h_blkno)) {
@@ -101,7 +102,8 @@
 	}
 
 	if (eb->h_fs_generation != ost->ost_fs_generation) {
-		if (prompt(ost, PY, 0, "An extent block at %"PRIu64" in inode "
+		if (prompt(ost, PY, PR_EB_GEN,
+			   "An extent block at %"PRIu64" in inode "
 			   "%"PRIu64" has a generation of %x which doesn't "
 			   "match the volume's generation of %x.  Consider "
 			   "this extent block invalid?", blkno, di->i_blkno,
@@ -110,8 +112,9 @@
 			*is_valid = 0;
 			goto out;
 		}
-		if (prompt(ost, PY, 0, "Update the extent block's generation to "
-			   "match the volume?")) {
+		if (prompt(ost, PY, PR_EB_GEN_FIX,
+			   "Update the extent block's generation to match the "
+			   "volume?")) {
 
 			eb->h_fs_generation = ost->ost_fs_generation;
 			changed = 1;
@@ -166,7 +169,8 @@
 		ei->ei_expected_depth = el->l_tree_depth - 1;
 		check_eb(ost, ei, di, er->e_blkno, &is_valid);
 		if (!is_valid && 
-		    prompt(ost, PY, 0, "The extent record for cluster offset "
+		    prompt(ost, PY, PR_EXTENT_EB_INVALID,
+			   "The extent record for cluster offset "
 			   "%"PRIu32" in inode %"PRIu64" refers to an invalid "
 			   "extent block at %"PRIu64".  Clear the reference "
 			   "to this invalid block?", er->e_cpos, di->i_blkno,
@@ -183,7 +187,8 @@
 	first_block = ocfs2_clusters_to_blocks(ost->ost_fs, first_block);
 
 	if (first_block != er->e_blkno &&
-	    prompt(ost, PY, 0, "The extent record for cluster offset %"PRIu32" "
+	    prompt(ost, PY, PR_EXTENT_BLKNO_UNALIGNED,
+		   "The extent record for cluster offset %"PRIu32" "
 		   "in inode %"PRIu64" refers to block %"PRIu64" which isn't "
 		   "aligned with the start of a cluster.  Point the extent "
 		   "record at block %"PRIu64" which starts this cluster?",
@@ -199,7 +204,8 @@
 		       er->e_clusters;
 
 	if (last_cluster > ost->ost_fs->fs_clusters &&
-	    prompt(ost, PY, 0, "The extent record for cluster offset %"PRIu32" "
+	    prompt(ost, PY, PR_EXTENT_CLUSTERS_OVERRUN,
+		   "The extent record for cluster offset %"PRIu32" "
 		   "in inode %"PRIu64" refers to an extent that goes beyond "
 		   "the end of the volume.  Truncate the extent by %"PRIu32" "
 		   "clusters to fit it in the volume?", er->e_cpos, 
@@ -233,7 +239,8 @@
 
 	if (ei->ei_expect_depth && 
 	    el->l_tree_depth != ei->ei_expected_depth &&
-	    prompt(ost, PY, 0, "Extent list in inode %"PRIu64" is recorded as "
+	    prompt(ost, PY, PR_EXTENT_LIST_DEPTH,
+		   "Extent list in inode %"PRIu64" is recorded as "
 		   "being at depth %u but we expect it to be at depth %u. "
 		   "update the list?", di->i_blkno, el->l_tree_depth,
 		   ei->ei_expected_depth)) {
@@ -243,7 +250,8 @@
 	}
 
 	if (el->l_count > max_recs &&
-	    prompt(ost, PY, 0, "Extent list in inode %"PRIu64" claims to have %u "
+	    prompt(ost, PY, PR_EXTENT_LIST_COUNT,
+		   "Extent list in inode %"PRIu64" claims to have %u "
 		   "records, but the maximum is %u. Fix the list's count?",
 		   di->i_blkno, el->l_count, max_recs)) {
 
@@ -255,7 +263,8 @@
 		max_recs = el->l_count;
 
 	if (el->l_next_free_rec > max_recs) {
-		if (prompt(ost, PY, 0, "Extent list in inode %"PRIu64" claims %u "
+		if (prompt(ost, PY, PR_EXTENT_LIST_FREE,
+		  	   "Extent list in inode %"PRIu64" claims %u "
 			   "as the next free chain record, but fsck believes "
 			   "the largest valid value is %u.  Clamp the next "
 			   "record value?", di->i_blkno, el->l_next_free_rec,
@@ -281,7 +290,8 @@
 
 		/* offer to remove records that point to nowhere */
 		if (ocfs2_block_out_of_range(ost->ost_fs, er->e_blkno) && 
-		    prompt(ost, PY, 0, "Extent record %u in inode %"PRIu64" "
+		    prompt(ost, PY, PR_EXTENT_BLKNO_RANGE,
+			   "Extent record %u in inode %"PRIu64" "
 			   "refers to a block that is out of range.  Remove "
 			   "this record from the extent list?", i,
 			   di->i_blkno)) {

Modified: trunk/fsck.ocfs2/fsck.ocfs2.checks.8.in
===================================================================
--- trunk/fsck.ocfs2/fsck.ocfs2.checks.8.in	2004-12-15 01:14:30 UTC (rev 492)
+++ trunk/fsck.ocfs2/fsck.ocfs2.checks.8.in	2004-12-15 01:22:14 UTC (rev 493)
@@ -16,24 +16,139 @@
 
 .SH "CHECKS"
 
-.SS "2"
-The group descriptors that make up the global bitmap chain allocator are
-static and should be found in specific chains in the allocator.  A given
-group descriptor wasn't found in the chain it should have been in.
+\" escape.c
 
-Answering yes relinks the given group descriptor into the head of the chain it
-should have been found in.
+.SS "EB_BLKNO"
+Extent blocks contain a record of the disk block where they are located.  An
+extent block was found at a block that didn't match its recorded location.
 
-.SS "3"
-The group descriptors that make up the global bitmap chain allocator are
-static and should be found in specific chains in the allocator.  A given
-group descriptor block existed on disk but wasn't linked into the global
-bitmap chain allocator.
+Answering yes will update the data structure in the extent block to reflect
+its real location on disk.
 
-Answering yes links the given group descriptor into the global bitmap chain
-allocator.
+.SS "EB_GEN"
+Extent blocks are created with a generation number to match the generation
+number of the volume at the time of creation.  An extent block was found which
+contains a generation number that doesn't match.
 
-.SS "4"
+Answering yes implies that the generation number is correct and that the
+extent block is from a previous file system.  The extent block will be ignored 
+and the file that contains it will lose the data it referenced.
+
+.SS "EB_GEN_FIX"
+Extent blocks are created with a generation number to match the generation
+number of the volume at the time of creation.  An extent block was found which
+contains a generation number that doesn't match.
+
+Answering yes implies that the generation number in the extent block is
+incorrect and that the extent block is valid.  The generation number in the
+block is updated to match the generation number in the volume.
+
+.SS "EXTENT_BLKNO_UNALIGNED"
+The block that marks the start of an extent should always fall on the start of a cluster.  An extent was found that starts part-way into a cluster.
+
+Answering yes moves the start of the extent back to the start of the addressed
+cluster.  This may add data to the middle of the file that contains this extent.
+
+.SS "EXTENT_CLUSTERS_OVERRUN"
+An extent was found which claims to contain clusters which are beyond the end of the volume.
+
+Answering yes clamps the extent to the end of the volume.  This may result in a
+reduced file size for the file that contains the extent, but it couldn't have
+addressed those final clusters anyway.  One can imagine this problem arising if
+there are problems shrinking a volume.
+
+.SS "EXTENT_EB_INVALID"
+Deep extent trees are built by forming a tree out of extent blocks.  An extent tree references an invalid extent block.
+
+Answering yes stops the tree from referencing the invalid extent block.  This
+may truncate data from the file which contains the tree.
+
+.SS "EXTENT_LIST_DEPTH"
+Extent lists contain a record of their depth in the tree.  An extent list
+was found whose recorded depth doesn't match the position they have in the tree.
+
+Answering yes updates the depth field in the list to match the tree on disk.
+
+.SS "EXTENT_LIST_COUNT"
+The number of entries in an extent list is bounded by either the size of the 
+inode or the size of the block which contains it.  An extent list was found
+which claims to have more entries than would fit in its container.
+
+Answering yes updates the count field in the exent list to match the container.
+Answering no to this question may stop further fixes from being done because
+the count value can not be trusted.
+
+.SS "EXTENT_LIST_FREE"
+The number of free entries in an extent list must be less than the total
+number of entries in the list.   A list was found which claims to have more free entries than possible entries.
+
+Answering yes sets the number of free entries in the list equal to the total
+possible entries.
+
+.SS "EXTENT_BLKNO_RANGE"
+An extent record was found which references a block which can not be referenced
+by an extent.  The referenced block is either very early in the volume, and
+thus reserved, or beyond the end of the volume.
+
+Answering yes removes this extent record from the tree.  This may remove data
+from the file which owns the tree but any such data was inaccesible.
+
+\" pass0.c
+
+.SS "GROUP_UNEXPECTED_DESC"
+The group descriptors that make up the global bitmap chain allocator reside
+at predictable locations on disk.  A group descriptor was found in the global
+bitmap allocator which isn't at one of these locations and so shouldn't
+be in the allocator.
+
+Answering yes removes this descriptor from the global bitmap allocator.
+
+.SS "GROUP_EXPECTED_DESC"
+The group descriptors that make up the global bitmap chain allocator reside
+at predictable locations on disk.  A group descriptor at one of these locations
+was not linked into the global bitmap allocator.
+
+Answering yes will relink this group into the allocator.
+
+.SS "GROUP_GEN"
+A group descriptor was found with a generation number that doesn't match
+the generation number of the volume.
+
+Answering yes sets the group descriptor's generation equal to the generation
+number in the volume.
+
+.SS "GROUP_PARENT"
+Group descriptors contain a pointer to the allocator inode which contains
+the chain they belong to.  A group descriptor was found in an allocator
+inode that doesn't match the descriptor's parent pointer.
+
+Answering yes updates the group descriptor's parent pointer to match the inode
+it resides in.
+
+.SS "GROUP_BLKNO"
+Group descriptors have a field which records their block location on disk.  A
+group descriptor was found at a given location but is recorded as being located
+somewhere else.
+
+Answering yes updates the group descriptor's recorded location to match where
+it actually is found on disk.
+
+.SS "GROUP_CHAIN"
+Group descriptors are found in a number of different singly-linked chains
+in an allocator inode.  A group descriptor records the chain number that it is linked in.  A group descriptor was found whose chain field doesn't match the chain it was found in.
+
+Answering yes sets the group descriptor's chain field to match the chain
+it is found in.
+
+.SS "GROUP_FREE_BITS"
+A group descriptor records the number of bits in its bitmap that are free.
+A group descriptor was found which claims to have more free bits than are
+valid in its bitmap.
+
+Answering yes decreases the number of recorded free bits so that it equals
+the total number of bits in the group descriptor's bitmap.
+
+.SS "CHAIN_COUNT"
 The chain list embedded in an inode is limited by the block size and the
 number of bytes consumed by the rest of the inode.  A chain list header was
 found which claimed that there are more entries in the list then could 
@@ -42,12 +157,12 @@
 Answering yes resets the header's cl_count member to the maximum size allowed
 by the block size after accounting for the space consumed by the inode.
 
-.SS "5"
-This is identical to test 4 except that it is testing and fixing the pointer
-to the next free list entry recorded in the cl_next_free_rec member instead of
-the total number of entries. 
+.SS "CHAIN_NEXT_FREE"
+This is identical to CHAIN_COUNT except that it is testing and fixing the
+pointer to the next free list entry recorded in the cl_next_free_rec member
+instead of the total number of entries. 
 
-.SS "6"
+.SS "CHAIN_EMPTY"
 Chain entries need to be packed such that there are no chains without 
 descriptors found before the chain that is marked as free by the chain header.
 A chain without descriptors was found found before that chain that was
@@ -56,7 +171,7 @@
 Answering yes will remove the unused chain and shift the remaining chains
 forward in the list.
 
-.SS "7"
+.SS "CHAIN_GROUP_BITS"
 The inode that contains an embedded chain list has fields which record the
 total number of bits covered by the chain as well as the amount free.  These 
 fields didn't match what was found in the chain. 
@@ -64,9 +179,33 @@
 Answering yes updates the fields in the inode to reflect what was actually
 found by walking the chain.
 
-.SS "8"
-Chains are built by the chain headers and group descriptors which are linked
-together by block references.  A reference a block reference was found which
+.SS "CHAIN_HEAD_LINK_RANGE"
+The header that starts a chain tried to reference a group descriptor at
+a block number that couldn't be valid.
+
+Answering yes will clear the reference to this invalid block and truncate the chain that it started.
+
+.SS "CHAIN_LINK_GEN"
+A reference was made to a group descriptor whose generation number doesn't
+match the generation of the volume.
+
+Answering yes to this question implies that the group descriptor is invalid
+and the chain is truncated at the point that it referred to this invalid
+group descriptor.  Answering no to this question considers the group descriptor
+as valid and its generation may be fixed.
+
+.SS "CHAIN_LINK_MAGIC"
+Chains are built by chain headers and group descriptors which are linked
+together by block references.  A reference was made to a group descriptor
+at a given block but a valid group descriptor signature wasn't found
+at that block.
+
+Answering yes clears the reference to this invalid block and truncates the
+chain at the point of the reference.
+
+.SS "CHAIN_LINK_RANGE"
+Chains are built by chain headers and group descriptors which are linked
+together by block references.  A reference a block was found which
 can't possibly be valid because it was either too small or extended beyond the
 volume.
 
@@ -75,23 +214,7 @@
 fixes later if the part of the chain that couldn't be referenced was valid
 at some point.
 
-.SS "10"
-The global bitmap chain allocator contains fixed blocks at predictable 
-offsets in the volume.  A group descriptor was found in this chain which
-wasn't at one of these predictable locations.
-
-Answering yes removes this unexpected group descriptor from the chain.  It's
-block will likely then be unused and marked as free in the bitmap later on.
-
-.SS "11"
-A reference was made to a group descriptor that is invalid, for whatever
-reason.
-
-Answering yes truncates the chain in question by removing the reference to
-this invalid group descriptor.  This has the same implications as answering
-yes to check 8. 
-
-.SS "12"
+.SS "CHAIN_BITS"
 A chain's header contains members which record the total number of bits in the
 chain as well as the number of bits that are free.  After walking through a
 chain it was found that the number of bits recorded in its header don't match
@@ -100,6 +223,297 @@
 Answering yes updates the c_total and c_free members of the header to reflect
 what was found in the group descriptors in the chain.
 
+\" pass1.c
+
+.SS "INODE_ALLOC_REPAIR"
+The inode allocator did not accurately reflect the set of inodes that are
+free and in use in the volume.
+
+Answering yes will update the inode allocator bitmaps.  Each bit that doesn't match the state of its inode will be inverted.
+
+.SS "INODE_SUBALLOC"
+Each inode records the node whose allocator is responsible for the inode.  An
+inode was found in a given node's allocator but the inode itself claimed to
+belong to a different node.
+
+Answering yes will correct the inode to point to the node's allocator that it
+belongs to.
+
+.SS "LALLOC_SIZE"
+Each node has a local allocator contained in a block that is used to allocate
+clusters in batches.  A node's local allocator claims to reflect more bytes
+than are possible for the volume's block size.
+
+Answering yes decreses the local allocator's size to reflect the volume's block
+size.
+
+.SS "LALLOC_NZ_USED"
+A given node's local allocator isn't in use but it claims to have bits
+in use in its bitmap.
+
+Answering yes zeros this used field.
+
+.SS "LALLOC_NZ_BM"
+A given node's local allocator isn't in use but it has a field which records
+the bitmap as starting at a non-zero cluster offset.
+
+Answering yes zeros the bm_off field.
+
+.SS "LALLOC_BM_OVERRUN"
+Each local allocator contains a reference to the first cluster that its bitmap
+addresses.  A given local allocator was found which references a starting
+cluster that is beyond the end of the volume.
+
+Answering yes resets the given local allocator.  No allocated data will
+be lost.
+
+.SS "LALLOC_BM_SIZE"
+The given local allocator claims to cover more bits than are possible for the
+size in bytes of its bitmap.
+
+Answering yes decreases the number of bits the allocator covers to reflect
+the size in bytes of the bitmap and resets the allocator.  No allocated
+data will be lost.
+
+.SS "LALLOC_BM_STRADDLE"
+The given local allocator claims to cover a region of clusters which extents
+beyond the end of the volume.
+
+Answering yes resets the given local allocator.  No allocated data will
+be lost.
+
+.SS "LALLOC_USED_OVERRUN"
+The given local allocator claims to have more bits in use than it has total
+bits in its bitmap.
+
+Answerying yes decreases the number of bits used so that it equals the total
+number of available bits.
+
+.SS "LALLOC_CLEAR"
+A local allocator inode was found to have problems.  This gives the operator
+a chance to just reset the local allocator inode. 
+
+Answering yes clears the local allocator.  No information is lost but the global
+bitmap allocator may need to be updated to reflect clusters that were reserved for the local allocator but were free.
+
+.SS "INODE_GEN"
+Inodes are created with a generation number to match the generation
+number of the volume at the time of creation.  An Inode was found which
+contains a generation number that doesn't match.
+
+Answering yes implies that the generation number is correct and that the
+inode is from a previous file system.  The inode will be recorded as free.
+
+.SS "INODE_GEN_FIX"
+Inodes are created with a generation number to match the generation
+number of the volume at the time of creation.  An inode was found which
+contains a generation number that doesn't match.
+
+Answering yes implies that the generation number in the inode is
+incorrect and that the inode is valid.  The generation number in the
+inode is updated to match the generation number in the volume.
+
+.SS "INODE_BLKNO"
+Inodes contain a field that must match the block that they reside in.  An inode was found at a block that doesn't match the field in the inode.
+
+Answering yes updates the field to match the inode's position on disk.
+
+.SS "ROOT_NOTDIR"
+The super block contains a reference to the inode that contains the root
+directory.  This block was found to contain an inode that isn't a directory.
+
+Answering yes clears this inode.  The operator will be asked to recreate
+the root directory at a point in the near future.
+
+.SS "INODE_NZ_DTIME"
+Inodes contain a field describing the time at which they were delted.  This
+can not be set for an inode that is still in use.  An inode was found
+which is in use but which contains a non-zero dtime.
+
+Answering yes implies that the inode is still valid and resets its dtime
+to zero.
+
+.SS "LINK_NULLTERM"
+The targets of links on disk must be null terminated.  A link was found
+whose target wasn't null terminated. 
+
+Answering yes clears the inode and so deletes the link.
+
+.SS "LINK_SIZE"
+The size of a link on disk must match the length of its target string.  A link was found whose size does not.
+
+Answering yes updates the link's size to reflect the length of its target
+string.
+
+.SS "LINK_BLOCKS"
+Links can not be sparse.  There must be exactly as many blocks allocated as are needed to cover its size.  A link was found which doesn't have enough blocks allocated to cover its size.
+
+Answering yes clears the link's inode and so deletes the link.
+
+.SS "DIR_ZERO"
+Directories must at least contain a block that has the "." and ".." entries.
+A directory was found which doesn't contain any blocks.
+
+Answering yes to this question clears the directorie's inode and so
+deletes the directory.
+
+.SS "INODE_CLUSTERS"
+Inodes contain a record of how many clusters are allocated to them.  An inode
+was found whose recorded number of clusters doesn't match the number of blocks
+that were found associated with the inode.
+
+Answering yes resets the inode's number of clusters to reflect the number
+of blocks that were associated with the file.
+
+.SS "LALLOC_REPAIR"
+An active local allocator did not accurately reflect the set of clusters that
+are free and in use in its region.
+
+Answering yes will update the local allocator bitmap.  Each bit that doesn't
+match the use of its cluster will be inverted.
+
+.SS "LALLOC_USED"
+A local allocator records the number of bits that are used in its bitmap.  An
+allocator was found whose used value doesn't reflect the number of bits that
+are set in its bitmap.
+
+Answering yes sets the used value to match the number of bits set in the 
+allocator's bitmap.
+
+.SS "CLUSTER_ALLOC_BIT"
+A specific cluster's use didn't match the setting of its bit in the cluster
+allocator.
+
+Answering yes will invert the bit in the allocator to match the use of the cluster -- either allocated and in use or free.
+
+\" pass2.c
+
+.SS "DIRENT_DOTTY_DUP"
+There can be only one instance of both the "." and ".." entries in a directory.
+A directory entry was found which duplicated one of these entries.
+
+Answering yes will remove the duplicate directory entry.
+
+.SS "DIRENT_NOT_DOTTY"
+The first and second directory entries in a directory must be "." and ".."
+respectively.  One of these directory entries was found to not match these
+rules.
+
+Answering yes will force the directory entry to be either "." or "..".  This
+might consume otherwise valid entries and cause some files to appear in 
+lost+found.
+
+.SS "DIRENT_DOT_INODE"
+The inode field of the "." directory entry must refer to the directory inode
+that contains the given directory block.  A "." entry was found which doesn't
+do so.
+
+Answering yes sets the directory entry's inode reference to the parent
+directory that contains the entry.
+
+.SS "DIRENT_DOT_EXCESS"
+A "." directory entry was found whose lengths exceeds the amount required
+for the single dot in the name.
+
+Answering yes creates another empty directory entry in this excess space.
+
+.SS "DIRENT_ZERO"
+A directory entry was found with a zero length name.
+
+Answering yes clears the directory entry so its space can be reused.
+
+.SS "DIRENT_NAME_CHARS"
+Directory entries can not contain either the NULL character (ascii 0) or 
+the forward slash (ascii 47).  A directory entry was found which contains
+either.
+
+Answering yes will change each instance of these forbidden characters into
+a period (ascii 46).
+
+.SS "DIRENT_INODE_RANGE"
+Each directory entry contains a inode field which the entry's name corresponds
+to.  An entry was found which referenced an inode number that is invalid
+for the current volume.
+
+Answering yes clears this entry so its space can be reused.  If the entry
+once corresponded to a real inode and was corrupted this inode may appear
+in lost+found.
+
+.SS "DIRENT_INODE_FREE"
+Each directory entry contains a inode field which the entry's name corresponds
+to.  An entry was found which referenced an inode number that isn't in
+use.
+
+Answering yes clears this directory entry.
+
+.SS "DIRENT_TYPE"
+Each directory entry contains a field which describes the type of file
+that the entry refers to.  An entry was found whose type doesn't match the
+inode it is referring to.
+
+Answering yes resets the entry's type to match the target inode.
+
+.SS "DIR_PARENT_DUP"
+Each directory can only be pointed to by one directory entry in a parent directory.  A directory entry was found which was the second entry to point to a given
+directory inode.
+
+Answering yes clears this entry which was the second to refer to a given directory.  This reflects the policy that hard links to directories are not allowed.
+
+.SS "DIRENT_LENGTH"
+There are very few directory entry lengths that are valid.  The lengths must be
+greater than the minimum required to record a single character directory, be
+rounded to 12 bytes, be within the amount of space remaining in a directory
+block, and be properly rounded for the size of the name of the directory entry.
+An entry was found which didn't meet these criteria.
+
+Answering yes will try to repair the directory entry.  This runs a very good
+chance of invalidating all the entries in the directory block.  Orphaned inodes
+may appear in lost+found.
+
+\" pass3.c
+
+.SS "ROOT_DIR_MISSING"
+The super block contains a reference to the inode that serves as the root directory.  This reference points to an inode that isn't in use.
+
+Answering yes will, actually, cause fsck to exit and make you cranky.
+
+.SS "LOSTFOUND_MISSING"
+The super block contains a reference to the inode that serves as the lost+found directory.  This reference points to an inode that isn't in use.
+
+Answering yes will create a new lost+found directory in the root directory.
+
+.SS "DIR_NOT_CONNECTED"
+Every directory in the file system should be reachable by a directory entry
+in its parent directory.  This is verified by walking every directory in
+the system.  A directory inode was found during this walk which doesn't have
+a parent directory entry.
+
+Answering yes moves this directory entry into the lost+found directory and 
+gives it a name based on its inode number.
+
+.SS "DIR_DOTDOT"
+A directory inode's ".." directory entry must refer to the parent directory.
+A directory was found whose ".." doesn't refer to its parent.
+
+Answering yes will read the directory block for the given directory and update
+its ".." entry to reflect its parent.
+
+.SS "INODE_NOT_CONNECTED"
+Most all inodes in the system should be referenced by a directory entry. An inode was found which isn't referred to by any directory entry.
+
+Answering yes moves this inode into the lost+found directory and 
+gives it a name based on its inode number.
+
+.SS "INODE_COUNT"
+Each inode records the number of directory entries that refer to it.  An inode
+was found whose recorded count doesn't match the number of entries that
+refer to it.
+
+Answering yes sets the inode's count to match the number of referring directory entries.
+
+
+\" pass4.c
+
 .SH "SEE ALSO"
 .BR ocfs2(8)
 

Modified: trunk/fsck.ocfs2/include/problem.h
===================================================================
--- trunk/fsck.ocfs2/include/problem.h	2004-12-15 01:14:30 UTC (rev 492)
+++ trunk/fsck.ocfs2/include/problem.h	2004-12-15 01:22:14 UTC (rev 493)
@@ -42,15 +42,20 @@
  * one call site.
  */
 #define prompt(ost, flags, code, fmt...) ({			\
-	static int fsck_prompt_callers_with_code_##code = code;	\
+	static int fsck_prompt_callers_with_code_##code = __LINE__;	\
 	int _ret = fsck_prompt_callers_with_code_##code;	\
 	_ret = prompt_input(ost, flags, code, fmt);		\
 	_ret;							\
 })
 
-int prompt_input(o2fsck_state *ost, unsigned flags, uint16_t code, 
+struct prompt_code {
+	const char *str;
+};
+
+#include "../prompt-codes.h"
+
+int prompt_input(o2fsck_state *ost, unsigned flags, struct prompt_code code,
 		 const char *fmt, ...)
 	 __attribute__ ((format (printf, 4, 5)));
 
 #endif /* __O2FSCK_PROBLEM_H__ */
-

Modified: trunk/fsck.ocfs2/pass0.c
===================================================================
--- trunk/fsck.ocfs2/pass0.c	2004-12-15 01:14:30 UTC (rev 492)
+++ trunk/fsck.ocfs2/pass0.c	2004-12-15 01:22:14 UTC (rev 493)
@@ -83,7 +83,8 @@
 		 bg->bg_chain, bg->bg_generation);
 
 	if (bg->bg_generation != ost->ost_fs_generation &&
-	    prompt(ost, PY, 0, "Group descriptor at block %"PRIu64" has "
+	    prompt(ost, PY, PR_GROUP_GEN,
+		   "Group descriptor at block %"PRIu64" has "
 		   "a generation of %"PRIx32" which doesn't match the "
 		   "volume's generation of %"PRIx32".  Change the generation "
 		   "in the descriptor to match the volume?", blkno,
@@ -97,7 +98,8 @@
 	 * kinds of descs have valid generations for the inodes they
 	 * reference */
 	if ((bg->bg_parent_dinode != di->i_blkno) &&
-	    prompt(ost, PY, 0, "Group descriptor at block %"PRIu64" is "
+	    prompt(ost, PY, PR_GROUP_PARENT,
+		   "Group descriptor at block %"PRIu64" is "
 		   "referenced by inode %"PRIu64" but thinks its parent inode "
 		   "is %"PRIu64".  Fix the descriptor's parent inode?", blkno,
 		   di->i_blkno, bg->bg_parent_dinode)) {
@@ -105,18 +107,9 @@
 		changed = 1;
 	}
 
-	if ((bg->bg_generation != di->i_generation) &&
-	    prompt(ost, PY, 0, "Group descriptor at block %"PRIu64" is "
-		   "referenced by inode %"PRIu64" who has a generation of "
-		   "%u, but the descriptor has a generation of %u.  Update "
-		   "the descriptor's generation?", blkno, di->i_blkno,
-		   di->i_generation, bg->bg_generation)) {
-		bg->bg_generation = di->i_generation;
-		changed = 1;
-	}
-
 	if ((bg->bg_blkno != blkno) &&
-	    prompt(ost, PY, 0, "Group descriptor read from block %"PRIu64" "
+	    prompt(ost, PY, PR_GROUP_BLKNO,
+		   "Group descriptor read from block %"PRIu64" "
 		   "claims to be located at block %"PRIu64".  Update its "
 		   "recorded block location?", blkno, di->i_blkno)) {
 		bg->bg_blkno = blkno;
@@ -124,7 +117,8 @@
 	}
 
 	if ((bg->bg_chain != cs->cs_chain_no) &&
-	    prompt(ost, PY, 0, "Group descriptor at block %"PRIu64" was "
+	    prompt(ost, PY, PR_GROUP_CHAIN,
+		   "Group descriptor at block %"PRIu64" was "
 		   "found in chain %u but it claims to be in chain %u. Update "
 		   "the descriptor's recorded chain?", blkno, cs->cs_chain_no,
 		   bg->bg_chain)) {
@@ -133,7 +127,8 @@
 	}
 
 	if ((bg->bg_free_bits_count > bg->bg_bits) &&
-	    prompt(ost, PY, 0, "Group descriptor at block %"PRIu64" claims to "
+	    prompt(ost, PY, PR_GROUP_FREE_BITS,
+		   "Group descriptor at block %"PRIu64" claims to "
 		   "have %u free bits which is more than its %u total bits. "
 		   "Drop its free bit count down to the total?", blkno,
 		   bg->bg_free_bits_count, bg->bg_bits)) {
@@ -334,7 +329,8 @@
 
 		/* is it even feasible? */
 		if (ocfs2_block_out_of_range(ost->ost_fs, blkno)) {
-			if (prompt(ost, PY, 8, "Chain %d in allocator at inode "
+			if (prompt(ost, PY, PR_CHAIN_LINK_RANGE,
+				   "Chain %d in allocator at inode "
 				   "%"PRIu64" contains a reference at depth "
 				   "%d to block %"PRIu64" which is out "
 				   "of range. Truncate this chain?",
@@ -350,7 +346,8 @@
 
 		ret = ocfs2_read_group_desc(ost->ost_fs, blkno, (char *)bg2);
 		if (ret == OCFS2_ET_BAD_GROUP_DESC_MAGIC) {
-			if (prompt(ost, PY, 8, "Chain %d in allocator at inode "
+			if (prompt(ost, PY, PR_CHAIN_LINK_MAGIC,
+				   "Chain %d in allocator at inode "
 				   "%"PRIu64" contains a reference at depth "
 				   "%d to block %"PRIu64" which doesn't have "
 				   "a valid checksum.  Truncate this chain?",
@@ -375,9 +372,10 @@
 		}
 
 		if (bg2->bg_generation != ost->ost_fs_generation &&
-		    prompt(ost, PY, 0, "Group descriptor at block %"PRIu64" "
+		    prompt(ost, PY, PR_CHAIN_LINK_GEN,
+			   "Group descriptor at block %"PRIu64" "
 			   "has a generation of %"PRIx32" which doesn't match "
-			   "the volume's generation of %"PRIx32".  Delete "
+			   "the volume's generation of %"PRIx32".  Unlink "
 			   "this group descriptor?", blkno, bg2->bg_generation,
 			   ost->ost_fs_generation)) {
 
@@ -420,7 +418,8 @@
 
 	if (cs->cs_total_bits != chain->c_total ||
 	    cs->cs_free_bits != chain->c_free) {
-		if (prompt(ost, PY, 12, "Chain %d in allocator inode %"PRIu64" "
+		if (prompt(ost, PY, PR_CHAIN_BITS,
+			   "Chain %d in allocator inode %"PRIu64" "
 			   "has %u bits marked free out of %d total bits "
 			   "but the block groups in the chain have %u "
 			   "free out of %u total.  Fix this by updating "
@@ -490,7 +489,8 @@
 
 		if (cr->c_blkno != 0&&
 		    ocfs2_block_out_of_range(ost->ost_fs, cr->c_blkno) &&
-		    prompt(ost, PY, 6, "Chain %d in allocator inode %"PRIu64" "
+		    prompt(ost, PY, PR_CHAIN_HEAD_LINK_RANGE,
+			   "Chain %d in allocator inode %"PRIu64" "
 			   "contains an initial block reference to %"PRIu64" "
 			   "which is out of range.  Clear this reference?",
 			   i, di->i_blkno, cr->c_blkno)) {
@@ -502,7 +502,8 @@
 
 	/* make sure cl_count is clamped to the size of the inode */
 	if (cl->cl_count > max_count &&
-	    prompt(ost, PY, 4, "Allocator inode %"PRIu64" claims to have %u "
+	    prompt(ost, PY, PR_CHAIN_COUNT,
+		   "Allocator inode %"PRIu64" claims to have %u "
 		   "chains, but the maximum is %u. Fix the inode's count?",
 		   di->i_blkno, cl->cl_count, max_count)) {
 		cl->cl_count = max_count;
@@ -513,7 +514,8 @@
 		max_count = cl->cl_count;
 
 	if (cl->cl_next_free_rec > max_count) {
-		if (prompt(ost, PY, 5, "Allocator inode %"PRIu64" claims %u "
+		if (prompt(ost, PY, PR_CHAIN_NEXT_FREE,
+			   "Allocator inode %"PRIu64" claims %u "
 			   "as the next free chain record, but fsck believes "
 			   "the largest valid value is %u.  Clamp the next "
 			   "record value?", di->i_blkno, cl->cl_next_free_rec,
@@ -547,7 +549,8 @@
 			continue;
 		}
 
-		if (prompt(ost, PY, 6, "Chain %d in allocator inode %"PRIu64" "
+		if (prompt(ost, PY, PR_CHAIN_EMPTY,
+			   "Chain %d in allocator inode %"PRIu64" "
 			   "is empty.  Remove it from the chain record "
 			   "array in the inode and shift further chains "
 			   "into its place?", cs.cs_chain_no, di->i_blkno)) {
@@ -579,7 +582,8 @@
 
 	if (di->id1.bitmap1.i_total != total || 
 	    (di->id1.bitmap1.i_used != total - free)) {
-		if (prompt(ost, PY, 7, "Allocator inode %"PRIu64" has %u bits "
+		if (prompt(ost, PY, PR_CHAIN_GROUP_BITS,
+			   "Allocator inode %"PRIu64" has %u bits "
 			   "marked used out of %d total bits but the chains "
 			   "have %u used out of %u total.  Fix this by "
 			   "updating the inode counts?", di->i_blkno,
@@ -666,7 +670,8 @@
 	for (blkno = ost->ost_fs->fs_first_cg_blkno;
 	     !ocfs2_bitmap_find_next_set(forbidden, blkno, &blkno);
 	     blkno++) {
-		if (!prompt(ost, PY, 3, "Block %"PRIu64" is a group "
+		if (!prompt(ost, PY, PR_GROUP_UNEXPECTED_DESC,
+			    "Block %"PRIu64" is a group "
 			    "descriptor in the bitmap chain allocator but it "
 			    "isn't at one of the pre-determined locations and "
 			    "so shouldn't be in the allocator.  Remove it "
@@ -699,7 +704,8 @@
 		if (!was_set)
 			continue;
 
-		if (!prompt(ost, PY, 3, "Block %"PRIu64" should be a group "
+		if (!prompt(ost, PY, PR_GROUP_EXPECTED_DESC,
+			    "Block %"PRIu64" should be a group "
 			    "descriptor for the bitmap chain allocator but it "
 			    "wasn't found in any chains.  Reinitialize it as "
 			    "a group desc and link it into the bitmap "

Modified: trunk/fsck.ocfs2/pass1.c
===================================================================
--- trunk/fsck.ocfs2/pass1.c	2004-12-15 01:14:30 UTC (rev 492)
+++ trunk/fsck.ocfs2/pass1.c	2004-12-15 01:22:14 UTC (rev 493)
@@ -126,7 +126,8 @@
 		 * bitmap and if the user wants us to keep tracking it and
 		 * write back the new map */
 		if (oldval != val && !ost->ost_write_inode_alloc_asked) {
-			yn = prompt(ost, PY, 0, "fsck found an inode whose "
+			yn = prompt(ost, PY, PR_INODE_ALLOC_REPAIR,
+				    "fsck found an inode whose "
 				    "allocation does not match the chain "
 				    "allocators.  Fix the allocation of this "
 				    "and all future inodes?");
@@ -151,7 +152,8 @@
 
 	/* make sure the inode's fields are consistent if it's allocated */
 	if (val == 1 && node != (uint16_t)di->i_suballoc_node &&
-	    prompt(ost, PY, 0, "Inode %"PRIu64" indicates that it was allocated "
+	    prompt(ost, PY, PR_INODE_SUBALLOC,
+		   "Inode %"PRIu64" indicates that it was allocated "
 		   "from node %"PRIu16" but node %"PRIu16"'s chain allocator "
 		   "covers the inode.  Fix the inode's record of where it is "
 		   "allocated?",
@@ -178,7 +180,8 @@
 
 	if (la->la_size > max) {
 		broken = 1;
-		if (prompt(ost, PY, 0, "Local alloc inode %"PRIu64" claims to "
+		if (prompt(ost, PY, PR_LALLOC_SIZE,
+			   "Local alloc inode %"PRIu64" claims to "
 			   "have %u bytes of bitmap data but %u bytes is the "
 			   "maximum allowed.  Set the inode's count to the "
 			   "maximum?", di->i_blkno, la->la_size, max)) {
@@ -192,7 +195,8 @@
 		/* ok, it's not used.  we don't mark these errors as 
 		 * 'broken' as the kernel shouldn't care.. right? */
 		if (di->id1.bitmap1.i_used != 0) {
-			if (prompt(ost, PY, 0, "Local alloc inode %"PRIu64" "
+			if (prompt(ost, PY, PR_LALLOC_NZ_USED,
+				   "Local alloc inode %"PRIu64" "
 			    "isn't in use bit its i_used isn't 0.  Set it to "
 			    "0?", di->i_blkno)) {
 
@@ -202,7 +206,8 @@
 		}
 
 		if (la->la_bm_off != 0) {
-			if (prompt(ost, PY, 0, "Local alloc inode %"PRIu64" "
+			if (prompt(ost, PY, PR_LALLOC_NZ_BM,
+				   "Local alloc inode %"PRIu64" "
 			    "isn't in use bit its i_bm_off isn't 0.  Set it "
 			    "to 0?", di->i_blkno)) {
 
@@ -216,7 +221,8 @@
 
 	if (la->la_bm_off >= ost->ost_fs->fs_clusters) {
 		broken = 1;
-		if (prompt(ost, PY, 0, "Local alloc inode %"PRIu64" claims to "
+		if (prompt(ost, PY, PR_LALLOC_BM_OVERRUN,
+			   "Local alloc inode %"PRIu64" claims to "
 			   "contain a bitmap that starts at cluster %u but "
 			   "the volume contains %u clusters.  Mark the local "
 			   "alloc bitmap as unused?", di->i_blkno,
@@ -227,7 +233,8 @@
 
 	if (di->id1.bitmap1.i_total > la->la_size * 8) {
 		broken = 1;
-		if (prompt(ost, PY, 0, "Local alloc inode %"PRIu64" claims to "
+		if (prompt(ost, PY, PR_LALLOC_BM_SIZE,
+			   "Local alloc inode %"PRIu64" claims to "
 			   "have a bitmap with %u bits but the inode can only "
 			   "fit %u bits.  Clamp the bitmap size to this "
 			   "maxmum?", di->i_blkno, di->id1.bitmap1.i_total,
@@ -241,7 +248,8 @@
 	if (la->la_bm_off + di->id1.bitmap1.i_total >
 	    ost->ost_fs->fs_clusters) {
 		broken = 1;
-		if (prompt(ost, PY, 0, "Local alloc inode %"PRIu64" claims to "
+		if (prompt(ost, PY, PR_LALLOC_BM_STRADDLE,
+			   "Local alloc inode %"PRIu64" claims to "
 			   "have a bitmap that covers clusters numbered %u "
 			   "through %u but %u is the last valid cluster. "
 			   "Mark the local bitmap as unused?",
@@ -249,6 +257,7 @@
 			   la->la_bm_off,
 			   la->la_bm_off + di->id1.bitmap1.i_total - 1, 
 			   ost->ost_fs->fs_clusters - 1)) {
+
 			clear = 1;
 		}
 		/* we can't possibly check _used if bm/off and total are
@@ -258,7 +267,8 @@
 
 	if (di->id1.bitmap1.i_used > di->id1.bitmap1.i_total) {
 		broken = 1;
-		if (prompt(ost, PY, 0, "Local alloc inode %"PRIu64" claims to "
+		if (prompt(ost, PY, PR_LALLOC_USED_OVERRUN,
+			   "Local alloc inode %"PRIu64" claims to "
 			   "contain a bitmap with %u bits and %u used.  Set "
 			   "i_used down to %u?", di->i_blkno,
 			   di->id1.bitmap1.i_total, di->id1.bitmap1.i_used, 
@@ -271,7 +281,8 @@
 
 out:
 	if (broken && !clear &&
-	    prompt(ost, PY, 0, "Local alloc inode %"PRIu64" contained errors. "
+	    prompt(ost, PY, PR_LALLOC_CLEAR,
+		   "Local alloc inode %"PRIu64" contained errors. "
 		   "Mark it as unused instead of trying to correct its "
 		   "bitmap?", di->i_blkno)) {
 		clear = 1;
@@ -312,7 +323,8 @@
 	verbosef("checking inode %"PRIu64"'s fields\n", blkno);
 
 	if (di->i_fs_generation != ost->ost_fs_generation) {
-		if (prompt(ost, PY, 0, "Inode read from block %"PRIu64" looks "
+		if (prompt(ost, PY, PR_INODE_GEN,
+			   "Inode read from block %"PRIu64" looks "
 			   "like it is valid but it has a generation of %x "
 			   "that doesn't match the current volume's "
 			   "generation of %x.  This is probably a harmless "
@@ -322,7 +334,8 @@
 			clear = 1;
 			goto out;
 		}
-		if (prompt(ost, PY, 0, "Update the inode's generation to match "
+		if (prompt(ost, PY, PR_INODE_GEN_FIX,
+			   "Update the inode's generation to match "
 			  "the volume?")) {
 
 			di->i_fs_generation = ost->ost_fs_generation;
@@ -342,9 +355,11 @@
 	 * fsck can do to fix it up */
 
 	if (di->i_blkno != blkno &&
-	    prompt(ost, PY, 0, "Inode read from block %"PRIu64" has i_blkno set "
+	    prompt(ost, PY, PR_INODE_BLKNO,
+		   "Inode read from block %"PRIu64" has i_blkno set "
 		   "to %"PRIu64".  Set the inode's i_blkno value to reflect "
 		   "its location on disk?", blkno, di->i_blkno)) {
+
 		di->i_blkno = blkno;
 		o2fsck_write_inode(ost, blkno, di);
 	}
@@ -356,8 +371,10 @@
 	/* offer to clear a non-directory root inode so that 
 	 * pass3:check_root() can re-create it */
 	if ((di->i_blkno == fs->fs_root_blkno) && !S_ISDIR(di->i_mode) && 
-	    prompt(ost, PY, 0, "Root inode isn't a directory.  Clear it in "
+	    prompt(ost, PY, PR_ROOT_NOTDIR,
+		   "Root inode isn't a directory.  Clear it in "
 		   "preparation for fixing it?")) {
+
 		di->i_dtime = 0ULL;
 		di->i_links_count = 0ULL;
 		o2fsck_icount_set(ost->ost_icount_in_inodes, di->i_blkno,
@@ -366,9 +383,11 @@
 		o2fsck_write_inode(ost, blkno, di);
 	}
 
-	if (di->i_dtime && prompt(ost, PY, 0, "Inode %"PRIu64" is in use but has "
-				  "a non-zero dtime.  Reset the dtime to 0?",  
-				   di->i_blkno)) {
+	if (di->i_dtime &&
+	    prompt(ost, PY, PR_INODE_NZ_DTIME,
+		   "Inode %"PRIu64" is in use but has a non-zero dtime. Reset "
+		   "the dtime to 0?",  di->i_blkno)) {
+
 		di->i_dtime = 0ULL;
 		o2fsck_write_inode(ost, blkno, di);
 	}
@@ -408,13 +427,11 @@
 
 struct verifying_blocks {
        unsigned		vb_clear:1,
-       			vb_saw_link_null:1,
-       			vb_link_read_error:1;
+       			vb_saw_link_null:1;
 
        uint64_t		vb_link_len;
        uint64_t		vb_num_blocks;	
        uint64_t		vb_last_block;	
-       int		vb_errors;
        o2fsck_state 	*vb_ost;
        ocfs2_dinode	*vb_di;
        errcode_t	vb_ret;
@@ -469,22 +486,13 @@
 	uint64_t expected;
 
 	verbosef("found a link: num %"PRIu64" last %"PRIu64" len "
-		"%"PRIu64" null %d error %d\n", vb->vb_num_blocks, 
-		vb->vb_last_block, vb->vb_link_len, vb->vb_saw_link_null, 
-		vb->vb_link_read_error);
+		"%"PRIu64" null %d\n", vb->vb_num_blocks, 
+		vb->vb_last_block, vb->vb_link_len, vb->vb_saw_link_null);
 
-	if (vb->vb_link_read_error) {
-		if (prompt(ost, PY, 0, "There was an error reading a data block "
-			   "for symlink inode %"PRIu64".  Clear the inode?",
-			   di->i_blkno)) {
-			vb->vb_clear = 1;
-			return;
-		}
-	}
-
 	/* XXX this could offer to null terminate */
 	if (!vb->vb_saw_link_null) {
-		if (prompt(ost, PY, 0, "The target of symlink inode %"PRIu64" "
+		if (prompt(ost, PY, PR_LINK_NULLTERM,
+			   "The target of symlink inode %"PRIu64" "
 			   "isn't null terminated.  Clear the inode?",
 			   di->i_blkno)) {
 			vb->vb_clear = 1;
@@ -495,7 +503,8 @@
 	expected = ocfs2_blocks_in_bytes(ost->ost_fs, vb->vb_link_len + 1);
 
 	if (di->i_size != vb->vb_link_len) {
-		if (prompt(ost, PY, 0, "The target of symlink inode %"PRIu64" "
+		if (prompt(ost, PY, PR_LINK_SIZE,
+			   "The target of symlink inode %"PRIu64" "
 			   "is %"PRIu64" bytes long on disk, but i_size is "
 			   "%"PRIu64" bytes long.  Update i_size to reflect "
 			   "the length on disk?",
@@ -509,7 +518,8 @@
 	/* maybe we don't shrink link target allocations, I don't know,
 	 * someone will holler if this is wrong :) */
 	if (vb->vb_num_blocks != expected) {
-		if (prompt(ost, PN, 0, "The target of symlink inode %"PRIu64" "
+		if (prompt(ost, PN, PR_LINK_BLOCKS,
+			   "The target of symlink inode %"PRIu64" "
 			   "fits in %"PRIu64" blocks but the inode has "
 			   "%"PRIu64" allocated.  Clear the inode?", 
 			   di->i_blkno, expected, vb->vb_num_blocks)) {
@@ -531,28 +541,6 @@
 	
 	/* someday we may want to worry about holes in files here */
 
-	if ((blkno < OCFS2_SUPER_BLOCK_BLKNO) || (blkno > fs->fs_blocks)) {
-		vb->vb_errors++;
-#if 0 /* XXX ext2 does this by returning a value to libext2 which clears the 
-	 block from the inode's allocation */
-		if (prompt(ost, PY, 0, "inode %"PRIu64" references bad physical "
-			   "block %"PRIu64" at logical block %"PRIu64", "
-			   "should it be cleared?", di->i_blkno, bklno, 
-			   bcount)) {
-		}
-#endif
-	}
-
-	/* XXX this logic should be more sophisticated.  It's not really clear
-	 * what ext2 is trying to do in theirs. */
-	if (vb->vb_errors == 12) {
-		if (prompt(ost, PY, 0, "inode %"PRIu64" has seen many errors, "
-			   "should it be cleared?", di->i_blkno)) {
-			vb->vb_clear = 1;
-			return OCFS2_BLOCK_ABORT;
-		}
-	}
-
 	if (S_ISDIR(di->i_mode)) {
 		verbosef("adding dir block %"PRIu64"\n", blkno);
 		ret = o2fsck_add_dir_block(&ost->ost_dirblocks, di->i_blkno,
@@ -622,11 +610,12 @@
 	if (S_ISLNK(di->i_mode))
 		check_link_data(&vb);
 
-	if (S_ISDIR(di->i_mode) && vb.vb_num_blocks == 0) {
-		if (prompt(ost, PY, 0, "Inode %"PRIu64" is a zero length "
-			   "directory, clear it?", di->i_blkno)) {
-			vb.vb_clear = 1;
-		}
+	if (S_ISDIR(di->i_mode) && vb.vb_num_blocks == 0 &&
+	    prompt(ost, PY, PR_DIR_ZERO,
+		   "Inode %"PRIu64" is a zero length directory, clear it?",
+		   di->i_blkno)) {
+
+		vb.vb_clear = 1;
 	}
 
 	/*
@@ -662,7 +651,8 @@
 		expected = ocfs2_clusters_in_blocks(fs, vb.vb_last_block + 1);
 
 	if (di->i_clusters < expected &&
-	    prompt(ost, PY, 0, "inode %"PRIu64" has %"PRIu32" clusters but its "
+	    prompt(ost, PY, PR_INODE_CLUSTERS,
+		   "Inode %"PRIu64" has %"PRIu32" clusters but its "
 		   "blocks fit in %"PRIu64" clusters.  Correct the number of "
 		   "clusters?", di->i_blkno, di->i_clusters, expected)) {
 		di->i_clusters = expected;
@@ -707,7 +697,8 @@
 
 		/* XXX specifically for each bit? */
 		if (!changed &&
-		    !prompt(ost, PY, 0, "Local alloc inode %"PRIu64" has bits "
+		    !prompt(ost, PY, PR_LALLOC_REPAIR,
+			    "Local alloc inode %"PRIu64" has bits "
 			    "in its bitmap which don't match what is used in "
 			    "the file system.  Sync its bitmap up with what "
 			    "is in use?", di->i_blkno))
@@ -729,7 +720,8 @@
 	}
 
 	if (di->id1.bitmap1.i_used != used) {
-		if (prompt(ost, PY, 0, "Local alloc inode %"PRIu64" now has "
+		if (prompt(ost, PY, PR_LALLOC_USED,
+			   "Local alloc inode %"PRIu64" now has "
 			   "%u bits set in its bitmap but it thinks there are "
 			   "%u set.  Fix the record of set bits to match "
 			   "how many are really set in the bitmap?",
@@ -856,7 +848,7 @@
 			 "bitmap?";
 	}
 
-	if (!prompt(ost, PY, 0, reason, bit))
+	if (!prompt(ost, PY, PR_CLUSTER_ALLOC_BIT, reason, bit))
 		return 0;
 
 	ret = ocfs2_chain_force_val(ost->ost_fs, ci, bit, !!val, NULL);

Modified: trunk/fsck.ocfs2/pass2.c
===================================================================
--- trunk/fsck.ocfs2/pass2.c	2004-12-15 01:14:30 UTC (rev 492)
+++ trunk/fsck.ocfs2/pass2.c	2004-12-15 01:22:14 UTC (rev 493)
@@ -109,8 +109,10 @@
 	       	if (!dirent_has_dots(dirent, 1) && !dirent_has_dots(dirent, 2))
 			goto out;
 			return 0;
-		if (prompt(ost, PY, 0, "Duplicate '%.*s' directory entry found, "
-			   "remove it?", dirent->name_len, dirent->name)) {
+		if (prompt(ost, PY, PR_DIRENT_DOTTY_DUP,
+			   "Duplicate '%.*s' directory entry found, remove "
+			   "it?", dirent->name_len, dirent->name)) {
+
 			dirent->inode = 0;
 			*flags |= OCFS2_DIRENT_CHANGED;
 			goto out;
@@ -118,7 +120,8 @@
 	}
 
 	if (!dirent_has_dots(dirent, expect_dots) &&
-	    prompt(ost, PY, 0, "The %s directory entry in directory inode "
+	    prompt(ost, PY, PR_DIRENT_NOT_DOTTY,
+		   "The %s directory entry in directory inode "
 		   "%"PRIu64" is '%.*s' instead of '%.*s'.  Clobber the "
 		   "current name with the expected dot name?", 
 		   expect_dots == 1 ? "first" : "second", dbe->e_ino, 
@@ -147,7 +150,8 @@
 	}
 
 	if ((dirent->inode != dbe->e_ino) &&
-            prompt(ost, PY, 0, "The '.' entry in directory inode %"PRIu64" "
+            prompt(ost, PY, PR_DIRENT_DOT_INODE,
+		   "The '.' entry in directory inode %"PRIu64" "
 		   "points to inode %"PRIu64" instead of itself.  Fix "
 		   "the '.' entry?", dbe->e_ino, dirent->inode)) {
 		dirent->inode = dbe->e_ino;
@@ -161,7 +165,8 @@
 	 */
 	new_len = OCFS2_DIR_REC_LEN(dirent->name_len) - dirent->rec_len;
 	if (new_len && (changed_len || 
-			prompt(ost, PY, 0, "The '.' entry in directory inode "
+			prompt(ost, PY, PR_DIRENT_DOT_EXCESS,
+			       "The '.' entry in directory inode "
 			       "%"PRIu64" is too long.  Try to create another "
 			       "directory entry from the excess?", 
 			       dbe->e_ino))) {
@@ -229,7 +234,8 @@
 	int len = dirent->name_len, fix = 0;
 
 	if (len == 0) {
-		if (prompt(ost, PY, 0, "Directory entry has a zero-length name, "
+		if (prompt(ost, PY, PR_DIRENT_ZERO,
+			   "Directory entry has a zero-length name, "
 				    "clear it?")) {
 			dirent->inode = 0;
 			*flags |= OCFS2_DIRENT_CHANGED;
@@ -239,7 +245,8 @@
 	for(; len-- > 0 && (*chr == '/' || *chr == '\0'); chr++) {
 		/* XXX in %s parent name */
 		if (!fix) {
-			fix = prompt(ost, PY, 0, "Directory entry '%.*s' "
+			fix = prompt(ost, PY, PR_DIRENT_NAME_CHARS,
+				     "Directory entry '%.*s' "
 				     "contains invalid characters, replace "
 				     "them with dots?", dirent->name_len, 
 				     dirent->name);
@@ -256,7 +263,8 @@
 			     int *flags)
 {
 	if (ocfs2_block_out_of_range(ost->ost_fs, dirent->inode) &&
-	    prompt(ost, PY, 0, "Directory entry '%.*s' refers to inode "
+	    prompt(ost, PY, PR_DIRENT_INODE_RANGE,
+		   "Directory entry '%.*s' refers to inode "
 		   "number %"PRIu64" which is out of range, clear the entry?",
 		   dirent->name_len, dirent->name, dirent->inode)) {
 
@@ -266,7 +274,8 @@
 	}
 
 	if (!o2fsck_test_inode_allocated(ost, dbe->e_ino) &&
-	    prompt(ost, PY, 0, "Directory entry '%.*s' refers to inode number "
+	    prompt(ost, PY, PR_DIRENT_INODE_FREE,
+		   "Directory entry '%.*s' refers to inode number "
 		   "%"PRIu64" which isn't allocated, clear the entry?", 
 		   dirent->name_len, dirent->name, dirent->inode)) {
 		dirent->inode = 0;
@@ -337,7 +346,8 @@
 
 check:
 	if ((dirent->file_type != expected_type) &&
-	    prompt(ost, PY, 0, "Directory entry %.*s contains file type %s (%u) "
+	    prompt(ost, PY, PR_DIRENT_TYPE,
+		   "Directory entry %.*s contains file type %s (%u) "
 		"but its inode %"PRIu64" leads to type %s (%u).  Reset the "
 		"entry's type to match the inode's?",
 		dirent->name_len, dirent->name, 
@@ -397,7 +407,8 @@
 		goto out;
 	}
 
-	if (prompt(ost, 0, 0, "Directory inode %"PRIu64" is not the first to "
+	if (prompt(ost, 0, PR_DIR_PARENT_DUP,
+		   "Directory inode %"PRIu64" is not the first to "
 		"claim to be the parent of subdir '%.*s' (inode %"PRIu64"). "
 		"Clear this directory entry and leave the previous parent of "
 		"the subdir's inode intact?", dbe->e_ino, 
@@ -504,7 +515,8 @@
 		/* if we can't trust this dirent then fix it up or skip
 		 * the whole block */
 		if (corrupt_dirent(dirent, dd->fs->fs_blocksize - offset)) {
-			if (!prompt(dd->ost, PY, 0, "Directory inode %"PRIu64" "
+			if (!prompt(dd->ost, PY, PR_DIRENT_LENGTH,
+				    "Directory inode %"PRIu64" "
 				    "corrupted in logical block %"PRIu64" "
 				    "physical block %"PRIu64" offset %d. "
 				    "Attempt to repair this block's directory "

Modified: trunk/fsck.ocfs2/pass3.c
===================================================================
--- trunk/fsck.ocfs2/pass3.c	2004-12-15 01:14:30 UTC (rev 492)
+++ trunk/fsck.ocfs2/pass3.c	2004-12-15 01:22:14 UTC (rev 493)
@@ -59,7 +59,8 @@
 		return;
 	}
 
-	if (!prompt(ost, PY, 0, "The root inode %"PRIu64" doesn't exist. "
+	if (!prompt(ost, PY, PR_ROOT_DIR_MISSING,
+		    "The root inode %"PRIu64" doesn't exist. "
 			"Should it be created?", ost->ost_fs->fs_root_blkno)) {
 		printf("Aborting.\n");
 		exit(FSCK_ERROR);
@@ -85,7 +86,8 @@
 	if (ret == 0)
 		return;
 
-	if (!prompt(ost, PY, 0, "/lost+found does not exist.  Create it so "
+	if (!prompt(ost, PY, PR_LOSTFOUND_MISSING,
+		    "/lost+found does not exist.  Create it so "
 		    "that we an possibly fill it with orphaned inodes?"))
 		return;
 
@@ -318,7 +320,8 @@
 		/* ok, we hit an orphan subtree with no parent or are at 
 		 * the dir in a subtree that is the first to try to reference
 		 * a dir in its children */
-		fix = prompt(ost, PY, 0, "Directory inode %"PRIu64" isn't "
+		fix = prompt(ost, PY, PR_DIR_NOT_CONNECTED,
+			     "Directory inode %"PRIu64" isn't "
 			     "connected to the filesystem.  Move it to "
 			     "lost+found?", dp->dp_ino);
 		if (fix)
@@ -328,7 +331,8 @@
 	}
 
 	if (dir->dp_dirent != dir->dp_dot_dot) {
-		fix = prompt(ost, PY, 0, "Directory inode %"PRIu64" is "
+		fix = prompt(ost, PY, PR_DIR_DOTDOT,
+			     "Directory inode %"PRIu64" is "
 			     "referenced by a dirent in directory %"PRIu64" "
 			     "but its '..' entry points to inode %"PRIu64". "
 			     "Fix the '..' entry to reference %"PRIu64"?", 

Modified: trunk/fsck.ocfs2/pass4.c
===================================================================
--- trunk/fsck.ocfs2/pass4.c	2004-12-15 01:14:30 UTC (rev 492)
+++ trunk/fsck.ocfs2/pass4.c	2004-12-15 01:22:14 UTC (rev 493)
@@ -51,7 +51,8 @@
 
 	/* XXX offer to remove files/dirs with no data? */
 	if (refs == 0 &&
-	    prompt(ost, PY, 0, "Inode %"PRIu64" isn't referenced by any "
+	    prompt(ost, PY, PR_INODE_NOT_CONNECTED,
+		   "Inode %"PRIu64" isn't referenced by any "
 		   "directory entries.  Move it to lost+found?", 
 		   di->i_blkno)) {
 		o2fsck_reconnect_file(ost, blkno);
@@ -74,7 +75,8 @@
 			"disk it is %"PRIu16, di->i_blkno, in_inode, 
 			di->i_links_count);
 
-	if (prompt(ost, PY, 0, "Inode %"PRIu64" has a link count of %"PRIu16" on "
+	if (prompt(ost, PY, PR_INODE_COUNT,
+		   "Inode %"PRIu64" has a link count of %"PRIu16" on "
 		   "disk but directory entry references come to %"PRIu16". "
 		   "Update the count on disk to match?", di->i_blkno, in_inode, 
 		   refs)) {

Modified: trunk/fsck.ocfs2/problem.c
===================================================================
--- trunk/fsck.ocfs2/problem.c	2004-12-15 01:14:30 UTC (rev 492)
+++ trunk/fsck.ocfs2/problem.c	2004-12-15 01:22:14 UTC (rev 493)
@@ -146,7 +146,7 @@
  * and have a notion of grouping, as well.  The caller is expected to provide
  * a fully formed question that isn't terminated with a newline.
  */
-int prompt_input(o2fsck_state *ost, unsigned flags, uint16_t code,
+int prompt_input(o2fsck_state *ost, unsigned flags, struct prompt_code code,
 		const char *fmt, ...)
 {
 	va_list ap;
@@ -169,7 +169,7 @@
 	}
 
 	if (flags & (PY|PN))
-		len += sizeof(yes) + 10; /* includes code and null */
+		len += sizeof(yes) + 80; /* W. includes code and null */
 
 	output = malloc(len);
 	if (output == NULL) {
@@ -177,7 +177,7 @@
 		exit(FSCK_ERROR);
 	}
 
-	part = snprintf(output, len, "[%u] ", code);
+	part = snprintf(output, len, "[%s] ", code.str);
 	if (part < 0) {
 		perror("vsnprintf failed when trying to bulid an output "
 		       "buffer");



More information about the Ocfs2-tools-commits mailing list