From 128a2c64f4ba6745c1aa68b8f18f4164c90ae836 Mon Sep 17 00:00:00 2001 From: Zach Brown Date: Sun, 23 Feb 2020 20:08:41 -0800 Subject: [PATCH] scoutfs: restore df/statfs block counts The removal of extent allocators in the server removed the tracking of total free blocks in the system as extents were allocated and freed. This restores tracking of total free blocks by observing the difference in each allocator's sm_total count as a new version is stored during a commit on the server. We change the single free_blocks counter in the super to separate counts of free metadata and data blocks to reflect the metadata and data allocators. The statfs net command is updated. Signed-off-by: Zach Brown --- kmod/src/format.h | 3 ++- kmod/src/server.c | 30 +++++++++++++++++++++++++++++- 2 files changed, 31 insertions(+), 2 deletions(-) diff --git a/kmod/src/format.h b/kmod/src/format.h index 6cfb7322..42eecc90 100644 --- a/kmod/src/format.h +++ b/kmod/src/format.h @@ -481,10 +481,11 @@ struct scoutfs_super_block { __le64 total_meta_blocks; /* both static and dynamic */ __le64 first_meta_blkno; /* first dynamically allocated */ __le64 last_meta_blkno; + __le64 free_meta_blocks; __le64 total_data_blocks; __le64 first_data_blkno; __le64 last_data_blkno; - __le64 free_blocks; + __le64 free_data_blocks; __le64 quorum_fenced_term; __le64 quorum_server_term; __le64 unmount_barrier; diff --git a/kmod/src/server.c b/kmod/src/server.c index 93c89fa7..b05ef812 100644 --- a/kmod/src/server.c +++ b/kmod/src/server.c @@ -144,6 +144,18 @@ static inline int wait_for_commit(struct commit_waiter *cw) return cw->ret; } +/* + * The caller is about to overwrite a ref to an alloc tree. As we do + * so we update the given super free block counter with the difference + * between the old and new allocator roots. + */ +static void update_free_blocks(__le64 *blocks, struct scoutfs_radix_root *prev, + struct scoutfs_radix_root *next) +{ + le64_add_cpu(blocks, le64_to_cpu(next->ref.sm_total) - + le64_to_cpu(prev->ref.sm_total)); +} + /* * A core function of request processing is to modify the manifest and * allocator. Often the processing needs to make the modifications @@ -184,6 +196,11 @@ static void scoutfs_server_commit_func(struct work_struct *work) goto out; } + update_free_blocks(&super->free_meta_blocks, &super->core_meta_avail, + &server->alloc.avail); + update_free_blocks(&super->free_meta_blocks, &super->core_meta_freed, + &server->alloc.freed); + super->core_meta_avail = server->alloc.avail; super->core_meta_freed = server->alloc.freed; @@ -414,6 +431,15 @@ static int server_commit_log_trees(struct super_block *sb, /* XXX probably want to merge free blocks */ + update_free_blocks(&super->free_meta_blocks, <v.meta_avail, + <->meta_avail); + update_free_blocks(&super->free_meta_blocks, <v.meta_freed, + <->meta_freed); + update_free_blocks(&super->free_data_blocks, <v.data_avail, + <->data_avail); + update_free_blocks(&super->free_data_blocks, <v.data_freed, + <->data_freed); + ltv.meta_avail = lt->meta_avail; ltv.meta_freed = lt->meta_freed; ltv.item_root = lt->item_root; @@ -712,7 +738,9 @@ static int server_statfs(struct super_block *sb, nstatfs.total_blocks = super->total_meta_blocks; le64_add_cpu(&nstatfs.total_blocks, le64_to_cpu(super->total_data_blocks)); - nstatfs.bfree = super->free_blocks; + nstatfs.bfree = super->free_meta_blocks; + le64_add_cpu(&nstatfs.bfree, + le64_to_cpu(super->free_data_blocks)); up_read(&server->alloc_rwsem); ret = 0; } else {