aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMark Fasheh <mark.fasheh@oracle.com>2007-05-29 17:28:51 -0400
committerMark Fasheh <mark.fasheh@oracle.com>2007-07-10 20:31:58 -0400
commitc3afcbb34426a9291e4c038540129053a72c3cd8 (patch)
tree39630188c8fe69dbb6be9f4c3a5b1f9d61cf7906
parent1f6697d072e6fd0b332a4301c21060dcb89bd623 (diff)
ocfs2: abstract btree growing calls
The top level calls and logic for growing a tree can easily be abstracted out of ocfs2_insert_extent() into a seperate function - ocfs2_grow_tree(). This allows future code to easily grow btrees when needed. Signed-off-by: Mark Fasheh <mark.fasheh@oracle.com>
-rw-r--r--fs/ocfs2/alloc.c119
1 files changed, 74 insertions, 45 deletions
diff --git a/fs/ocfs2/alloc.c b/fs/ocfs2/alloc.c
index b5327b4cdb34..a02d026cb0e4 100644
--- a/fs/ocfs2/alloc.c
+++ b/fs/ocfs2/alloc.c
@@ -825,6 +825,74 @@ bail:
825} 825}
826 826
827/* 827/*
828 * Grow a b-tree so that it has more records.
829 *
830 * We might shift the tree depth in which case existing paths should
831 * be considered invalid.
832 *
833 * Tree depth after the grow is returned via *final_depth.
834 */
835static int ocfs2_grow_tree(struct inode *inode, handle_t *handle,
836 struct buffer_head *di_bh, int *final_depth,
837 struct buffer_head *last_eb_bh,
838 struct ocfs2_alloc_context *meta_ac)
839{
840 int ret, shift;
841 struct ocfs2_dinode *di = (struct ocfs2_dinode *)di_bh->b_data;
842 int depth = le16_to_cpu(di->id2.i_list.l_tree_depth);
843 struct ocfs2_super *osb = OCFS2_SB(inode->i_sb);
844 struct buffer_head *bh = NULL;
845
846 BUG_ON(meta_ac == NULL);
847
848 shift = ocfs2_find_branch_target(osb, inode, di_bh, &bh);
849 if (shift < 0) {
850 ret = shift;
851 mlog_errno(ret);
852 goto out;
853 }
854
855 /* We traveled all the way to the bottom of the allocation tree
856 * and didn't find room for any more extents - we need to add
857 * another tree level */
858 if (shift) {
859 BUG_ON(bh);
860 mlog(0, "need to shift tree depth (current = %d)\n", depth);
861
862 /* ocfs2_shift_tree_depth will return us a buffer with
863 * the new extent block (so we can pass that to
864 * ocfs2_add_branch). */
865 ret = ocfs2_shift_tree_depth(osb, handle, inode, di_bh,
866 meta_ac, &bh);
867 if (ret < 0) {
868 mlog_errno(ret);
869 goto out;
870 }
871 depth++;
872 /* Special case: we have room now if we shifted from
873 * tree_depth 0 */
874 if (depth == 1)
875 goto out;
876 }
877
878 /* call ocfs2_add_branch to add the final part of the tree with
879 * the new data. */
880 mlog(0, "add branch. bh = %p\n", bh);
881 ret = ocfs2_add_branch(osb, handle, inode, di_bh, bh, last_eb_bh,
882 meta_ac);
883 if (ret < 0) {
884 mlog_errno(ret);
885 goto out;
886 }
887
888out:
889 if (final_depth)
890 *final_depth = depth;
891 brelse(bh);
892 return ret;
893}
894
895/*
828 * This is only valid for leaf nodes, which are the only ones that can 896 * This is only valid for leaf nodes, which are the only ones that can
829 * have empty extents anyway. 897 * have empty extents anyway.
830 */ 898 */
@@ -2325,7 +2393,7 @@ int ocfs2_insert_extent(struct ocfs2_super *osb,
2325 u32 new_clusters, 2393 u32 new_clusters,
2326 struct ocfs2_alloc_context *meta_ac) 2394 struct ocfs2_alloc_context *meta_ac)
2327{ 2395{
2328 int status, shift; 2396 int status;
2329 struct buffer_head *last_eb_bh = NULL; 2397 struct buffer_head *last_eb_bh = NULL;
2330 struct buffer_head *bh = NULL; 2398 struct buffer_head *bh = NULL;
2331 struct ocfs2_insert_type insert = {0, }; 2399 struct ocfs2_insert_type insert = {0, };
@@ -2360,55 +2428,16 @@ int ocfs2_insert_extent(struct ocfs2_super *osb,
2360 insert.ins_appending, insert.ins_contig, insert.ins_contig_index, 2428 insert.ins_appending, insert.ins_contig, insert.ins_contig_index,
2361 insert.ins_free_records, insert.ins_tree_depth); 2429 insert.ins_free_records, insert.ins_tree_depth);
2362 2430
2363 /* 2431 if (insert.ins_contig == CONTIG_NONE && insert.ins_free_records == 0) {
2364 * Avoid growing the tree unless we're out of records and the 2432 status = ocfs2_grow_tree(inode, handle, fe_bh,
2365 * insert type requres one. 2433 &insert.ins_tree_depth, last_eb_bh,
2366 */ 2434 meta_ac);
2367 if (insert.ins_contig != CONTIG_NONE || insert.ins_free_records) 2435 if (status) {
2368 goto out_add;
2369
2370 shift = ocfs2_find_branch_target(osb, inode, fe_bh, &bh);
2371 if (shift < 0) {
2372 status = shift;
2373 mlog_errno(status);
2374 goto bail;
2375 }
2376
2377 /* We traveled all the way to the bottom of the allocation tree
2378 * and didn't find room for any more extents - we need to add
2379 * another tree level */
2380 if (shift) {
2381 BUG_ON(bh);
2382 mlog(0, "need to shift tree depth "
2383 "(current = %d)\n", insert.ins_tree_depth);
2384
2385 /* ocfs2_shift_tree_depth will return us a buffer with
2386 * the new extent block (so we can pass that to
2387 * ocfs2_add_branch). */
2388 status = ocfs2_shift_tree_depth(osb, handle, inode, fe_bh,
2389 meta_ac, &bh);
2390 if (status < 0) {
2391 mlog_errno(status); 2436 mlog_errno(status);
2392 goto bail; 2437 goto bail;
2393 } 2438 }
2394 insert.ins_tree_depth++;
2395 /* Special case: we have room now if we shifted from
2396 * tree_depth 0 */
2397 if (insert.ins_tree_depth == 1)
2398 goto out_add;
2399 }
2400
2401 /* call ocfs2_add_branch to add the final part of the tree with
2402 * the new data. */
2403 mlog(0, "add branch. bh = %p\n", bh);
2404 status = ocfs2_add_branch(osb, handle, inode, fe_bh, bh, last_eb_bh,
2405 meta_ac);
2406 if (status < 0) {
2407 mlog_errno(status);
2408 goto bail;
2409 } 2439 }
2410 2440
2411out_add:
2412 /* Finally, we can add clusters. This might rotate the tree for us. */ 2441 /* Finally, we can add clusters. This might rotate the tree for us. */
2413 status = ocfs2_do_insert_extent(inode, handle, fe_bh, &rec, &insert); 2442 status = ocfs2_do_insert_extent(inode, handle, fe_bh, &rec, &insert);
2414 if (status < 0) 2443 if (status < 0)