diff options
Diffstat (limited to 'fs/btrfs')
-rw-r--r-- | fs/btrfs/ctree.h | 4 | ||||
-rw-r--r-- | fs/btrfs/inode.c | 34 | ||||
-rw-r--r-- | fs/btrfs/super.c | 2 |
3 files changed, 23 insertions, 17 deletions
diff --git a/fs/btrfs/ctree.h b/fs/btrfs/ctree.h index 29c20092847e..eaf286abad17 100644 --- a/fs/btrfs/ctree.h +++ b/fs/btrfs/ctree.h | |||
@@ -2389,13 +2389,13 @@ unsigned long btrfs_force_ra(struct address_space *mapping, | |||
2389 | pgoff_t offset, pgoff_t last_index); | 2389 | pgoff_t offset, pgoff_t last_index); |
2390 | int btrfs_page_mkwrite(struct vm_area_struct *vma, struct vm_fault *vmf); | 2390 | int btrfs_page_mkwrite(struct vm_area_struct *vma, struct vm_fault *vmf); |
2391 | int btrfs_readpage(struct file *file, struct page *page); | 2391 | int btrfs_readpage(struct file *file, struct page *page); |
2392 | void btrfs_delete_inode(struct inode *inode); | 2392 | void btrfs_evict_inode(struct inode *inode); |
2393 | void btrfs_put_inode(struct inode *inode); | 2393 | void btrfs_put_inode(struct inode *inode); |
2394 | int btrfs_write_inode(struct inode *inode, struct writeback_control *wbc); | 2394 | int btrfs_write_inode(struct inode *inode, struct writeback_control *wbc); |
2395 | void btrfs_dirty_inode(struct inode *inode); | 2395 | void btrfs_dirty_inode(struct inode *inode); |
2396 | struct inode *btrfs_alloc_inode(struct super_block *sb); | 2396 | struct inode *btrfs_alloc_inode(struct super_block *sb); |
2397 | void btrfs_destroy_inode(struct inode *inode); | 2397 | void btrfs_destroy_inode(struct inode *inode); |
2398 | void btrfs_drop_inode(struct inode *inode); | 2398 | int btrfs_drop_inode(struct inode *inode); |
2399 | int btrfs_init_cachep(void); | 2399 | int btrfs_init_cachep(void); |
2400 | void btrfs_destroy_cachep(void); | 2400 | void btrfs_destroy_cachep(void); |
2401 | long btrfs_ioctl_trans_end(struct file *file); | 2401 | long btrfs_ioctl_trans_end(struct file *file); |
diff --git a/fs/btrfs/inode.c b/fs/btrfs/inode.c index 1bff92ad4744..8976c3343a96 100644 --- a/fs/btrfs/inode.c +++ b/fs/btrfs/inode.c | |||
@@ -2938,7 +2938,6 @@ int btrfs_unlink_subvol(struct btrfs_trans_handle *trans, | |||
2938 | dir->i_mtime = dir->i_ctime = CURRENT_TIME; | 2938 | dir->i_mtime = dir->i_ctime = CURRENT_TIME; |
2939 | ret = btrfs_update_inode(trans, root, dir); | 2939 | ret = btrfs_update_inode(trans, root, dir); |
2940 | BUG_ON(ret); | 2940 | BUG_ON(ret); |
2941 | dir->i_sb->s_dirt = 1; | ||
2942 | 2941 | ||
2943 | btrfs_free_path(path); | 2942 | btrfs_free_path(path); |
2944 | return 0; | 2943 | return 0; |
@@ -3656,17 +3655,19 @@ static int btrfs_setattr(struct dentry *dentry, struct iattr *attr) | |||
3656 | if (err) | 3655 | if (err) |
3657 | return err; | 3656 | return err; |
3658 | } | 3657 | } |
3659 | attr->ia_valid &= ~ATTR_SIZE; | ||
3660 | 3658 | ||
3661 | if (attr->ia_valid) | 3659 | if (attr->ia_valid) { |
3662 | err = inode_setattr(inode, attr); | 3660 | setattr_copy(inode, attr); |
3661 | mark_inode_dirty(inode); | ||
3662 | |||
3663 | if (attr->ia_valid & ATTR_MODE) | ||
3664 | err = btrfs_acl_chmod(inode); | ||
3665 | } | ||
3663 | 3666 | ||
3664 | if (!err && ((attr->ia_valid & ATTR_MODE))) | ||
3665 | err = btrfs_acl_chmod(inode); | ||
3666 | return err; | 3667 | return err; |
3667 | } | 3668 | } |
3668 | 3669 | ||
3669 | void btrfs_delete_inode(struct inode *inode) | 3670 | void btrfs_evict_inode(struct inode *inode) |
3670 | { | 3671 | { |
3671 | struct btrfs_trans_handle *trans; | 3672 | struct btrfs_trans_handle *trans; |
3672 | struct btrfs_root *root = BTRFS_I(inode)->root; | 3673 | struct btrfs_root *root = BTRFS_I(inode)->root; |
@@ -3674,10 +3675,14 @@ void btrfs_delete_inode(struct inode *inode) | |||
3674 | int ret; | 3675 | int ret; |
3675 | 3676 | ||
3676 | truncate_inode_pages(&inode->i_data, 0); | 3677 | truncate_inode_pages(&inode->i_data, 0); |
3678 | if (inode->i_nlink && btrfs_root_refs(&root->root_item) != 0) | ||
3679 | goto no_delete; | ||
3680 | |||
3677 | if (is_bad_inode(inode)) { | 3681 | if (is_bad_inode(inode)) { |
3678 | btrfs_orphan_del(NULL, inode); | 3682 | btrfs_orphan_del(NULL, inode); |
3679 | goto no_delete; | 3683 | goto no_delete; |
3680 | } | 3684 | } |
3685 | /* do we really want it for ->i_nlink > 0 and zero btrfs_root_refs? */ | ||
3681 | btrfs_wait_ordered_range(inode, 0, (u64)-1); | 3686 | btrfs_wait_ordered_range(inode, 0, (u64)-1); |
3682 | 3687 | ||
3683 | if (root->fs_info->log_root_recovering) { | 3688 | if (root->fs_info->log_root_recovering) { |
@@ -3727,7 +3732,7 @@ void btrfs_delete_inode(struct inode *inode) | |||
3727 | btrfs_end_transaction(trans, root); | 3732 | btrfs_end_transaction(trans, root); |
3728 | btrfs_btree_balance_dirty(root, nr); | 3733 | btrfs_btree_balance_dirty(root, nr); |
3729 | no_delete: | 3734 | no_delete: |
3730 | clear_inode(inode); | 3735 | end_writeback(inode); |
3731 | return; | 3736 | return; |
3732 | } | 3737 | } |
3733 | 3738 | ||
@@ -3858,7 +3863,7 @@ again: | |||
3858 | p = &parent->rb_right; | 3863 | p = &parent->rb_right; |
3859 | else { | 3864 | else { |
3860 | WARN_ON(!(entry->vfs_inode.i_state & | 3865 | WARN_ON(!(entry->vfs_inode.i_state & |
3861 | (I_WILL_FREE | I_FREEING | I_CLEAR))); | 3866 | (I_WILL_FREE | I_FREEING))); |
3862 | rb_erase(parent, &root->inode_tree); | 3867 | rb_erase(parent, &root->inode_tree); |
3863 | RB_CLEAR_NODE(parent); | 3868 | RB_CLEAR_NODE(parent); |
3864 | spin_unlock(&root->inode_lock); | 3869 | spin_unlock(&root->inode_lock); |
@@ -3937,7 +3942,7 @@ again: | |||
3937 | if (atomic_read(&inode->i_count) > 1) | 3942 | if (atomic_read(&inode->i_count) > 1) |
3938 | d_prune_aliases(inode); | 3943 | d_prune_aliases(inode); |
3939 | /* | 3944 | /* |
3940 | * btrfs_drop_inode will remove it from | 3945 | * btrfs_drop_inode will have it removed from |
3941 | * the inode cache when its usage count | 3946 | * the inode cache when its usage count |
3942 | * hits zero. | 3947 | * hits zero. |
3943 | */ | 3948 | */ |
@@ -6331,13 +6336,14 @@ free: | |||
6331 | kmem_cache_free(btrfs_inode_cachep, BTRFS_I(inode)); | 6336 | kmem_cache_free(btrfs_inode_cachep, BTRFS_I(inode)); |
6332 | } | 6337 | } |
6333 | 6338 | ||
6334 | void btrfs_drop_inode(struct inode *inode) | 6339 | int btrfs_drop_inode(struct inode *inode) |
6335 | { | 6340 | { |
6336 | struct btrfs_root *root = BTRFS_I(inode)->root; | 6341 | struct btrfs_root *root = BTRFS_I(inode)->root; |
6337 | if (inode->i_nlink > 0 && btrfs_root_refs(&root->root_item) == 0) | 6342 | |
6338 | generic_delete_inode(inode); | 6343 | if (btrfs_root_refs(&root->root_item) == 0) |
6344 | return 1; | ||
6339 | else | 6345 | else |
6340 | generic_drop_inode(inode); | 6346 | return generic_drop_inode(inode); |
6341 | } | 6347 | } |
6342 | 6348 | ||
6343 | static void init_once(void *foo) | 6349 | static void init_once(void *foo) |
diff --git a/fs/btrfs/super.c b/fs/btrfs/super.c index f2393b390318..1776dbd8dc98 100644 --- a/fs/btrfs/super.c +++ b/fs/btrfs/super.c | |||
@@ -797,7 +797,7 @@ static int btrfs_unfreeze(struct super_block *sb) | |||
797 | 797 | ||
798 | static const struct super_operations btrfs_super_ops = { | 798 | static const struct super_operations btrfs_super_ops = { |
799 | .drop_inode = btrfs_drop_inode, | 799 | .drop_inode = btrfs_drop_inode, |
800 | .delete_inode = btrfs_delete_inode, | 800 | .evict_inode = btrfs_evict_inode, |
801 | .put_super = btrfs_put_super, | 801 | .put_super = btrfs_put_super, |
802 | .sync_fs = btrfs_sync_fs, | 802 | .sync_fs = btrfs_sync_fs, |
803 | .show_options = btrfs_show_options, | 803 | .show_options = btrfs_show_options, |