From c54998209d2b2c51981315522b2ddb6a68f843a2 Mon Sep 17 00:00:00 2001 From: Zdenek Kabelac Date: Fri, 20 Jan 2012 16:59:58 +0000 Subject: [PATCH] Update lvdisplay to show more info about thin LVs Reformat name and path how the LV is represented with lvm1 compatible option, to switch to the old way - which had number of problem - i.e. many links do not exist - since for private devices we are not creating them. Add more info about thin pools and volumes. --- WHATS_NEW | 1 + doc/example.conf.in | 5 +++ lib/config/defaults.h | 1 + lib/display/display.c | 99 +++++++++++++++++++++++++++++++++---------- 4 files changed, 83 insertions(+), 23 deletions(-) diff --git a/WHATS_NEW b/WHATS_NEW index 80c57803f..71bc85f30 100644 --- a/WHATS_NEW +++ b/WHATS_NEW @@ -1,5 +1,6 @@ Version 2.02.89 - ================================== + Update lvdisplay with backward compat. config opt. lvm1_compatible_display. Do not report linear segtype for non-striped targets. Keep info about creation host and time for each logical volume. Make error message hit when preallocated memlock memory exceeded clearer. diff --git a/doc/example.conf.in b/doc/example.conf.in index 5dbe15d9f..00ff3421a 100644 --- a/doc/example.conf.in +++ b/doc/example.conf.in @@ -445,6 +445,11 @@ global { # Specify the '--type ' option to override this default # setting. mirror_segtype_default = "mirror" + + # Whether to lvdisplay LV name in lvm1 compatible format /dev/vgname/lvname + # Default is now to display LV name and path (if exists) separately. + # If the old behavior is preffered use set to 1. + # lvm1_compatible_display = 1 } activation { diff --git a/lib/config/defaults.h b/lib/config/defaults.h index 2a62856d3..13d8c31cf 100644 --- a/lib/config/defaults.h +++ b/lib/config/defaults.h @@ -49,6 +49,7 @@ #define DEFAULT_PRIORITISE_WRITE_LOCKS 1 #define DEFAULT_USE_MLOCKALL 0 #define DEFAULT_METADATA_READ_ONLY 0 +#define DEFAULT_LVM1_COMPATIBLE_DISPLAY 0 #define DEFAULT_MIRROR_SEGTYPE "mirror" #define DEFAULT_MIRRORLOG "disk" diff --git a/lib/display/display.c b/lib/display/display.c index 9f3f187af..df21009a4 100644 --- a/lib/display/display.c +++ b/lib/display/display.c @@ -19,6 +19,7 @@ #include "activate.h" #include "toolcontext.h" #include "segtype.h" +#include "defaults.h" #define SIZE_BUF 128 @@ -503,7 +504,13 @@ int lvdisplay_full(struct cmd_context *cmd, char uuid[64] __attribute__((aligned(8))); const char *access_str; struct lv_segment *snap_seg = NULL, *mirror_seg = NULL; + struct lv_segment *seg = NULL; + int lvm1compat; percent_t snap_percent; + int thin_data_active = 0, thin_metadata_active = 0; + percent_t thin_data_percent, thin_metadata_percent; + int thin_active = 0; + percent_t thin_percent; if (!id_write_format(&lv->lvid.id[1], uuid, sizeof(uuid))) return_0; @@ -519,13 +526,28 @@ int lvdisplay_full(struct cmd_context *cmd, log_print("--- Logical volume ---"); - log_print("LV Name %s%s/%s", lv->vg->cmd->dev_dir, - lv->vg->name, lv->name); + lvm1compat = find_config_tree_int(cmd, "global/lvm1_compatible_display", + DEFAULT_LVM1_COMPATIBLE_DISPLAY); + + if (lvm1compat) { + /* Note: Invisible devices do not get /dev/vg/lv */ + log_print("LV Name %s%s/%s", + lv->vg->cmd->dev_dir, lv->vg->name, lv->name); + } else if (lv_is_visible(lv)) { + /* Thin pool does not have /dev/vg/name link */ + if (!lv_is_thin_pool(lv)) + log_print("LV Path %s%s/%s", + lv->vg->cmd->dev_dir, + lv->vg->name, lv->name); + log_print("LV Name %s", lv->name); + } else + log_print("Invisible LV Name %s", lv->name); + log_print("VG Name %s", lv->vg->name); - log_print("LV UUID %s", uuid); - log_print("LV Write Access %s", access_str); + log_print("LV Creation host, time %s, %s", + lv_host_dup(cmd->mem, lv), lv_time_dup(cmd->mem, lv)); if (lv_is_origin(lv)) { log_print("LV snapshot status source of"); @@ -537,10 +559,15 @@ int lvdisplay_full(struct cmd_context *cmd, &snap_percent))) if (snap_percent == PERCENT_INVALID) snap_active = 0; - log_print(" %s%s/%s [%s]", - lv->vg->cmd->dev_dir, lv->vg->name, - snap_seg->cow->name, - snap_active ? "active" : "INACTIVE"); + if (lvm1compat) + log_print(" %s%s/%s [%s]", + lv->vg->cmd->dev_dir, lv->vg->name, + snap_seg->cow->name, + snap_active ? "active" : "INACTIVE"); + else + log_print(" %s [%s]", + snap_seg->cow->name, + snap_active ? "active" : "INACTIVE"); } snap_seg = NULL; } else if ((snap_seg = find_cow(lv))) { @@ -550,25 +577,39 @@ int lvdisplay_full(struct cmd_context *cmd, if (snap_percent == PERCENT_INVALID) snap_active = 0; - log_print("LV snapshot status %s destination for %s%s/%s", - snap_active ? "active" : "INACTIVE", - lv->vg->cmd->dev_dir, lv->vg->name, - snap_seg->origin->name); + if (lvm1compat) + log_print("LV snapshot status %s destination for %s%s/%s", + snap_active ? "active" : "INACTIVE", + lv->vg->cmd->dev_dir, lv->vg->name, + snap_seg->origin->name); + else + log_print("LV snapshot status %s destination for %s", + snap_active ? "active" : "INACTIVE", + snap_seg->origin->name); } if (lv_is_thin_volume(lv)) { - log_print("LV Thin pool %s%s/%s", lv->vg->cmd->dev_dir, - lv->vg->name, first_seg(lv)->pool_lv->name); + seg = first_seg(lv); + log_print("LV Pool name %s", seg->pool_lv->name); + if (seg->origin) + log_print("LV Thin origin name %s", + seg->origin->name); + if (inkernel) + thin_active = lv_thin_percent(lv, 0, &thin_percent); } else if (lv_is_thin_pool(lv)) { + if (inkernel) { + thin_data_active = lv_thin_pool_percent(lv, 0, &thin_data_percent); + thin_metadata_active = lv_thin_pool_percent(lv, 1, &thin_metadata_percent); + } /* FIXME: display thin_pool targets transid for activated LV as well */ - log_print("LV Thin transaction ID %" PRIu64, - first_seg(lv)->transaction_id); - log_print("LV Thin metadata %s%s/%s", lv->vg->cmd->dev_dir, - lv->vg->name, first_seg(lv)->metadata_lv->name); - log_print("LV Thin data pool %s%s/%s", lv->vg->cmd->dev_dir, - lv->vg->name, seg_lv(first_seg(lv), 0)->name); + seg = first_seg(lv); + log_print("LV Pool transaction ID %" PRIu64, seg->transaction_id); + log_print("LV Pool metadata %s", seg->metadata_lv->name); + log_print("LV Pool data %s", seg_lv(seg, 0)->name); + log_print("LV Pool chunk size %s", + display_size(cmd, seg->data_block_size)); log_print("LV Zero new blocks %s", - first_seg(lv)->zero_new_blocks ? "yes" : "no"); + seg->zero_new_blocks ? "yes" : "no"); } if (inkernel && info.suspended) @@ -588,6 +629,18 @@ int lvdisplay_full(struct cmd_context *cmd, display_size(cmd, snap_seg ? snap_seg->origin->size : lv->size)); + if (thin_data_active) + log_print("Allocated pool data %.2f%%", + percent_to_float(thin_data_percent)); + + if (thin_metadata_active) + log_print("Allocated metadata %.2f%%", + percent_to_float(thin_metadata_percent)); + + if (thin_active) + log_print("Mapped size %.2f%%", + percent_to_float(thin_percent)); + log_print("Current LE %u", snap_seg ? snap_seg->origin->le_count : lv->le_count); @@ -597,7 +650,7 @@ int lvdisplay_full(struct cmd_context *cmd, log_print("COW-table LE %u", lv->le_count); if (snap_active) - log_print("Allocated to snapshot %.2f%% ", + log_print("Allocated to snapshot %.2f%%", percent_to_float(snap_percent)); log_print("Snapshot chunk size %s", @@ -605,7 +658,7 @@ int lvdisplay_full(struct cmd_context *cmd, } if (lv->status & MIRRORED) { - mirror_seg = first_seg(lv); + mirror_seg = first_seg(lv); log_print("Mirrored volumes %" PRIu32, mirror_seg->area_count); if (lv->status & CONVERTING) log_print("LV type Mirror undergoing conversion");