[Ocfs2-commits] mfasheh commits r1630 - branches/cluster-groups/src
svn-commits at oss.oracle.com
svn-commits at oss.oracle.com
Tue Nov 9 22:09:12 CST 2004
Author: mfasheh
Date: 2004-11-09 22:09:10 -0600 (Tue, 09 Nov 2004)
New Revision: 1630
Modified:
branches/cluster-groups/src/localalloc.c
branches/cluster-groups/src/suballoc.c
branches/cluster-groups/src/suballoc.h
Log:
* rename ocfs_search_suballoc_chain to ocfs_search_chain
* simplify some of the code for doing group descriptor searches
* factor out the cluster bitmap setup code into it's own function so local
alloc can call that when sliding windows.
* some of our cluster group calculations for delete were off
* la_set_bits wasn't being updated properly. Update it correctly, and rely
on that in ocfs_reserve_local_alloc_bits instead of a bitmap search.
* fix an inode leak in ocfs_reserve_local_alloc_bits
* add some code to help debug window shifts
* lots of debugging printks. these will be removed when we sync back to
trunk.
Modified: branches/cluster-groups/src/localalloc.c
===================================================================
--- branches/cluster-groups/src/localalloc.c 2004-11-10 04:02:40 UTC (rev 1629)
+++ branches/cluster-groups/src/localalloc.c 2004-11-10 04:09:10 UTC (rev 1630)
@@ -124,8 +124,8 @@
if (osb->have_local_alloc
&& (ocfs2_clusters_to_bytes(osb->sb, bits) <= OCFS_LOCAL_ALLOC_MAX_ALLOC)
&& (bits <= ocfs_local_alloc_window_bits(osb)))
- return(1);
- return(0);
+ return 1;
+ return 0;
}
/*
@@ -491,9 +491,9 @@
ocfs2_alloc_context *ac)
{
int status;
- int startoff;
ocfs2_dinode *alloc;
struct inode *local_alloc_inode;
+ int free_bits;
LOG_ENTRY();
@@ -531,8 +531,13 @@
}
alloc = (ocfs2_dinode *) osb->local_alloc_bh->b_data;
- startoff = ocfs_local_alloc_find_clear_bits(osb, alloc, bits_wanted);
- if (startoff == -1) {
+
+ OCFS_ASSERT(LOCAL_ALLOC(alloc)->la_bits_set ==
+ ocfs_local_alloc_count_bits(alloc));
+
+ free_bits = le16_to_cpu(LOCAL_ALLOC(alloc)->la_bm_bits) -
+ le16_to_cpu(LOCAL_ALLOC(alloc)->la_bits_set);
+ if (bits_wanted > free_bits) {
/* uhoh, window change time. */
status =
ocfs_local_alloc_slide_window(osb, local_alloc_inode);
@@ -549,6 +554,8 @@
ac->ac_which = OCFS_AC_USE_LOCAL;
status = 0;
bail:
+ if (local_alloc_inode)
+ iput(local_alloc_inode);
LOG_EXIT_STATUS(status);
return(status);
@@ -599,6 +606,8 @@
while(bits_wanted--)
ocfs2_set_bit(start++, bitmap);
+ LOCAL_ALLOC(alloc)->la_bits_set += *num_bits;
+
status = ocfs_journal_dirty(handle, osb->local_alloc_bh);
if (status < 0) {
LOG_ERROR_STATUS(status);
@@ -714,6 +723,25 @@
return;
} /* ocfs_clear_local_alloc */
+#if 0
+/* turn this on and uncomment below to aid debugging window shifts. */
+static void ocfs2_verify_zero_bits(unsigned long *bitmap,
+ unsigned int start,
+ unsigned int count)
+{
+ unsigned int tmp = count;
+ while(tmp--) {
+ if (ocfs2_test_bit(start + tmp, bitmap)) {
+ printk("ocfs2_verify_zero_bits: start = %u, count = "
+ "%u\n", start, count);
+ printk("ocfs2_verify_zero_bits: bit %u is set!",
+ start + tmp);
+ BUG();
+ }
+ }
+}
+#endif
+
/*
* ocfs_sync_local_to_main
*
@@ -734,8 +762,8 @@
u64 blkno;
void *bitmap;
- LOG_ENTRY_ARGS("alloc->la_bm_bits = %u, COUNT = %u, la_bits_set = %u\n",
- LOCAL_ALLOC(alloc)->la_bm_bits,
+ LOG_ENTRY_ARGS("alloc->la_bm_bits = %u, COUNT = %u, "
+ "la_bits_set = %u\n", LOCAL_ALLOC(alloc)->la_bm_bits,
ocfs_local_alloc_count_bits(alloc),
LOCAL_ALLOC(alloc)->la_bits_set);
@@ -750,6 +778,11 @@
goto bail;
}
+ printk("sync_local_to_main: alloc->la_bm_bits = %u, COUNT = %u, "
+ "la_bits_set = %u\n", LOCAL_ALLOC(alloc)->la_bm_bits,
+ ocfs_local_alloc_count_bits(alloc),
+ LOCAL_ALLOC(alloc)->la_bits_set);
+
la_start_blk = ocfs2_clusters_to_blocks(osb->sb,
LOCAL_ALLOC(alloc)->la_bm_off);
bitmap = LOCAL_ALLOC(alloc)->la_bitmap;
@@ -764,19 +797,23 @@
continue;
}
if (count) {
- blkno = la_start_blk + (u64) (start - count);
+// ocfs2_verify_zero_bits(bitmap, start, count);
- printk("freeing %u bits starting at local alloc bit "
- "%u (la_start_blk = %llu, blkno = %llu)\n",
- count, start, la_start_blk, blkno);
+ blkno = la_start_blk +
+ ocfs2_clusters_to_blocks(osb->sb,
+ start - count);
+ printk("sync_local_to_main: freeing %u bits starting "
+ "at local alloc bit %u (la_start_blk = %llu, "
+ "blkno = %llu)\n", count, start - count,
+ la_start_blk, blkno);
+
status = ocfs_free_clusters(handle, main_bm_inode,
main_bm_bh, blkno, count);
if (status < 0) {
LOG_ERROR_STATUS(status);
goto bail;
}
-
}
if (bit_off >= left)
break;
@@ -806,17 +843,8 @@
memset(*ac, 0, sizeof(ocfs2_alloc_context));
(*ac)->ac_handle = handle;
(*ac)->ac_bits_wanted = ocfs_local_alloc_window_bits(osb);
- (*ac)->ac_inode = ocfs_get_system_file_inode(osb,
- GLOBAL_BITMAP_SYSTEM_INODE,
- -1);
- if (!(*ac)->ac_inode) {
- status = -EINVAL;
- LOG_ERROR_STR("Could not get bitmap inode!");
- goto bail;
- }
- (*ac)->ac_which = OCFS_AC_USE_MAIN;
- status = ocfs_reserve_suballoc_bits(osb, *ac);
+ status = ocfs_reserve_cluster_bitmap_bits(osb, *ac);
if (status < 0) {
LOG_ERROR_STATUS(status);
goto bail;
Modified: branches/cluster-groups/src/suballoc.c
===================================================================
--- branches/cluster-groups/src/suballoc.c 2004-11-10 04:02:40 UTC (rev 1629)
+++ branches/cluster-groups/src/suballoc.c 2004-11-10 04:09:10 UTC (rev 1630)
@@ -59,6 +59,10 @@
static int ocfs_block_group_alloc(ocfs_super *osb,
struct inode *alloc_inode,
struct buffer_head *bh);
+
+static int ocfs_reserve_suballoc_bits(ocfs_super *osb,
+ ocfs2_alloc_context *ac);
+
static int ocfs2_cluster_group_search(struct inode *inode,
struct buffer_head *group_bh,
u32 bits_wanted, u32 min_bits,
@@ -67,12 +71,12 @@
struct buffer_head *group_bh,
u32 bits_wanted, u32 min_bits,
u16 *bit_off, u16 *bits_found);
-static int ocfs_search_suballoc_chain(ocfs2_alloc_context *ac,
- u32 bits_wanted,
- u32 min_bits,
- u16 *bit_off,
- unsigned int *num_bits,
- u64 *bg_blkno);
+static int ocfs_search_chain(ocfs2_alloc_context *ac,
+ u32 bits_wanted,
+ u32 min_bits,
+ u16 *bit_off,
+ unsigned int *num_bits,
+ u64 *bg_blkno);
static int ocfs_claim_suballoc_bits(ocfs_super *osb,
ocfs2_alloc_context *ac,
u32 bits_wanted,
@@ -407,8 +411,8 @@
return status;
}
-int ocfs_reserve_suballoc_bits(ocfs_super *osb,
- ocfs2_alloc_context *ac)
+static int ocfs_reserve_suballoc_bits(ocfs_super *osb,
+ ocfs2_alloc_context *ac)
{
int status;
u32 bits_wanted = ac->ac_bits_wanted;
@@ -571,6 +575,31 @@
return status;
}
+/* local alloc code has to do the same thing, so rather than do this
+ * twice.. */
+int ocfs_reserve_cluster_bitmap_bits(ocfs_super *osb,
+ ocfs2_alloc_context *ac)
+{
+ int status;
+
+ ac->ac_inode = ocfs_get_system_file_inode(osb,
+ GLOBAL_BITMAP_SYSTEM_INODE,
+ -1);
+ if (!ac->ac_inode) {
+ status = -EINVAL;
+ LOG_ERROR_STR("Could not get bitmap inode!");
+ goto bail;
+ }
+ ac->ac_which = OCFS_AC_USE_MAIN;
+ ac->ac_group_search = &ocfs2_cluster_group_search;
+
+ status = ocfs_reserve_suballoc_bits(osb, ac);
+ if (status < 0)
+ LOG_ERROR_STATUS(status);
+bail:
+ return status;
+}
+
/* Callers don't need to care which bitmap (local alloc or main) to
* use so we figure it out for them, but unfortunately this clutters
* things a bit. */
@@ -580,7 +609,6 @@
ocfs2_alloc_context **ac)
{
int status;
- struct inode *main_bitmap_inode = NULL;
LOG_ENTRY();
@@ -617,18 +645,7 @@
}
if (status == -ENOSPC) {
- main_bitmap_inode = ocfs_get_system_file_inode(osb,
- GLOBAL_BITMAP_SYSTEM_INODE,
- -1);
- if (!main_bitmap_inode) {
- status = -EINVAL;
- LOG_ERROR_STR("Could not get bitmap inode!");
- goto bail;
- }
- (*ac)->ac_which = OCFS_AC_USE_MAIN;
- (*ac)->ac_inode = igrab(main_bitmap_inode);
- (*ac)->ac_group_search = &ocfs2_cluster_group_search;
- status = ocfs_reserve_suballoc_bits(osb, *ac);
+ status = ocfs_reserve_cluster_bitmap_bits(osb, *ac);
if (status < 0) {
LOG_ERROR_STATUS(status);
goto bail;
@@ -641,8 +658,6 @@
ocfs_free_alloc_context(*ac);
*ac = NULL;
}
- if (main_bitmap_inode)
- iput(main_bitmap_inode);
LOG_EXIT_STATUS(status);
return(status);
@@ -901,15 +916,15 @@
return bg->bg_free_bits_count > wanted;
}
-/* return 0 to keep searching, > 0 on succes (and populate the return
- * values) and < 0 on failure. -ENOSPC means that we hit the end of
- * the chain without finding anything. */
+/* return 0 on success, -ENOSPC to keep searching and any other < 0
+ * value on error. */
static int ocfs2_cluster_group_search(struct inode *inode,
struct buffer_head *group_bh,
u32 bits_wanted, u32 min_bits,
u16 *bit_off, u16 *bits_found)
{
- int ret = 0;
+ int search = -ENOSPC;
+ int ret;
ocfs2_group_desc *bg = (ocfs2_group_desc *) group_bh->b_data;
u16 tmp_off, tmp_found;
@@ -919,20 +934,16 @@
ret = ocfs_block_group_find_clear_bits(OCFS2_SB(inode->i_sb),
group_bh, bits_wanted,
&tmp_off, &tmp_found);
- if (ret == -ENOSPC)
- ret = 0;
- else if (!ret) {
+ if (!ret) {
if (min_bits <= tmp_found) {
*bit_off = tmp_off;
*bits_found = tmp_found;
- ret = 1; /* success */
+ search = 0; /* success */
}
}
}
- if (!ret && !bg->bg_next_group)
- ret = -ENOSPC;
- return ret;
+ return search;
}
static int ocfs2_block_group_search(struct inode *inode,
@@ -940,55 +951,45 @@
u32 bits_wanted, u32 min_bits,
u16 *bit_off, u16 *bits_found)
{
- int ret = 0;
+ int ret = -ENOSPC;
ocfs2_group_desc *bg = (ocfs2_group_desc *) group_bh->b_data;
OCFS_ASSERT(min_bits == 1);
OCFS_ASSERT(!ocfs2_is_cluster_bitmap(inode));
- if (bg->bg_free_bits_count) {
+ if (bg->bg_free_bits_count)
ret = ocfs_block_group_find_clear_bits(OCFS2_SB(inode->i_sb),
group_bh, bits_wanted,
bit_off, bits_found);
- if (ret == -ENOSPC)
- ret = 0;
- else if (!ret)
- ret = 1; /* success */
- } else if (!bg->bg_next_group) {
- /* This really shouldn't happen... */
- LOG_ERROR_ARGS("Failure to find free space in suballoc "
- "chain!\n");
- ret = -ENOSPC;
- }
+
return ret;
}
-static int ocfs_search_suballoc_chain(ocfs2_alloc_context *ac,
- u32 bits_wanted,
- u32 min_bits,
- u16 *bit_off,
- unsigned int *num_bits,
- u64 *bg_blkno)
+static int ocfs_search_chain(ocfs2_alloc_context *ac,
+ u32 bits_wanted,
+ u32 min_bits,
+ u16 *bit_off,
+ unsigned int *num_bits,
+ u64 *bg_blkno)
{
int status;
+ u16 chain, tmp_bits;
+ u64 next_group;
ocfs_journal_handle *handle = ac->ac_handle;
struct inode *alloc_inode = ac->ac_inode;
- ocfs_super *osb = OCFS2_SB(alloc_inode->i_sb);
struct buffer_head *group_bh = NULL;
struct buffer_head *prev_group_bh = NULL;
ocfs2_dinode *fe = (ocfs2_dinode *) ac->ac_bh->b_data;
ocfs2_chain_list *cl = (ocfs2_chain_list *) &fe->id2.i_chain;
ocfs2_group_desc *bg;
- u16 chain, tmp_bits;
- u64 next_group;
-
chain = ac->ac_chain;
- LOG_TRACE_ARGS("trying to alloc %u bits from chain %u, inode %llu\n",
- bits_wanted, chain, OCFS_I(alloc_inode)->ip_blkno);
+ printk("trying to alloc %u bits from chain %u, inode %llu\n",
+ bits_wanted, chain, OCFS_I(alloc_inode)->ip_blkno);
- status = ocfs_read_block(osb, cl->cl_recs[chain].c_blkno,
- &group_bh, OCFS_BH_CACHED, alloc_inode);
+ status = ocfs_read_block(OCFS2_SB(alloc_inode->i_sb),
+ cl->cl_recs[chain].c_blkno, &group_bh,
+ OCFS_BH_CACHED, alloc_inode);
if (status < 0) {
LOG_ERROR_STATUS(status);
goto bail;
@@ -996,18 +997,14 @@
bg = (ocfs2_group_desc *) group_bh->b_data;
OCFS_ASSERT_RO(IS_VALID_GROUP_DESC(bg));
+ status = -ENOSPC;
/* for now, the chain search is a bit simplistic. We just use
* the 1st group with any empty bits. */
while ((status = ac->ac_group_search(alloc_inode, group_bh,
bits_wanted, min_bits, bit_off,
- &tmp_bits)) == 0) {
- /*
- * This means we've walked off the end of a chain that
- * we thought had bits, but didn't. While this
- * _could_ be a code error, it is more likely to be
- * corruption on disk.
- */
- OCFS_ASSERT_RO(bg->bg_next_group);
+ &tmp_bits)) == -ENOSPC) {
+ if (!bg->bg_next_group)
+ break;
if (prev_group_bh) {
brelse(prev_group_bh);
@@ -1016,7 +1013,8 @@
next_group = bg->bg_next_group;
prev_group_bh = group_bh;
group_bh = NULL;
- status = ocfs_read_block(osb, next_group, &group_bh,
+ status = ocfs_read_block(OCFS2_SB(alloc_inode->i_sb),
+ next_group, &group_bh,
OCFS_BH_CACHED, alloc_inode);
if (status < 0) {
LOG_ERROR_STATUS(status);
@@ -1031,6 +1029,9 @@
goto bail;
}
+ printk("alloc succeeds: we give %u bits from block group %llu\n",
+ tmp_bits, bg->bg_blkno);
+
*num_bits = tmp_bits;
OCFS_ASSERT(*num_bits);
@@ -1140,7 +1141,7 @@
ac->ac_chain = victim;
ac->ac_allow_chain_relink = 1;
- status = ocfs_search_suballoc_chain(ac, bits_wanted, min_bits, bit_off,
+ status = ocfs_search_chain(ac, bits_wanted, min_bits, bit_off,
num_bits, bg_blkno);
if (!status)
goto bail;
@@ -1161,9 +1162,9 @@
continue;
ac->ac_chain = i;
- status = ocfs_search_suballoc_chain(ac, bits_wanted, min_bits,
- bit_off, num_bits,
- bg_blkno);
+ status = ocfs_search_chain(ac, bits_wanted, min_bits,
+ bit_off, num_bits,
+ bg_blkno);
if (!status)
break;
if (status < 0 && status != -ENOSPC) {
@@ -1507,15 +1508,15 @@
u32 cluster)
{
ocfs_super *osb = OCFS2_SB(inode->i_sb);
- u32 group_cluster_off;
+ u32 group_no;
OCFS_ASSERT(ocfs2_is_cluster_bitmap(inode));
- /* align us to the cluster groups 1st cluster */
- group_cluster_off = cluster / osb->bitmap_cpg;
- if (!group_cluster_off)
+ group_no = cluster / osb->bitmap_cpg;
+ if (!group_no)
return osb->first_cluster_group_blkno;
- return ocfs2_clusters_to_blocks(inode->i_sb, group_cluster_off);
+ return ocfs2_clusters_to_blocks(inode->i_sb,
+ group_no * osb->bitmap_cpg);
}
/* given the block number of a cluster start, calculate which cluster
Modified: branches/cluster-groups/src/suballoc.h
===================================================================
--- branches/cluster-groups/src/suballoc.h 2004-11-10 04:02:40 UTC (rev 1629)
+++ branches/cluster-groups/src/suballoc.h 2004-11-10 04:09:10 UTC (rev 1630)
@@ -126,7 +126,7 @@
/* This is for local alloc ONLY. Others should use the task-specific
* apis above. */
-int ocfs_reserve_suballoc_bits(ocfs_super *osb,
- ocfs2_alloc_context *ac);
+int ocfs_reserve_cluster_bitmap_bits(ocfs_super *osb,
+ ocfs2_alloc_context *ac);
#endif /* _CHAINALLOC_H_ */
More information about the Ocfs2-commits
mailing list