1
0
mirror of git://sourceware.org/git/lvm2.git synced 2024-12-21 13:34:40 +03:00

Add support for querying a device's inactive table.

Currently this data is invisible to userspace.
Requires dm >= 4.16 (likely to be in linux 2.6.33).
This commit is contained in:
Alasdair Kergon 2009-11-06 00:43:08 +00:00
parent 6ddadf4023
commit 9abf5e70be
9 changed files with 82 additions and 7 deletions

View File

@ -1,5 +1,7 @@
Version 1.02.40 - Version 1.02.40 -
=================================== ===================================
Add dmsetup --inactive support.
Add dm_task_query_inactive_table to libdevmapper for kernel driver >= 4.16.
Fix hash lookup segfault when keys compared are different lengths. Fix hash lookup segfault when keys compared are different lengths.
Version 1.02.39 - 26th October 2009 Version 1.02.39 - 26th October 2009

View File

@ -40,6 +40,7 @@ dm_task_add_target
dm_task_no_flush dm_task_no_flush
dm_task_no_open_count dm_task_no_open_count
dm_task_skip_lockfs dm_task_skip_lockfs
dm_task_query_inactive_table
dm_task_update_nodes dm_task_update_nodes
dm_task_run dm_task_run
dm_get_next_target dm_get_next_target

View File

@ -1135,6 +1135,13 @@ int dm_task_skip_lockfs(struct dm_task *dmt)
return 1; return 1;
} }
int dm_task_query_inactive_table(struct dm_task *dmt)
{
dmt->query_inactive_table = 1;
return 1;
}
int dm_task_set_event_nr(struct dm_task *dmt, uint32_t event_nr) int dm_task_set_event_nr(struct dm_task *dmt, uint32_t event_nr)
{ {
dmt->event_nr = event_nr; dmt->event_nr = event_nr;
@ -1382,6 +1389,12 @@ static struct dm_ioctl *_flatten(struct dm_task *dmt, unsigned repeat_count)
dmi->flags |= DM_READONLY_FLAG; dmi->flags |= DM_READONLY_FLAG;
if (dmt->skip_lockfs) if (dmt->skip_lockfs)
dmi->flags |= DM_SKIP_LOCKFS_FLAG; dmi->flags |= DM_SKIP_LOCKFS_FLAG;
if (dmt->query_inactive_table) {
if (_dm_version_minor < 16)
log_warn("WARNING: Inactive table query unsupported "
"by kernel. It will use live table.");
dmi->flags |= DM_QUERY_INACTIVE_TABLE_FLAG;
}
dmi->target_count = count; dmi->target_count = count;
dmi->event_nr = dmt->event_nr; dmi->event_nr = dmt->event_nr;
@ -1723,7 +1736,7 @@ static struct dm_ioctl *_do_dm_ioctl(struct dm_task *dmt, unsigned command,
} }
log_debug("dm %s %s %s%s%s %s%.0d%s%.0d%s" log_debug("dm %s %s %s%s%s %s%.0d%s%.0d%s"
"%s%c%c%s %.0" PRIu64 " %s [%u]", "%s%c%c%s%s %.0" PRIu64 " %s [%u]",
_cmd_data_v4[dmt->type].name, _cmd_data_v4[dmt->type].name,
dmi->name, dmi->uuid, dmt->newname ? " " : "", dmi->name, dmi->uuid, dmt->newname ? " " : "",
dmt->newname ? dmt->newname : "", dmt->newname ? dmt->newname : "",
@ -1736,6 +1749,7 @@ static struct dm_ioctl *_do_dm_ioctl(struct dm_task *dmt, unsigned command,
dmt->no_open_count ? 'N' : 'O', dmt->no_open_count ? 'N' : 'O',
dmt->no_flush ? 'N' : 'F', dmt->no_flush ? 'N' : 'F',
dmt->skip_lockfs ? "S " : "", dmt->skip_lockfs ? "S " : "",
dmt->query_inactive_table ? "I " : "",
dmt->sector, dmt->message ? dmt->message : "", dmt->sector, dmt->message ? dmt->message : "",
dmi->data_size); dmi->data_size);
#ifdef DM_IOCTLS #ifdef DM_IOCTLS

View File

@ -58,6 +58,7 @@ struct dm_task {
int no_flush; int no_flush;
int no_open_count; int no_open_count;
int skip_lockfs; int skip_lockfs;
int query_inactive_table;
int suppress_identical_reload; int suppress_identical_reload;
uint64_t existing_table_size; uint64_t existing_table_size;
int cookie_set; int cookie_set;

View File

@ -172,6 +172,7 @@ int dm_task_set_sector(struct dm_task *dmt, uint64_t sector);
int dm_task_no_flush(struct dm_task *dmt); int dm_task_no_flush(struct dm_task *dmt);
int dm_task_no_open_count(struct dm_task *dmt); int dm_task_no_open_count(struct dm_task *dmt);
int dm_task_skip_lockfs(struct dm_task *dmt); int dm_task_skip_lockfs(struct dm_task *dmt);
int dm_task_query_inactive_table(struct dm_task *dmt);
int dm_task_suppress_identical_reload(struct dm_task *dmt); int dm_task_suppress_identical_reload(struct dm_task *dmt);
/* /*

View File

@ -181,6 +181,7 @@ struct dm_task *dm_task_create(int type)
dmt->read_ahead_flags = 0; dmt->read_ahead_flags = 0;
dmt->event_nr = 0; dmt->event_nr = 0;
dmt->cookie_set = 0; dmt->cookie_set = 0;
dmt->query_inactive_table = 0;
return dmt; return dmt;
} }

View File

@ -1,6 +1,6 @@
/* /*
* Copyright (C) 2001 - 2003 Sistina Software (UK) Limited. * Copyright (C) 2001 - 2003 Sistina Software (UK) Limited.
* Copyright (C) 2004 - 2005 Red Hat, Inc. All rights reserved. * Copyright (C) 2004 - 2009 Red Hat, Inc. All rights reserved.
* *
* This file is released under the LGPL. * This file is released under the LGPL.
*/ */
@ -268,9 +268,9 @@ enum {
#define DM_DEV_SET_GEOMETRY _IOWR(DM_IOCTL, DM_DEV_SET_GEOMETRY_CMD, struct dm_ioctl) #define DM_DEV_SET_GEOMETRY _IOWR(DM_IOCTL, DM_DEV_SET_GEOMETRY_CMD, struct dm_ioctl)
#define DM_VERSION_MAJOR 4 #define DM_VERSION_MAJOR 4
#define DM_VERSION_MINOR 15 #define DM_VERSION_MINOR 16
#define DM_VERSION_PATCHLEVEL 0 #define DM_VERSION_PATCHLEVEL 0
#define DM_VERSION_EXTRA "-ioctl (2009-04-01)" #define DM_VERSION_EXTRA "-ioctl (2009-11-05)"
/* Status bits */ /* Status bits */
#define DM_READONLY_FLAG (1 << 0) /* In/Out */ #define DM_READONLY_FLAG (1 << 0) /* In/Out */
@ -311,4 +311,11 @@ enum {
*/ */
#define DM_NOFLUSH_FLAG (1 << 11) /* In */ #define DM_NOFLUSH_FLAG (1 << 11) /* In */
/*
* If set, any table information returned will relate to the inactive
* table instead of the live one. Always check DM_INACTIVE_PRESENT_FLAG
* is set before using the data returned.
*/
#define DM_QUERY_INACTIVE_TABLE_FLAG (1 << 12) /* In */
#endif /* _LINUX_DM_IOCTL_H */ #endif /* _LINUX_DM_IOCTL_H */

View File

@ -107,6 +107,11 @@ Invoking the command as \fBdevmap_name\fP is equivalent to
.IP \fB-c|-C|--columns .IP \fB-c|-C|--columns
.br .br
Display output in columns rather than as Field: Value lines. Display output in columns rather than as Field: Value lines.
.IP \fB--inactive
.br
When returning any table information from the kernel report on the
inactive table instead of the live table.
Requires kernel driver version 4.16.0 or above.
.IP \fB-j|--major\ \fImajor .IP \fB-j|--major\ \fImajor
.br .br
Specify the major number. Specify the major number.
@ -277,7 +282,7 @@ Sets the device geometry to C/H/S.
Splits given device name into subsystem constituents. Splits given device name into subsystem constituents.
Default subsystem is LVM. Default subsystem is LVM.
.IP \fBstatus .IP \fBstatus
.I [--target target_type] .I [--target target_type] [--inactive]
.I [device_name] .I [device_name]
.br .br
Outputs status information for each of the device's targets. Outputs status information for each of the device's targets.
@ -296,7 +301,7 @@ Some targets such as recent (October 2006) versions of multipath may support
the --noflush option. This lets outstanding I/O that has not yet reached the the --noflush option. This lets outstanding I/O that has not yet reached the
device to remain unflushed. device to remain unflushed.
.IP \fBtable .IP \fBtable
.I [--target target_type] .I [--target target_type] [--inactive]
.I [device_name] .I [device_name]
.br .br
Outputs the current table for the device in a format that can be fed Outputs the current table for the device in a format that can be fed

View File

@ -117,6 +117,7 @@ enum {
EXEC_ARG, EXEC_ARG,
FORCE_ARG, FORCE_ARG,
GID_ARG, GID_ARG,
INACTIVE_ARG,
MAJOR_ARG, MAJOR_ARG,
MINOR_ARG, MINOR_ARG,
MODE_ARG, MODE_ARG,
@ -296,6 +297,9 @@ static struct dm_task *_get_deps_task(int major, int minor)
if (_switches[NOOPENCOUNT_ARG] && !dm_task_no_open_count(dmt)) if (_switches[NOOPENCOUNT_ARG] && !dm_task_no_open_count(dmt))
goto err; goto err;
if (_switches[INACTIVE_ARG] && !dm_task_query_inactive_table(dmt))
goto err;
if (!dm_task_run(dmt)) if (!dm_task_run(dmt))
goto err; goto err;
@ -530,6 +534,9 @@ static int _load(int argc, char **argv, void *data __attribute((unused)))
if (_switches[NOOPENCOUNT_ARG] && !dm_task_no_open_count(dmt)) if (_switches[NOOPENCOUNT_ARG] && !dm_task_no_open_count(dmt))
goto out; goto out;
if (_switches[INACTIVE_ARG] && !dm_task_query_inactive_table(dmt))
goto out;
if (!dm_task_run(dmt)) if (!dm_task_run(dmt))
goto out; goto out;
@ -587,6 +594,9 @@ static int _create(int argc, char **argv, void *data __attribute((unused)))
if (_switches[NOOPENCOUNT_ARG] && !dm_task_no_open_count(dmt)) if (_switches[NOOPENCOUNT_ARG] && !dm_task_no_open_count(dmt))
goto out; goto out;
if (_switches[INACTIVE_ARG] && !dm_task_query_inactive_table(dmt))
goto out;
if (_switches[READAHEAD_ARG] && if (_switches[READAHEAD_ARG] &&
!dm_task_set_read_ahead(dmt, _int_args[READAHEAD_ARG], !dm_task_set_read_ahead(dmt, _int_args[READAHEAD_ARG],
_read_ahead_flags)) _read_ahead_flags))
@ -630,6 +640,9 @@ static int _rename(int argc, char **argv, void *data __attribute((unused)))
if (_switches[NOOPENCOUNT_ARG] && !dm_task_no_open_count(dmt)) if (_switches[NOOPENCOUNT_ARG] && !dm_task_no_open_count(dmt))
goto out; goto out;
if (_switches[INACTIVE_ARG] && !dm_task_query_inactive_table(dmt))
goto out;
if (!dm_task_set_cookie(dmt, &cookie, 0) || if (!dm_task_set_cookie(dmt, &cookie, 0) ||
!dm_task_run(dmt)) !dm_task_run(dmt))
goto out; goto out;
@ -696,6 +709,9 @@ static int _message(int argc, char **argv, void *data __attribute((unused)))
if (_switches[NOOPENCOUNT_ARG] && !dm_task_no_open_count(dmt)) if (_switches[NOOPENCOUNT_ARG] && !dm_task_no_open_count(dmt))
goto out; goto out;
if (_switches[INACTIVE_ARG] && !dm_task_query_inactive_table(dmt))
goto out;
if (!dm_task_run(dmt)) if (!dm_task_run(dmt))
goto out; goto out;
@ -728,6 +744,12 @@ static int _setgeometry(int argc, char **argv, void *data __attribute((unused)))
if (!dm_task_set_geometry(dmt, argv[1], argv[2], argv[3], argv[4])) if (!dm_task_set_geometry(dmt, argv[1], argv[2], argv[3], argv[4]))
goto out; goto out;
if (_switches[NOOPENCOUNT_ARG] && !dm_task_no_open_count(dmt))
goto out;
if (_switches[INACTIVE_ARG] && !dm_task_query_inactive_table(dmt))
goto out;
/* run the task */ /* run the task */
if (!dm_task_run(dmt)) if (!dm_task_run(dmt))
goto out; goto out;
@ -1002,6 +1024,9 @@ static int _simple(int task, const char *name, uint32_t event_nr, int display)
if (_switches[NOOPENCOUNT_ARG] && !dm_task_no_open_count(dmt)) if (_switches[NOOPENCOUNT_ARG] && !dm_task_no_open_count(dmt))
goto out; goto out;
if (_switches[INACTIVE_ARG] && !dm_task_query_inactive_table(dmt))
goto out;
if (_switches[NOLOCKFS_ARG] && !dm_task_skip_lockfs(dmt)) if (_switches[NOLOCKFS_ARG] && !dm_task_skip_lockfs(dmt))
goto out; goto out;
@ -1115,6 +1140,9 @@ static uint64_t _get_device_size(const char *name)
if (_switches[NOOPENCOUNT_ARG] && !dm_task_no_open_count(dmt)) if (_switches[NOOPENCOUNT_ARG] && !dm_task_no_open_count(dmt))
goto out; goto out;
if (_switches[INACTIVE_ARG] && !dm_task_query_inactive_table(dmt))
goto out;
if (!dm_task_run(dmt)) if (!dm_task_run(dmt))
goto out; goto out;
@ -1162,6 +1190,9 @@ static int _error_device(int argc __attribute((unused)), char **argv __attribute
if (_switches[NOOPENCOUNT_ARG] && !dm_task_no_open_count(dmt)) if (_switches[NOOPENCOUNT_ARG] && !dm_task_no_open_count(dmt))
goto error; goto error;
if (_switches[INACTIVE_ARG] && !dm_task_query_inactive_table(dmt))
goto error;
if (!dm_task_run(dmt)) if (!dm_task_run(dmt))
goto error; goto error;
@ -1337,6 +1368,9 @@ static int _status(int argc, char **argv, void *data)
if (_switches[NOOPENCOUNT_ARG] && !dm_task_no_open_count(dmt)) if (_switches[NOOPENCOUNT_ARG] && !dm_task_no_open_count(dmt))
goto out; goto out;
if (_switches[INACTIVE_ARG] && !dm_task_query_inactive_table(dmt))
goto out;
if (!dm_task_run(dmt)) if (!dm_task_run(dmt))
goto out; goto out;
@ -1458,6 +1492,9 @@ static int _info(int argc, char **argv, void *data)
if (_switches[NOOPENCOUNT_ARG] && !dm_task_no_open_count(dmt)) if (_switches[NOOPENCOUNT_ARG] && !dm_task_no_open_count(dmt))
goto out; goto out;
if (_switches[INACTIVE_ARG] && !dm_task_query_inactive_table(dmt))
goto out;
if (!dm_task_run(dmt)) if (!dm_task_run(dmt))
goto out; goto out;
@ -1496,6 +1533,9 @@ static int _deps(int argc, char **argv, void *data)
if (_switches[NOOPENCOUNT_ARG] && !dm_task_no_open_count(dmt)) if (_switches[NOOPENCOUNT_ARG] && !dm_task_no_open_count(dmt))
goto out; goto out;
if (_switches[INACTIVE_ARG] && !dm_task_query_inactive_table(dmt))
goto out;
if (!dm_task_run(dmt)) if (!dm_task_run(dmt))
goto out; goto out;
@ -2510,7 +2550,7 @@ static void _usage(FILE *out)
fprintf(out, "Usage:\n\n"); fprintf(out, "Usage:\n\n");
fprintf(out, "dmsetup [--version] [-v|--verbose [-v|--verbose ...]]\n" fprintf(out, "dmsetup [--version] [-v|--verbose [-v|--verbose ...]]\n"
" [-r|--readonly] [--noopencount] [--nolockfs]\n" " [-r|--readonly] [--noopencount] [--nolockfs] [--inactive]\n"
" [--noudevsync] [-y|--yes] [--readahead [+]<sectors>|auto|none]\n" " [--noudevsync] [-y|--yes] [--readahead [+]<sectors>|auto|none]\n"
" [-c|-C|--columns] [-o <fields>] [-O|--sort <sort_fields>]\n" " [-c|-C|--columns] [-o <fields>] [-O|--sort <sort_fields>]\n"
" [--nameprefixes] [--noheadings] [--separator <separator>]\n\n"); " [--nameprefixes] [--noheadings] [--separator <separator>]\n\n");
@ -2866,6 +2906,7 @@ static int _process_switches(int *argc, char ***argv, const char *dev_dir)
{"exec", 1, &ind, EXEC_ARG}, {"exec", 1, &ind, EXEC_ARG},
{"force", 0, &ind, FORCE_ARG}, {"force", 0, &ind, FORCE_ARG},
{"gid", 1, &ind, GID_ARG}, {"gid", 1, &ind, GID_ARG},
{"inactive", 0, &ind, INACTIVE_ARG},
{"major", 1, &ind, MAJOR_ARG}, {"major", 1, &ind, MAJOR_ARG},
{"minor", 1, &ind, MINOR_ARG}, {"minor", 1, &ind, MINOR_ARG},
{"mode", 1, &ind, MODE_ARG}, {"mode", 1, &ind, MODE_ARG},
@ -3010,6 +3051,8 @@ static int _process_switches(int *argc, char ***argv, const char *dev_dir)
_switches[TARGET_ARG]++; _switches[TARGET_ARG]++;
_target = optarg; _target = optarg;
} }
if ((ind == INACTIVE_ARG))
_switches[INACTIVE_ARG]++;
if ((ind == NAMEPREFIXES_ARG)) if ((ind == NAMEPREFIXES_ARG))
_switches[NAMEPREFIXES_ARG]++; _switches[NAMEPREFIXES_ARG]++;
if ((ind == NOFLUSH_ARG)) if ((ind == NOFLUSH_ARG))