aboutsummaryrefslogtreecommitdiffstats
path: root/fs/btrfs
diff options
context:
space:
mode:
authorJosef Bacik <josef@redhat.com>2012-01-13 12:09:22 -0500
committerChris Mason <chris.mason@oracle.com>2012-01-16 15:29:43 -0500
commitf248679e86fead40cc78e724c7181d6bec1a2046 (patch)
tree88abeee0b2a87c0f0377509525c92d3c9ec15a15 /fs/btrfs
parent8c2a3ca20f6233677ac3222c6506174010eb414f (diff)
Btrfs: add a delalloc mutex to inodes for delalloc reservations
I was using i_mutex for this, but we're getting bogus lockdep warnings by doing that and theres no real way to get rid of those, so just stop using i_mutex to protect delalloc metadata reservations and use a delalloc mutex instead. This shouldn't be contended often at all, only if you are writing and mmap writing to the file at the same time. Thanks, Signed-off-by: Josef Bacik <josef@redhat.com>
Diffstat (limited to 'fs/btrfs')
-rw-r--r--fs/btrfs/btrfs_inode.h3
-rw-r--r--fs/btrfs/extent-tree.c5
-rw-r--r--fs/btrfs/inode.c11
-rw-r--r--fs/btrfs/ioctl.c2
-rw-r--r--fs/btrfs/relocation.c2
5 files changed, 7 insertions, 16 deletions
diff --git a/fs/btrfs/btrfs_inode.h b/fs/btrfs/btrfs_inode.h
index 634608d2a6d..9b9b15fd520 100644
--- a/fs/btrfs/btrfs_inode.h
+++ b/fs/btrfs/btrfs_inode.h
@@ -51,6 +51,9 @@ struct btrfs_inode {
51 /* held while logging the inode in tree-log.c */ 51 /* held while logging the inode in tree-log.c */
52 struct mutex log_mutex; 52 struct mutex log_mutex;
53 53
54 /* held while doing delalloc reservations */
55 struct mutex delalloc_mutex;
56
54 /* used to order data wrt metadata */ 57 /* used to order data wrt metadata */
55 struct btrfs_ordered_inode_tree ordered_tree; 58 struct btrfs_ordered_inode_tree ordered_tree;
56 59
diff --git a/fs/btrfs/extent-tree.c b/fs/btrfs/extent-tree.c
index 556f9aa25bb..e0ad5f0f895 100644
--- a/fs/btrfs/extent-tree.c
+++ b/fs/btrfs/extent-tree.c
@@ -4345,12 +4345,11 @@ int btrfs_delalloc_reserve_metadata(struct inode *inode, u64 num_bytes)
4345 /* Need to be holding the i_mutex here if we aren't free space cache */ 4345 /* Need to be holding the i_mutex here if we aren't free space cache */
4346 if (btrfs_is_free_space_inode(root, inode)) 4346 if (btrfs_is_free_space_inode(root, inode))
4347 flush = 0; 4347 flush = 0;
4348 else
4349 WARN_ON(!mutex_is_locked(&inode->i_mutex));
4350 4348
4351 if (flush && btrfs_transaction_in_commit(root->fs_info)) 4349 if (flush && btrfs_transaction_in_commit(root->fs_info))
4352 schedule_timeout(1); 4350 schedule_timeout(1);
4353 4351
4352 mutex_lock(&BTRFS_I(inode)->delalloc_mutex);
4354 num_bytes = ALIGN(num_bytes, root->sectorsize); 4353 num_bytes = ALIGN(num_bytes, root->sectorsize);
4355 4354
4356 spin_lock(&BTRFS_I(inode)->lock); 4355 spin_lock(&BTRFS_I(inode)->lock);
@@ -4405,6 +4404,7 @@ int btrfs_delalloc_reserve_metadata(struct inode *inode, u64 num_bytes)
4405 btrfs_ino(inode), 4404 btrfs_ino(inode),
4406 to_free, 0); 4405 to_free, 0);
4407 } 4406 }
4407 mutex_unlock(&BTRFS_I(inode)->delalloc_mutex);
4408 return ret; 4408 return ret;
4409 } 4409 }
4410 4410
@@ -4415,6 +4415,7 @@ int btrfs_delalloc_reserve_metadata(struct inode *inode, u64 num_bytes)
4415 } 4415 }
4416 BTRFS_I(inode)->reserved_extents += nr_extents; 4416 BTRFS_I(inode)->reserved_extents += nr_extents;
4417 spin_unlock(&BTRFS_I(inode)->lock); 4417 spin_unlock(&BTRFS_I(inode)->lock);
4418 mutex_unlock(&BTRFS_I(inode)->delalloc_mutex);
4418 4419
4419 if (to_reserve) 4420 if (to_reserve)
4420 trace_btrfs_space_reservation(root->fs_info,"delalloc", 4421 trace_btrfs_space_reservation(root->fs_info,"delalloc",
diff --git a/fs/btrfs/inode.c b/fs/btrfs/inode.c
index 619742d3716..5977987abdb 100644
--- a/fs/btrfs/inode.c
+++ b/fs/btrfs/inode.c
@@ -2239,14 +2239,7 @@ int btrfs_orphan_cleanup(struct btrfs_root *root)
2239 continue; 2239 continue;
2240 } 2240 }
2241 nr_truncate++; 2241 nr_truncate++;
2242 /*
2243 * Need to hold the imutex for reservation purposes, not
2244 * a huge deal here but I have a WARN_ON in
2245 * btrfs_delalloc_reserve_space to catch offenders.
2246 */
2247 mutex_lock(&inode->i_mutex);
2248 ret = btrfs_truncate(inode); 2242 ret = btrfs_truncate(inode);
2249 mutex_unlock(&inode->i_mutex);
2250 } else { 2243 } else {
2251 nr_unlink++; 2244 nr_unlink++;
2252 } 2245 }
@@ -6411,10 +6404,7 @@ int btrfs_page_mkwrite(struct vm_area_struct *vma, struct vm_fault *vmf)
6411 u64 page_start; 6404 u64 page_start;
6412 u64 page_end; 6405 u64 page_end;
6413 6406
6414 /* Need this to keep space reservations serialized */
6415 mutex_lock(&inode->i_mutex);
6416 ret = btrfs_delalloc_reserve_space(inode, PAGE_CACHE_SIZE); 6407 ret = btrfs_delalloc_reserve_space(inode, PAGE_CACHE_SIZE);
6417 mutex_unlock(&inode->i_mutex);
6418 if (!ret) 6408 if (!ret)
6419 ret = btrfs_update_time(vma->vm_file); 6409 ret = btrfs_update_time(vma->vm_file);
6420 if (ret) { 6410 if (ret) {
@@ -6758,6 +6748,7 @@ struct inode *btrfs_alloc_inode(struct super_block *sb)
6758 extent_io_tree_init(&ei->io_tree, &inode->i_data); 6748 extent_io_tree_init(&ei->io_tree, &inode->i_data);
6759 extent_io_tree_init(&ei->io_failure_tree, &inode->i_data); 6749 extent_io_tree_init(&ei->io_failure_tree, &inode->i_data);
6760 mutex_init(&ei->log_mutex); 6750 mutex_init(&ei->log_mutex);
6751 mutex_init(&ei->delalloc_mutex);
6761 btrfs_ordered_inode_tree_init(&ei->ordered_tree); 6752 btrfs_ordered_inode_tree_init(&ei->ordered_tree);
6762 INIT_LIST_HEAD(&ei->i_orphan); 6753 INIT_LIST_HEAD(&ei->i_orphan);
6763 INIT_LIST_HEAD(&ei->delalloc_inodes); 6754 INIT_LIST_HEAD(&ei->delalloc_inodes);
diff --git a/fs/btrfs/ioctl.c b/fs/btrfs/ioctl.c
index 7fdf22c2dc0..6834be4c870 100644
--- a/fs/btrfs/ioctl.c
+++ b/fs/btrfs/ioctl.c
@@ -868,10 +868,8 @@ static int cluster_pages_for_defrag(struct inode *inode,
868 return 0; 868 return 0;
869 file_end = (isize - 1) >> PAGE_CACHE_SHIFT; 869 file_end = (isize - 1) >> PAGE_CACHE_SHIFT;
870 870
871 mutex_lock(&inode->i_mutex);
872 ret = btrfs_delalloc_reserve_space(inode, 871 ret = btrfs_delalloc_reserve_space(inode,
873 num_pages << PAGE_CACHE_SHIFT); 872 num_pages << PAGE_CACHE_SHIFT);
874 mutex_unlock(&inode->i_mutex);
875 if (ret) 873 if (ret)
876 return ret; 874 return ret;
877again: 875again:
diff --git a/fs/btrfs/relocation.c b/fs/btrfs/relocation.c
index efe9f792544..8c1aae2c845 100644
--- a/fs/btrfs/relocation.c
+++ b/fs/btrfs/relocation.c
@@ -2949,9 +2949,7 @@ static int relocate_file_extent_cluster(struct inode *inode,
2949 index = (cluster->start - offset) >> PAGE_CACHE_SHIFT; 2949 index = (cluster->start - offset) >> PAGE_CACHE_SHIFT;
2950 last_index = (cluster->end - offset) >> PAGE_CACHE_SHIFT; 2950 last_index = (cluster->end - offset) >> PAGE_CACHE_SHIFT;
2951 while (index <= last_index) { 2951 while (index <= last_index) {
2952 mutex_lock(&inode->i_mutex);
2953 ret = btrfs_delalloc_reserve_metadata(inode, PAGE_CACHE_SIZE); 2952 ret = btrfs_delalloc_reserve_metadata(inode, PAGE_CACHE_SIZE);
2954 mutex_unlock(&inode->i_mutex);
2955 if (ret) 2953 if (ret)
2956 goto out; 2954 goto out;
2957 2955