xref: /openbmc/linux/fs/btrfs/ctree.c (revision 9f3a7427)
16cbd5570SChris Mason /*
26cbd5570SChris Mason  * Copyright (C) 2007 Oracle.  All rights reserved.
36cbd5570SChris Mason  *
46cbd5570SChris Mason  * This program is free software; you can redistribute it and/or
56cbd5570SChris Mason  * modify it under the terms of the GNU General Public
66cbd5570SChris Mason  * License v2 as published by the Free Software Foundation.
76cbd5570SChris Mason  *
86cbd5570SChris Mason  * This program is distributed in the hope that it will be useful,
96cbd5570SChris Mason  * but WITHOUT ANY WARRANTY; without even the implied warranty of
106cbd5570SChris Mason  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
116cbd5570SChris Mason  * General Public License for more details.
126cbd5570SChris Mason  *
136cbd5570SChris Mason  * You should have received a copy of the GNU General Public
146cbd5570SChris Mason  * License along with this program; if not, write to the
156cbd5570SChris Mason  * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
166cbd5570SChris Mason  * Boston, MA 021110-1307, USA.
176cbd5570SChris Mason  */
186cbd5570SChris Mason 
19eb60ceacSChris Mason #include "ctree.h"
20eb60ceacSChris Mason #include "disk-io.h"
217f5c1516SChris Mason #include "transaction.h"
229a8dd150SChris Mason 
23e089f05cSChris Mason static int split_node(struct btrfs_trans_handle *trans, struct btrfs_root
24e089f05cSChris Mason 		      *root, struct btrfs_path *path, int level);
25e089f05cSChris Mason static int split_leaf(struct btrfs_trans_handle *trans, struct btrfs_root
26d4dbff95SChris Mason 		      *root, struct btrfs_key *ins_key,
27d4dbff95SChris Mason 		      struct btrfs_path *path, int data_size);
28e089f05cSChris Mason static int push_node_left(struct btrfs_trans_handle *trans, struct btrfs_root
29e20d96d6SChris Mason 			  *root, struct buffer_head *dst, struct buffer_head
30e089f05cSChris Mason 			  *src);
31e089f05cSChris Mason static int balance_node_right(struct btrfs_trans_handle *trans, struct
32e20d96d6SChris Mason 			      btrfs_root *root, struct buffer_head *dst_buf,
33e20d96d6SChris Mason 			      struct buffer_head *src_buf);
34e089f05cSChris Mason static int del_ptr(struct btrfs_trans_handle *trans, struct btrfs_root *root,
35e089f05cSChris Mason 		   struct btrfs_path *path, int level, int slot);
36d97e63b6SChris Mason 
37df24a2b9SChris Mason inline void btrfs_init_path(struct btrfs_path *p)
38df24a2b9SChris Mason {
39df24a2b9SChris Mason 	memset(p, 0, sizeof(*p));
40df24a2b9SChris Mason }
41df24a2b9SChris Mason 
422c90e5d6SChris Mason struct btrfs_path *btrfs_alloc_path(void)
432c90e5d6SChris Mason {
44df24a2b9SChris Mason 	struct btrfs_path *path;
45df24a2b9SChris Mason 	path = kmem_cache_alloc(btrfs_path_cachep, GFP_NOFS);
46df24a2b9SChris Mason 	if (path)
47df24a2b9SChris Mason 		btrfs_init_path(path);
48df24a2b9SChris Mason 	return path;
492c90e5d6SChris Mason }
502c90e5d6SChris Mason 
512c90e5d6SChris Mason void btrfs_free_path(struct btrfs_path *p)
522c90e5d6SChris Mason {
53df24a2b9SChris Mason 	btrfs_release_path(NULL, p);
542c90e5d6SChris Mason 	kmem_cache_free(btrfs_path_cachep, p);
552c90e5d6SChris Mason }
562c90e5d6SChris Mason 
57234b63a0SChris Mason void btrfs_release_path(struct btrfs_root *root, struct btrfs_path *p)
58eb60ceacSChris Mason {
59eb60ceacSChris Mason 	int i;
60234b63a0SChris Mason 	for (i = 0; i < BTRFS_MAX_LEVEL; i++) {
61eb60ceacSChris Mason 		if (!p->nodes[i])
62eb60ceacSChris Mason 			break;
63234b63a0SChris Mason 		btrfs_block_release(root, p->nodes[i]);
64eb60ceacSChris Mason 	}
65aa5d6bedSChris Mason 	memset(p, 0, sizeof(*p));
66eb60ceacSChris Mason }
67eb60ceacSChris Mason 
68e089f05cSChris Mason static int btrfs_cow_block(struct btrfs_trans_handle *trans, struct btrfs_root
69e20d96d6SChris Mason 			   *root, struct buffer_head *buf, struct buffer_head
70e20d96d6SChris Mason 			   *parent, int parent_slot, struct buffer_head
71e089f05cSChris Mason 			   **cow_ret)
7202217ed2SChris Mason {
73e20d96d6SChris Mason 	struct buffer_head *cow;
74e20d96d6SChris Mason 	struct btrfs_node *cow_node;
7554aa1f4dSChris Mason 	int ret;
7602217ed2SChris Mason 
77ccd467d6SChris Mason 	WARN_ON(!buffer_uptodate(buf));
78ccd467d6SChris Mason 	if (trans->transaction != root->fs_info->running_transaction) {
79ccd467d6SChris Mason 		printk(KERN_CRIT "trans %Lu running %Lu\n", trans->transid,
80ccd467d6SChris Mason 		       root->fs_info->running_transaction->transid);
81ccd467d6SChris Mason 		WARN_ON(1);
82ccd467d6SChris Mason 	}
83ccd467d6SChris Mason 	if (trans->transid != root->fs_info->generation) {
84ccd467d6SChris Mason 		printk(KERN_CRIT "trans %Lu running %Lu\n", trans->transid,
85ccd467d6SChris Mason 		       root->fs_info->generation);
86ccd467d6SChris Mason 		WARN_ON(1);
87ccd467d6SChris Mason 	}
887f5c1516SChris Mason 	if (btrfs_header_generation(btrfs_buffer_header(buf)) ==
897f5c1516SChris Mason 				    trans->transid) {
9002217ed2SChris Mason 		*cow_ret = buf;
9102217ed2SChris Mason 		return 0;
9202217ed2SChris Mason 	}
9331f3c99bSChris Mason 	cow = btrfs_alloc_free_block(trans, root, buf->b_blocknr);
9454aa1f4dSChris Mason 	if (IS_ERR(cow))
9554aa1f4dSChris Mason 		return PTR_ERR(cow);
96e20d96d6SChris Mason 	cow_node = btrfs_buffer_node(cow);
972c90e5d6SChris Mason 	if (buf->b_size != root->blocksize || cow->b_size != root->blocksize)
982c90e5d6SChris Mason 		WARN_ON(1);
99e20d96d6SChris Mason 	memcpy(cow_node, btrfs_buffer_node(buf), root->blocksize);
1007eccb903SChris Mason 	btrfs_set_header_blocknr(&cow_node->header, bh_blocknr(cow));
1017f5c1516SChris Mason 	btrfs_set_header_generation(&cow_node->header, trans->transid);
1024d775673SChris Mason 	btrfs_set_header_owner(&cow_node->header, root->root_key.objectid);
10354aa1f4dSChris Mason 	ret = btrfs_inc_ref(trans, root, buf);
10454aa1f4dSChris Mason 	if (ret)
10554aa1f4dSChris Mason 		return ret;
10602217ed2SChris Mason 	if (buf == root->node) {
10702217ed2SChris Mason 		root->node = cow;
108e20d96d6SChris Mason 		get_bh(cow);
1092c90e5d6SChris Mason 		if (buf != root->commit_root) {
1107eccb903SChris Mason 			btrfs_free_extent(trans, root, bh_blocknr(buf), 1, 1);
1112c90e5d6SChris Mason 		}
112234b63a0SChris Mason 		btrfs_block_release(root, buf);
11302217ed2SChris Mason 	} else {
114e20d96d6SChris Mason 		btrfs_set_node_blockptr(btrfs_buffer_node(parent), parent_slot,
1157eccb903SChris Mason 					bh_blocknr(cow));
116d6025579SChris Mason 		btrfs_mark_buffer_dirty(parent);
1177eccb903SChris Mason 		btrfs_free_extent(trans, root, bh_blocknr(buf), 1, 1);
11802217ed2SChris Mason 	}
119234b63a0SChris Mason 	btrfs_block_release(root, buf);
120ccd467d6SChris Mason 	btrfs_mark_buffer_dirty(cow);
1212c90e5d6SChris Mason 	*cow_ret = cow;
12202217ed2SChris Mason 	return 0;
12302217ed2SChris Mason }
12402217ed2SChris Mason 
12574123bd7SChris Mason /*
12674123bd7SChris Mason  * The leaf data grows from end-to-front in the node.
12774123bd7SChris Mason  * this returns the address of the start of the last item,
12874123bd7SChris Mason  * which is the stop of the leaf data stack
12974123bd7SChris Mason  */
130123abc88SChris Mason static inline unsigned int leaf_data_end(struct btrfs_root *root,
131123abc88SChris Mason 					 struct btrfs_leaf *leaf)
132be0e5c09SChris Mason {
1337518a238SChris Mason 	u32 nr = btrfs_header_nritems(&leaf->header);
134be0e5c09SChris Mason 	if (nr == 0)
135123abc88SChris Mason 		return BTRFS_LEAF_DATA_SIZE(root);
1360783fcfcSChris Mason 	return btrfs_item_offset(leaf->items + nr - 1);
137be0e5c09SChris Mason }
138be0e5c09SChris Mason 
13974123bd7SChris Mason /*
14074123bd7SChris Mason  * compare two keys in a memcmp fashion
14174123bd7SChris Mason  */
1429aca1d51SChris Mason static int comp_keys(struct btrfs_disk_key *disk, struct btrfs_key *k2)
143be0e5c09SChris Mason {
144e2fa7227SChris Mason 	struct btrfs_key k1;
145e2fa7227SChris Mason 
146e2fa7227SChris Mason 	btrfs_disk_key_to_cpu(&k1, disk);
147e2fa7227SChris Mason 
148e2fa7227SChris Mason 	if (k1.objectid > k2->objectid)
149be0e5c09SChris Mason 		return 1;
150e2fa7227SChris Mason 	if (k1.objectid < k2->objectid)
151be0e5c09SChris Mason 		return -1;
152f254e52cSChris Mason 	if (k1.flags > k2->flags)
153f254e52cSChris Mason 		return 1;
154f254e52cSChris Mason 	if (k1.flags < k2->flags)
155f254e52cSChris Mason 		return -1;
15670b2befdSChris Mason 	if (k1.offset > k2->offset)
15770b2befdSChris Mason 		return 1;
15870b2befdSChris Mason 	if (k1.offset < k2->offset)
15970b2befdSChris Mason 		return -1;
160be0e5c09SChris Mason 	return 0;
161be0e5c09SChris Mason }
16274123bd7SChris Mason 
163123abc88SChris Mason static int check_node(struct btrfs_root *root, struct btrfs_path *path,
164123abc88SChris Mason 		      int level)
165aa5d6bedSChris Mason {
166234b63a0SChris Mason 	struct btrfs_node *parent = NULL;
167e20d96d6SChris Mason 	struct btrfs_node *node = btrfs_buffer_node(path->nodes[level]);
168aa5d6bedSChris Mason 	int parent_slot;
1698d7be552SChris Mason 	int slot;
1708d7be552SChris Mason 	struct btrfs_key cpukey;
1717518a238SChris Mason 	u32 nritems = btrfs_header_nritems(&node->header);
172aa5d6bedSChris Mason 
173aa5d6bedSChris Mason 	if (path->nodes[level + 1])
174e20d96d6SChris Mason 		parent = btrfs_buffer_node(path->nodes[level + 1]);
175a1f39630SAneesh 
1768d7be552SChris Mason 	slot = path->slots[level];
1777518a238SChris Mason 	BUG_ON(nritems == 0);
1787518a238SChris Mason 	if (parent) {
179e2fa7227SChris Mason 		struct btrfs_disk_key *parent_key;
180a1f39630SAneesh 
181a1f39630SAneesh 		parent_slot = path->slots[level + 1];
182123abc88SChris Mason 		parent_key = &parent->ptrs[parent_slot].key;
183123abc88SChris Mason 		BUG_ON(memcmp(parent_key, &node->ptrs[0].key,
184e2fa7227SChris Mason 			      sizeof(struct btrfs_disk_key)));
1851d4f8a0cSChris Mason 		BUG_ON(btrfs_node_blockptr(parent, parent_slot) !=
1867518a238SChris Mason 		       btrfs_header_blocknr(&node->header));
187aa5d6bedSChris Mason 	}
188123abc88SChris Mason 	BUG_ON(nritems > BTRFS_NODEPTRS_PER_BLOCK(root));
1898d7be552SChris Mason 	if (slot != 0) {
1908d7be552SChris Mason 		btrfs_disk_key_to_cpu(&cpukey, &node->ptrs[slot - 1].key);
1918d7be552SChris Mason 		BUG_ON(comp_keys(&node->ptrs[slot].key, &cpukey) <= 0);
1928d7be552SChris Mason 	}
1938d7be552SChris Mason 	if (slot < nritems - 1) {
1948d7be552SChris Mason 		btrfs_disk_key_to_cpu(&cpukey, &node->ptrs[slot + 1].key);
1958d7be552SChris Mason 		BUG_ON(comp_keys(&node->ptrs[slot].key, &cpukey) >= 0);
196aa5d6bedSChris Mason 	}
197aa5d6bedSChris Mason 	return 0;
198aa5d6bedSChris Mason }
199aa5d6bedSChris Mason 
200123abc88SChris Mason static int check_leaf(struct btrfs_root *root, struct btrfs_path *path,
201123abc88SChris Mason 		      int level)
202aa5d6bedSChris Mason {
203e20d96d6SChris Mason 	struct btrfs_leaf *leaf = btrfs_buffer_leaf(path->nodes[level]);
204234b63a0SChris Mason 	struct btrfs_node *parent = NULL;
205aa5d6bedSChris Mason 	int parent_slot;
2068d7be552SChris Mason 	int slot = path->slots[0];
2078d7be552SChris Mason 	struct btrfs_key cpukey;
2088d7be552SChris Mason 
2097518a238SChris Mason 	u32 nritems = btrfs_header_nritems(&leaf->header);
210aa5d6bedSChris Mason 
211aa5d6bedSChris Mason 	if (path->nodes[level + 1])
212e20d96d6SChris Mason 		parent = btrfs_buffer_node(path->nodes[level + 1]);
213a1f39630SAneesh 
214123abc88SChris Mason 	BUG_ON(btrfs_leaf_free_space(root, leaf) < 0);
2157518a238SChris Mason 
2167518a238SChris Mason 	if (nritems == 0)
2177518a238SChris Mason 		return 0;
2187518a238SChris Mason 
2197518a238SChris Mason 	if (parent) {
220e2fa7227SChris Mason 		struct btrfs_disk_key *parent_key;
221a1f39630SAneesh 
222a1f39630SAneesh 		parent_slot = path->slots[level + 1];
223123abc88SChris Mason 		parent_key = &parent->ptrs[parent_slot].key;
224aa5d6bedSChris Mason 		BUG_ON(memcmp(parent_key, &leaf->items[0].key,
225e2fa7227SChris Mason 		       sizeof(struct btrfs_disk_key)));
2261d4f8a0cSChris Mason 		BUG_ON(btrfs_node_blockptr(parent, parent_slot) !=
2277518a238SChris Mason 		       btrfs_header_blocknr(&leaf->header));
228aa5d6bedSChris Mason 	}
2298d7be552SChris Mason 	if (slot != 0) {
2308d7be552SChris Mason 		btrfs_disk_key_to_cpu(&cpukey, &leaf->items[slot - 1].key);
2318d7be552SChris Mason 		BUG_ON(comp_keys(&leaf->items[slot].key, &cpukey) <= 0);
2328d7be552SChris Mason 		BUG_ON(btrfs_item_offset(leaf->items + slot - 1) !=
2338d7be552SChris Mason 			btrfs_item_end(leaf->items + slot));
234aa5d6bedSChris Mason 	}
2358d7be552SChris Mason 	if (slot < nritems - 1) {
2368d7be552SChris Mason 		btrfs_disk_key_to_cpu(&cpukey, &leaf->items[slot + 1].key);
2378d7be552SChris Mason 		BUG_ON(comp_keys(&leaf->items[slot].key, &cpukey) >= 0);
2388d7be552SChris Mason 		BUG_ON(btrfs_item_offset(leaf->items + slot) !=
2398d7be552SChris Mason 			btrfs_item_end(leaf->items + slot + 1));
240aa5d6bedSChris Mason 	}
2418d7be552SChris Mason 	BUG_ON(btrfs_item_offset(leaf->items) +
2428d7be552SChris Mason 	       btrfs_item_size(leaf->items) != BTRFS_LEAF_DATA_SIZE(root));
243aa5d6bedSChris Mason 	return 0;
244aa5d6bedSChris Mason }
245aa5d6bedSChris Mason 
246123abc88SChris Mason static int check_block(struct btrfs_root *root, struct btrfs_path *path,
247123abc88SChris Mason 			int level)
248aa5d6bedSChris Mason {
2493eb0314dSChris Mason 	struct btrfs_node *node = btrfs_buffer_node(path->nodes[level]);
2503eb0314dSChris Mason 	if (memcmp(node->header.fsid, root->fs_info->disk_super->fsid,
2513eb0314dSChris Mason 		   sizeof(node->header.fsid)))
2523eb0314dSChris Mason 		BUG();
253aa5d6bedSChris Mason 	if (level == 0)
254123abc88SChris Mason 		return check_leaf(root, path, level);
255123abc88SChris Mason 	return check_node(root, path, level);
256aa5d6bedSChris Mason }
257aa5d6bedSChris Mason 
25874123bd7SChris Mason /*
25974123bd7SChris Mason  * search for key in the array p.  items p are item_size apart
26074123bd7SChris Mason  * and there are 'max' items in p
26174123bd7SChris Mason  * the slot in the array is returned via slot, and it points to
26274123bd7SChris Mason  * the place where you would insert key if it is not found in
26374123bd7SChris Mason  * the array.
26474123bd7SChris Mason  *
26574123bd7SChris Mason  * slot may point to max if the key is bigger than all of the keys
26674123bd7SChris Mason  */
2679aca1d51SChris Mason static int generic_bin_search(char *p, int item_size, struct btrfs_key *key,
268be0e5c09SChris Mason 		       int max, int *slot)
269be0e5c09SChris Mason {
270be0e5c09SChris Mason 	int low = 0;
271be0e5c09SChris Mason 	int high = max;
272be0e5c09SChris Mason 	int mid;
273be0e5c09SChris Mason 	int ret;
274e2fa7227SChris Mason 	struct btrfs_disk_key *tmp;
275be0e5c09SChris Mason 
276be0e5c09SChris Mason 	while(low < high) {
277be0e5c09SChris Mason 		mid = (low + high) / 2;
278e2fa7227SChris Mason 		tmp = (struct btrfs_disk_key *)(p + mid * item_size);
279be0e5c09SChris Mason 		ret = comp_keys(tmp, key);
280be0e5c09SChris Mason 
281be0e5c09SChris Mason 		if (ret < 0)
282be0e5c09SChris Mason 			low = mid + 1;
283be0e5c09SChris Mason 		else if (ret > 0)
284be0e5c09SChris Mason 			high = mid;
285be0e5c09SChris Mason 		else {
286be0e5c09SChris Mason 			*slot = mid;
287be0e5c09SChris Mason 			return 0;
288be0e5c09SChris Mason 		}
289be0e5c09SChris Mason 	}
290be0e5c09SChris Mason 	*slot = low;
291be0e5c09SChris Mason 	return 1;
292be0e5c09SChris Mason }
293be0e5c09SChris Mason 
29497571fd0SChris Mason /*
29597571fd0SChris Mason  * simple bin_search frontend that does the right thing for
29697571fd0SChris Mason  * leaves vs nodes
29797571fd0SChris Mason  */
2989aca1d51SChris Mason static int bin_search(struct btrfs_node *c, struct btrfs_key *key, int *slot)
299be0e5c09SChris Mason {
3007518a238SChris Mason 	if (btrfs_is_leaf(c)) {
301234b63a0SChris Mason 		struct btrfs_leaf *l = (struct btrfs_leaf *)c;
3020783fcfcSChris Mason 		return generic_bin_search((void *)l->items,
3030783fcfcSChris Mason 					  sizeof(struct btrfs_item),
3047518a238SChris Mason 					  key, btrfs_header_nritems(&c->header),
3057518a238SChris Mason 					  slot);
306be0e5c09SChris Mason 	} else {
307123abc88SChris Mason 		return generic_bin_search((void *)c->ptrs,
308123abc88SChris Mason 					  sizeof(struct btrfs_key_ptr),
3097518a238SChris Mason 					  key, btrfs_header_nritems(&c->header),
3107518a238SChris Mason 					  slot);
311be0e5c09SChris Mason 	}
312be0e5c09SChris Mason 	return -1;
313be0e5c09SChris Mason }
314be0e5c09SChris Mason 
315e20d96d6SChris Mason static struct buffer_head *read_node_slot(struct btrfs_root *root,
316e20d96d6SChris Mason 				   struct buffer_head *parent_buf,
317bb803951SChris Mason 				   int slot)
318bb803951SChris Mason {
319e20d96d6SChris Mason 	struct btrfs_node *node = btrfs_buffer_node(parent_buf);
320bb803951SChris Mason 	if (slot < 0)
321bb803951SChris Mason 		return NULL;
3227518a238SChris Mason 	if (slot >= btrfs_header_nritems(&node->header))
323bb803951SChris Mason 		return NULL;
3241d4f8a0cSChris Mason 	return read_tree_block(root, btrfs_node_blockptr(node, slot));
325bb803951SChris Mason }
326bb803951SChris Mason 
327e089f05cSChris Mason static int balance_level(struct btrfs_trans_handle *trans, struct btrfs_root
328e089f05cSChris Mason 			 *root, struct btrfs_path *path, int level)
329bb803951SChris Mason {
330e20d96d6SChris Mason 	struct buffer_head *right_buf;
331e20d96d6SChris Mason 	struct buffer_head *mid_buf;
332e20d96d6SChris Mason 	struct buffer_head *left_buf;
333e20d96d6SChris Mason 	struct buffer_head *parent_buf = NULL;
334234b63a0SChris Mason 	struct btrfs_node *right = NULL;
335234b63a0SChris Mason 	struct btrfs_node *mid;
336234b63a0SChris Mason 	struct btrfs_node *left = NULL;
337234b63a0SChris Mason 	struct btrfs_node *parent = NULL;
338bb803951SChris Mason 	int ret = 0;
339bb803951SChris Mason 	int wret;
340bb803951SChris Mason 	int pslot;
341bb803951SChris Mason 	int orig_slot = path->slots[level];
34254aa1f4dSChris Mason 	int err_on_enospc = 0;
34379f95c82SChris Mason 	u64 orig_ptr;
344bb803951SChris Mason 
345bb803951SChris Mason 	if (level == 0)
346bb803951SChris Mason 		return 0;
347bb803951SChris Mason 
348bb803951SChris Mason 	mid_buf = path->nodes[level];
349e20d96d6SChris Mason 	mid = btrfs_buffer_node(mid_buf);
3501d4f8a0cSChris Mason 	orig_ptr = btrfs_node_blockptr(mid, orig_slot);
35179f95c82SChris Mason 
352234b63a0SChris Mason 	if (level < BTRFS_MAX_LEVEL - 1)
353bb803951SChris Mason 		parent_buf = path->nodes[level + 1];
354bb803951SChris Mason 	pslot = path->slots[level + 1];
355bb803951SChris Mason 
35640689478SChris Mason 	/*
35740689478SChris Mason 	 * deal with the case where there is only one pointer in the root
35840689478SChris Mason 	 * by promoting the node below to a root
35940689478SChris Mason 	 */
360bb803951SChris Mason 	if (!parent_buf) {
361e20d96d6SChris Mason 		struct buffer_head *child;
3627eccb903SChris Mason 		u64 blocknr = bh_blocknr(mid_buf);
363bb803951SChris Mason 
3647518a238SChris Mason 		if (btrfs_header_nritems(&mid->header) != 1)
365bb803951SChris Mason 			return 0;
366bb803951SChris Mason 
367bb803951SChris Mason 		/* promote the child to a root */
368bb803951SChris Mason 		child = read_node_slot(root, mid_buf, 0);
369bb803951SChris Mason 		BUG_ON(!child);
370bb803951SChris Mason 		root->node = child;
371bb803951SChris Mason 		path->nodes[level] = NULL;
372d6025579SChris Mason 		clean_tree_block(trans, root, mid_buf);
373d6025579SChris Mason 		wait_on_buffer(mid_buf);
374bb803951SChris Mason 		/* once for the path */
375234b63a0SChris Mason 		btrfs_block_release(root, mid_buf);
376bb803951SChris Mason 		/* once for the root ptr */
377234b63a0SChris Mason 		btrfs_block_release(root, mid_buf);
378e089f05cSChris Mason 		return btrfs_free_extent(trans, root, blocknr, 1, 1);
379bb803951SChris Mason 	}
380e20d96d6SChris Mason 	parent = btrfs_buffer_node(parent_buf);
381bb803951SChris Mason 
382123abc88SChris Mason 	if (btrfs_header_nritems(&mid->header) >
383123abc88SChris Mason 	    BTRFS_NODEPTRS_PER_BLOCK(root) / 4)
384bb803951SChris Mason 		return 0;
385bb803951SChris Mason 
38654aa1f4dSChris Mason 	if (btrfs_header_nritems(&mid->header) < 2)
38754aa1f4dSChris Mason 		err_on_enospc = 1;
38854aa1f4dSChris Mason 
389bb803951SChris Mason 	left_buf = read_node_slot(root, parent_buf, pslot - 1);
390bb803951SChris Mason 	right_buf = read_node_slot(root, parent_buf, pslot + 1);
39179f95c82SChris Mason 
39279f95c82SChris Mason 	/* first, try to make some room in the middle buffer */
393bb803951SChris Mason 	if (left_buf) {
39454aa1f4dSChris Mason 		wret = btrfs_cow_block(trans, root, left_buf,
39554aa1f4dSChris Mason 				       parent_buf, pslot - 1, &left_buf);
39654aa1f4dSChris Mason 		if (wret) {
39754aa1f4dSChris Mason 			ret = wret;
39854aa1f4dSChris Mason 			goto enospc;
39954aa1f4dSChris Mason 		}
400e20d96d6SChris Mason 		left = btrfs_buffer_node(left_buf);
4017518a238SChris Mason 		orig_slot += btrfs_header_nritems(&left->header);
402e089f05cSChris Mason 		wret = push_node_left(trans, root, left_buf, mid_buf);
40379f95c82SChris Mason 		if (wret < 0)
40479f95c82SChris Mason 			ret = wret;
40554aa1f4dSChris Mason 		if (btrfs_header_nritems(&mid->header) < 2)
40654aa1f4dSChris Mason 			err_on_enospc = 1;
407bb803951SChris Mason 	}
40879f95c82SChris Mason 
40979f95c82SChris Mason 	/*
41079f95c82SChris Mason 	 * then try to empty the right most buffer into the middle
41179f95c82SChris Mason 	 */
412bb803951SChris Mason 	if (right_buf) {
41354aa1f4dSChris Mason 		wret = btrfs_cow_block(trans, root, right_buf,
41454aa1f4dSChris Mason 				       parent_buf, pslot + 1, &right_buf);
41554aa1f4dSChris Mason 		if (wret) {
41654aa1f4dSChris Mason 			ret = wret;
41754aa1f4dSChris Mason 			goto enospc;
41854aa1f4dSChris Mason 		}
41954aa1f4dSChris Mason 
420e20d96d6SChris Mason 		right = btrfs_buffer_node(right_buf);
421e089f05cSChris Mason 		wret = push_node_left(trans, root, mid_buf, right_buf);
42254aa1f4dSChris Mason 		if (wret < 0 && wret != -ENOSPC)
42379f95c82SChris Mason 			ret = wret;
4247518a238SChris Mason 		if (btrfs_header_nritems(&right->header) == 0) {
4257eccb903SChris Mason 			u64 blocknr = bh_blocknr(right_buf);
426e089f05cSChris Mason 			clean_tree_block(trans, root, right_buf);
427d6025579SChris Mason 			wait_on_buffer(right_buf);
428d6025579SChris Mason 			btrfs_block_release(root, right_buf);
429bb803951SChris Mason 			right_buf = NULL;
430bb803951SChris Mason 			right = NULL;
431e089f05cSChris Mason 			wret = del_ptr(trans, root, path, level + 1, pslot +
432e089f05cSChris Mason 				       1);
433bb803951SChris Mason 			if (wret)
434bb803951SChris Mason 				ret = wret;
435e089f05cSChris Mason 			wret = btrfs_free_extent(trans, root, blocknr, 1, 1);
436bb803951SChris Mason 			if (wret)
437bb803951SChris Mason 				ret = wret;
438bb803951SChris Mason 		} else {
439d6025579SChris Mason 			btrfs_memcpy(root, parent,
440d6025579SChris Mason 				     &parent->ptrs[pslot + 1].key,
441123abc88SChris Mason 				     &right->ptrs[0].key,
442e2fa7227SChris Mason 				     sizeof(struct btrfs_disk_key));
443d6025579SChris Mason 			btrfs_mark_buffer_dirty(parent_buf);
444bb803951SChris Mason 		}
445bb803951SChris Mason 	}
4467518a238SChris Mason 	if (btrfs_header_nritems(&mid->header) == 1) {
44779f95c82SChris Mason 		/*
44879f95c82SChris Mason 		 * we're not allowed to leave a node with one item in the
44979f95c82SChris Mason 		 * tree during a delete.  A deletion from lower in the tree
45079f95c82SChris Mason 		 * could try to delete the only pointer in this node.
45179f95c82SChris Mason 		 * So, pull some keys from the left.
45279f95c82SChris Mason 		 * There has to be a left pointer at this point because
45379f95c82SChris Mason 		 * otherwise we would have pulled some pointers from the
45479f95c82SChris Mason 		 * right
45579f95c82SChris Mason 		 */
45679f95c82SChris Mason 		BUG_ON(!left_buf);
457e089f05cSChris Mason 		wret = balance_node_right(trans, root, mid_buf, left_buf);
45854aa1f4dSChris Mason 		if (wret < 0) {
45979f95c82SChris Mason 			ret = wret;
46054aa1f4dSChris Mason 			goto enospc;
46154aa1f4dSChris Mason 		}
46279f95c82SChris Mason 		BUG_ON(wret == 1);
46379f95c82SChris Mason 	}
4647518a238SChris Mason 	if (btrfs_header_nritems(&mid->header) == 0) {
46579f95c82SChris Mason 		/* we've managed to empty the middle node, drop it */
4667eccb903SChris Mason 		u64 blocknr = bh_blocknr(mid_buf);
467e089f05cSChris Mason 		clean_tree_block(trans, root, mid_buf);
468d6025579SChris Mason 		wait_on_buffer(mid_buf);
469d6025579SChris Mason 		btrfs_block_release(root, mid_buf);
470bb803951SChris Mason 		mid_buf = NULL;
471bb803951SChris Mason 		mid = NULL;
472e089f05cSChris Mason 		wret = del_ptr(trans, root, path, level + 1, pslot);
473bb803951SChris Mason 		if (wret)
474bb803951SChris Mason 			ret = wret;
475e089f05cSChris Mason 		wret = btrfs_free_extent(trans, root, blocknr, 1, 1);
476bb803951SChris Mason 		if (wret)
477bb803951SChris Mason 			ret = wret;
47879f95c82SChris Mason 	} else {
47979f95c82SChris Mason 		/* update the parent key to reflect our changes */
480d6025579SChris Mason 		btrfs_memcpy(root, parent,
481d6025579SChris Mason 			     &parent->ptrs[pslot].key, &mid->ptrs[0].key,
482e2fa7227SChris Mason 			     sizeof(struct btrfs_disk_key));
483d6025579SChris Mason 		btrfs_mark_buffer_dirty(parent_buf);
48479f95c82SChris Mason 	}
485bb803951SChris Mason 
48679f95c82SChris Mason 	/* update the path */
487bb803951SChris Mason 	if (left_buf) {
4887518a238SChris Mason 		if (btrfs_header_nritems(&left->header) > orig_slot) {
489e20d96d6SChris Mason 			get_bh(left_buf);
490bb803951SChris Mason 			path->nodes[level] = left_buf;
491bb803951SChris Mason 			path->slots[level + 1] -= 1;
492bb803951SChris Mason 			path->slots[level] = orig_slot;
493bb803951SChris Mason 			if (mid_buf)
494234b63a0SChris Mason 				btrfs_block_release(root, mid_buf);
495bb803951SChris Mason 		} else {
4967518a238SChris Mason 			orig_slot -= btrfs_header_nritems(&left->header);
497bb803951SChris Mason 			path->slots[level] = orig_slot;
498bb803951SChris Mason 		}
499bb803951SChris Mason 	}
50079f95c82SChris Mason 	/* double check we haven't messed things up */
501123abc88SChris Mason 	check_block(root, path, level);
502e20d96d6SChris Mason 	if (orig_ptr !=
503e20d96d6SChris Mason 	    btrfs_node_blockptr(btrfs_buffer_node(path->nodes[level]),
5041d4f8a0cSChris Mason 				path->slots[level]))
50579f95c82SChris Mason 		BUG();
50654aa1f4dSChris Mason enospc:
507bb803951SChris Mason 	if (right_buf)
508234b63a0SChris Mason 		btrfs_block_release(root, right_buf);
509bb803951SChris Mason 	if (left_buf)
510234b63a0SChris Mason 		btrfs_block_release(root, left_buf);
511bb803951SChris Mason 	return ret;
512bb803951SChris Mason }
513bb803951SChris Mason 
514e66f709bSChris Mason /* returns zero if the push worked, non-zero otherwise */
515e66f709bSChris Mason static int push_nodes_for_insert(struct btrfs_trans_handle *trans,
516e66f709bSChris Mason 				struct btrfs_root *root,
517e66f709bSChris Mason 				struct btrfs_path *path, int level)
518e66f709bSChris Mason {
519e66f709bSChris Mason 	struct buffer_head *right_buf;
520e66f709bSChris Mason 	struct buffer_head *mid_buf;
521e66f709bSChris Mason 	struct buffer_head *left_buf;
522e66f709bSChris Mason 	struct buffer_head *parent_buf = NULL;
523e66f709bSChris Mason 	struct btrfs_node *right = NULL;
524e66f709bSChris Mason 	struct btrfs_node *mid;
525e66f709bSChris Mason 	struct btrfs_node *left = NULL;
526e66f709bSChris Mason 	struct btrfs_node *parent = NULL;
527e66f709bSChris Mason 	int ret = 0;
528e66f709bSChris Mason 	int wret;
529e66f709bSChris Mason 	int pslot;
530e66f709bSChris Mason 	int orig_slot = path->slots[level];
531e66f709bSChris Mason 	u64 orig_ptr;
532e66f709bSChris Mason 
533e66f709bSChris Mason 	if (level == 0)
534e66f709bSChris Mason 		return 1;
535e66f709bSChris Mason 
536e66f709bSChris Mason 	mid_buf = path->nodes[level];
537e66f709bSChris Mason 	mid = btrfs_buffer_node(mid_buf);
538e66f709bSChris Mason 	orig_ptr = btrfs_node_blockptr(mid, orig_slot);
539e66f709bSChris Mason 
540e66f709bSChris Mason 	if (level < BTRFS_MAX_LEVEL - 1)
541e66f709bSChris Mason 		parent_buf = path->nodes[level + 1];
542e66f709bSChris Mason 	pslot = path->slots[level + 1];
543e66f709bSChris Mason 
544e66f709bSChris Mason 	if (!parent_buf)
545e66f709bSChris Mason 		return 1;
546e66f709bSChris Mason 	parent = btrfs_buffer_node(parent_buf);
547e66f709bSChris Mason 
548e66f709bSChris Mason 	left_buf = read_node_slot(root, parent_buf, pslot - 1);
549e66f709bSChris Mason 
550e66f709bSChris Mason 	/* first, try to make some room in the middle buffer */
551e66f709bSChris Mason 	if (left_buf) {
552e66f709bSChris Mason 		u32 left_nr;
553e66f709bSChris Mason 		left = btrfs_buffer_node(left_buf);
554e66f709bSChris Mason 		left_nr = btrfs_header_nritems(&left->header);
55533ade1f8SChris Mason 		if (left_nr >= BTRFS_NODEPTRS_PER_BLOCK(root) - 1) {
55633ade1f8SChris Mason 			wret = 1;
55733ade1f8SChris Mason 		} else {
55854aa1f4dSChris Mason 			ret = btrfs_cow_block(trans, root, left_buf, parent_buf,
55933ade1f8SChris Mason 					      pslot - 1, &left_buf);
56054aa1f4dSChris Mason 			if (ret)
56154aa1f4dSChris Mason 				wret = 1;
56254aa1f4dSChris Mason 			else {
56333ade1f8SChris Mason 				left = btrfs_buffer_node(left_buf);
56454aa1f4dSChris Mason 				wret = push_node_left(trans, root,
56554aa1f4dSChris Mason 						      left_buf, mid_buf);
56654aa1f4dSChris Mason 			}
56733ade1f8SChris Mason 		}
568e66f709bSChris Mason 		if (wret < 0)
569e66f709bSChris Mason 			ret = wret;
570e66f709bSChris Mason 		if (wret == 0) {
571e66f709bSChris Mason 			orig_slot += left_nr;
572e66f709bSChris Mason 			btrfs_memcpy(root, parent,
573e66f709bSChris Mason 				     &parent->ptrs[pslot].key,
574e66f709bSChris Mason 				     &mid->ptrs[0].key,
575e66f709bSChris Mason 				     sizeof(struct btrfs_disk_key));
576e66f709bSChris Mason 			btrfs_mark_buffer_dirty(parent_buf);
577e66f709bSChris Mason 			if (btrfs_header_nritems(&left->header) > orig_slot) {
578e66f709bSChris Mason 				path->nodes[level] = left_buf;
579e66f709bSChris Mason 				path->slots[level + 1] -= 1;
580e66f709bSChris Mason 				path->slots[level] = orig_slot;
581e66f709bSChris Mason 				btrfs_block_release(root, mid_buf);
582e66f709bSChris Mason 			} else {
583e66f709bSChris Mason 				orig_slot -=
584e66f709bSChris Mason 					btrfs_header_nritems(&left->header);
585e66f709bSChris Mason 				path->slots[level] = orig_slot;
586e66f709bSChris Mason 				btrfs_block_release(root, left_buf);
587e66f709bSChris Mason 			}
588e66f709bSChris Mason 			check_node(root, path, level);
589e66f709bSChris Mason 			return 0;
590e66f709bSChris Mason 		}
591e66f709bSChris Mason 		btrfs_block_release(root, left_buf);
592e66f709bSChris Mason 	}
593e66f709bSChris Mason 	right_buf = read_node_slot(root, parent_buf, pslot + 1);
594e66f709bSChris Mason 
595e66f709bSChris Mason 	/*
596e66f709bSChris Mason 	 * then try to empty the right most buffer into the middle
597e66f709bSChris Mason 	 */
598e66f709bSChris Mason 	if (right_buf) {
59933ade1f8SChris Mason 		u32 right_nr;
600e66f709bSChris Mason 		right = btrfs_buffer_node(right_buf);
60133ade1f8SChris Mason 		right_nr = btrfs_header_nritems(&right->header);
60233ade1f8SChris Mason 		if (right_nr >= BTRFS_NODEPTRS_PER_BLOCK(root) - 1) {
60333ade1f8SChris Mason 			wret = 1;
60433ade1f8SChris Mason 		} else {
60554aa1f4dSChris Mason 			ret = btrfs_cow_block(trans, root, right_buf,
60654aa1f4dSChris Mason 					      parent_buf, pslot + 1,
60754aa1f4dSChris Mason 					      &right_buf);
60854aa1f4dSChris Mason 			if (ret)
60954aa1f4dSChris Mason 				wret = 1;
61054aa1f4dSChris Mason 			else {
61133ade1f8SChris Mason 				right = btrfs_buffer_node(right_buf);
61233ade1f8SChris Mason 				wret = balance_node_right(trans, root,
61333ade1f8SChris Mason 							  right_buf, mid_buf);
61433ade1f8SChris Mason 			}
61554aa1f4dSChris Mason 		}
616e66f709bSChris Mason 		if (wret < 0)
617e66f709bSChris Mason 			ret = wret;
618e66f709bSChris Mason 		if (wret == 0) {
619e66f709bSChris Mason 			btrfs_memcpy(root, parent,
620e66f709bSChris Mason 				     &parent->ptrs[pslot + 1].key,
621e66f709bSChris Mason 				     &right->ptrs[0].key,
622e66f709bSChris Mason 				     sizeof(struct btrfs_disk_key));
623e66f709bSChris Mason 			btrfs_mark_buffer_dirty(parent_buf);
624e66f709bSChris Mason 			if (btrfs_header_nritems(&mid->header) <= orig_slot) {
625e66f709bSChris Mason 				path->nodes[level] = right_buf;
626e66f709bSChris Mason 				path->slots[level + 1] += 1;
627e66f709bSChris Mason 				path->slots[level] = orig_slot -
628e66f709bSChris Mason 					btrfs_header_nritems(&mid->header);
629e66f709bSChris Mason 				btrfs_block_release(root, mid_buf);
630e66f709bSChris Mason 			} else {
631e66f709bSChris Mason 				btrfs_block_release(root, right_buf);
632e66f709bSChris Mason 			}
633e66f709bSChris Mason 			check_node(root, path, level);
634e66f709bSChris Mason 			return 0;
635e66f709bSChris Mason 		}
636e66f709bSChris Mason 		btrfs_block_release(root, right_buf);
637e66f709bSChris Mason 	}
638e66f709bSChris Mason 	check_node(root, path, level);
639e66f709bSChris Mason 	return 1;
640e66f709bSChris Mason }
641e66f709bSChris Mason 
64274123bd7SChris Mason /*
64374123bd7SChris Mason  * look for key in the tree.  path is filled in with nodes along the way
64474123bd7SChris Mason  * if key is found, we return zero and you can find the item in the leaf
64574123bd7SChris Mason  * level of the path (level 0)
64674123bd7SChris Mason  *
64774123bd7SChris Mason  * If the key isn't found, the path points to the slot where it should
648aa5d6bedSChris Mason  * be inserted, and 1 is returned.  If there are other errors during the
649aa5d6bedSChris Mason  * search a negative error number is returned.
65097571fd0SChris Mason  *
65197571fd0SChris Mason  * if ins_len > 0, nodes and leaves will be split as we walk down the
65297571fd0SChris Mason  * tree.  if ins_len < 0, nodes will be merged as we walk down the tree (if
65397571fd0SChris Mason  * possible)
65474123bd7SChris Mason  */
655e089f05cSChris Mason int btrfs_search_slot(struct btrfs_trans_handle *trans, struct btrfs_root
656e089f05cSChris Mason 		      *root, struct btrfs_key *key, struct btrfs_path *p, int
657e089f05cSChris Mason 		      ins_len, int cow)
658be0e5c09SChris Mason {
659e20d96d6SChris Mason 	struct buffer_head *b;
660e20d96d6SChris Mason 	struct buffer_head *cow_buf;
661234b63a0SChris Mason 	struct btrfs_node *c;
6629f3a7427SChris Mason 	struct btrfs_root_item *root_item = &root->root_item;
663be0e5c09SChris Mason 	int slot;
664be0e5c09SChris Mason 	int ret;
665be0e5c09SChris Mason 	int level;
6669f3a7427SChris Mason 	u8 lowest_level = 0;
6679f3a7427SChris Mason 
6689f3a7427SChris Mason 	if (btrfs_root_refs(root_item) == 0 && root->ref_cows) {
6699f3a7427SChris Mason 		lowest_level = root_item->drop_level;
6709f3a7427SChris Mason 		WARN_ON(ins_len || cow);
6719f3a7427SChris Mason 	}
6725c680ed6SChris Mason 
67322b0ebdaSChris Mason 	WARN_ON(p->nodes[0] != NULL);
67422b0ebdaSChris Mason 	WARN_ON(!mutex_is_locked(&root->fs_info->fs_mutex));
675bb803951SChris Mason again:
676bb803951SChris Mason 	b = root->node;
677e20d96d6SChris Mason 	get_bh(b);
678eb60ceacSChris Mason 	while (b) {
679e20d96d6SChris Mason 		c = btrfs_buffer_node(b);
680e20d96d6SChris Mason 		level = btrfs_header_level(&c->header);
68102217ed2SChris Mason 		if (cow) {
68202217ed2SChris Mason 			int wret;
683e20d96d6SChris Mason 			wret = btrfs_cow_block(trans, root, b,
684e20d96d6SChris Mason 					       p->nodes[level + 1],
685e20d96d6SChris Mason 					       p->slots[level + 1],
686e089f05cSChris Mason 					       &cow_buf);
68754aa1f4dSChris Mason 			if (wret) {
68854aa1f4dSChris Mason 				btrfs_block_release(root, cow_buf);
68954aa1f4dSChris Mason 				return wret;
69054aa1f4dSChris Mason 			}
69102217ed2SChris Mason 			b = cow_buf;
6922c90e5d6SChris Mason 			c = btrfs_buffer_node(b);
69302217ed2SChris Mason 		}
69402217ed2SChris Mason 		BUG_ON(!cow && ins_len);
6952c90e5d6SChris Mason 		if (level != btrfs_header_level(&c->header))
6962c90e5d6SChris Mason 			WARN_ON(1);
6972c90e5d6SChris Mason 		level = btrfs_header_level(&c->header);
698eb60ceacSChris Mason 		p->nodes[level] = b;
699123abc88SChris Mason 		ret = check_block(root, p, level);
700aa5d6bedSChris Mason 		if (ret)
701aa5d6bedSChris Mason 			return -1;
702be0e5c09SChris Mason 		ret = bin_search(c, key, &slot);
7037518a238SChris Mason 		if (!btrfs_is_leaf(c)) {
704be0e5c09SChris Mason 			if (ret && slot > 0)
705be0e5c09SChris Mason 				slot -= 1;
706be0e5c09SChris Mason 			p->slots[level] = slot;
707d4dbff95SChris Mason 			if (ins_len > 0 && btrfs_header_nritems(&c->header) >=
708d4dbff95SChris Mason 			    BTRFS_NODEPTRS_PER_BLOCK(root) - 1) {
709e089f05cSChris Mason 				int sret = split_node(trans, root, p, level);
7105c680ed6SChris Mason 				BUG_ON(sret > 0);
7115c680ed6SChris Mason 				if (sret)
7125c680ed6SChris Mason 					return sret;
7135c680ed6SChris Mason 				b = p->nodes[level];
714e20d96d6SChris Mason 				c = btrfs_buffer_node(b);
7155c680ed6SChris Mason 				slot = p->slots[level];
716bb803951SChris Mason 			} else if (ins_len < 0) {
717e089f05cSChris Mason 				int sret = balance_level(trans, root, p,
718e089f05cSChris Mason 							 level);
719bb803951SChris Mason 				if (sret)
720bb803951SChris Mason 					return sret;
721bb803951SChris Mason 				b = p->nodes[level];
722bb803951SChris Mason 				if (!b)
723bb803951SChris Mason 					goto again;
724e20d96d6SChris Mason 				c = btrfs_buffer_node(b);
725bb803951SChris Mason 				slot = p->slots[level];
7267518a238SChris Mason 				BUG_ON(btrfs_header_nritems(&c->header) == 1);
7275c680ed6SChris Mason 			}
7289f3a7427SChris Mason 			/* this is only true while dropping a snapshot */
7299f3a7427SChris Mason 			if (level == lowest_level)
7309f3a7427SChris Mason 				break;
7311d4f8a0cSChris Mason 			b = read_tree_block(root, btrfs_node_blockptr(c, slot));
732be0e5c09SChris Mason 		} else {
733234b63a0SChris Mason 			struct btrfs_leaf *l = (struct btrfs_leaf *)c;
734be0e5c09SChris Mason 			p->slots[level] = slot;
735123abc88SChris Mason 			if (ins_len > 0 && btrfs_leaf_free_space(root, l) <
7360783fcfcSChris Mason 			    sizeof(struct btrfs_item) + ins_len) {
737d4dbff95SChris Mason 				int sret = split_leaf(trans, root, key,
738d4dbff95SChris Mason 						      p, ins_len);
7395c680ed6SChris Mason 				BUG_ON(sret > 0);
7405c680ed6SChris Mason 				if (sret)
7415c680ed6SChris Mason 					return sret;
7425c680ed6SChris Mason 			}
743be0e5c09SChris Mason 			return ret;
744be0e5c09SChris Mason 		}
745be0e5c09SChris Mason 	}
746aa5d6bedSChris Mason 	return 1;
747be0e5c09SChris Mason }
748be0e5c09SChris Mason 
74974123bd7SChris Mason /*
75074123bd7SChris Mason  * adjust the pointers going up the tree, starting at level
75174123bd7SChris Mason  * making sure the right key of each node is points to 'key'.
75274123bd7SChris Mason  * This is used after shifting pointers to the left, so it stops
75374123bd7SChris Mason  * fixing up pointers when a given leaf/node is not in slot 0 of the
75474123bd7SChris Mason  * higher levels
755aa5d6bedSChris Mason  *
756aa5d6bedSChris Mason  * If this fails to write a tree block, it returns -1, but continues
757aa5d6bedSChris Mason  * fixing up the blocks in ram so the tree is consistent.
75874123bd7SChris Mason  */
759e089f05cSChris Mason static int fixup_low_keys(struct btrfs_trans_handle *trans, struct btrfs_root
760e089f05cSChris Mason 			  *root, struct btrfs_path *path, struct btrfs_disk_key
761e089f05cSChris Mason 			  *key, int level)
762be0e5c09SChris Mason {
763be0e5c09SChris Mason 	int i;
764aa5d6bedSChris Mason 	int ret = 0;
765234b63a0SChris Mason 	for (i = level; i < BTRFS_MAX_LEVEL; i++) {
766234b63a0SChris Mason 		struct btrfs_node *t;
767be0e5c09SChris Mason 		int tslot = path->slots[i];
768eb60ceacSChris Mason 		if (!path->nodes[i])
769be0e5c09SChris Mason 			break;
770e20d96d6SChris Mason 		t = btrfs_buffer_node(path->nodes[i]);
771d6025579SChris Mason 		btrfs_memcpy(root, t, &t->ptrs[tslot].key, key, sizeof(*key));
772d6025579SChris Mason 		btrfs_mark_buffer_dirty(path->nodes[i]);
773be0e5c09SChris Mason 		if (tslot != 0)
774be0e5c09SChris Mason 			break;
775be0e5c09SChris Mason 	}
776aa5d6bedSChris Mason 	return ret;
777be0e5c09SChris Mason }
778be0e5c09SChris Mason 
77974123bd7SChris Mason /*
78074123bd7SChris Mason  * try to push data from one node into the next node left in the
78179f95c82SChris Mason  * tree.
782aa5d6bedSChris Mason  *
783aa5d6bedSChris Mason  * returns 0 if some ptrs were pushed left, < 0 if there was some horrible
784aa5d6bedSChris Mason  * error, and > 0 if there was no room in the left hand block.
78574123bd7SChris Mason  */
786e089f05cSChris Mason static int push_node_left(struct btrfs_trans_handle *trans, struct btrfs_root
787e20d96d6SChris Mason 			  *root, struct buffer_head *dst_buf, struct
788e20d96d6SChris Mason 			  buffer_head *src_buf)
789be0e5c09SChris Mason {
790e20d96d6SChris Mason 	struct btrfs_node *src = btrfs_buffer_node(src_buf);
791e20d96d6SChris Mason 	struct btrfs_node *dst = btrfs_buffer_node(dst_buf);
792be0e5c09SChris Mason 	int push_items = 0;
793bb803951SChris Mason 	int src_nritems;
794bb803951SChris Mason 	int dst_nritems;
795aa5d6bedSChris Mason 	int ret = 0;
796be0e5c09SChris Mason 
7977518a238SChris Mason 	src_nritems = btrfs_header_nritems(&src->header);
7987518a238SChris Mason 	dst_nritems = btrfs_header_nritems(&dst->header);
799123abc88SChris Mason 	push_items = BTRFS_NODEPTRS_PER_BLOCK(root) - dst_nritems;
80054aa1f4dSChris Mason 
801eb60ceacSChris Mason 	if (push_items <= 0) {
802be0e5c09SChris Mason 		return 1;
803eb60ceacSChris Mason 	}
804be0e5c09SChris Mason 
805be0e5c09SChris Mason 	if (src_nritems < push_items)
806be0e5c09SChris Mason 		push_items = src_nritems;
80779f95c82SChris Mason 
808d6025579SChris Mason 	btrfs_memcpy(root, dst, dst->ptrs + dst_nritems, src->ptrs,
809123abc88SChris Mason 		     push_items * sizeof(struct btrfs_key_ptr));
810bb803951SChris Mason 	if (push_items < src_nritems) {
811d6025579SChris Mason 		btrfs_memmove(root, src, src->ptrs, src->ptrs + push_items,
812e2fa7227SChris Mason 			(src_nritems - push_items) *
813123abc88SChris Mason 			sizeof(struct btrfs_key_ptr));
814bb803951SChris Mason 	}
8157518a238SChris Mason 	btrfs_set_header_nritems(&src->header, src_nritems - push_items);
8167518a238SChris Mason 	btrfs_set_header_nritems(&dst->header, dst_nritems + push_items);
817d6025579SChris Mason 	btrfs_mark_buffer_dirty(src_buf);
818d6025579SChris Mason 	btrfs_mark_buffer_dirty(dst_buf);
819bb803951SChris Mason 	return ret;
820be0e5c09SChris Mason }
821be0e5c09SChris Mason 
82297571fd0SChris Mason /*
82379f95c82SChris Mason  * try to push data from one node into the next node right in the
82479f95c82SChris Mason  * tree.
82579f95c82SChris Mason  *
82679f95c82SChris Mason  * returns 0 if some ptrs were pushed, < 0 if there was some horrible
82779f95c82SChris Mason  * error, and > 0 if there was no room in the right hand block.
82879f95c82SChris Mason  *
82979f95c82SChris Mason  * this will  only push up to 1/2 the contents of the left node over
83079f95c82SChris Mason  */
831e089f05cSChris Mason static int balance_node_right(struct btrfs_trans_handle *trans, struct
832e20d96d6SChris Mason 			      btrfs_root *root, struct buffer_head *dst_buf,
833e20d96d6SChris Mason 			      struct buffer_head *src_buf)
83479f95c82SChris Mason {
835e20d96d6SChris Mason 	struct btrfs_node *src = btrfs_buffer_node(src_buf);
836e20d96d6SChris Mason 	struct btrfs_node *dst = btrfs_buffer_node(dst_buf);
83779f95c82SChris Mason 	int push_items = 0;
83879f95c82SChris Mason 	int max_push;
83979f95c82SChris Mason 	int src_nritems;
84079f95c82SChris Mason 	int dst_nritems;
84179f95c82SChris Mason 	int ret = 0;
84279f95c82SChris Mason 
8437518a238SChris Mason 	src_nritems = btrfs_header_nritems(&src->header);
8447518a238SChris Mason 	dst_nritems = btrfs_header_nritems(&dst->header);
845123abc88SChris Mason 	push_items = BTRFS_NODEPTRS_PER_BLOCK(root) - dst_nritems;
84679f95c82SChris Mason 	if (push_items <= 0) {
84779f95c82SChris Mason 		return 1;
84879f95c82SChris Mason 	}
84979f95c82SChris Mason 
85079f95c82SChris Mason 	max_push = src_nritems / 2 + 1;
85179f95c82SChris Mason 	/* don't try to empty the node */
85279f95c82SChris Mason 	if (max_push > src_nritems)
85379f95c82SChris Mason 		return 1;
85479f95c82SChris Mason 	if (max_push < push_items)
85579f95c82SChris Mason 		push_items = max_push;
85679f95c82SChris Mason 
857d6025579SChris Mason 	btrfs_memmove(root, dst, dst->ptrs + push_items, dst->ptrs,
858123abc88SChris Mason 		      dst_nritems * sizeof(struct btrfs_key_ptr));
859d6025579SChris Mason 
860d6025579SChris Mason 	btrfs_memcpy(root, dst, dst->ptrs,
861d6025579SChris Mason 		     src->ptrs + src_nritems - push_items,
862123abc88SChris Mason 		     push_items * sizeof(struct btrfs_key_ptr));
86379f95c82SChris Mason 
8647518a238SChris Mason 	btrfs_set_header_nritems(&src->header, src_nritems - push_items);
8657518a238SChris Mason 	btrfs_set_header_nritems(&dst->header, dst_nritems + push_items);
86679f95c82SChris Mason 
867d6025579SChris Mason 	btrfs_mark_buffer_dirty(src_buf);
868d6025579SChris Mason 	btrfs_mark_buffer_dirty(dst_buf);
86979f95c82SChris Mason 	return ret;
87079f95c82SChris Mason }
87179f95c82SChris Mason 
87279f95c82SChris Mason /*
87397571fd0SChris Mason  * helper function to insert a new root level in the tree.
87497571fd0SChris Mason  * A new node is allocated, and a single item is inserted to
87597571fd0SChris Mason  * point to the existing root
876aa5d6bedSChris Mason  *
877aa5d6bedSChris Mason  * returns zero on success or < 0 on failure.
87897571fd0SChris Mason  */
879e089f05cSChris Mason static int insert_new_root(struct btrfs_trans_handle *trans, struct btrfs_root
880e089f05cSChris Mason 			   *root, struct btrfs_path *path, int level)
88174123bd7SChris Mason {
882e20d96d6SChris Mason 	struct buffer_head *t;
883234b63a0SChris Mason 	struct btrfs_node *lower;
884234b63a0SChris Mason 	struct btrfs_node *c;
885e2fa7227SChris Mason 	struct btrfs_disk_key *lower_key;
8865c680ed6SChris Mason 
8875c680ed6SChris Mason 	BUG_ON(path->nodes[level]);
8885c680ed6SChris Mason 	BUG_ON(path->nodes[level-1] != root->node);
8895c680ed6SChris Mason 
89031f3c99bSChris Mason 	t = btrfs_alloc_free_block(trans, root, root->node->b_blocknr);
89154aa1f4dSChris Mason 	if (IS_ERR(t))
89254aa1f4dSChris Mason 		return PTR_ERR(t);
893e20d96d6SChris Mason 	c = btrfs_buffer_node(t);
894123abc88SChris Mason 	memset(c, 0, root->blocksize);
8957518a238SChris Mason 	btrfs_set_header_nritems(&c->header, 1);
8967518a238SChris Mason 	btrfs_set_header_level(&c->header, level);
8977eccb903SChris Mason 	btrfs_set_header_blocknr(&c->header, bh_blocknr(t));
8987f5c1516SChris Mason 	btrfs_set_header_generation(&c->header, trans->transid);
8994d775673SChris Mason 	btrfs_set_header_owner(&c->header, root->root_key.objectid);
900e20d96d6SChris Mason 	lower = btrfs_buffer_node(path->nodes[level-1]);
9013eb0314dSChris Mason 	memcpy(c->header.fsid, root->fs_info->disk_super->fsid,
9023eb0314dSChris Mason 	       sizeof(c->header.fsid));
9037518a238SChris Mason 	if (btrfs_is_leaf(lower))
904234b63a0SChris Mason 		lower_key = &((struct btrfs_leaf *)lower)->items[0].key;
90574123bd7SChris Mason 	else
906123abc88SChris Mason 		lower_key = &lower->ptrs[0].key;
907d6025579SChris Mason 	btrfs_memcpy(root, c, &c->ptrs[0].key, lower_key,
908d6025579SChris Mason 		     sizeof(struct btrfs_disk_key));
9097eccb903SChris Mason 	btrfs_set_node_blockptr(c, 0, bh_blocknr(path->nodes[level - 1]));
910d5719762SChris Mason 
911d6025579SChris Mason 	btrfs_mark_buffer_dirty(t);
912d5719762SChris Mason 
913cfaa7295SChris Mason 	/* the super has an extra ref to root->node */
914234b63a0SChris Mason 	btrfs_block_release(root, root->node);
91574123bd7SChris Mason 	root->node = t;
916e20d96d6SChris Mason 	get_bh(t);
91774123bd7SChris Mason 	path->nodes[level] = t;
91874123bd7SChris Mason 	path->slots[level] = 0;
91974123bd7SChris Mason 	return 0;
92074123bd7SChris Mason }
9215c680ed6SChris Mason 
9225c680ed6SChris Mason /*
9235c680ed6SChris Mason  * worker function to insert a single pointer in a node.
9245c680ed6SChris Mason  * the node should have enough room for the pointer already
92597571fd0SChris Mason  *
9265c680ed6SChris Mason  * slot and level indicate where you want the key to go, and
9275c680ed6SChris Mason  * blocknr is the block the key points to.
928aa5d6bedSChris Mason  *
929aa5d6bedSChris Mason  * returns zero on success and < 0 on any error
9305c680ed6SChris Mason  */
931e089f05cSChris Mason static int insert_ptr(struct btrfs_trans_handle *trans, struct btrfs_root
932e089f05cSChris Mason 		      *root, struct btrfs_path *path, struct btrfs_disk_key
933e089f05cSChris Mason 		      *key, u64 blocknr, int slot, int level)
9345c680ed6SChris Mason {
935234b63a0SChris Mason 	struct btrfs_node *lower;
9365c680ed6SChris Mason 	int nritems;
9375c680ed6SChris Mason 
9385c680ed6SChris Mason 	BUG_ON(!path->nodes[level]);
939e20d96d6SChris Mason 	lower = btrfs_buffer_node(path->nodes[level]);
9407518a238SChris Mason 	nritems = btrfs_header_nritems(&lower->header);
94174123bd7SChris Mason 	if (slot > nritems)
94274123bd7SChris Mason 		BUG();
943123abc88SChris Mason 	if (nritems == BTRFS_NODEPTRS_PER_BLOCK(root))
94474123bd7SChris Mason 		BUG();
94574123bd7SChris Mason 	if (slot != nritems) {
946d6025579SChris Mason 		btrfs_memmove(root, lower, lower->ptrs + slot + 1,
947d6025579SChris Mason 			      lower->ptrs + slot,
948123abc88SChris Mason 			      (nritems - slot) * sizeof(struct btrfs_key_ptr));
94974123bd7SChris Mason 	}
950d6025579SChris Mason 	btrfs_memcpy(root, lower, &lower->ptrs[slot].key,
951d6025579SChris Mason 		     key, sizeof(struct btrfs_disk_key));
9521d4f8a0cSChris Mason 	btrfs_set_node_blockptr(lower, slot, blocknr);
9537518a238SChris Mason 	btrfs_set_header_nritems(&lower->header, nritems + 1);
954d6025579SChris Mason 	btrfs_mark_buffer_dirty(path->nodes[level]);
955098f59c2SChris Mason 	check_node(root, path, level);
95674123bd7SChris Mason 	return 0;
95774123bd7SChris Mason }
95874123bd7SChris Mason 
95997571fd0SChris Mason /*
96097571fd0SChris Mason  * split the node at the specified level in path in two.
96197571fd0SChris Mason  * The path is corrected to point to the appropriate node after the split
96297571fd0SChris Mason  *
96397571fd0SChris Mason  * Before splitting this tries to make some room in the node by pushing
96497571fd0SChris Mason  * left and right, if either one works, it returns right away.
965aa5d6bedSChris Mason  *
966aa5d6bedSChris Mason  * returns 0 on success and < 0 on failure
96797571fd0SChris Mason  */
968e089f05cSChris Mason static int split_node(struct btrfs_trans_handle *trans, struct btrfs_root
969e089f05cSChris Mason 		      *root, struct btrfs_path *path, int level)
970be0e5c09SChris Mason {
971e20d96d6SChris Mason 	struct buffer_head *t;
972234b63a0SChris Mason 	struct btrfs_node *c;
973e20d96d6SChris Mason 	struct buffer_head *split_buffer;
974234b63a0SChris Mason 	struct btrfs_node *split;
975be0e5c09SChris Mason 	int mid;
9765c680ed6SChris Mason 	int ret;
977aa5d6bedSChris Mason 	int wret;
9787518a238SChris Mason 	u32 c_nritems;
979be0e5c09SChris Mason 
9805c680ed6SChris Mason 	t = path->nodes[level];
981e20d96d6SChris Mason 	c = btrfs_buffer_node(t);
9825c680ed6SChris Mason 	if (t == root->node) {
9835c680ed6SChris Mason 		/* trying to split the root, lets make a new one */
984e089f05cSChris Mason 		ret = insert_new_root(trans, root, path, level + 1);
9855c680ed6SChris Mason 		if (ret)
9865c680ed6SChris Mason 			return ret;
987e66f709bSChris Mason 	} else {
988e66f709bSChris Mason 		ret = push_nodes_for_insert(trans, root, path, level);
989e66f709bSChris Mason 		t = path->nodes[level];
990e66f709bSChris Mason 		c = btrfs_buffer_node(t);
991e66f709bSChris Mason 		if (!ret &&
992e66f709bSChris Mason 		    btrfs_header_nritems(&c->header) <
993e66f709bSChris Mason 		    BTRFS_NODEPTRS_PER_BLOCK(root) - 1)
994e66f709bSChris Mason 			return 0;
99554aa1f4dSChris Mason 		if (ret < 0)
99654aa1f4dSChris Mason 			return ret;
9975c680ed6SChris Mason 	}
998e66f709bSChris Mason 
9997518a238SChris Mason 	c_nritems = btrfs_header_nritems(&c->header);
100031f3c99bSChris Mason 	split_buffer = btrfs_alloc_free_block(trans, root, t->b_blocknr);
100154aa1f4dSChris Mason 	if (IS_ERR(split_buffer))
100254aa1f4dSChris Mason 		return PTR_ERR(split_buffer);
100354aa1f4dSChris Mason 
1004e20d96d6SChris Mason 	split = btrfs_buffer_node(split_buffer);
10057518a238SChris Mason 	btrfs_set_header_flags(&split->header, btrfs_header_flags(&c->header));
10069a6f11edSChris Mason 	btrfs_set_header_level(&split->header, btrfs_header_level(&c->header));
10077eccb903SChris Mason 	btrfs_set_header_blocknr(&split->header, bh_blocknr(split_buffer));
10087f5c1516SChris Mason 	btrfs_set_header_generation(&split->header, trans->transid);
10094d775673SChris Mason 	btrfs_set_header_owner(&split->header, root->root_key.objectid);
10103eb0314dSChris Mason 	memcpy(split->header.fsid, root->fs_info->disk_super->fsid,
10113eb0314dSChris Mason 	       sizeof(split->header.fsid));
10127518a238SChris Mason 	mid = (c_nritems + 1) / 2;
1013d6025579SChris Mason 	btrfs_memcpy(root, split, split->ptrs, c->ptrs + mid,
1014123abc88SChris Mason 		     (c_nritems - mid) * sizeof(struct btrfs_key_ptr));
10157518a238SChris Mason 	btrfs_set_header_nritems(&split->header, c_nritems - mid);
10167518a238SChris Mason 	btrfs_set_header_nritems(&c->header, mid);
1017aa5d6bedSChris Mason 	ret = 0;
1018aa5d6bedSChris Mason 
1019d6025579SChris Mason 	btrfs_mark_buffer_dirty(t);
1020d6025579SChris Mason 	btrfs_mark_buffer_dirty(split_buffer);
1021e089f05cSChris Mason 	wret = insert_ptr(trans, root, path, &split->ptrs[0].key,
10227eccb903SChris Mason 			  bh_blocknr(split_buffer), path->slots[level + 1] + 1,
1023123abc88SChris Mason 			  level + 1);
1024aa5d6bedSChris Mason 	if (wret)
1025aa5d6bedSChris Mason 		ret = wret;
1026aa5d6bedSChris Mason 
10275de08d7dSChris Mason 	if (path->slots[level] >= mid) {
10285c680ed6SChris Mason 		path->slots[level] -= mid;
1029234b63a0SChris Mason 		btrfs_block_release(root, t);
10305c680ed6SChris Mason 		path->nodes[level] = split_buffer;
10315c680ed6SChris Mason 		path->slots[level + 1] += 1;
1032eb60ceacSChris Mason 	} else {
1033234b63a0SChris Mason 		btrfs_block_release(root, split_buffer);
1034be0e5c09SChris Mason 	}
1035aa5d6bedSChris Mason 	return ret;
1036be0e5c09SChris Mason }
1037be0e5c09SChris Mason 
103874123bd7SChris Mason /*
103974123bd7SChris Mason  * how many bytes are required to store the items in a leaf.  start
104074123bd7SChris Mason  * and nr indicate which items in the leaf to check.  This totals up the
104174123bd7SChris Mason  * space used both by the item structs and the item data
104274123bd7SChris Mason  */
1043234b63a0SChris Mason static int leaf_space_used(struct btrfs_leaf *l, int start, int nr)
1044be0e5c09SChris Mason {
1045be0e5c09SChris Mason 	int data_len;
1046d4dbff95SChris Mason 	int nritems = btrfs_header_nritems(&l->header);
1047d4dbff95SChris Mason 	int end = min(nritems, start + nr) - 1;
1048be0e5c09SChris Mason 
1049be0e5c09SChris Mason 	if (!nr)
1050be0e5c09SChris Mason 		return 0;
10510783fcfcSChris Mason 	data_len = btrfs_item_end(l->items + start);
10520783fcfcSChris Mason 	data_len = data_len - btrfs_item_offset(l->items + end);
10530783fcfcSChris Mason 	data_len += sizeof(struct btrfs_item) * nr;
1054d4dbff95SChris Mason 	WARN_ON(data_len < 0);
1055be0e5c09SChris Mason 	return data_len;
1056be0e5c09SChris Mason }
1057be0e5c09SChris Mason 
105874123bd7SChris Mason /*
1059d4dbff95SChris Mason  * The space between the end of the leaf items and
1060d4dbff95SChris Mason  * the start of the leaf data.  IOW, how much room
1061d4dbff95SChris Mason  * the leaf has left for both items and data
1062d4dbff95SChris Mason  */
1063d4dbff95SChris Mason int btrfs_leaf_free_space(struct btrfs_root *root, struct btrfs_leaf *leaf)
1064d4dbff95SChris Mason {
1065d4dbff95SChris Mason 	int nritems = btrfs_header_nritems(&leaf->header);
1066d4dbff95SChris Mason 	return BTRFS_LEAF_DATA_SIZE(root) - leaf_space_used(leaf, 0, nritems);
1067d4dbff95SChris Mason }
1068d4dbff95SChris Mason 
1069d4dbff95SChris Mason /*
107000ec4c51SChris Mason  * push some data in the path leaf to the right, trying to free up at
107100ec4c51SChris Mason  * least data_size bytes.  returns zero if the push worked, nonzero otherwise
1072aa5d6bedSChris Mason  *
1073aa5d6bedSChris Mason  * returns 1 if the push failed because the other node didn't have enough
1074aa5d6bedSChris Mason  * room, 0 if everything worked out and < 0 if there were major errors.
107500ec4c51SChris Mason  */
1076e089f05cSChris Mason static int push_leaf_right(struct btrfs_trans_handle *trans, struct btrfs_root
1077e089f05cSChris Mason 			   *root, struct btrfs_path *path, int data_size)
107800ec4c51SChris Mason {
1079e20d96d6SChris Mason 	struct buffer_head *left_buf = path->nodes[0];
1080e20d96d6SChris Mason 	struct btrfs_leaf *left = btrfs_buffer_leaf(left_buf);
1081234b63a0SChris Mason 	struct btrfs_leaf *right;
1082e20d96d6SChris Mason 	struct buffer_head *right_buf;
1083e20d96d6SChris Mason 	struct buffer_head *upper;
1084e20d96d6SChris Mason 	struct btrfs_node *upper_node;
108500ec4c51SChris Mason 	int slot;
108600ec4c51SChris Mason 	int i;
108700ec4c51SChris Mason 	int free_space;
108800ec4c51SChris Mason 	int push_space = 0;
108900ec4c51SChris Mason 	int push_items = 0;
10900783fcfcSChris Mason 	struct btrfs_item *item;
10917518a238SChris Mason 	u32 left_nritems;
10927518a238SChris Mason 	u32 right_nritems;
109354aa1f4dSChris Mason 	int ret;
109400ec4c51SChris Mason 
109500ec4c51SChris Mason 	slot = path->slots[1];
109600ec4c51SChris Mason 	if (!path->nodes[1]) {
109700ec4c51SChris Mason 		return 1;
109800ec4c51SChris Mason 	}
109900ec4c51SChris Mason 	upper = path->nodes[1];
1100e20d96d6SChris Mason 	upper_node = btrfs_buffer_node(upper);
1101e20d96d6SChris Mason 	if (slot >= btrfs_header_nritems(&upper_node->header) - 1) {
110200ec4c51SChris Mason 		return 1;
110300ec4c51SChris Mason 	}
1104e20d96d6SChris Mason 	right_buf = read_tree_block(root,
1105e20d96d6SChris Mason 		    btrfs_node_blockptr(btrfs_buffer_node(upper), slot + 1));
1106e20d96d6SChris Mason 	right = btrfs_buffer_leaf(right_buf);
1107123abc88SChris Mason 	free_space = btrfs_leaf_free_space(root, right);
11080783fcfcSChris Mason 	if (free_space < data_size + sizeof(struct btrfs_item)) {
1109234b63a0SChris Mason 		btrfs_block_release(root, right_buf);
111000ec4c51SChris Mason 		return 1;
111100ec4c51SChris Mason 	}
111202217ed2SChris Mason 	/* cow and double check */
111354aa1f4dSChris Mason 	ret = btrfs_cow_block(trans, root, right_buf, upper,
111454aa1f4dSChris Mason 			      slot + 1, &right_buf);
111554aa1f4dSChris Mason 	if (ret) {
111654aa1f4dSChris Mason 		btrfs_block_release(root, right_buf);
111754aa1f4dSChris Mason 		return 1;
111854aa1f4dSChris Mason 	}
1119e20d96d6SChris Mason 	right = btrfs_buffer_leaf(right_buf);
1120123abc88SChris Mason 	free_space = btrfs_leaf_free_space(root, right);
11210783fcfcSChris Mason 	if (free_space < data_size + sizeof(struct btrfs_item)) {
1122234b63a0SChris Mason 		btrfs_block_release(root, right_buf);
112302217ed2SChris Mason 		return 1;
112402217ed2SChris Mason 	}
112502217ed2SChris Mason 
11267518a238SChris Mason 	left_nritems = btrfs_header_nritems(&left->header);
1127a429e513SChris Mason 	if (left_nritems == 0) {
1128a429e513SChris Mason 		btrfs_block_release(root, right_buf);
1129a429e513SChris Mason 		return 1;
1130a429e513SChris Mason 	}
1131a429e513SChris Mason 	for (i = left_nritems - 1; i >= 1; i--) {
113200ec4c51SChris Mason 		item = left->items + i;
113300ec4c51SChris Mason 		if (path->slots[0] == i)
113400ec4c51SChris Mason 			push_space += data_size + sizeof(*item);
11350783fcfcSChris Mason 		if (btrfs_item_size(item) + sizeof(*item) + push_space >
11360783fcfcSChris Mason 		    free_space)
113700ec4c51SChris Mason 			break;
113800ec4c51SChris Mason 		push_items++;
11390783fcfcSChris Mason 		push_space += btrfs_item_size(item) + sizeof(*item);
114000ec4c51SChris Mason 	}
114100ec4c51SChris Mason 	if (push_items == 0) {
1142234b63a0SChris Mason 		btrfs_block_release(root, right_buf);
114300ec4c51SChris Mason 		return 1;
114400ec4c51SChris Mason 	}
1145a429e513SChris Mason 	if (push_items == left_nritems)
1146a429e513SChris Mason 		WARN_ON(1);
11477518a238SChris Mason 	right_nritems = btrfs_header_nritems(&right->header);
114800ec4c51SChris Mason 	/* push left to right */
11490783fcfcSChris Mason 	push_space = btrfs_item_end(left->items + left_nritems - push_items);
1150123abc88SChris Mason 	push_space -= leaf_data_end(root, left);
115100ec4c51SChris Mason 	/* make room in the right data area */
1152d6025579SChris Mason 	btrfs_memmove(root, right, btrfs_leaf_data(right) +
1153d6025579SChris Mason 		      leaf_data_end(root, right) - push_space,
1154d6025579SChris Mason 		      btrfs_leaf_data(right) +
1155d6025579SChris Mason 		      leaf_data_end(root, right), BTRFS_LEAF_DATA_SIZE(root) -
1156d6025579SChris Mason 		      leaf_data_end(root, right));
115700ec4c51SChris Mason 	/* copy from the left data area */
1158d6025579SChris Mason 	btrfs_memcpy(root, right, btrfs_leaf_data(right) +
1159d6025579SChris Mason 		     BTRFS_LEAF_DATA_SIZE(root) - push_space,
1160d6025579SChris Mason 		     btrfs_leaf_data(left) + leaf_data_end(root, left),
1161d6025579SChris Mason 		     push_space);
1162d6025579SChris Mason 	btrfs_memmove(root, right, right->items + push_items, right->items,
11630783fcfcSChris Mason 		right_nritems * sizeof(struct btrfs_item));
116400ec4c51SChris Mason 	/* copy the items from left to right */
1165d6025579SChris Mason 	btrfs_memcpy(root, right, right->items, left->items +
1166d6025579SChris Mason 		     left_nritems - push_items,
11670783fcfcSChris Mason 		     push_items * sizeof(struct btrfs_item));
116800ec4c51SChris Mason 
116900ec4c51SChris Mason 	/* update the item pointers */
11707518a238SChris Mason 	right_nritems += push_items;
11717518a238SChris Mason 	btrfs_set_header_nritems(&right->header, right_nritems);
1172123abc88SChris Mason 	push_space = BTRFS_LEAF_DATA_SIZE(root);
11737518a238SChris Mason 	for (i = 0; i < right_nritems; i++) {
11740783fcfcSChris Mason 		btrfs_set_item_offset(right->items + i, push_space -
11750783fcfcSChris Mason 				      btrfs_item_size(right->items + i));
11760783fcfcSChris Mason 		push_space = btrfs_item_offset(right->items + i);
117700ec4c51SChris Mason 	}
11787518a238SChris Mason 	left_nritems -= push_items;
11797518a238SChris Mason 	btrfs_set_header_nritems(&left->header, left_nritems);
118000ec4c51SChris Mason 
1181d6025579SChris Mason 	btrfs_mark_buffer_dirty(left_buf);
1182d6025579SChris Mason 	btrfs_mark_buffer_dirty(right_buf);
1183a429e513SChris Mason 
1184d6025579SChris Mason 	btrfs_memcpy(root, upper_node, &upper_node->ptrs[slot + 1].key,
1185e2fa7227SChris Mason 		&right->items[0].key, sizeof(struct btrfs_disk_key));
1186d6025579SChris Mason 	btrfs_mark_buffer_dirty(upper);
118702217ed2SChris Mason 
118800ec4c51SChris Mason 	/* then fixup the leaf pointer in the path */
11897518a238SChris Mason 	if (path->slots[0] >= left_nritems) {
11907518a238SChris Mason 		path->slots[0] -= left_nritems;
1191234b63a0SChris Mason 		btrfs_block_release(root, path->nodes[0]);
119200ec4c51SChris Mason 		path->nodes[0] = right_buf;
119300ec4c51SChris Mason 		path->slots[1] += 1;
119400ec4c51SChris Mason 	} else {
1195234b63a0SChris Mason 		btrfs_block_release(root, right_buf);
119600ec4c51SChris Mason 	}
1197098f59c2SChris Mason 	if (path->nodes[1])
1198098f59c2SChris Mason 		check_node(root, path, 1);
119900ec4c51SChris Mason 	return 0;
120000ec4c51SChris Mason }
120100ec4c51SChris Mason /*
120274123bd7SChris Mason  * push some data in the path leaf to the left, trying to free up at
120374123bd7SChris Mason  * least data_size bytes.  returns zero if the push worked, nonzero otherwise
120474123bd7SChris Mason  */
1205e089f05cSChris Mason static int push_leaf_left(struct btrfs_trans_handle *trans, struct btrfs_root
1206e089f05cSChris Mason 			  *root, struct btrfs_path *path, int data_size)
1207be0e5c09SChris Mason {
1208e20d96d6SChris Mason 	struct buffer_head *right_buf = path->nodes[0];
1209e20d96d6SChris Mason 	struct btrfs_leaf *right = btrfs_buffer_leaf(right_buf);
1210e20d96d6SChris Mason 	struct buffer_head *t;
1211234b63a0SChris Mason 	struct btrfs_leaf *left;
1212be0e5c09SChris Mason 	int slot;
1213be0e5c09SChris Mason 	int i;
1214be0e5c09SChris Mason 	int free_space;
1215be0e5c09SChris Mason 	int push_space = 0;
1216be0e5c09SChris Mason 	int push_items = 0;
12170783fcfcSChris Mason 	struct btrfs_item *item;
12187518a238SChris Mason 	u32 old_left_nritems;
1219aa5d6bedSChris Mason 	int ret = 0;
1220aa5d6bedSChris Mason 	int wret;
1221be0e5c09SChris Mason 
1222be0e5c09SChris Mason 	slot = path->slots[1];
1223be0e5c09SChris Mason 	if (slot == 0) {
1224be0e5c09SChris Mason 		return 1;
1225be0e5c09SChris Mason 	}
1226be0e5c09SChris Mason 	if (!path->nodes[1]) {
1227be0e5c09SChris Mason 		return 1;
1228be0e5c09SChris Mason 	}
1229e20d96d6SChris Mason 	t = read_tree_block(root,
1230e20d96d6SChris Mason 	    btrfs_node_blockptr(btrfs_buffer_node(path->nodes[1]), slot - 1));
1231e20d96d6SChris Mason 	left = btrfs_buffer_leaf(t);
1232123abc88SChris Mason 	free_space = btrfs_leaf_free_space(root, left);
12330783fcfcSChris Mason 	if (free_space < data_size + sizeof(struct btrfs_item)) {
1234234b63a0SChris Mason 		btrfs_block_release(root, t);
1235be0e5c09SChris Mason 		return 1;
1236be0e5c09SChris Mason 	}
123702217ed2SChris Mason 
123802217ed2SChris Mason 	/* cow and double check */
123954aa1f4dSChris Mason 	ret = btrfs_cow_block(trans, root, t, path->nodes[1], slot - 1, &t);
124054aa1f4dSChris Mason 	if (ret) {
124154aa1f4dSChris Mason 		/* we hit -ENOSPC, but it isn't fatal here */
124254aa1f4dSChris Mason 		return 1;
124354aa1f4dSChris Mason 	}
1244e20d96d6SChris Mason 	left = btrfs_buffer_leaf(t);
1245123abc88SChris Mason 	free_space = btrfs_leaf_free_space(root, left);
12460783fcfcSChris Mason 	if (free_space < data_size + sizeof(struct btrfs_item)) {
1247234b63a0SChris Mason 		btrfs_block_release(root, t);
124802217ed2SChris Mason 		return 1;
124902217ed2SChris Mason 	}
125002217ed2SChris Mason 
1251a429e513SChris Mason 	if (btrfs_header_nritems(&right->header) == 0) {
1252a429e513SChris Mason 		btrfs_block_release(root, t);
1253a429e513SChris Mason 		return 1;
1254a429e513SChris Mason 	}
1255a429e513SChris Mason 
1256a429e513SChris Mason 	for (i = 0; i < btrfs_header_nritems(&right->header) - 1; i++) {
1257be0e5c09SChris Mason 		item = right->items + i;
1258be0e5c09SChris Mason 		if (path->slots[0] == i)
1259be0e5c09SChris Mason 			push_space += data_size + sizeof(*item);
12600783fcfcSChris Mason 		if (btrfs_item_size(item) + sizeof(*item) + push_space >
12610783fcfcSChris Mason 		    free_space)
1262be0e5c09SChris Mason 			break;
1263be0e5c09SChris Mason 		push_items++;
12640783fcfcSChris Mason 		push_space += btrfs_item_size(item) + sizeof(*item);
1265be0e5c09SChris Mason 	}
1266be0e5c09SChris Mason 	if (push_items == 0) {
1267234b63a0SChris Mason 		btrfs_block_release(root, t);
1268be0e5c09SChris Mason 		return 1;
1269be0e5c09SChris Mason 	}
1270a429e513SChris Mason 	if (push_items == btrfs_header_nritems(&right->header))
1271a429e513SChris Mason 		WARN_ON(1);
1272be0e5c09SChris Mason 	/* push data from right to left */
1273d6025579SChris Mason 	btrfs_memcpy(root, left, left->items +
1274d6025579SChris Mason 		     btrfs_header_nritems(&left->header),
12750783fcfcSChris Mason 		     right->items, push_items * sizeof(struct btrfs_item));
1276123abc88SChris Mason 	push_space = BTRFS_LEAF_DATA_SIZE(root) -
12770783fcfcSChris Mason 		     btrfs_item_offset(right->items + push_items -1);
1278d6025579SChris Mason 	btrfs_memcpy(root, left, btrfs_leaf_data(left) +
1279d6025579SChris Mason 		     leaf_data_end(root, left) - push_space,
1280123abc88SChris Mason 		     btrfs_leaf_data(right) +
1281123abc88SChris Mason 		     btrfs_item_offset(right->items + push_items - 1),
1282be0e5c09SChris Mason 		     push_space);
12837518a238SChris Mason 	old_left_nritems = btrfs_header_nritems(&left->header);
1284eb60ceacSChris Mason 	BUG_ON(old_left_nritems < 0);
1285eb60ceacSChris Mason 
1286be0e5c09SChris Mason 	for (i = old_left_nritems; i < old_left_nritems + push_items; i++) {
1287123abc88SChris Mason 		u32 ioff = btrfs_item_offset(left->items + i);
1288123abc88SChris Mason 		btrfs_set_item_offset(left->items + i, ioff -
1289123abc88SChris Mason 				     (BTRFS_LEAF_DATA_SIZE(root) -
12900783fcfcSChris Mason 				      btrfs_item_offset(left->items +
12910783fcfcSChris Mason 						        old_left_nritems - 1)));
1292be0e5c09SChris Mason 	}
12937518a238SChris Mason 	btrfs_set_header_nritems(&left->header, old_left_nritems + push_items);
1294be0e5c09SChris Mason 
1295be0e5c09SChris Mason 	/* fixup right node */
12960783fcfcSChris Mason 	push_space = btrfs_item_offset(right->items + push_items - 1) -
1297123abc88SChris Mason 		     leaf_data_end(root, right);
1298d6025579SChris Mason 	btrfs_memmove(root, right, btrfs_leaf_data(right) +
1299d6025579SChris Mason 		      BTRFS_LEAF_DATA_SIZE(root) - push_space,
1300d6025579SChris Mason 		      btrfs_leaf_data(right) +
1301123abc88SChris Mason 		      leaf_data_end(root, right), push_space);
1302d6025579SChris Mason 	btrfs_memmove(root, right, right->items, right->items + push_items,
13037518a238SChris Mason 		(btrfs_header_nritems(&right->header) - push_items) *
13040783fcfcSChris Mason 		sizeof(struct btrfs_item));
13057518a238SChris Mason 	btrfs_set_header_nritems(&right->header,
13067518a238SChris Mason 				 btrfs_header_nritems(&right->header) -
13077518a238SChris Mason 				 push_items);
1308123abc88SChris Mason 	push_space = BTRFS_LEAF_DATA_SIZE(root);
1309eb60ceacSChris Mason 
13107518a238SChris Mason 	for (i = 0; i < btrfs_header_nritems(&right->header); i++) {
13110783fcfcSChris Mason 		btrfs_set_item_offset(right->items + i, push_space -
13120783fcfcSChris Mason 				      btrfs_item_size(right->items + i));
13130783fcfcSChris Mason 		push_space = btrfs_item_offset(right->items + i);
1314be0e5c09SChris Mason 	}
1315eb60ceacSChris Mason 
1316d6025579SChris Mason 	btrfs_mark_buffer_dirty(t);
1317d6025579SChris Mason 	btrfs_mark_buffer_dirty(right_buf);
1318098f59c2SChris Mason 
1319e089f05cSChris Mason 	wret = fixup_low_keys(trans, root, path, &right->items[0].key, 1);
1320aa5d6bedSChris Mason 	if (wret)
1321aa5d6bedSChris Mason 		ret = wret;
1322be0e5c09SChris Mason 
1323be0e5c09SChris Mason 	/* then fixup the leaf pointer in the path */
1324be0e5c09SChris Mason 	if (path->slots[0] < push_items) {
1325be0e5c09SChris Mason 		path->slots[0] += old_left_nritems;
1326234b63a0SChris Mason 		btrfs_block_release(root, path->nodes[0]);
1327eb60ceacSChris Mason 		path->nodes[0] = t;
1328be0e5c09SChris Mason 		path->slots[1] -= 1;
1329be0e5c09SChris Mason 	} else {
1330234b63a0SChris Mason 		btrfs_block_release(root, t);
1331be0e5c09SChris Mason 		path->slots[0] -= push_items;
1332be0e5c09SChris Mason 	}
1333eb60ceacSChris Mason 	BUG_ON(path->slots[0] < 0);
1334098f59c2SChris Mason 	if (path->nodes[1])
1335098f59c2SChris Mason 		check_node(root, path, 1);
1336aa5d6bedSChris Mason 	return ret;
1337be0e5c09SChris Mason }
1338be0e5c09SChris Mason 
133974123bd7SChris Mason /*
134074123bd7SChris Mason  * split the path's leaf in two, making sure there is at least data_size
134174123bd7SChris Mason  * available for the resulting leaf level of the path.
1342aa5d6bedSChris Mason  *
1343aa5d6bedSChris Mason  * returns 0 if all went well and < 0 on failure.
134474123bd7SChris Mason  */
1345e089f05cSChris Mason static int split_leaf(struct btrfs_trans_handle *trans, struct btrfs_root
1346d4dbff95SChris Mason 		      *root, struct btrfs_key *ins_key,
1347d4dbff95SChris Mason 		      struct btrfs_path *path, int data_size)
1348be0e5c09SChris Mason {
1349e20d96d6SChris Mason 	struct buffer_head *l_buf;
1350234b63a0SChris Mason 	struct btrfs_leaf *l;
13517518a238SChris Mason 	u32 nritems;
1352eb60ceacSChris Mason 	int mid;
1353eb60ceacSChris Mason 	int slot;
1354234b63a0SChris Mason 	struct btrfs_leaf *right;
1355e20d96d6SChris Mason 	struct buffer_head *right_buffer;
13560783fcfcSChris Mason 	int space_needed = data_size + sizeof(struct btrfs_item);
1357be0e5c09SChris Mason 	int data_copy_size;
1358be0e5c09SChris Mason 	int rt_data_off;
1359be0e5c09SChris Mason 	int i;
1360d4dbff95SChris Mason 	int ret = 0;
1361aa5d6bedSChris Mason 	int wret;
1362d4dbff95SChris Mason 	int double_split = 0;
1363d4dbff95SChris Mason 	struct btrfs_disk_key disk_key;
1364be0e5c09SChris Mason 
136540689478SChris Mason 	/* first try to make some room by pushing left and right */
1366e089f05cSChris Mason 	wret = push_leaf_left(trans, root, path, data_size);
1367eaee50e8SChris Mason 	if (wret < 0)
1368eaee50e8SChris Mason 		return wret;
1369eaee50e8SChris Mason 	if (wret) {
1370e089f05cSChris Mason 		wret = push_leaf_right(trans, root, path, data_size);
1371eaee50e8SChris Mason 		if (wret < 0)
1372eaee50e8SChris Mason 			return wret;
1373eaee50e8SChris Mason 	}
1374eb60ceacSChris Mason 	l_buf = path->nodes[0];
1375e20d96d6SChris Mason 	l = btrfs_buffer_leaf(l_buf);
1376aa5d6bedSChris Mason 
1377aa5d6bedSChris Mason 	/* did the pushes work? */
1378123abc88SChris Mason 	if (btrfs_leaf_free_space(root, l) >=
1379123abc88SChris Mason 	    sizeof(struct btrfs_item) + data_size)
1380be0e5c09SChris Mason 		return 0;
1381aa5d6bedSChris Mason 
13825c680ed6SChris Mason 	if (!path->nodes[1]) {
1383e089f05cSChris Mason 		ret = insert_new_root(trans, root, path, 1);
13845c680ed6SChris Mason 		if (ret)
13855c680ed6SChris Mason 			return ret;
13865c680ed6SChris Mason 	}
1387eb60ceacSChris Mason 	slot = path->slots[0];
13887518a238SChris Mason 	nritems = btrfs_header_nritems(&l->header);
1389eb60ceacSChris Mason 	mid = (nritems + 1)/ 2;
139054aa1f4dSChris Mason 
139131f3c99bSChris Mason 	right_buffer = btrfs_alloc_free_block(trans, root, l_buf->b_blocknr);
139254aa1f4dSChris Mason 	if (IS_ERR(right_buffer))
139354aa1f4dSChris Mason 		return PTR_ERR(right_buffer);
139454aa1f4dSChris Mason 
1395e20d96d6SChris Mason 	right = btrfs_buffer_leaf(right_buffer);
1396123abc88SChris Mason 	memset(&right->header, 0, sizeof(right->header));
13977eccb903SChris Mason 	btrfs_set_header_blocknr(&right->header, bh_blocknr(right_buffer));
13987f5c1516SChris Mason 	btrfs_set_header_generation(&right->header, trans->transid);
13994d775673SChris Mason 	btrfs_set_header_owner(&right->header, root->root_key.objectid);
14007518a238SChris Mason 	btrfs_set_header_level(&right->header, 0);
14013eb0314dSChris Mason 	memcpy(right->header.fsid, root->fs_info->disk_super->fsid,
14023eb0314dSChris Mason 	       sizeof(right->header.fsid));
1403d4dbff95SChris Mason 	if (mid <= slot) {
1404d4dbff95SChris Mason 		if (nritems == 1 ||
1405d4dbff95SChris Mason 		    leaf_space_used(l, mid, nritems - mid) + space_needed >
1406d4dbff95SChris Mason 			BTRFS_LEAF_DATA_SIZE(root)) {
1407d4dbff95SChris Mason 			if (slot >= nritems) {
1408d4dbff95SChris Mason 				btrfs_cpu_key_to_disk(&disk_key, ins_key);
1409d4dbff95SChris Mason 				btrfs_set_header_nritems(&right->header, 0);
1410d4dbff95SChris Mason 				wret = insert_ptr(trans, root, path,
1411d4dbff95SChris Mason 						  &disk_key,
14127eccb903SChris Mason 						  bh_blocknr(right_buffer),
1413d4dbff95SChris Mason 						  path->slots[1] + 1, 1);
1414d4dbff95SChris Mason 				if (wret)
1415d4dbff95SChris Mason 					ret = wret;
1416d4dbff95SChris Mason 				btrfs_block_release(root, path->nodes[0]);
1417d4dbff95SChris Mason 				path->nodes[0] = right_buffer;
1418d4dbff95SChris Mason 				path->slots[0] = 0;
1419d4dbff95SChris Mason 				path->slots[1] += 1;
1420d4dbff95SChris Mason 				return ret;
1421d4dbff95SChris Mason 			}
1422d4dbff95SChris Mason 			mid = slot;
1423d4dbff95SChris Mason 			double_split = 1;
1424d4dbff95SChris Mason 		}
1425d4dbff95SChris Mason 	} else {
1426d4dbff95SChris Mason 		if (leaf_space_used(l, 0, mid + 1) + space_needed >
1427d4dbff95SChris Mason 			BTRFS_LEAF_DATA_SIZE(root)) {
1428d4dbff95SChris Mason 			if (slot == 0) {
1429d4dbff95SChris Mason 				btrfs_cpu_key_to_disk(&disk_key, ins_key);
1430d4dbff95SChris Mason 				btrfs_set_header_nritems(&right->header, 0);
1431d4dbff95SChris Mason 				wret = insert_ptr(trans, root, path,
1432d4dbff95SChris Mason 						  &disk_key,
14337eccb903SChris Mason 						  bh_blocknr(right_buffer),
1434098f59c2SChris Mason 						  path->slots[1], 1);
1435d4dbff95SChris Mason 				if (wret)
1436d4dbff95SChris Mason 					ret = wret;
1437d4dbff95SChris Mason 				btrfs_block_release(root, path->nodes[0]);
1438d4dbff95SChris Mason 				path->nodes[0] = right_buffer;
1439d4dbff95SChris Mason 				path->slots[0] = 0;
1440a429e513SChris Mason 				if (path->slots[1] == 0) {
1441a429e513SChris Mason 					wret = fixup_low_keys(trans, root,
1442a429e513SChris Mason 					           path, &disk_key, 1);
1443a429e513SChris Mason 					if (wret)
1444a429e513SChris Mason 						ret = wret;
1445a429e513SChris Mason 				}
1446d4dbff95SChris Mason 				return ret;
1447d4dbff95SChris Mason 			}
1448d4dbff95SChris Mason 			mid = slot;
1449d4dbff95SChris Mason 			double_split = 1;
1450d4dbff95SChris Mason 		}
1451d4dbff95SChris Mason 	}
1452d4dbff95SChris Mason 	btrfs_set_header_nritems(&right->header, nritems - mid);
1453123abc88SChris Mason 	data_copy_size = btrfs_item_end(l->items + mid) -
1454123abc88SChris Mason 			 leaf_data_end(root, l);
1455d6025579SChris Mason 	btrfs_memcpy(root, right, right->items, l->items + mid,
14560783fcfcSChris Mason 		     (nritems - mid) * sizeof(struct btrfs_item));
1457d6025579SChris Mason 	btrfs_memcpy(root, right,
1458d6025579SChris Mason 		     btrfs_leaf_data(right) + BTRFS_LEAF_DATA_SIZE(root) -
1459123abc88SChris Mason 		     data_copy_size, btrfs_leaf_data(l) +
1460123abc88SChris Mason 		     leaf_data_end(root, l), data_copy_size);
1461123abc88SChris Mason 	rt_data_off = BTRFS_LEAF_DATA_SIZE(root) -
1462123abc88SChris Mason 		      btrfs_item_end(l->items + mid);
146374123bd7SChris Mason 
14640783fcfcSChris Mason 	for (i = 0; i < btrfs_header_nritems(&right->header); i++) {
1465123abc88SChris Mason 		u32 ioff = btrfs_item_offset(right->items + i);
14660783fcfcSChris Mason 		btrfs_set_item_offset(right->items + i, ioff + rt_data_off);
14670783fcfcSChris Mason 	}
146874123bd7SChris Mason 
14697518a238SChris Mason 	btrfs_set_header_nritems(&l->header, mid);
1470aa5d6bedSChris Mason 	ret = 0;
1471e089f05cSChris Mason 	wret = insert_ptr(trans, root, path, &right->items[0].key,
14727eccb903SChris Mason 			  bh_blocknr(right_buffer), path->slots[1] + 1, 1);
1473aa5d6bedSChris Mason 	if (wret)
1474aa5d6bedSChris Mason 		ret = wret;
1475d6025579SChris Mason 	btrfs_mark_buffer_dirty(right_buffer);
1476d6025579SChris Mason 	btrfs_mark_buffer_dirty(l_buf);
1477eb60ceacSChris Mason 	BUG_ON(path->slots[0] != slot);
1478be0e5c09SChris Mason 	if (mid <= slot) {
1479234b63a0SChris Mason 		btrfs_block_release(root, path->nodes[0]);
1480eb60ceacSChris Mason 		path->nodes[0] = right_buffer;
1481be0e5c09SChris Mason 		path->slots[0] -= mid;
1482be0e5c09SChris Mason 		path->slots[1] += 1;
1483eb60ceacSChris Mason 	} else
1484234b63a0SChris Mason 		btrfs_block_release(root, right_buffer);
1485eb60ceacSChris Mason 	BUG_ON(path->slots[0] < 0);
1486098f59c2SChris Mason 	check_node(root, path, 1);
1487d4dbff95SChris Mason 
1488d4dbff95SChris Mason 	if (!double_split)
1489d4dbff95SChris Mason 		return ret;
149031f3c99bSChris Mason 	right_buffer = btrfs_alloc_free_block(trans, root, l_buf->b_blocknr);
149154aa1f4dSChris Mason 	if (IS_ERR(right_buffer))
149254aa1f4dSChris Mason 		return PTR_ERR(right_buffer);
149354aa1f4dSChris Mason 
1494d4dbff95SChris Mason 	right = btrfs_buffer_leaf(right_buffer);
1495d4dbff95SChris Mason 	memset(&right->header, 0, sizeof(right->header));
14967eccb903SChris Mason 	btrfs_set_header_blocknr(&right->header, bh_blocknr(right_buffer));
1497d4dbff95SChris Mason 	btrfs_set_header_generation(&right->header, trans->transid);
14984d775673SChris Mason 	btrfs_set_header_owner(&right->header, root->root_key.objectid);
1499d4dbff95SChris Mason 	btrfs_set_header_level(&right->header, 0);
15003eb0314dSChris Mason 	memcpy(right->header.fsid, root->fs_info->disk_super->fsid,
15013eb0314dSChris Mason 	       sizeof(right->header.fsid));
1502d4dbff95SChris Mason 	btrfs_cpu_key_to_disk(&disk_key, ins_key);
1503d4dbff95SChris Mason 	btrfs_set_header_nritems(&right->header, 0);
1504d4dbff95SChris Mason 	wret = insert_ptr(trans, root, path,
1505d4dbff95SChris Mason 			  &disk_key,
15067eccb903SChris Mason 			  bh_blocknr(right_buffer),
1507d4dbff95SChris Mason 			  path->slots[1], 1);
1508d4dbff95SChris Mason 	if (wret)
1509d4dbff95SChris Mason 		ret = wret;
1510a429e513SChris Mason 	if (path->slots[1] == 0) {
1511a429e513SChris Mason 		wret = fixup_low_keys(trans, root, path, &disk_key, 1);
1512a429e513SChris Mason 		if (wret)
1513a429e513SChris Mason 			ret = wret;
1514a429e513SChris Mason 	}
1515d4dbff95SChris Mason 	btrfs_block_release(root, path->nodes[0]);
1516d4dbff95SChris Mason 	path->nodes[0] = right_buffer;
1517d4dbff95SChris Mason 	path->slots[0] = 0;
1518d4dbff95SChris Mason 	check_node(root, path, 1);
1519d4dbff95SChris Mason 	check_leaf(root, path, 0);
1520be0e5c09SChris Mason 	return ret;
1521be0e5c09SChris Mason }
1522be0e5c09SChris Mason 
1523b18c6685SChris Mason int btrfs_truncate_item(struct btrfs_trans_handle *trans,
1524b18c6685SChris Mason 			struct btrfs_root *root,
1525b18c6685SChris Mason 			struct btrfs_path *path,
1526b18c6685SChris Mason 			u32 new_size)
1527b18c6685SChris Mason {
1528b18c6685SChris Mason 	int ret = 0;
1529b18c6685SChris Mason 	int slot;
1530b18c6685SChris Mason 	int slot_orig;
1531b18c6685SChris Mason 	struct btrfs_leaf *leaf;
1532b18c6685SChris Mason 	struct buffer_head *leaf_buf;
1533b18c6685SChris Mason 	u32 nritems;
1534b18c6685SChris Mason 	unsigned int data_end;
1535b18c6685SChris Mason 	unsigned int old_data_start;
1536b18c6685SChris Mason 	unsigned int old_size;
1537b18c6685SChris Mason 	unsigned int size_diff;
1538b18c6685SChris Mason 	int i;
1539b18c6685SChris Mason 
1540b18c6685SChris Mason 	slot_orig = path->slots[0];
1541b18c6685SChris Mason 	leaf_buf = path->nodes[0];
1542b18c6685SChris Mason 	leaf = btrfs_buffer_leaf(leaf_buf);
1543b18c6685SChris Mason 
1544b18c6685SChris Mason 	nritems = btrfs_header_nritems(&leaf->header);
1545b18c6685SChris Mason 	data_end = leaf_data_end(root, leaf);
1546b18c6685SChris Mason 
1547b18c6685SChris Mason 	slot = path->slots[0];
1548b18c6685SChris Mason 	old_data_start = btrfs_item_offset(leaf->items + slot);
1549b18c6685SChris Mason 	old_size = btrfs_item_size(leaf->items + slot);
1550b18c6685SChris Mason 	BUG_ON(old_size <= new_size);
1551b18c6685SChris Mason 	size_diff = old_size - new_size;
1552b18c6685SChris Mason 
1553b18c6685SChris Mason 	BUG_ON(slot < 0);
1554b18c6685SChris Mason 	BUG_ON(slot >= nritems);
1555b18c6685SChris Mason 
1556b18c6685SChris Mason 	/*
1557b18c6685SChris Mason 	 * item0..itemN ... dataN.offset..dataN.size .. data0.size
1558b18c6685SChris Mason 	 */
1559b18c6685SChris Mason 	/* first correct the data pointers */
1560b18c6685SChris Mason 	for (i = slot; i < nritems; i++) {
1561b18c6685SChris Mason 		u32 ioff = btrfs_item_offset(leaf->items + i);
1562b18c6685SChris Mason 		btrfs_set_item_offset(leaf->items + i,
1563b18c6685SChris Mason 				      ioff + size_diff);
1564b18c6685SChris Mason 	}
1565b18c6685SChris Mason 	/* shift the data */
1566b18c6685SChris Mason 	btrfs_memmove(root, leaf, btrfs_leaf_data(leaf) +
1567b18c6685SChris Mason 		      data_end + size_diff, btrfs_leaf_data(leaf) +
1568b18c6685SChris Mason 		      data_end, old_data_start + new_size - data_end);
1569b18c6685SChris Mason 	btrfs_set_item_size(leaf->items + slot, new_size);
1570b18c6685SChris Mason 	btrfs_mark_buffer_dirty(leaf_buf);
1571b18c6685SChris Mason 
1572b18c6685SChris Mason 	ret = 0;
1573b18c6685SChris Mason 	if (btrfs_leaf_free_space(root, leaf) < 0)
1574b18c6685SChris Mason 		BUG();
1575b18c6685SChris Mason 	check_leaf(root, path, 0);
1576b18c6685SChris Mason 	return ret;
1577b18c6685SChris Mason }
1578b18c6685SChris Mason 
15796567e837SChris Mason int btrfs_extend_item(struct btrfs_trans_handle *trans, struct btrfs_root
15806567e837SChris Mason 		      *root, struct btrfs_path *path, u32 data_size)
15816567e837SChris Mason {
15826567e837SChris Mason 	int ret = 0;
15836567e837SChris Mason 	int slot;
15846567e837SChris Mason 	int slot_orig;
15856567e837SChris Mason 	struct btrfs_leaf *leaf;
15866567e837SChris Mason 	struct buffer_head *leaf_buf;
15876567e837SChris Mason 	u32 nritems;
15886567e837SChris Mason 	unsigned int data_end;
15896567e837SChris Mason 	unsigned int old_data;
15906567e837SChris Mason 	unsigned int old_size;
15916567e837SChris Mason 	int i;
15926567e837SChris Mason 
15936567e837SChris Mason 	slot_orig = path->slots[0];
15946567e837SChris Mason 	leaf_buf = path->nodes[0];
15956567e837SChris Mason 	leaf = btrfs_buffer_leaf(leaf_buf);
15966567e837SChris Mason 
15976567e837SChris Mason 	nritems = btrfs_header_nritems(&leaf->header);
15986567e837SChris Mason 	data_end = leaf_data_end(root, leaf);
15996567e837SChris Mason 
16006567e837SChris Mason 	if (btrfs_leaf_free_space(root, leaf) < data_size)
16016567e837SChris Mason 		BUG();
16026567e837SChris Mason 	slot = path->slots[0];
16036567e837SChris Mason 	old_data = btrfs_item_end(leaf->items + slot);
16046567e837SChris Mason 
16056567e837SChris Mason 	BUG_ON(slot < 0);
16066567e837SChris Mason 	BUG_ON(slot >= nritems);
16076567e837SChris Mason 
16086567e837SChris Mason 	/*
16096567e837SChris Mason 	 * item0..itemN ... dataN.offset..dataN.size .. data0.size
16106567e837SChris Mason 	 */
16116567e837SChris Mason 	/* first correct the data pointers */
16126567e837SChris Mason 	for (i = slot; i < nritems; i++) {
16136567e837SChris Mason 		u32 ioff = btrfs_item_offset(leaf->items + i);
16146567e837SChris Mason 		btrfs_set_item_offset(leaf->items + i,
16156567e837SChris Mason 				      ioff - data_size);
16166567e837SChris Mason 	}
16176567e837SChris Mason 	/* shift the data */
16186567e837SChris Mason 	btrfs_memmove(root, leaf, btrfs_leaf_data(leaf) +
16196567e837SChris Mason 		      data_end - data_size, btrfs_leaf_data(leaf) +
16206567e837SChris Mason 		      data_end, old_data - data_end);
16216567e837SChris Mason 	data_end = old_data;
16226567e837SChris Mason 	old_size = btrfs_item_size(leaf->items + slot);
16236567e837SChris Mason 	btrfs_set_item_size(leaf->items + slot, old_size + data_size);
16246567e837SChris Mason 	btrfs_mark_buffer_dirty(leaf_buf);
16256567e837SChris Mason 
16266567e837SChris Mason 	ret = 0;
16276567e837SChris Mason 	if (btrfs_leaf_free_space(root, leaf) < 0)
16286567e837SChris Mason 		BUG();
16296567e837SChris Mason 	check_leaf(root, path, 0);
16306567e837SChris Mason 	return ret;
16316567e837SChris Mason }
16326567e837SChris Mason 
163374123bd7SChris Mason /*
163474123bd7SChris Mason  * Given a key and some data, insert an item into the tree.
163574123bd7SChris Mason  * This does all the path init required, making room in the tree if needed.
163674123bd7SChris Mason  */
1637e089f05cSChris Mason int btrfs_insert_empty_item(struct btrfs_trans_handle *trans, struct btrfs_root
1638e089f05cSChris Mason 			    *root, struct btrfs_path *path, struct btrfs_key
1639e089f05cSChris Mason 			    *cpu_key, u32 data_size)
1640be0e5c09SChris Mason {
1641aa5d6bedSChris Mason 	int ret = 0;
1642be0e5c09SChris Mason 	int slot;
1643eb60ceacSChris Mason 	int slot_orig;
1644234b63a0SChris Mason 	struct btrfs_leaf *leaf;
1645e20d96d6SChris Mason 	struct buffer_head *leaf_buf;
16467518a238SChris Mason 	u32 nritems;
1647be0e5c09SChris Mason 	unsigned int data_end;
1648e2fa7227SChris Mason 	struct btrfs_disk_key disk_key;
1649e2fa7227SChris Mason 
1650e2fa7227SChris Mason 	btrfs_cpu_key_to_disk(&disk_key, cpu_key);
1651be0e5c09SChris Mason 
165274123bd7SChris Mason 	/* create a root if there isn't one */
16535c680ed6SChris Mason 	if (!root->node)
1654cfaa7295SChris Mason 		BUG();
1655e089f05cSChris Mason 	ret = btrfs_search_slot(trans, root, cpu_key, path, data_size, 1);
1656eb60ceacSChris Mason 	if (ret == 0) {
1657f0930a37SChris Mason 		return -EEXIST;
1658aa5d6bedSChris Mason 	}
1659ed2ff2cbSChris Mason 	if (ret < 0)
1660ed2ff2cbSChris Mason 		goto out;
1661be0e5c09SChris Mason 
166262e2749eSChris Mason 	slot_orig = path->slots[0];
166362e2749eSChris Mason 	leaf_buf = path->nodes[0];
1664e20d96d6SChris Mason 	leaf = btrfs_buffer_leaf(leaf_buf);
166574123bd7SChris Mason 
16667518a238SChris Mason 	nritems = btrfs_header_nritems(&leaf->header);
1667123abc88SChris Mason 	data_end = leaf_data_end(root, leaf);
1668eb60ceacSChris Mason 
1669123abc88SChris Mason 	if (btrfs_leaf_free_space(root, leaf) <
1670d4dbff95SChris Mason 	    sizeof(struct btrfs_item) + data_size) {
1671be0e5c09SChris Mason 		BUG();
1672d4dbff95SChris Mason 	}
167362e2749eSChris Mason 	slot = path->slots[0];
1674eb60ceacSChris Mason 	BUG_ON(slot < 0);
1675be0e5c09SChris Mason 	if (slot != nritems) {
1676be0e5c09SChris Mason 		int i;
16770783fcfcSChris Mason 		unsigned int old_data = btrfs_item_end(leaf->items + slot);
1678be0e5c09SChris Mason 
1679be0e5c09SChris Mason 		/*
1680be0e5c09SChris Mason 		 * item0..itemN ... dataN.offset..dataN.size .. data0.size
1681be0e5c09SChris Mason 		 */
1682be0e5c09SChris Mason 		/* first correct the data pointers */
16830783fcfcSChris Mason 		for (i = slot; i < nritems; i++) {
1684123abc88SChris Mason 			u32 ioff = btrfs_item_offset(leaf->items + i);
16850783fcfcSChris Mason 			btrfs_set_item_offset(leaf->items + i,
16860783fcfcSChris Mason 					      ioff - data_size);
16870783fcfcSChris Mason 		}
1688be0e5c09SChris Mason 
1689be0e5c09SChris Mason 		/* shift the items */
1690d6025579SChris Mason 		btrfs_memmove(root, leaf, leaf->items + slot + 1,
1691d6025579SChris Mason 			      leaf->items + slot,
16920783fcfcSChris Mason 			      (nritems - slot) * sizeof(struct btrfs_item));
1693be0e5c09SChris Mason 
1694be0e5c09SChris Mason 		/* shift the data */
1695d6025579SChris Mason 		btrfs_memmove(root, leaf, btrfs_leaf_data(leaf) +
1696d6025579SChris Mason 			      data_end - data_size, btrfs_leaf_data(leaf) +
1697be0e5c09SChris Mason 			      data_end, old_data - data_end);
1698be0e5c09SChris Mason 		data_end = old_data;
1699be0e5c09SChris Mason 	}
170062e2749eSChris Mason 	/* setup the item for the new data */
1701d6025579SChris Mason 	btrfs_memcpy(root, leaf, &leaf->items[slot].key, &disk_key,
1702e2fa7227SChris Mason 		     sizeof(struct btrfs_disk_key));
17030783fcfcSChris Mason 	btrfs_set_item_offset(leaf->items + slot, data_end - data_size);
17040783fcfcSChris Mason 	btrfs_set_item_size(leaf->items + slot, data_size);
17057518a238SChris Mason 	btrfs_set_header_nritems(&leaf->header, nritems + 1);
1706d6025579SChris Mason 	btrfs_mark_buffer_dirty(leaf_buf);
1707aa5d6bedSChris Mason 
1708aa5d6bedSChris Mason 	ret = 0;
17098e19f2cdSChris Mason 	if (slot == 0)
1710e089f05cSChris Mason 		ret = fixup_low_keys(trans, root, path, &disk_key, 1);
1711aa5d6bedSChris Mason 
1712123abc88SChris Mason 	if (btrfs_leaf_free_space(root, leaf) < 0)
1713be0e5c09SChris Mason 		BUG();
171462e2749eSChris Mason 	check_leaf(root, path, 0);
1715ed2ff2cbSChris Mason out:
171662e2749eSChris Mason 	return ret;
171762e2749eSChris Mason }
171862e2749eSChris Mason 
171962e2749eSChris Mason /*
172062e2749eSChris Mason  * Given a key and some data, insert an item into the tree.
172162e2749eSChris Mason  * This does all the path init required, making room in the tree if needed.
172262e2749eSChris Mason  */
1723e089f05cSChris Mason int btrfs_insert_item(struct btrfs_trans_handle *trans, struct btrfs_root
1724e089f05cSChris Mason 		      *root, struct btrfs_key *cpu_key, void *data, u32
1725e089f05cSChris Mason 		      data_size)
172662e2749eSChris Mason {
172762e2749eSChris Mason 	int ret = 0;
17282c90e5d6SChris Mason 	struct btrfs_path *path;
172962e2749eSChris Mason 	u8 *ptr;
173062e2749eSChris Mason 
17312c90e5d6SChris Mason 	path = btrfs_alloc_path();
17322c90e5d6SChris Mason 	BUG_ON(!path);
17332c90e5d6SChris Mason 	ret = btrfs_insert_empty_item(trans, root, path, cpu_key, data_size);
173462e2749eSChris Mason 	if (!ret) {
17352c90e5d6SChris Mason 		ptr = btrfs_item_ptr(btrfs_buffer_leaf(path->nodes[0]),
17362c90e5d6SChris Mason 				     path->slots[0], u8);
17372c90e5d6SChris Mason 		btrfs_memcpy(root, path->nodes[0]->b_data,
1738d6025579SChris Mason 			     ptr, data, data_size);
17392c90e5d6SChris Mason 		btrfs_mark_buffer_dirty(path->nodes[0]);
174062e2749eSChris Mason 	}
17412c90e5d6SChris Mason 	btrfs_free_path(path);
1742aa5d6bedSChris Mason 	return ret;
1743be0e5c09SChris Mason }
1744be0e5c09SChris Mason 
174574123bd7SChris Mason /*
17465de08d7dSChris Mason  * delete the pointer from a given node.
174774123bd7SChris Mason  *
174874123bd7SChris Mason  * If the delete empties a node, the node is removed from the tree,
174974123bd7SChris Mason  * continuing all the way the root if required.  The root is converted into
175074123bd7SChris Mason  * a leaf if all the nodes are emptied.
175174123bd7SChris Mason  */
1752e089f05cSChris Mason static int del_ptr(struct btrfs_trans_handle *trans, struct btrfs_root *root,
1753e089f05cSChris Mason 		   struct btrfs_path *path, int level, int slot)
1754be0e5c09SChris Mason {
1755234b63a0SChris Mason 	struct btrfs_node *node;
1756e20d96d6SChris Mason 	struct buffer_head *parent = path->nodes[level];
17577518a238SChris Mason 	u32 nritems;
1758aa5d6bedSChris Mason 	int ret = 0;
1759bb803951SChris Mason 	int wret;
1760be0e5c09SChris Mason 
1761e20d96d6SChris Mason 	node = btrfs_buffer_node(parent);
17627518a238SChris Mason 	nritems = btrfs_header_nritems(&node->header);
1763be0e5c09SChris Mason 	if (slot != nritems -1) {
1764d6025579SChris Mason 		btrfs_memmove(root, node, node->ptrs + slot,
1765d6025579SChris Mason 			      node->ptrs + slot + 1,
1766d6025579SChris Mason 			      sizeof(struct btrfs_key_ptr) *
1767d6025579SChris Mason 			      (nritems - slot - 1));
1768be0e5c09SChris Mason 	}
17697518a238SChris Mason 	nritems--;
17707518a238SChris Mason 	btrfs_set_header_nritems(&node->header, nritems);
17717518a238SChris Mason 	if (nritems == 0 && parent == root->node) {
1772e20d96d6SChris Mason 		struct btrfs_header *header = btrfs_buffer_header(root->node);
1773e20d96d6SChris Mason 		BUG_ON(btrfs_header_level(header) != 1);
1774eb60ceacSChris Mason 		/* just turn the root into a leaf and break */
1775e20d96d6SChris Mason 		btrfs_set_header_level(header, 0);
1776bb803951SChris Mason 	} else if (slot == 0) {
1777e089f05cSChris Mason 		wret = fixup_low_keys(trans, root, path, &node->ptrs[0].key,
1778123abc88SChris Mason 				      level + 1);
17790f70abe2SChris Mason 		if (wret)
17800f70abe2SChris Mason 			ret = wret;
1781be0e5c09SChris Mason 	}
1782d6025579SChris Mason 	btrfs_mark_buffer_dirty(parent);
1783aa5d6bedSChris Mason 	return ret;
1784be0e5c09SChris Mason }
1785be0e5c09SChris Mason 
178674123bd7SChris Mason /*
178774123bd7SChris Mason  * delete the item at the leaf level in path.  If that empties
178874123bd7SChris Mason  * the leaf, remove it from the tree
178974123bd7SChris Mason  */
1790e089f05cSChris Mason int btrfs_del_item(struct btrfs_trans_handle *trans, struct btrfs_root *root,
1791e089f05cSChris Mason 		   struct btrfs_path *path)
1792be0e5c09SChris Mason {
1793be0e5c09SChris Mason 	int slot;
1794234b63a0SChris Mason 	struct btrfs_leaf *leaf;
1795e20d96d6SChris Mason 	struct buffer_head *leaf_buf;
1796be0e5c09SChris Mason 	int doff;
1797be0e5c09SChris Mason 	int dsize;
1798aa5d6bedSChris Mason 	int ret = 0;
1799aa5d6bedSChris Mason 	int wret;
18007518a238SChris Mason 	u32 nritems;
1801be0e5c09SChris Mason 
1802eb60ceacSChris Mason 	leaf_buf = path->nodes[0];
1803e20d96d6SChris Mason 	leaf = btrfs_buffer_leaf(leaf_buf);
18044920c9acSChris Mason 	slot = path->slots[0];
18050783fcfcSChris Mason 	doff = btrfs_item_offset(leaf->items + slot);
18060783fcfcSChris Mason 	dsize = btrfs_item_size(leaf->items + slot);
18077518a238SChris Mason 	nritems = btrfs_header_nritems(&leaf->header);
1808be0e5c09SChris Mason 
18097518a238SChris Mason 	if (slot != nritems - 1) {
1810be0e5c09SChris Mason 		int i;
1811123abc88SChris Mason 		int data_end = leaf_data_end(root, leaf);
1812d6025579SChris Mason 		btrfs_memmove(root, leaf, btrfs_leaf_data(leaf) +
1813d6025579SChris Mason 			      data_end + dsize,
1814123abc88SChris Mason 			      btrfs_leaf_data(leaf) + data_end,
1815be0e5c09SChris Mason 			      doff - data_end);
18160783fcfcSChris Mason 		for (i = slot + 1; i < nritems; i++) {
1817123abc88SChris Mason 			u32 ioff = btrfs_item_offset(leaf->items + i);
18180783fcfcSChris Mason 			btrfs_set_item_offset(leaf->items + i, ioff + dsize);
18190783fcfcSChris Mason 		}
1820d6025579SChris Mason 		btrfs_memmove(root, leaf, leaf->items + slot,
1821d6025579SChris Mason 			      leaf->items + slot + 1,
18220783fcfcSChris Mason 			      sizeof(struct btrfs_item) *
18237518a238SChris Mason 			      (nritems - slot - 1));
1824be0e5c09SChris Mason 	}
18257518a238SChris Mason 	btrfs_set_header_nritems(&leaf->header, nritems - 1);
18267518a238SChris Mason 	nritems--;
182774123bd7SChris Mason 	/* delete the leaf if we've emptied it */
18287518a238SChris Mason 	if (nritems == 0) {
1829eb60ceacSChris Mason 		if (leaf_buf == root->node) {
18307518a238SChris Mason 			btrfs_set_header_level(&leaf->header, 0);
18319a8dd150SChris Mason 		} else {
1832e089f05cSChris Mason 			clean_tree_block(trans, root, leaf_buf);
1833d6025579SChris Mason 			wait_on_buffer(leaf_buf);
1834e089f05cSChris Mason 			wret = del_ptr(trans, root, path, 1, path->slots[1]);
1835aa5d6bedSChris Mason 			if (wret)
1836aa5d6bedSChris Mason 				ret = wret;
1837e089f05cSChris Mason 			wret = btrfs_free_extent(trans, root,
18387eccb903SChris Mason 						 bh_blocknr(leaf_buf), 1, 1);
18390f70abe2SChris Mason 			if (wret)
18400f70abe2SChris Mason 				ret = wret;
18419a8dd150SChris Mason 		}
1842be0e5c09SChris Mason 	} else {
18437518a238SChris Mason 		int used = leaf_space_used(leaf, 0, nritems);
1844aa5d6bedSChris Mason 		if (slot == 0) {
1845e089f05cSChris Mason 			wret = fixup_low_keys(trans, root, path,
1846aa5d6bedSChris Mason 					      &leaf->items[0].key, 1);
1847aa5d6bedSChris Mason 			if (wret)
1848aa5d6bedSChris Mason 				ret = wret;
1849aa5d6bedSChris Mason 		}
1850aa5d6bedSChris Mason 
185174123bd7SChris Mason 		/* delete the leaf if it is mostly empty */
1852123abc88SChris Mason 		if (used < BTRFS_LEAF_DATA_SIZE(root) / 3) {
1853be0e5c09SChris Mason 			/* push_leaf_left fixes the path.
1854be0e5c09SChris Mason 			 * make sure the path still points to our leaf
1855be0e5c09SChris Mason 			 * for possible call to del_ptr below
1856be0e5c09SChris Mason 			 */
18574920c9acSChris Mason 			slot = path->slots[1];
1858e20d96d6SChris Mason 			get_bh(leaf_buf);
1859e089f05cSChris Mason 			wret = push_leaf_left(trans, root, path, 1);
186054aa1f4dSChris Mason 			if (wret < 0 && wret != -ENOSPC)
1861aa5d6bedSChris Mason 				ret = wret;
1862f0930a37SChris Mason 			if (path->nodes[0] == leaf_buf &&
18637518a238SChris Mason 			    btrfs_header_nritems(&leaf->header)) {
1864e089f05cSChris Mason 				wret = push_leaf_right(trans, root, path, 1);
186554aa1f4dSChris Mason 				if (wret < 0 && wret != -ENOSPC)
1866aa5d6bedSChris Mason 					ret = wret;
1867aa5d6bedSChris Mason 			}
18687518a238SChris Mason 			if (btrfs_header_nritems(&leaf->header) == 0) {
18697eccb903SChris Mason 				u64 blocknr = bh_blocknr(leaf_buf);
1870e089f05cSChris Mason 				clean_tree_block(trans, root, leaf_buf);
1871d6025579SChris Mason 				wait_on_buffer(leaf_buf);
1872e089f05cSChris Mason 				wret = del_ptr(trans, root, path, 1, slot);
1873aa5d6bedSChris Mason 				if (wret)
1874aa5d6bedSChris Mason 					ret = wret;
1875234b63a0SChris Mason 				btrfs_block_release(root, leaf_buf);
1876e089f05cSChris Mason 				wret = btrfs_free_extent(trans, root, blocknr,
1877e089f05cSChris Mason 							 1, 1);
18780f70abe2SChris Mason 				if (wret)
18790f70abe2SChris Mason 					ret = wret;
18805de08d7dSChris Mason 			} else {
1881d6025579SChris Mason 				btrfs_mark_buffer_dirty(leaf_buf);
1882234b63a0SChris Mason 				btrfs_block_release(root, leaf_buf);
1883be0e5c09SChris Mason 			}
1884d5719762SChris Mason 		} else {
1885d6025579SChris Mason 			btrfs_mark_buffer_dirty(leaf_buf);
1886be0e5c09SChris Mason 		}
18879a8dd150SChris Mason 	}
1888aa5d6bedSChris Mason 	return ret;
18899a8dd150SChris Mason }
18909a8dd150SChris Mason 
189197571fd0SChris Mason /*
189297571fd0SChris Mason  * walk up the tree as far as required to find the next leaf.
18930f70abe2SChris Mason  * returns 0 if it found something or 1 if there are no greater leaves.
18940f70abe2SChris Mason  * returns < 0 on io errors.
189597571fd0SChris Mason  */
1896234b63a0SChris Mason int btrfs_next_leaf(struct btrfs_root *root, struct btrfs_path *path)
1897d97e63b6SChris Mason {
1898d97e63b6SChris Mason 	int slot;
1899d97e63b6SChris Mason 	int level = 1;
1900d97e63b6SChris Mason 	u64 blocknr;
1901e20d96d6SChris Mason 	struct buffer_head *c;
1902e20d96d6SChris Mason 	struct btrfs_node *c_node;
1903e20d96d6SChris Mason 	struct buffer_head *next = NULL;
1904d97e63b6SChris Mason 
1905234b63a0SChris Mason 	while(level < BTRFS_MAX_LEVEL) {
1906d97e63b6SChris Mason 		if (!path->nodes[level])
19070f70abe2SChris Mason 			return 1;
1908d97e63b6SChris Mason 		slot = path->slots[level] + 1;
1909d97e63b6SChris Mason 		c = path->nodes[level];
1910e20d96d6SChris Mason 		c_node = btrfs_buffer_node(c);
1911e20d96d6SChris Mason 		if (slot >= btrfs_header_nritems(&c_node->header)) {
1912d97e63b6SChris Mason 			level++;
1913d97e63b6SChris Mason 			continue;
1914d97e63b6SChris Mason 		}
1915e20d96d6SChris Mason 		blocknr = btrfs_node_blockptr(c_node, slot);
1916cfaa7295SChris Mason 		if (next)
1917234b63a0SChris Mason 			btrfs_block_release(root, next);
1918d97e63b6SChris Mason 		next = read_tree_block(root, blocknr);
1919d97e63b6SChris Mason 		break;
1920d97e63b6SChris Mason 	}
1921d97e63b6SChris Mason 	path->slots[level] = slot;
1922d97e63b6SChris Mason 	while(1) {
1923d97e63b6SChris Mason 		level--;
1924d97e63b6SChris Mason 		c = path->nodes[level];
1925234b63a0SChris Mason 		btrfs_block_release(root, c);
1926d97e63b6SChris Mason 		path->nodes[level] = next;
1927d97e63b6SChris Mason 		path->slots[level] = 0;
1928d97e63b6SChris Mason 		if (!level)
1929d97e63b6SChris Mason 			break;
19301d4f8a0cSChris Mason 		next = read_tree_block(root,
1931e20d96d6SChris Mason 		       btrfs_node_blockptr(btrfs_buffer_node(next), 0));
1932d97e63b6SChris Mason 	}
1933d97e63b6SChris Mason 	return 0;
1934d97e63b6SChris Mason }
1935