[Ocfs2-tools-devel] [PATCH] Fix alloc_clusters returning small clusters

Goldwyn Rodrigues rgoldwyn at gmail.com
Mon May 10 13:31:34 PDT 2010


The cluster allocation is returning smaller clusters even if bigger
clusters are available. The best match is checked in the
bitmap region being processed as opposed to all the bitmap regions.

This fix checks cluster allocation across all bitmap regions and
returns the best possible cluster available for allocation.

Signed-off-by: Goldwyn Rodrigues <rgoldwyn at suse.de>

---
diff --git a/libocfs2/bitmap.c b/libocfs2/bitmap.c
index a5fe511..cc6f761 100644
--- a/libocfs2/bitmap.c
+++ b/libocfs2/bitmap.c
@@ -640,8 +640,9 @@ struct alloc_range_args {
 	ocfs2_bitmap	*ar_bitmap;
 	uint64_t	ar_min_len;
 	uint64_t	ar_len;
-	uint64_t	ar_first_bit;
-	uint64_t	ar_bits_found;
+	struct ocfs2_bitmap_region *ar_br;
+	int 		ar_start;
+	int		ar_end;
 	errcode_t	ar_ret;
 };

@@ -653,11 +654,10 @@ static errcode_t alloc_range_func(struct
ocfs2_bitmap_region *br,
 {
 	struct alloc_range_args *ar = private_data;
 	errcode_t ret = 0;
-	uint64_t best_start = UINT64_MAX, best_len = 0;
 	int start, end;

 	if ((br->br_total_bits - br->br_set_bits) < ar->ar_min_len)
-		goto out;
+		return 0;

 	for (start = 0; start + ar->ar_min_len <= br->br_total_bits; ) {
 		start = ocfs2_find_next_bit_clear(br->br_bitmap,
@@ -674,36 +674,25 @@ static errcode_t alloc_range_func(struct
ocfs2_bitmap_region *br,

 		/* We've found a region large enough to hold our max. */
 		if ((end - start) >= ar->ar_len) {
-			end = start + ar->ar_len;
-			goto found;
+			ar->ar_br = br;
+			ar->ar_start = start;
+			ar->ar_end = start + ar->ar_len;
+			ar->ar_ret = 0;
+			ret = OCFS2_ET_ITERATION_COMPLETE;
+			break;
 		}

-		if ((end - start) > best_len) {
-			best_len = end - start;
-			best_start = start;
+		/* check and collect best fit */
+		if (((end - start) > (ar->ar_end - ar->ar_start)) &&
+			((end - start) >= ar->ar_min_len)){
+			ar->ar_br = br;
+			ar->ar_start = start;
+			ar->ar_end = end;
+			ar->ar_ret = 0;
 		}

 		start = end + 1;
 	}
-
-	/* Nothing found at all */
-	if (best_start == UINT64_MAX || best_len < ar->ar_min_len)
-		goto out;
-
-	/* Best fit works */
-	start = best_start;
-	end = best_start + best_len;
-found:
-	ar->ar_first_bit = br->br_start_bit + start;
-	ar->ar_bits_found = end - start;
-
-	for (; start < end; start++)
-		set_generic_shared(ar->ar_bitmap, br,
-				   start + br->br_start_bit);
-
-	ar->ar_ret = 0;
-	ret = OCFS2_ET_ITERATION_COMPLETE;
-out:
 	return ret;
 }

@@ -718,6 +707,9 @@ errcode_t
ocfs2_bitmap_alloc_range_generic(ocfs2_bitmap *bitmap,
 		.ar_bitmap = bitmap,
 		.ar_min_len = min_len,
 		.ar_len = len,
+		.ar_br = NULL,
+		.ar_start = 0,
+		.ar_end = 0,
 		.ar_ret = OCFS2_ET_BIT_NOT_FOUND,
 	};

@@ -727,8 +719,12 @@ errcode_t
ocfs2_bitmap_alloc_range_generic(ocfs2_bitmap *bitmap,
 		ret = ar.ar_ret;

 	if (ret == 0) {
-		*first_bit = ar.ar_first_bit;
-		*bits_found = ar.ar_bits_found;
+		int i = ar.ar_start;
+		for(; i < ar.ar_end; i++)
+			set_generic_shared(bitmap, ar.ar_br,
+					ar.ar_br->br_start_bit + i);
+		*first_bit = ar.ar_br->br_start_bit + ar.ar_start;
+		*bits_found = ar.ar_end - ar.ar_start;
 	}

 	return ret;



More information about the Ocfs2-tools-devel mailing list