⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ibalance.c

📁 reiserfsprogs-3.6.19.tar.gz 源码 给有需要的人!
💻 C
📖 第 1 页 / 共 3 页
字号:
 */static void internal_move_pointers_items (reiserfs_filsys_t * fs,					  struct buffer_info * dest_bi, 					  struct buffer_info * src_bi, 					  int last_first, int cpy_num, int del_par){    int first_pointer;    int first_item;        internal_copy_pointers_items (fs, dest_bi, src_bi->bi_bh, last_first, cpy_num);        if (last_first == FIRST_TO_LAST) {	/* shift_left occurs */	first_pointer = 0;	first_item = 0;	/* delete cpy_num - del_par pointers and keys starting for pointers with first_pointer, 	   for key - with first_item */	internal_delete_pointers_items (fs, src_bi, first_pointer, first_item, cpy_num - del_par);    } else {			/* shift_right occurs */	int i, j;		i = ( cpy_num - del_par == ( j = B_NR_ITEMS(src_bi->bi_bh)) + 1 ) ? 0 : j - cpy_num + del_par;		internal_delete_pointers_items (fs, src_bi, j + 1 - cpy_num + del_par, i, cpy_num - del_par);    }}/* Insert n_src'th key of buffer src before n_dest'th key of buffer dest. */static void internal_insert_key (reiserfs_filsys_t * fs,				 struct buffer_info * dest_bi, 				 int dest_position_before,                 /* insert key before key with n_dest number */				 struct buffer_head * src, 				 int src_position ){    struct buffer_head * dest = dest_bi->bi_bh;    int nr;    struct block_head * blkh;    struct key * key;    blkh = B_BLK_HEAD(dest);    nr = get_blkh_nr_items (blkh);    /* prepare space for inserting key */    key = B_N_PDELIM_KEY (dest, dest_position_before);    memmove (key + 1, key, (nr - dest_position_before) * KEY_SIZE + (nr + 1) * DC_SIZE);    /* insert key */    memcpy (key, B_N_PDELIM_KEY(src, src_position), KEY_SIZE);    /* Change dirt, free space, item number fields. */    set_blkh_nr_items (blkh, get_blkh_nr_items (blkh) + 1);    set_blkh_free_space (blkh, get_blkh_free_space (blkh) - KEY_SIZE);    mark_buffer_dirty (dest);    if (dest_bi->bi_parent) {	struct disk_child * dc;		dc = B_N_CHILD(dest_bi->bi_parent,dest_bi->bi_position);	set_dc_child_size (dc, get_dc_child_size (dc) + KEY_SIZE);	mark_buffer_dirty (dest_bi->bi_parent);    }}/* Insert d_key'th (delimiting) key from buffer cfl to tail of dest.  * Copy pointer_amount node pointers and pointer_amount - 1 items from buffer src to buffer dest. * Replace  d_key'th key in buffer cfl. * Delete pointer_amount items and node pointers from buffer src. *//* this can be invoked both to shift from S to L and from R to S */static void internal_shift_left (int mode,	/* INTERNAL_FROM_S_TO_L | INTERNAL_FROM_R_TO_S */				 struct tree_balance * tb, int h,				 int pointer_amount){    struct buffer_info dest_bi, src_bi;    struct buffer_head * cf;    int d_key_position;    internal_define_dest_src_infos (mode, tb, h, &dest_bi, &src_bi, &d_key_position, &cf);    /*printk("pointer_amount = %d\n",pointer_amount);*/    if (pointer_amount) {	/* insert delimiting key from common father of dest and src to node dest into position B_NR_ITEM(dest) */	internal_insert_key (tb->tb_fs, &dest_bi, B_NR_ITEMS(dest_bi.bi_bh), cf, d_key_position);	if (B_NR_ITEMS(src_bi.bi_bh) == pointer_amount - 1) {	    if (src_bi.bi_position/*src->b_item_order*/ == 0)		replace_key (tb->tb_fs, cf, d_key_position, src_bi.bi_parent/*src->b_parent*/, 0);	} else	    replace_key (tb->tb_fs, cf, d_key_position, src_bi.bi_bh, pointer_amount - 1);    }    /* last parameter is del_parameter */    internal_move_pointers_items (tb->tb_fs, &dest_bi, &src_bi, FIRST_TO_LAST, pointer_amount, 0);}/* Insert delimiting key to L[h]. * Copy n node pointers and n - 1 items from buffer S[h] to L[h]. * Delete n - 1 items and node pointers from buffer S[h]. *//* it always shifts from S[h] to L[h] */static void internal_shift1_left (struct tree_balance * tb, 				  int h, int pointer_amount){    struct buffer_info dest_bi, src_bi;    struct buffer_head * cf;    int d_key_position;        internal_define_dest_src_infos (INTERNAL_SHIFT_FROM_S_TO_L, tb, h, &dest_bi, &src_bi, &d_key_position, &cf);        if ( pointer_amount > 0 ) /* insert lkey[h]-th key  from CFL[h] to left neighbor L[h] */	internal_insert_key (tb->tb_fs, &dest_bi, B_NR_ITEMS(dest_bi.bi_bh), cf, d_key_position);        /* last parameter is del_parameter */    internal_move_pointers_items (tb->tb_fs, &dest_bi, &src_bi, FIRST_TO_LAST, pointer_amount, 1);}/* Insert d_key'th (delimiting) key from buffer cfr to head of dest.  * Copy n node pointers and n - 1 items from buffer src to buffer dest. * Replace  d_key'th key in buffer cfr. * Delete n items and node pointers from buffer src. */static void internal_shift_right (int mode,	/* INTERNAL_FROM_S_TO_R | INTERNAL_FROM_L_TO_S */				  struct tree_balance * tb, int h,				  int pointer_amount){    struct buffer_info dest_bi, src_bi;    struct buffer_head * cf;    int d_key_position;    int nr;    internal_define_dest_src_infos (mode, tb, h, &dest_bi, &src_bi, &d_key_position, &cf);    nr = B_NR_ITEMS (src_bi.bi_bh);    if (pointer_amount > 0) {	/* insert delimiting key from common father of dest and src to dest node into position 0 */	internal_insert_key (tb->tb_fs, &dest_bi, 0, cf, d_key_position);	if (nr == pointer_amount - 1) {	    /* when S[h] disappers replace left delemiting key as well */	    if (tb->CFL[h])		replace_key(tb->tb_fs, cf, d_key_position, tb->CFL[h], tb->lkey[h]);	} else	    replace_key(tb->tb_fs, cf, d_key_position, src_bi.bi_bh, nr - pointer_amount);    }          /* last parameter is del_parameter */    internal_move_pointers_items (tb->tb_fs, &dest_bi, &src_bi, LAST_TO_FIRST, pointer_amount, 0);}/* Insert delimiting key to R[h]. * Copy n node pointers and n - 1 items from buffer S[h] to R[h]. * Delete n - 1 items and node pointers from buffer S[h]. *//* it always shift from S[h] to R[h] */static void internal_shift1_right (struct tree_balance * tb, 				   int h, int pointer_amount){    struct buffer_info dest_bi, src_bi;    struct buffer_head * cf;    int d_key_position;    internal_define_dest_src_infos (INTERNAL_SHIFT_FROM_S_TO_R, tb, h, &dest_bi, &src_bi, &d_key_position, &cf);        if (pointer_amount > 0) /* insert rkey from CFR[h] to right neighbor R[h] */	internal_insert_key (tb->tb_fs, &dest_bi, 0, cf, d_key_position);        /* last parameter is del_parameter */    internal_move_pointers_items (tb->tb_fs, &dest_bi, &src_bi, LAST_TO_FIRST, pointer_amount, 1);}/* Delete insert_num node pointers together with their left items * and balance current node.*/static void balance_internal_when_delete (struct tree_balance * tb, 					  int h, int child_pos){    int insert_num;    int n;    struct buffer_head * tbSh = PATH_H_PBUFFER (tb->tb_path, h);    struct buffer_info bi;    insert_num = tb->insert_size[h] / ((int)(DC_SIZE + KEY_SIZE));      /* delete child-node-pointer(s) together with their left item(s) */    bi.bi_bh = tbSh;    bi.bi_parent = PATH_H_PPARENT (tb->tb_path, h);    bi.bi_position = PATH_H_POSITION (tb->tb_path, h + 1);    internal_delete_childs (tb->tb_fs, &bi, child_pos, -insert_num);    n = B_NR_ITEMS(tbSh);    if ( tb->lnum[h] == 0 && tb->rnum[h] == 0 ) {	if ( tb->blknum[h] == 0 ) {	    /* node S[h] (root of the tree) is empty now */	    struct buffer_head *new_root;	    struct reiserfs_super_block * sb;	    /* choose a new root */	    if ( ! tb->L[h-1] || ! B_NR_ITEMS(tb->L[h-1]) )		new_root = tb->R[h-1];	    else		new_root = tb->L[h-1];	    /* update super block's tree height and pointer to a root block */	    sb = tb->tb_fs->fs_ondisk_sb;	    set_sb_root_block (sb, new_root->b_blocknr);	    set_sb_tree_height (sb, get_sb_tree_height (sb) - 1);	    mark_buffer_dirty (tb->tb_fs->fs_super_bh);	    tb->tb_fs->fs_dirt = 1;	    /* mark buffer S[h] not uptodate and put it in free list */	    reiserfs_invalidate_buffer(tb, tbSh, 1);	    return;	}	return;    }    if ( tb->L[h] && tb->lnum[h] == -B_NR_ITEMS(tb->L[h]) - 1 ) { /* join S[h] with L[h] */	internal_shift_left (INTERNAL_SHIFT_FROM_S_TO_L, tb, h, n + 1);/*tb->L[h], tb->CFL[h], tb->lkey[h], tb->S[h], n+1);*/	reiserfs_invalidate_buffer(tb, tbSh, 1); /* preserve not needed, internal, 1 mean free block */	return;    }    if ( tb->R[h] &&  tb->rnum[h] == -B_NR_ITEMS(tb->R[h]) - 1 ) { /* join S[h] with R[h] */	internal_shift_right (INTERNAL_SHIFT_FROM_S_TO_R, tb, h, n + 1);	reiserfs_invalidate_buffer (tb, tbSh, 1);	return;    }    if ( tb->lnum[h] < 0 ) { /* borrow from left neighbor L[h] */	internal_shift_right (INTERNAL_SHIFT_FROM_L_TO_S, tb, h, -tb->lnum[h]);	return;    }    if ( tb->rnum[h] < 0 ) { /* borrow from right neighbor R[h] */	internal_shift_left (INTERNAL_SHIFT_FROM_R_TO_S, tb, h, -tb->rnum[h]);/*tb->S[h], tb->CFR[h], tb->rkey[h], tb->R[h], -tb->rnum[h]);*/	return;    }    if ( tb->lnum[h] > 0 ) { /* split S[h] into two parts and put them into neighbors */	internal_shift_left (INTERNAL_SHIFT_FROM_S_TO_L, tb, h, tb->lnum[h]);/*tb->L[h], tb->CFL[h], tb->lkey[h], tb->S[h], tb->lnum[h]);*/	internal_shift_right (INTERNAL_SHIFT_FROM_S_TO_R, tb, h, tb->rnum[h]);	reiserfs_invalidate_buffer (tb, tbSh, 1);	return;    }    reiserfs_panic ("balance_internal_when_delete", "unexpected tb->lnum[%d]==%d or tb->rnum[%d]==%d",		    h, tb->lnum[h], h, tb->rnum[h]);}/* Replace delimiting key of buffers L[h] and S[h] by the given key.*/void replace_lkey (struct tree_balance * tb,		   int h, struct item_head * key){    if (B_NR_ITEMS(PATH_H_PBUFFER(tb->tb_path, h)) == 0)	return;    memcpy (B_N_PDELIM_KEY(tb->CFL[h],tb->lkey[h]), key, KEY_SIZE);    mark_buffer_dirty (tb->CFL[h]);}/* Replace delimiting key of buffers S[h] and R[h] by the given key.*/void replace_rkey (struct tree_balance * tb,		   int h, struct item_head * key){    memcpy (B_N_PDELIM_KEY(tb->CFR[h],tb->rkey[h]), key, KEY_SIZE);        mark_buffer_dirty (tb->CFR[h]);}int balance_internal (struct tree_balance * tb,			/* tree_balance structure 		*/		      int h,					/* level of the tree 			*/		      int child_pos,		      struct item_head * insert_key,		/* key for insertion on higher level   	*/		      struct buffer_head ** insert_ptr)	/* node for insertion on higher level*/  /* if inserting/pasting   {   child_pos is the position of the node-pointer in S[h] that	 *   pointed to S[h-1] before balancing of the h-1 level;		 *   this means that new pointers and items must be inserted AFTER *   child_pos   }

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -