Whamcloud - gitweb
LU-11721 utils: print used inodes ratio when using "lfs df -i" 58/33758/6
authorNikitas Angelinas <nangelinas@cray.com>
Thu, 29 Nov 2018 23:23:05 +0000 (15:23 -0800)
committerOleg Drokin <green@whamcloud.com>
Wed, 30 Jan 2019 02:40:26 +0000 (02:40 +0000)
"lfs df -i" prints the used blocks percentage, instead of the used
inodes percentage. Fix this by allowing obd_statfs_ratio() to
distinguish when "-i" is used.

Round up the ratio returned from obd_statfs_ratio() in a ceiling
manner, to match the output of df(1). Add a sanity test to check
that the outputs from df(1) and lfs df match.

Signed-off-by: Nikitas Angelinas <nangelinas@cray.com>
Cray-bug-id: LUS-6748
Test-Parameters: trivial
Change-Id: I0b31ecb7371875c93bc07dda1f1c89e04d5b4576
Reviewed-on: https://review.whamcloud.com/33758
Tested-by: Jenkins
Reviewed-by: Andreas Dilger <adilger@whamcloud.com>
Tested-by: Maloo <maloo@whamcloud.com>
Reviewed-by: Lai Siyao <lai.siyao@whamcloud.com>
lustre/tests/sanity.sh
lustre/utils/lfs.c

index c0a3eb4..ec6ae03 100755 (executable)
@@ -19359,6 +19359,82 @@ test_417() {
 }
 run_test 417 "disable remote dir, striped dir and dir migration"
 
 }
 run_test 417 "disable remote dir, striped dir and dir migration"
 
+# Checks that the outputs of df [-i] and lfs df [-i] match
+#
+# usage: check_lfs_df <blocks | inodes> <mountpoint>
+check_lfs_df() {
+       local dir=$2
+       local inodes
+       local df_out
+       local lfs_df_out
+
+       # blocks or inodes
+       [ "$1" == "blocks" ] && inodes= || inodes="-i"
+
+       # read the lines of interest
+       df_out=($(df $inodes $dir | tail -n +2)) ||
+               error "df $inodes $dir | tail -n +2 failed"
+       lfs_df_out=($($LFS df $inodes $dir | grep filesystem_summary:)) ||
+               error "lfs df $inodes $dir | grep filesystem_summary: failed"
+
+       # skip the first substrings of each command output as they are different
+       # <NID>:/<fsname for df, filesystem_summary: for lfs df
+       df_out=(${df_out[@]:1})
+       lfs_df_out=(${lfs_df_out[@]:1})
+
+       # compare the two outputs
+       for i in {0..4}; do
+               [ "${df_out[i]}" != "${lfs_df_out[i]}" ] &&
+                       error "df and lfs df output mismatch:" \
+                             "df${inodes}: ${df_out[*]}," \
+                             "lfs df${inodes}: ${lfs_df_out[*]}"
+       done
+}
+
+test_418() {
+       local dir=$DIR/$tdir
+       local numfiles=$((RANDOM % 4096 + 2))
+       local numblocks=$((RANDOM % 256 + 1))
+
+       wait_delete_completed
+       test_mkdir $dir
+
+       # check block output
+       check_lfs_df blocks $dir
+       # check inode output
+       check_lfs_df inodes $dir
+
+       # create a single file and retest
+       echo "Creating a single file and testing"
+       createmany -o $dir/$tfile- 1 &>/dev/null ||
+               error "creating 1 file in $dir failed"
+       cancel_lru_locks osc
+       sync; sleep 2
+       check_lfs_df blocks $dir
+       check_lfs_df inodes $dir
+
+       # create a random number of files
+       echo "Creating $((numfiles - 1)) files and testing"
+       createmany -o $dir/$tfile- 1 $((numfiles - 1)) &>/dev/null ||
+               error "creating $((numfiles - 1)) files in $dir failed"
+
+       # write a random number of blocks to the first test file
+       echo "Writing $numblocks 4K blocks and testing"
+       dd if=/dev/urandom of=$dir/${tfile}-0 bs=4K conv=fsync \
+               count=$numblocks &>/dev/null ||
+               error "dd to $dir/${tfile}-0 failed"
+
+       # retest
+       cancel_lru_locks osc
+       sync; sleep 10
+       check_lfs_df blocks $dir
+       check_lfs_df inodes $dir
+
+       unlinkmany $dir/$tfile- $numfiles &>/dev/null ||
+               error "unlinking $numfiles files in $dir failed"
+}
+run_test 418 "df and lfs df outputs match"
+
 prep_801() {
        [[ $(lustre_version_code mds1) -lt $(version_code 2.9.55) ]] ||
        [[ $OST1_VERSION -lt $(version_code 2.9.55) ]] &&
 prep_801() {
        [[ $(lustre_version_code mds1) -lt $(version_code 2.9.55) ]] ||
        [[ $OST1_VERSION -lt $(version_code 2.9.55) ]] &&
index 63d4aa4..6225437 100644 (file)
@@ -4606,16 +4606,22 @@ enum mntdf_flags {
 #define RSF     "%4s"
 #define RDF     "%3d%%"
 
 #define RSF     "%4s"
 #define RDF     "%3d%%"
 
-static inline int obd_statfs_ratio(const struct obd_statfs *st)
+static inline int obd_statfs_ratio(const struct obd_statfs *st, bool inodes)
 {
        double avail, used, ratio = 0;
 
 {
        double avail, used, ratio = 0;
 
-       avail = st->os_bavail;
-       used  = st->os_blocks - st->os_bfree;
+       if (inodes) {
+               avail = st->os_ffree;
+               used = st->os_files - st->os_ffree;
+       } else {
+               avail = st->os_bavail;
+               used = st->os_blocks - st->os_bfree;
+       }
        if (avail + used > 0)
        if (avail + used > 0)
-               ratio = used / (used + avail) * 100 + 0.5;
+               ratio = used / (used + avail) * 100;
 
 
-       return (int)ratio;
+       /* Round up to match df(1) usage percentage */
+       return (ratio - (int)ratio) > 0 ? (int)(ratio + 1) : (int)ratio;
 }
 
 static int showdf(char *mntdir, struct obd_statfs *stat,
 }
 
 static int showdf(char *mntdir, struct obd_statfs *stat,
@@ -4649,7 +4655,7 @@ static int showdf(char *mntdir, struct obd_statfs *stat,
                        total = (stat->os_blocks * stat->os_bsize) >> shift;
                }
 
                        total = (stat->os_blocks * stat->os_bsize) >> shift;
                }
 
-               ratio = obd_statfs_ratio(stat);
+               ratio = obd_statfs_ratio(stat, flags & MNTDF_INODES);
 
                if (flags & MNTDF_COOKED) {
                        int i;
 
                if (flags & MNTDF_COOKED) {
                        int i;
@@ -4893,8 +4899,8 @@ static int ll_statfs_data_comp(const void *sd1, const void *sd2)
                                                sd_st;
        const struct obd_statfs *st2 = &((const struct ll_statfs_data *)sd2)->
                                                sd_st;
                                                sd_st;
        const struct obd_statfs *st2 = &((const struct ll_statfs_data *)sd2)->
                                                sd_st;
-       int r1 = obd_statfs_ratio(st1);
-       int r2 = obd_statfs_ratio(st2);
+       int r1 = obd_statfs_ratio(st1, false);
+       int r2 = obd_statfs_ratio(st2, false);
        int64_t result = r1 - r2;
 
        /* if both space usage are above 90, compare free inodes */
        int64_t result = r1 - r2;
 
        /* if both space usage are above 90, compare free inodes */
@@ -5174,8 +5180,8 @@ static int lfs_setdirstripe(int argc, char **argv)
 
                                /* don't use server whose usage is above 90% */
                                while (nr != param->lsp_stripe_count &&
 
                                /* don't use server whose usage is above 90% */
                                while (nr != param->lsp_stripe_count &&
-                                      obd_statfs_ratio(&lsb->sb_buf[nr].sd_st)
-                                      > 90)
+                                      obd_statfs_ratio(&lsb->sb_buf[nr].sd_st,
+                                                       false) > 90)
                                        nr = MAX(param->lsp_stripe_count,
                                                 nr / 2);
 
                                        nr = MAX(param->lsp_stripe_count,
                                                 nr / 2);