Merge branch 'delayed_inode' into inode_numbers
Chris Mason [Sun, 22 May 2011 11:07:01 +0000 (07:07 -0400)]
Conflicts:
fs/btrfs/inode.c
fs/btrfs/ioctl.c
fs/btrfs/transaction.c

Signed-off-by: Chris Mason <chris.mason@oracle.com>

1  2 
fs/btrfs/btrfs_inode.h
fs/btrfs/ctree.h
fs/btrfs/disk-io.c
fs/btrfs/extent-tree.c
fs/btrfs/inode.c
fs/btrfs/ioctl.c
fs/btrfs/transaction.c
fs/btrfs/tree-log.c

Simple merge
Simple merge
Simple merge
Simple merge
@@@ -2659,11 -2647,26 +2659,26 @@@ noinline int btrfs_update_inode(struct 
        struct extent_buffer *leaf;
        int ret;
  
+       /*
+        * If root is tree root, it means this inode is used to
+        * store free space information. And these inodes are updated
+        * when committing the transaction, so they needn't delaye to
+        * be updated, or deadlock will occured.
+        */
 -      if (likely(root != root->fs_info->tree_root)) {
++      if (!is_free_space_inode(root, inode)) {
+               ret = btrfs_delayed_update_inode(trans, root, inode);
+               if (!ret)
+                       btrfs_set_inode_last_trans(trans, inode);
+               return ret;
+       }
        path = btrfs_alloc_path();
-       BUG_ON(!path);
+       if (!path)
+               return -ENOMEM;
        path->leave_spinning = 1;
-       ret = btrfs_lookup_inode(trans, root, path,
-                                &BTRFS_I(inode)->location, 1);
+       ret = btrfs_lookup_inode(trans, root, path, &BTRFS_I(inode)->location,
+                                1);
        if (ret) {
                if (ret > 0)
                        ret = -ENOENT;
@@@ -2737,21 -2738,12 +2751,12 @@@ static int __btrfs_unlink_inode(struct 
                goto err;
        }
  
-       di = btrfs_lookup_dir_index_item(trans, root, path, dir_ino,
-                                        index, name, name_len, -1);
-       if (IS_ERR(di)) {
-               ret = PTR_ERR(di);
-               goto err;
-       }
-       if (!di) {
-               ret = -ENOENT;
+       ret = btrfs_delete_delayed_dir_index(trans, root, dir, index);
+       if (ret)
                goto err;
-       }
-       ret = btrfs_delete_one_dir_name(trans, root, path, di);
-       btrfs_release_path(root, path);
  
        ret = btrfs_del_inode_ref_in_log(trans, root, name, name_len,
 -                                       inode, dir->i_ino);
 +                                       inode, dir_ino);
        BUG_ON(ret != 0 && ret != -ENOENT);
  
        ret = btrfs_del_dir_entries_in_log(trans, root, name, name_len,
@@@ -2939,7 -2929,15 +2944,15 @@@ static struct btrfs_trans_handle *__unl
        index = btrfs_inode_ref_index(path->nodes[0], ref);
        btrfs_release_path(root, path);
  
+       /*
+        * This is a commit root search, if we can lookup inode item and other
+        * relative items in the commit root, it means the transaction of
+        * dir/file creation has been committed, and the dir index item that we
+        * delay to insert has also been inserted into the commit root. So
+        * we needn't worry about the delayed insertion of the dir index item
+        * here.
+        */
 -      di = btrfs_lookup_dir_index_item(trans, root, path, dir->i_ino, index,
 +      di = btrfs_lookup_dir_index_item(trans, root, path, dir_ino, index,
                                dentry->d_name.name, dentry->d_name.len, 0);
        if (IS_ERR(di)) {
                err = PTR_ERR(di);
@@@ -4280,11 -4275,19 +4297,19 @@@ static int btrfs_real_readdir(struct fi
                filp->f_pos = 2;
        }
        path = btrfs_alloc_path();
+       if (!path)
+               return -ENOMEM;
        path->reada = 2;
  
+       if (key_type == BTRFS_DIR_INDEX_KEY) {
+               INIT_LIST_HEAD(&ins_list);
+               INIT_LIST_HEAD(&del_list);
+               btrfs_get_delayed_items(inode, &ins_list, &del_list);
+       }
        btrfs_set_key_type(&key, key_type);
        key.offset = filp->f_pos;
 -      key.objectid = inode->i_ino;
 +      key.objectid = btrfs_ino(inode);
  
        ret = btrfs_search_slot(NULL, root, &key, path, 0, 0);
        if (ret < 0)
Simple merge
Simple merge
Simple merge