fsck_util: improve fsck output format

Now the built-in fsck handler and `bookmarkctl fsck` produces
output that is both parsable and human-readable.

Also document the output format in the user manual.
This commit is contained in:
CismonX 2025-03-30 14:10:31 +08:00
parent cbda096f44
commit 159c2c7625
No known key found for this signature in database
GPG key ID: 3094873E29A482FB
5 changed files with 46 additions and 31 deletions

View file

@ -603,6 +603,9 @@ bookmarkctl fsck @var{pathname}
Path to the directory to perform checks on.
@end table
The output shares the same format with the built-in fsck handler.
@xref{Filesystem-Check Output Format}.
For the full fsck functionalities, @pxref{fsck.bookmarkfs}.
@item xattr-list
@ -3235,6 +3238,30 @@ Defaults to @samp{_}.
For each bookmark entry, the built-in handler prints a message
to standard output explaining why the bookmark name is invalid.
@anchor{Filesystem-Check Output Format}
@cindex Filesystem-Check Output Format
Output format (with an ASCII HT character separating each item):
@example
@var{id} @var{why} @var{extra} @var{name}
@end example
@table @var
@item why
Name of the result code, without the @samp{BOOKMARKFS_FSCK_RESULT_} prefix.
@xref{Filesystem-Check Result Code}.
@item id
@itemx extra
@itemx name
Information of this entry.
@xref{Filesystem-Check Data}.
Integers are printed in decimal format.
ASCII control characters in @var{name} are replaced with @samp{?}.
@end table
When the @option{-o repair} option is given, the handler renames the bookmark
according to the following rules:

View file

@ -157,7 +157,7 @@ subcmd_fsck (
log_printf("ioctl(): %s", strerror(errno));
break;
}
if (0 != explain_fsck_result(status, &fsck_data)) {
if (0 != print_fsck_result(status, &fsck_data)) {
break;
}
} while (status != BOOKMARKFS_FSCK_RESULT_END);

View file

@ -282,7 +282,7 @@ handle_entry (
}
struct bookmarkfs_fsck_data *entry_data = &entry->data;
if (0 != explain_fsck_result(why, entry_data)) {
if (0 != print_fsck_result(why, entry_data)) {
return -1;
}

View file

@ -34,46 +34,34 @@
#include "xstd.h"
int
explain_fsck_result (
print_fsck_result (
enum bookmarkfs_fsck_result result,
struct bookmarkfs_fsck_data const *data
) {
char name_buf[sizeof(data->name)];
translit_control_chars(name_buf, sizeof(name_buf), data->name, '?');
#define PRINT_FSCK_RESULT(s, ...) \
printf("bookmark %" PRIu64 " name '%.*s' " s "\n", data->id, \
(int)sizeof(name_buf), name_buf, __VA_ARGS__);
char *result_str;
switch (result) {
case BOOKMARKFS_FSCK_RESULT_END:
break;
return 0;
case BOOKMARKFS_FSCK_RESULT_NAME_DUPLICATE:
PRINT_FSCK_RESULT("duplicates with %" PRIu64, data->extra);
break;
case BOOKMARKFS_FSCK_RESULT_NAME_BADCHAR:
PRINT_FSCK_RESULT("contains a bad character at offset %" PRIu64,
data->extra);
break;
case BOOKMARKFS_FSCK_RESULT_NAME_BADLEN:
PRINT_FSCK_RESULT("has invalid length %" PRIu64, data->extra);
break;
case BOOKMARKFS_FSCK_RESULT_NAME_DOTDOT:
PRINT_FSCK_RESULT("%s", "is invalid (must not be '.' or '..')");
break;
case BOOKMARKFS_FSCK_RESULT_NAME_INVALID:
PRINT_FSCK_RESULT("is invalid (reason number %" PRIu64 ")",
data->extra);
#define FSCK_RESULT(result) \
case BOOKMARKFS_FSCK_RESULT_##result: \
result_str = #result; \
break;
FSCK_RESULT(NAME_DUPLICATE)
FSCK_RESULT(NAME_BADCHAR)
FSCK_RESULT(NAME_BADLEN)
FSCK_RESULT(NAME_DOTDOT)
FSCK_RESULT(NAME_INVALID)
default:
log_printf("unknown fsck result code: %d", result);
return -1;
}
char name_buf[sizeof(data->name)];
translit_control_chars(name_buf, sizeof(name_buf), data->name, '?');
printf("%" PRIu64 "\t%s\t%" PRIu64 "\t%.*s\n", data->id, result_str,
data->extra, (int)sizeof(name_buf), name_buf);
return 0;
}

View file

@ -28,7 +28,7 @@
#include "common.h"
int
explain_fsck_result (
print_fsck_result (
enum bookmarkfs_fsck_result result,
struct bookmarkfs_fsck_data const *data
);