Skip to content

Commit

Permalink
Add kdump_set_filenames() as an easy API to set multiple names
Browse files Browse the repository at this point in the history
Provide an easier-to-use API to set descriptive file names.

Signed-off-by: Petr Tesarik <petr@tesarici.cz>
  • Loading branch information
ptesarik committed Nov 11, 2023
1 parent 3e8b619 commit 5a468f2
Show file tree
Hide file tree
Showing 5 changed files with 151 additions and 1 deletion.
12 changes: 12 additions & 0 deletions include/libkdumpfile/kdumpfile.h.in
Original file line number Diff line number Diff line change
Expand Up @@ -317,6 +317,18 @@ uint_fast32_t kdump_d32toh(kdump_ctx_t *ctx, uint_fast32_t val);
*/
uint_fast64_t kdump_d64toh(kdump_ctx_t *ctx, uint_fast64_t val);

/** Set descriptive file names.
* @param ctx Dump file object.
* @param n Number of names in @p names.
* @param names Names. @c NULL means clear the name.
* @returns Error status.
*
* Set the optional file names. These names are used in error messages to give
* humans a clue which file of a multi-file dump the error is related.
*/
kdump_status kdump_set_filenames(kdump_ctx_t *ctx, unsigned n,
const char *const *names);

/** Open a set of dump files.
* @param ctx Dump file object.
* @param nfds Number of file descriptors in @p fds.
Expand Down
2 changes: 1 addition & 1 deletion src/kdumpfile/Makefile.am
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ libkdumpfile_la_LIBADD = \
$(SNAPPY_LIBS) \
$(ZSTD_LIBS)

libkdumpfile_la_LDFLAGS = -version-info 10:2:0
libkdumpfile_la_LDFLAGS = -version-info 11:0:1

if HAVE_LD_VERSION_SCRIPT
libkdumpfile_la_LDFLAGS += -Wl,--version-script=$(srcdir)/libkdumpfile.map
Expand Down
1 change: 1 addition & 0 deletions src/kdumpfile/libkdumpfile.map
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ LIBKDUMPFILE_0 {
kdump_d32toh;
kdump_d64toh;

kdump_set_filenames;
kdump_open_fdset;
kdump_read;
kdump_read_string;
Expand Down
40 changes: 40 additions & 0 deletions src/kdumpfile/open.c
Original file line number Diff line number Diff line change
Expand Up @@ -376,6 +376,46 @@ clear_all_fds(kdump_ctx_t *ctx)
}
}

kdump_status
kdump_set_filenames(kdump_ctx_t *ctx, unsigned n, const char *const *names)
{
struct attr_data *dir;
kdump_status status;

clear_error(ctx);

if (get_num_files(ctx) < n &&
(status = set_attr_number(ctx, gattr(ctx, GKI_num_files),
ATTR_PERSIST, n)) != KDUMP_OK)
return set_error(ctx, status,
"Cannot initialize file set size");

for (dir = gattr(ctx, GKI_dir_file_set)->dir; dir; dir = dir->next) {
struct attr_data *child;
unsigned fidx;

if (dir->template->type != KDUMP_DIRECTORY)
continue;
fidx = dir->template->fidx;
if (fidx >= n)
continue;
child = lookup_dir_attr(ctx->dict, dir, "name", 4);
if (!child)
continue;

if (names[fidx]) {
status = set_attr_string(ctx, child, ATTR_PERSIST,
names[fidx]);
if (status != KDUMP_OK)
return set_error(ctx, status, "%s",
err_filename(ctx, fidx));
} else
clear_attr(ctx, child);
}

return KDUMP_OK;
}

DEFINE_ALIAS(open_fdset);

kdump_status
Expand Down
97 changes: 97 additions & 0 deletions tests/fdset.c
Original file line number Diff line number Diff line change
Expand Up @@ -205,6 +205,7 @@ main(int argc, char **argv)
kdump_attr_t attr;
kdump_ctx_t *ctx;
kdump_status status;
const char *names[2];
int fd;
int ret;
int rc;
Expand Down Expand Up @@ -555,6 +556,102 @@ main(int argc, char **argv)
else if (rc != TEST_OK)
ret = rc;

/*************************************************************
* RESET.
*/
attr.type = KDUMP_NUMBER;
attr.val.number = 0;
status = kdump_attr_ref_set(ctx, &number, &attr);
if (status != KDUMP_OK) {
fprintf(stderr, "Cannot clean up the file set: %s\n",
kdump_get_err(ctx));
rc = TEST_FAIL;
}

/*************************************************************
* Unset file names.
*/
names[0] = NULL;
names[1] = NULL;
status = kdump_set_filenames(ctx, 2, names);
if (status != KDUMP_OK) {
fprintf(stderr, "Cannot set file names: %s\n",
kdump_get_err(ctx));
rc = TEST_FAIL;
}

/* Check that fdset size is two. */
rc = check_fileset_size(ctx, 2);
if (rc == TEST_ERR)
return rc;
else if (rc != TEST_OK)
ret = rc;

/* Check that file.set.0.name and file.set.1.name are unset */
rc = check_unset_file(ctx, &fileset, "0.name", KDUMP_STRING);
if (rc == TEST_ERR)
return rc;
else if (rc != TEST_OK)
ret = rc;
rc = check_unset_file(ctx, &fileset, "1.name", KDUMP_STRING);
if (rc == TEST_ERR)
return rc;
else if (rc != TEST_OK)
ret = rc;

/*************************************************************
* Real file names.
*/
names[0] = FILENAME_0;
names[1] = FILENAME_1;
status = kdump_set_filenames(ctx, 2, names);
if (status != KDUMP_OK) {
fprintf(stderr, "Cannot set file names: %s\n",
kdump_get_err(ctx));
rc = TEST_FAIL;
}

/* Check that fdset size is two. */
rc = check_fileset_size(ctx, 2);
if (rc == TEST_ERR)
return rc;
else if (rc != TEST_OK)
ret = rc;

/* Verify file.set.0.name and file.set.1.name. */
rc = check_filename(ctx, &fileset, "0.name", FILENAME_0);
if (rc == TEST_ERR)
return rc;
else if (rc != TEST_OK)
ret = rc;
rc = check_filename(ctx, &fileset, "1.name", FILENAME_1);
if (rc == TEST_ERR)
return rc;
else if (rc != TEST_OK)
ret = rc;

/* Set the file descriptor and reduce the set to one file. */
status = kdump_open_fd(ctx, fd);
if (status != KDUMP_OK && status != KDUMP_ERR_NOTIMPL) {
fprintf(stderr, "Cannot set dump file descriptor: %s\n",
kdump_get_err(ctx));
return TEST_ERR;
}

/* Verify file.set.0.name is still set. */
rc = check_filename(ctx, &fileset, "0.name", FILENAME_0);
if (rc == TEST_ERR)
return rc;
else if (rc != TEST_OK)
ret = rc;

/* But file.set.1.name no longer exists. */
rc = check_not_exist(ctx, &fileset, "1.name");
if (rc == TEST_ERR)
return rc;
else if (rc != TEST_OK)
ret = rc;

/*************************************************************
* Clean up.
*/
Expand Down

0 comments on commit 5a468f2

Please sign in to comment.