Btrfs: use percpu counter for dirty metadata count
PATCH 6/11 Btrfs: use percpu counter for dirty metadata count
->dirty_metadata_bytes is accessed very frequently, so use percpu counter instead of the u64 variant to reduce the contention of the lock.
Signed-off-by Miao Xie <[email protected]>
--- fs/btrfs/ctree.h | 9 ++++---- fs/btrfs/disk-io.c | 64 ++++++++++++++++++++++++++++------------------------ fs/btrfs/extent_io.c | 9 +++----- 3 files changed, 42 insertions(+), 40 deletions(-)
fs/btrfs/ctree.h +5 -4
@@ -191,6 +191,8 @@ static int btrfs_csum_sizes[] = { 4, 0 };/* ioprio of readahead is set to idle */ #define BTRFS_IOPRIO_READA (IOPRIO_PRIO_VALUE(IOPRIO_CLASS_IDLE, 0)) +#define BTRFS_DIRTY_METADATA_THRESH (32 * 1024 * 1024) +/* * The key defines the order in the tree, and so it also defines (optimal) * block layout.
@@ -1439,10 +1441,9 @@ struct btrfs_fs_info {u64 total_pinned; -/* protected by the delalloc lock, used to keep from writing -* metadata until there is a nice batch -*/ -u64 dirty_metadata_bytes; +/* used to keep from writing metadata until there is a nice batch */ +struct percpu_counter dirty_metadata_bytes; +s32 dirty_metadata_batch;struct list_head dirty_cowonly_roots;struct btrfs_fs_devices *fs_devices;
fs/btrfs/disk-io.c +34 -30
132 lines not on this page · raw message
fs/btrfs/extent_io.c +3 -6
@@ -3124,12 +3124,9 @@ static int lock_extent_buffer_for_io(struct extent_buffer *eb,set_bit (EXTENT_BUFFER_WRITEBACK , &eb->bflags);spin_unlock (&eb->refs_lock);btrfs_set_header_flag (eb,BTRFS_HEADER_FLAG_WRITTEN ); -spin_lock (&fs_info->delalloc_lock); -if (fs_info->dirty_metadata_bytes >= eb->len) - fs_info->dirty_metadata_bytes -= eb->len; -else -WARN_ON (1 ); -spin_unlock (&fs_info->delalloc_lock); +__percpu_counter_add (&fs_info->dirty_metadata_bytes, + -eb->len, + fs_info->dirty_metadata_batch); ret =1 ; }else {spin_unlock (&eb->refs_lock);
Signature · 1 line
1.7.11.7