btrfs-progs: dev stats: fix printing wrong values in tabular output

The tabular output prints the same value for all columns:

  # btrfs device stats /srv/btrfs-data
  [/dev/sdc1].write_io_errs    0
  [/dev/sdc1].read_io_errs     0
  [/dev/sdc1].flush_io_errs    0
  [/dev/sdc1].corruption_errs  0
  [/dev/sdc1].generation_errs  0
  [/dev/sdb1].write_io_errs    7489899
  [/dev/sdb1].read_io_errs     3751023
  [/dev/sdb1].flush_io_errs    117
  [/dev/sdb1].corruption_errs  68
  [/dev/sdb1].generation_errs  25

  # btrfs device stats -T /srv/btrfs-data
  Id Path      Write errors Read errors Flush errors Corruption errors Generation errors
  -- --------- ------------ ----------- ------------ ----------------- -----------------
   1 /dev/sdc1            0           0            0                 0                 0
   2 /dev/sdb1           25          25           25                25                25

The table_printf has a fixed list of columns and should not iterate over
them. Only check if some of the value is set and return error.

Bugzilla: https://bugzilla.kernel.org/show_bug.cgi?id=217045
Issue: #585
Signed-off-by: David Sterba <dsterba@suse.com>
This commit is contained in:
David Sterba 2023-03-07 21:09:03 +01:00
parent 3edfc2b29a
commit cba1ef1a42
1 changed files with 7 additions and 23 deletions

View File

@ -648,16 +648,6 @@ static int print_device_stat_tabular(struct string_table *table, int row,
char *canonical_path = path_canonicalize(path); char *canonical_path = path_canonicalize(path);
int j; int j;
int err = 0; int err = 0;
static const struct {
const char name[32];
enum btrfs_dev_stat_values stat_idx;
} dev_stats[] = {
{ "write_io_errs", BTRFS_DEV_STAT_WRITE_ERRS },
{ "read_io_errs", BTRFS_DEV_STAT_READ_ERRS },
{ "flush_io_errs", BTRFS_DEV_STAT_FLUSH_ERRS },
{ "corruption_errs", BTRFS_DEV_STAT_CORRUPTION_ERRS },
{ "generation_errs", BTRFS_DEV_STAT_GENERATION_ERRS },
};
/* Skip header + --- line */ /* Skip header + --- line */
row += 2; row += 2;
@ -677,20 +667,14 @@ static int print_device_stat_tabular(struct string_table *table, int row,
table_printf(table, 1, row, ">%s", canonical_path); table_printf(table, 1, row, ">%s", canonical_path);
free(canonical_path); free(canonical_path);
for (j = 0; j < ARRAY_SIZE(dev_stats); j++) { table_printf(table, 2, row, ">%llu", args->values[BTRFS_DEV_STAT_WRITE_ERRS]);
enum btrfs_dev_stat_values stat_idx = dev_stats[j].stat_idx; table_printf(table, 3, row, ">%llu", args->values[BTRFS_DEV_STAT_READ_ERRS]);
table_printf(table, 4, row, ">%llu", args->values[BTRFS_DEV_STAT_FLUSH_ERRS]);
table_printf(table, 5, row, ">%llu", args->values[BTRFS_DEV_STAT_CORRUPTION_ERRS]);
table_printf(table, 6, row, ">%llu", args->values[BTRFS_DEV_STAT_GENERATION_ERRS]);
/* We got fewer items than we know */ for (j = 0; j < BTRFS_DEV_STAT_VALUES_MAX; j++) {
if (args->nr_items < stat_idx + 1) if (check && (args->values[j] > 0))
continue;
table_printf(table, 2, row, ">%llu", args->values[stat_idx]);
table_printf(table, 3, row, ">%llu", args->values[stat_idx]);
table_printf(table, 4, row, ">%llu", args->values[stat_idx]);
table_printf(table, 5, row, ">%llu", args->values[stat_idx]);
table_printf(table, 6, row, ">%llu", args->values[stat_idx]);
if (check && (args->values[stat_idx] > 0))
err |= 64; err |= 64;
} }