Skip to contentSkip to conversation

btrfs: delay to insert the initial inode

PATCH In review Miao Xie 2 participants 3 messages Apr 22, 2011 – Apr 26, 2011 Btrfs file system

lore
Share & tools
lore

Miao Xie

author
#0 lore raw

PATCH v6 3/3 btrfs: delay to insert the initial inode

Since we have implemented the delayed update of the inode, we can also delayed to insert the initial inode, then we can merge the inode update and the initial inode insertions to one insertion.

---
 fs/btrfs/delayed-inode.c |   18 +++++++++--
 fs/btrfs/delayed-inode.h |    8 ++++-
 fs/btrfs/inode.c         |   74 +++++++++++++++++++++++++++++++--------------
 3 files changed, 72 insertions(+), 28 deletions(-)
fs/btrfs/delayed-inode.c +15 -3
index 9548531..dd62b7b 100644
@@ -979,12 +979,20 @@ static int btrfs_update_delayed_inode(struct btrfs_trans_handle *trans,
 	key.objectid = node->inode_id;
 	btrfs_set_key_type(&key, BTRFS_INODE_ITEM_KEY);
 	key.offset = 0;
-	ret = btrfs_lookup_inode(trans, root, path, &key, 1);
+	if (node->inode_dirty == BTRFS_INODE_UPDATE) {
+		ret = btrfs_lookup_inode(trans, root, path, &key, 1);
+	} else if (node->inode_dirty == BTRFS_INODE_NEW)
+		ret = btrfs_insert_empty_item(trans, root, path, &key,
+					      sizeof(*inode_item));
+	else
+		BUG();
 	if (ret > 0) {
 		btrfs_release_path(root, path);
 		mutex_unlock(&node->mutex);
 		return -ENOENT;
 	} else if (ret < 0) {
+		WARN_ON(ret == -EEXIST && node->inode_dirty == BTRFS_INODE_NEW);
+		btrfs_release_path(root, path);
 		mutex_unlock(&node->mutex);
 		return ret;
 	}
@@ -1591,7 +1599,8 @@ static void fill_stack_inode_item(struct btrfs_trans_handle *trans,
 }
 
 int btrfs_delayed_update_inode(struct btrfs_trans_handle *trans,
-			       struct btrfs_root *root, struct inode *inode)
+			       struct btrfs_root *root, struct inode *inode,
+			       bool new_ino)
 {
 	struct btrfs_delayed_node *delayed_node;
 	int ret;
@@ -1614,7 +1623,10 @@ int btrfs_delayed_update_inode(struct btrfs_trans_handle *trans,
 	BUG_ON(ret);
 
 	fill_stack_inode_item(trans, &delayed_node->inode_item, inode);
-	delayed_node->inode_dirty = 1;
+	if (new_ino)
+		delayed_node->inode_dirty = BTRFS_INODE_NEW;
+	else
+		delayed_node->inode_dirty = BTRFS_INODE_UPDATE;
 	delayed_node->count++;
 	atomic_inc(&root->fs_info->delayed_root->items);
 release_node:
fs/btrfs/delayed-inode.h +6 -2
index eb7d240..79b009f 100644
@@ -33,6 +33,9 @@
 #define BTRFS_DELAYED_INSERTION_ITEM	1
 #define BTRFS_DELAYED_DELETION_ITEM	2
 
+#define BTRFS_INODE_NEW		1
+#define BTRFS_INODE_UPDATE	2
+
 struct btrfs_delayed_root {
 	spinlock_t lock;
 	struct list_head node_list;
@@ -64,8 +67,8 @@ struct btrfs_delayed_node {
 	struct btrfs_inode_item inode_item;
 	atomic_t refs;
 	u64 index_cnt;
+	u8 inode_dirty;
 	bool in_list;
-	bool inode_dirty;
 	int count;
 };
 
@@ -119,7 +122,8 @@ void btrfs_kill_delayed_inode_items(struct inode *inode);
 
 
 int btrfs_delayed_update_inode(struct btrfs_trans_handle *trans,
-			       struct btrfs_root *root, struct inode *inode);
+			       struct btrfs_root *root, struct inode *inode,
+			       bool new_ino);
 
 /* Used for drop dead root */
 void btrfs_kill_all_delayed_nodes(struct btrfs_root *root);
fs/btrfs/inode.c +51 -23

100 lines not on this page · raw message

Signature · 1 line
1.7.4
#1 lore raw

Excerpts from Miao Xie's message of 2011-04-22 06:12:24 -0400:

Quoted 3 lines

Since we have implemented the delayed update of the inode, we can also delayed to insert the initial inode, then we can merge the inode update and the initial inode insertions to one insertion.

Awesome. With things separate from the inode this should solve our oom problems. We might need to register a shrinker for the delayed inode operations too, but that shouldn't be a problem.

-chris

author
#2 lore raw
Quoted 8 lines · Chris Mason

Excerpts from Miao Xie's message of 2011-04-22 06:12:24 -0400:

Quoted 3 lines

Since we have implemented the delayed update of the inode, we can also delayed to insert the initial inode, then we can merge the inode update and the initial inode insertions to one insertion.

Awesome. With things separate from the inode this should solve our oom problems. We might need to register a shrinker for the delayed inode operations too, but that shouldn't be a problem.

I think this shrinker may block the task which is reclaiming the memory, because the shrinker need some free memory to do extent buffer cow when it does delayed item insertion/deletion. So...

But don't worry about it, those delayed nodes will be freed after the transaction is committed.

Thanks
Miao

Quoted 3 lines

-chris