cluster: RHEL510 - gfs2_convert: calculate height 1 for small files that were once big

Bob Peterson rpeterso at fedoraproject.org
Fri Apr 5 15:24:14 UTC 2013


Gitweb:        http://git.fedorahosted.org/git/?p=cluster.git;a=commitdiff;h=078afe992b4ad9b96e8fb2079a6cedbd1cdda843
Commit:        078afe992b4ad9b96e8fb2079a6cedbd1cdda843
Parent:        11795482c88f4866654c583466e336fd5fffdece
Author:        Bob Peterson <rpeterso at redhat.com>
AuthorDate:    Mon Dec 17 15:11:34 2012 -0600
Committer:     Bob Peterson <rpeterso at redhat.com>
CommitterDate: Fri Apr 5 07:02:06 2013 -0700

gfs2_convert: calculate height 1 for small files that were once big

This patch changes function calc_gfs2_tree_height so that it gives
a height of 1 to small files that once were big. The problems here
is with files that were once big (needed two levels of indirection
(height 2)) and then are truncated to a tiny non-zero size
(ordinarily, they would be stuffed, but due to the growth followed
by truncate, they're still at height 2). The required GFS2 height is
zero, whereas the GFS1 height is 2. After the conversion the file
will not really be stuffed, because function fix_metatree will
unstuff the dinode as part of its conversion. So at least it will
be at height 1. The problem is that if we don't fix the 0 height to
its proper value of 1, fix_ind_reg_or_dir gets called with gfs2_hgt=0,
which then calls mp_gfs1_to_gfs2, which then tries to set:
gfs2factor[gfs2_h - 1] = 1ull. This results in a negative index of the
array.

rhbz#887374
---
 gfs2/convert/gfs2_convert.c |    6 ++++++
 1 files changed, 6 insertions(+), 0 deletions(-)

diff --git a/gfs2/convert/gfs2_convert.c b/gfs2/convert/gfs2_convert.c
index b3e9538..659127a 100644
--- a/gfs2/convert/gfs2_convert.c
+++ b/gfs2/convert/gfs2_convert.c
@@ -268,6 +268,12 @@ static unsigned int calc_gfs2_tree_height(struct gfs2_inode *ip, uint64_t size)
 	for (height = 0; height < max; height++)
 		if (arr[height] >= size)
 			break;
+	/* If calc_gfs2_tree_height was called, the dinode is not stuffed or
+	   we would have returned before this point. After the call, a call is
+	   made to fix_metatree, which unstuffs the dinode. Therefore, the
+	   smallest height that can result after this call is 1. */
+	if (!height)
+		height = 1;
 
 	return height;
 }


More information about the cluster-commits mailing list