Define new polling method poll_progress that is caller periodically. The method can return: 0 --- error PROGRESS_TRY_AGAIN --- should be called again after specified interval PROGRESS_UPDATE_METADATA --- should call update_metadata method and continue polling PROGRESS_FINISHED --- should call finish_copy and exit polling The hard-coded mirror-specific code in polldaemon was moved to function poll_mirror_progress. The rest of the polldaemon is mirror-free so it can be used for merging snapshots as well. Signed-off-by: Mikulas Patocka --- tools/lvconvert.c | 1 tools/polldaemon.c | 55 +++++++++++++++++++++++++++++++++++------------------ tools/polldaemon.h | 31 ++++++++++++++++++++--------- tools/pvmove.c | 1 4 files changed, 60 insertions(+), 28 deletions(-) Index: LVM2.2.02.43/tools/lvconvert.c =================================================================== --- LVM2.2.02.43.orig/tools/lvconvert.c 2008-11-25 19:14:34.000000000 +0100 +++ LVM2.2.02.43/tools/lvconvert.c 2008-11-25 19:15:32.000000000 +0100 @@ -330,6 +330,7 @@ static struct poll_functions _lvconvert_ .get_copy_vg = _get_lvconvert_vg, .get_copy_lv = _get_lvconvert_lv, .update_metadata = _update_lvconvert_mirror, + .poll_progress = poll_mirror_progress, .finish_copy = _finish_lvconvert_mirror, }; Index: LVM2.2.02.43/tools/polldaemon.c =================================================================== --- LVM2.2.02.43.orig/tools/polldaemon.c 2008-11-25 19:14:39.000000000 +0100 +++ LVM2.2.02.43/tools/polldaemon.c 2008-11-25 19:15:32.000000000 +0100 @@ -62,6 +62,38 @@ static int _become_daemon(struct cmd_con return 1; } +int poll_mirror_progress(struct cmd_context *cmd, struct volume_group *vg, + struct logical_volume *lv, struct daemon_parms *parms) +{ + float segment_percent = 0.0, overall_percent = 0.0; + int status, overall_status; + uint32_t event_nr = 0; + + if (!(status = lv_mirror_percent(cmd, lv, !parms->interval, + &segment_percent, &event_nr))) { + log_error("ABORTING: Mirror percentage check failed."); + return 0; + } + + overall_status = copy_percent(lv, &overall_percent); + if (parms->progress_display) + log_print("%s: %s: %.1f%%", lv->name, parms->progress_title, + overall_percent); + else + log_verbose("%s: %s: %.1f%%", lv->name, parms->progress_title, + overall_percent); + + if (status < TARGET_STATUS_FINISHED) { + /* The only case the caller *should* try again later */ + return PROGRESS_TRY_AGAIN; + } + + if (overall_status == TARGET_STATUS_FINISHED) + return PROGRESS_FINISHED; + else + return PROGRESS_UPDATE_METADATA; +} + static int _check_lv_status(struct cmd_context *cmd, struct volume_group *vg, struct logical_volume *lv, @@ -69,9 +101,7 @@ static int _check_lv_status(struct cmd_c int *finished) { struct dm_list *lvs_changed; - float segment_percent = 0.0, overall_percent = 0.0; - int status, overall_status; - uint32_t event_nr = 0; + int r; /* By default, caller should not retry */ *finished = 1; @@ -86,22 +116,11 @@ static int _check_lv_status(struct cmd_c return 0; } - if (!(status = lv_mirror_percent(cmd, lv, !parms->interval, - &segment_percent, &event_nr))) { - log_error("ABORTING: Mirror percentage check failed."); + r = parms->poll_fns->poll_progress(cmd, vg, lv, parms); + if (!r) return 0; - } - overall_status = copy_percent(lv, &overall_percent); - if (parms->progress_display) - log_print("%s: %s: %.1f%%", name, parms->progress_title, - overall_percent); - else - log_verbose("%s: %s: %.1f%%", name, parms->progress_title, - overall_percent); - - if (status < TARGET_STATUS_FINISHED) { - /* The only case the caller *should* try again later */ + if (r == PROGRESS_TRY_AGAIN) { *finished = 0; return 1; } @@ -112,7 +131,7 @@ static int _check_lv_status(struct cmd_c } /* Finished? Or progress to next segment? */ - if (overall_status == TARGET_STATUS_FINISHED) { + if (r == PROGRESS_FINISHED) { if (!parms->poll_fns->finish_copy(cmd, vg, lv, lvs_changed)) return 0; } else { Index: LVM2.2.02.43/tools/polldaemon.h =================================================================== --- LVM2.2.02.43.orig/tools/polldaemon.h 2008-11-25 19:13:07.000000000 +0100 +++ LVM2.2.02.43/tools/polldaemon.h 2008-11-25 19:15:32.000000000 +0100 @@ -18,6 +18,19 @@ #include "metadata-exported.h" +struct poll_functions; + +struct daemon_parms { + unsigned interval; + unsigned aborting; + unsigned background; + unsigned outstanding_count; + unsigned progress_display; + const char *progress_title; + uint32_t lv_type; + struct poll_functions *poll_fns; +}; + struct poll_functions { const char *(*get_copy_name_from_lv) (struct logical_volume *lv); struct volume_group *(*get_copy_vg) (struct cmd_context *cmd, @@ -26,6 +39,8 @@ struct poll_functions { struct volume_group *vg, const char *name, uint32_t lv_type); + int (*poll_progress) (struct cmd_context *cmd, struct volume_group *vg, + struct logical_volume *lv, struct daemon_parms *parms); int (*update_metadata) (struct cmd_context *cmd, struct volume_group *vg, struct logical_volume *lv, @@ -36,16 +51,12 @@ struct poll_functions { struct dm_list *lvs_changed); }; -struct daemon_parms { - unsigned interval; - unsigned aborting; - unsigned background; - unsigned outstanding_count; - unsigned progress_display; - const char *progress_title; - uint32_t lv_type; - struct poll_functions *poll_fns; -}; +int poll_mirror_progress(struct cmd_context *cmd, struct volume_group *vg, + struct logical_volume *lv, struct daemon_parms *parms); + +#define PROGRESS_TRY_AGAIN 1 +#define PROGRESS_UPDATE_METADATA 2 +#define PROGRESS_FINISHED 3 int poll_daemon(struct cmd_context *cmd, const char *name, unsigned background, uint32_t lv_type, struct poll_functions *poll_fns, Index: LVM2.2.02.43/tools/pvmove.c =================================================================== --- LVM2.2.02.43.orig/tools/pvmove.c 2008-11-03 23:14:30.000000000 +0100 +++ LVM2.2.02.43/tools/pvmove.c 2008-11-25 19:15:32.000000000 +0100 @@ -578,6 +578,7 @@ static struct poll_functions _pvmove_fns .get_copy_name_from_lv = get_pvmove_pvname_from_lv_mirr, .get_copy_vg = _get_move_vg, .get_copy_lv = find_pvmove_lv_from_pvname, + .poll_progress = poll_mirror_progress, .update_metadata = _update_metadata, .finish_copy = _finish_pvmove, };