From a710cb740cdcd633f09ab0ede9aa34902059badb Mon Sep 17 00:00:00 2001 From: David Teigland Date: Wed, 7 May 2025 17:51:01 -0500 Subject: [PATCH 2/8] lvmlockd: fix hosts check for vgremove errors from lock manager were not being considered. EAGAIN from sanlock should be considered EBUSY. (cherry picked from commit 53752ef851d3210e52297ebb4744fdd766c060c6) --- daemons/lvmlockd/lvmlockd-core.c | 11 ++++++++--- daemons/lvmlockd/lvmlockd-dlm.c | 8 ++++++++ daemons/lvmlockd/lvmlockd-sanlock.c | 26 ++++++++++++++++++++++---- 3 files changed, 38 insertions(+), 7 deletions(-) diff --git a/daemons/lvmlockd/lvmlockd-core.c b/daemons/lvmlockd/lvmlockd-core.c index c65a3cc39..e4aa91216 100644 --- a/daemons/lvmlockd/lvmlockd-core.c +++ b/daemons/lvmlockd/lvmlockd-core.c @@ -2708,13 +2708,16 @@ static void *lockspace_thread_main(void *arg_in) rv = lm_hosts(ls, 1); if (rv) { /* + * rv < 0: error (don't remove) + * rv > 0: other hosts in lockspace (cannot remove) + * rv = 0: only local host in lockspace (can remove) * Checking for hosts here in addition to after the * main loop allows vgremove to fail and be rerun * after the ls is stopped on other hosts. */ log_error("S %s lockspace hosts %d", ls->name, rv); list_del(&act->list); - act->result = -EBUSY; + act->result = (rv < 0) ? rv : -EBUSY; add_client_result(act); continue; } @@ -2727,7 +2730,9 @@ static void *lockspace_thread_main(void *arg_in) if (act->op == LD_OP_BUSY && act->rt == LD_RT_VG) { log_debug("S %s checking if lockspace is busy", ls->name); rv = lm_hosts(ls, 0); - if (rv) + if (rv < 0) + act->result = rv; + else if (rv) act->result = -EBUSY; else act->result = 0; @@ -2743,7 +2748,7 @@ static void *lockspace_thread_main(void *arg_in) if (rv) { log_error("S %s lockspace hosts %d", ls->name, rv); list_del(&act->list); - act->result = -EBUSY; + act->result = (rv < 0) ? rv : -EBUSY; add_client_result(act); continue; } diff --git a/daemons/lvmlockd/lvmlockd-dlm.c b/daemons/lvmlockd/lvmlockd-dlm.c index 72b139170..7529ad327 100644 --- a/daemons/lvmlockd/lvmlockd-dlm.c +++ b/daemons/lvmlockd/lvmlockd-dlm.c @@ -799,6 +799,14 @@ int lm_unlock_dlm(struct lockspace *ls, struct resource *r, * the stale lockspaces on the others eventually.) */ +/* + * On error, returns < 0 + * + * On success: + * If other hosts are found, returns the number. + * If no other hosts are found (only ourself), returns 0. + */ + int lm_hosts_dlm(struct lockspace *ls, int notify) { char ls_nodes_path[PATH_MAX]; diff --git a/daemons/lvmlockd/lvmlockd-sanlock.c b/daemons/lvmlockd/lvmlockd-sanlock.c index 1a3982071..d50d0ce4b 100644 --- a/daemons/lvmlockd/lvmlockd-sanlock.c +++ b/daemons/lvmlockd/lvmlockd-sanlock.c @@ -2296,6 +2296,13 @@ int lm_unlock_sanlock(struct lockspace *ls, struct resource *r, return 0; } +/* + * On error, returns < 0 + * Else: + * If other hosts are found, returns the number. + * If no other hosts are found (only ourself), returns 0. + */ + int lm_hosts_sanlock(struct lockspace *ls, int notify) { struct sanlk_host *hss = NULL; @@ -2310,14 +2317,25 @@ int lm_hosts_sanlock(struct lockspace *ls, int notify) return 0; rv = sanlock_get_hosts(ls->name, 0, &hss, &hss_count, 0); + + if (rv == -EAGAIN) { + /* + * No host info is available yet (perhaps lockspace was + * just started so other host state is unknown.) Pretend + * there is one other host (busy). + */ + log_debug("S %s hosts_san no info, retry later", ls->name); + return 1; + } + if (rv < 0) { log_error("S %s hosts_san get_hosts error %d", ls->name, rv); - return 0; + return -1; } if (!hss || !hss_count) { log_error("S %s hosts_san zero hosts", ls->name); - return 0; + return -1; } hs = hss; @@ -2336,7 +2354,7 @@ int lm_hosts_sanlock(struct lockspace *ls, int notify) } state = hs->flags & SANLK_HOST_MASK; - if (state == SANLK_HOST_LIVE) + if ((state == SANLK_HOST_LIVE) || (state == SANLK_HOST_UNKNOWN)) found_others++; hs++; } @@ -2358,7 +2376,7 @@ int lm_hosts_sanlock(struct lockspace *ls, int notify) if (!found_self) { log_error("S %s hosts_san self not found others %d", ls->name, found_others); - return 0; + return -1; } return found_others; -- 2.49.0