btrfs-progs: list-chunks: port to sorting API
Use the sorting API. This is 1:1 transformation of previous single key sorting and needs to be updated so there are multiple accepted instead. Signed-off-by: David Sterba <dsterba@suse.com>
This commit is contained in:
parent
7f9bcab309
commit
00e401752f
|
@ -43,6 +43,7 @@
|
||||||
#include "common/units.h"
|
#include "common/units.h"
|
||||||
#include "common/string-utils.h"
|
#include "common/string-utils.h"
|
||||||
#include "common/string-table.h"
|
#include "common/string-table.h"
|
||||||
|
#include "common/sort-utils.h"
|
||||||
#include "cmds/commands.h"
|
#include "cmds/commands.h"
|
||||||
|
|
||||||
static const char * const inspect_cmd_group_usage[] = {
|
static const char * const inspect_cmd_group_usage[] = {
|
||||||
|
@ -714,17 +715,6 @@ static const char * const cmd_inspect_list_chunks_usage[] = {
|
||||||
NULL
|
NULL
|
||||||
};
|
};
|
||||||
|
|
||||||
enum {
|
|
||||||
CHUNK_SORT_PSTART,
|
|
||||||
CHUNK_SORT_LSTART,
|
|
||||||
CHUNK_SORT_USAGE,
|
|
||||||
/* Length, secondary physical start */
|
|
||||||
CHUNK_SORT_LENGTH_P,
|
|
||||||
/* Length, secondary logical start */
|
|
||||||
CHUNK_SORT_LENGTH_L,
|
|
||||||
CHUNK_SORT_DEFAULT = CHUNK_SORT_PSTART
|
|
||||||
};
|
|
||||||
|
|
||||||
struct list_chunks_entry {
|
struct list_chunks_entry {
|
||||||
u64 devid;
|
u64 devid;
|
||||||
u64 start;
|
u64 start;
|
||||||
|
@ -834,7 +824,7 @@ static int cmp_cse_length_logical(const void *va, const void *vb)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int print_list_chunks(struct list_chunks_ctx *ctx, unsigned sort_mode,
|
static int print_list_chunks(struct list_chunks_ctx *ctx, const char* sortmode,
|
||||||
unsigned unit_mode, bool with_usage, bool with_empty)
|
unsigned unit_mode, bool with_usage, bool with_empty)
|
||||||
{
|
{
|
||||||
u64 devid;
|
u64 devid;
|
||||||
|
@ -846,6 +836,47 @@ static int print_list_chunks(struct list_chunks_ctx *ctx, unsigned sort_mode,
|
||||||
u64 number;
|
u64 number;
|
||||||
u32 gaps;
|
u32 gaps;
|
||||||
u32 tabidx;
|
u32 tabidx;
|
||||||
|
static const struct sortdef sortit[] = {
|
||||||
|
{ .name = "pstart", .comp = (sort_cmp_t)cmp_cse_devid_start,
|
||||||
|
.desc = "sort by physical srart offset, group by device" },
|
||||||
|
{ .name = "lstart", .comp = (sort_cmp_t)cmp_cse_devid_lstart,
|
||||||
|
.desc = "sort by logical offset" },
|
||||||
|
{ .name = "usage", .comp = (sort_cmp_t)cmp_cse_devid_usage,
|
||||||
|
.desc = "sort by chunk usage" },
|
||||||
|
{ .name = "length_p", .comp = (sort_cmp_t)cmp_cse_length_physical,
|
||||||
|
.desc = "sort by lentgh, secondary by physical offset" },
|
||||||
|
{ .name = "length_l", .comp = (sort_cmp_t)cmp_cse_length_logical,
|
||||||
|
.desc = "sort by lentgh, secondary by logical offset" },
|
||||||
|
};
|
||||||
|
enum {
|
||||||
|
CHUNK_SORT_PSTART,
|
||||||
|
CHUNK_SORT_LSTART,
|
||||||
|
CHUNK_SORT_USAGE,
|
||||||
|
CHUNK_SORT_LENGTH_P,
|
||||||
|
CHUNK_SORT_LENGTH_L,
|
||||||
|
CHUNK_SORT_DEFAULT = CHUNK_SORT_PSTART
|
||||||
|
};
|
||||||
|
unsigned int sort_mode;
|
||||||
|
struct compare comp;
|
||||||
|
|
||||||
|
if (!sortmode) {
|
||||||
|
sort_mode = CHUNK_SORT_DEFAULT;
|
||||||
|
sortmode = "pstart";
|
||||||
|
} else if (strcmp(sortmode, "pstart") == 0) {
|
||||||
|
sort_mode = CHUNK_SORT_PSTART;
|
||||||
|
} else if (strcmp(sortmode, "lstart") == 0) {
|
||||||
|
sort_mode = CHUNK_SORT_LSTART;
|
||||||
|
} else if (strcmp(sortmode, "usage") == 0) {
|
||||||
|
sort_mode = CHUNK_SORT_USAGE;
|
||||||
|
with_usage = true;
|
||||||
|
} else if (strcmp(sortmode, "length_p") == 0) {
|
||||||
|
sort_mode = CHUNK_SORT_LENGTH_P;
|
||||||
|
} else if (strcmp(sortmode, "length_l") == 0) {
|
||||||
|
sort_mode = CHUNK_SORT_LENGTH_L;
|
||||||
|
} else {
|
||||||
|
error("unknown sort mode: %s", sortmode);
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Chunks are sorted logically as found by the ioctl, we need to sort
|
* Chunks are sorted logically as found by the ioctl, we need to sort
|
||||||
|
@ -869,18 +900,10 @@ static int print_list_chunks(struct list_chunks_ctx *ctx, unsigned sort_mode,
|
||||||
lastend = e.start + e.length;
|
lastend = e.start + e.length;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (sort_mode == CHUNK_SORT_LSTART)
|
compare_init(&comp, sortit);
|
||||||
qsort(ctx->stats, ctx->length, sizeof(ctx->stats[0]),
|
compare_add_sort_key(&comp, sortmode);
|
||||||
cmp_cse_devid_lstart);
|
qsort_r(ctx->stats, ctx->length, sizeof(ctx->stats[0]), (sort_r_cmp_t)compare_cmp_multi,
|
||||||
else if (sort_mode == CHUNK_SORT_USAGE)
|
&comp);
|
||||||
qsort(ctx->stats, ctx->length, sizeof(ctx->stats[0]),
|
|
||||||
cmp_cse_devid_usage);
|
|
||||||
else if (sort_mode == CHUNK_SORT_LENGTH_P)
|
|
||||||
qsort(ctx->stats, ctx->length, sizeof(ctx->stats[0]),
|
|
||||||
cmp_cse_length_physical);
|
|
||||||
else if (sort_mode == CHUNK_SORT_LENGTH_L)
|
|
||||||
qsort(ctx->stats, ctx->length, sizeof(ctx->stats[0]),
|
|
||||||
cmp_cse_length_logical);
|
|
||||||
|
|
||||||
/* Optional usage, two rows for header and separator, gaps */
|
/* Optional usage, two rows for header and separator, gaps */
|
||||||
table = table_create(7 + (int)with_usage, 2 + ctx->length + gaps);
|
table = table_create(7 + (int)with_usage, 2 + ctx->length + gaps);
|
||||||
|
@ -1003,7 +1026,7 @@ static int cmd_inspect_list_chunks(const struct cmd_struct *cmd,
|
||||||
int e;
|
int e;
|
||||||
DIR *dirstream = NULL;
|
DIR *dirstream = NULL;
|
||||||
unsigned unit_mode;
|
unsigned unit_mode;
|
||||||
unsigned sort_mode = 0;
|
char *sortmode = NULL;
|
||||||
bool with_usage = true;
|
bool with_usage = true;
|
||||||
bool with_empty = true;
|
bool with_empty = true;
|
||||||
const char *path;
|
const char *path;
|
||||||
|
@ -1036,21 +1059,8 @@ static int cmd_inspect_list_chunks(const struct cmd_struct *cmd,
|
||||||
|
|
||||||
switch (c) {
|
switch (c) {
|
||||||
case GETOPT_VAL_SORT:
|
case GETOPT_VAL_SORT:
|
||||||
if (strcmp(optarg, "pstart") == 0) {
|
free(sortmode);
|
||||||
sort_mode = CHUNK_SORT_PSTART;
|
sortmode = strdup(optarg);
|
||||||
} else if (strcmp(optarg, "lstart") == 0) {
|
|
||||||
sort_mode = CHUNK_SORT_LSTART;
|
|
||||||
} else if (strcmp(optarg, "usage") == 0) {
|
|
||||||
sort_mode = CHUNK_SORT_USAGE;
|
|
||||||
with_usage = true;
|
|
||||||
} else if (strcmp(optarg, "length_p") == 0) {
|
|
||||||
sort_mode = CHUNK_SORT_LENGTH_P;
|
|
||||||
} else if (strcmp(optarg, "length_l") == 0) {
|
|
||||||
sort_mode = CHUNK_SORT_LENGTH_L;
|
|
||||||
} else {
|
|
||||||
error("unknown sort mode: %s", optarg);
|
|
||||||
exit(1);
|
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
case GETOPT_VAL_USAGE:
|
case GETOPT_VAL_USAGE:
|
||||||
case GETOPT_VAL_NO_USAGE:
|
case GETOPT_VAL_NO_USAGE:
|
||||||
|
@ -1181,7 +1191,7 @@ static int cmd_inspect_list_chunks(const struct cmd_struct *cmd,
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
ret = print_list_chunks(&ctx, sort_mode, unit_mode, with_usage, with_empty);
|
ret = print_list_chunks(&ctx, sortmode, unit_mode, with_usage, with_empty);
|
||||||
close_file_or_dir(fd, dirstream);
|
close_file_or_dir(fd, dirstream);
|
||||||
|
|
||||||
out_nomem:
|
out_nomem:
|
||||||
|
|
Loading…
Reference in New Issue