diff --git a/Jinja2-3.0.2.tar.gz b/Jinja2-3.0.2.tar.gz deleted file mode 100644 index e30ebdd1e203b1ae2bf6b359d075962acc049056..0000000000000000000000000000000000000000 Binary files a/Jinja2-3.0.2.tar.gz and /dev/null differ diff --git a/MarkupSafe-2.0.1.tar.gz b/MarkupSafe-2.0.1.tar.gz deleted file mode 100644 index 7a37fc9069a67e6fc00536671e7b846e2879d115..0000000000000000000000000000000000000000 Binary files a/MarkupSafe-2.0.1.tar.gz and /dev/null differ diff --git a/PyYAML-5.1.tar.gz b/PyYAML-5.1.tar.gz deleted file mode 100644 index 91ba249905136e08cb348378f20950bc3b6e77a9..0000000000000000000000000000000000000000 Binary files a/PyYAML-5.1.tar.gz and /dev/null differ diff --git a/PyYAML-6.0.tar.gz b/PyYAML-6.0.tar.gz deleted file mode 100644 index 82259d5b842b72ff3a7e5963ca5cc3ea6000442e..0000000000000000000000000000000000000000 Binary files a/PyYAML-6.0.tar.gz and /dev/null differ diff --git a/aliyun-python-sdk-core-2.11.5.tar.gz b/aliyun-python-sdk-core-2.11.5.tar.gz deleted file mode 100644 index 8e95df81a5aa09b542b01616debd7ef44c6ce6fe..0000000000000000000000000000000000000000 Binary files a/aliyun-python-sdk-core-2.11.5.tar.gz and /dev/null differ diff --git a/awscli-2.2.15.tar.gz b/awscli-2.2.15.tar.gz deleted file mode 100644 index 88b650389f0e14991d383d21f087f8a92988d57e..0000000000000000000000000000000000000000 Binary files a/awscli-2.2.15.tar.gz and /dev/null differ diff --git a/azure-identity-1.10.0.zip b/azure-identity-1.10.0.zip new file mode 100644 index 0000000000000000000000000000000000000000..d30f2052aa1957d85915286d2abbe2f8cd300bdf Binary files /dev/null and b/azure-identity-1.10.0.zip differ diff --git a/bz2123009-fence_ibm_powervs-proxy-private-api-servers.patch b/bz2123009-fence_ibm_powervs-proxy-private-api-servers.patch new file mode 100644 index 0000000000000000000000000000000000000000..36f07fca595e4084f3d5a825de200c02981a13da --- /dev/null +++ b/bz2123009-fence_ibm_powervs-proxy-private-api-servers.patch @@ -0,0 +1,455 @@ +From 98fec5c6d55369ad681abc0cde0d8677835957ab Mon Sep 17 00:00:00 2001 +From: Arnold Beilmann +Date: Thu, 5 May 2022 15:26:22 +0200 +Subject: [PATCH 1/2] modified for PowerVS + +--- + agents/ibm_powervs/fence_ibm_powervs.py | 108 +++++++++++++++++++----- + 1 file changed, 89 insertions(+), 19 deletions(-) + +diff --git a/agents/ibm_powervs/fence_ibm_powervs.py b/agents/ibm_powervs/fence_ibm_powervs.py +index 6649771ea..727009220 100755 +--- a/agents/ibm_powervs/fence_ibm_powervs.py ++++ b/agents/ibm_powervs/fence_ibm_powervs.py +@@ -1,10 +1,11 @@ +-#!@PYTHON@ -tt ++#!/usr/libexec/platform-python -tt + + import sys + import pycurl, io, json + import logging + import atexit +-sys.path.append("@FENCEAGENTSLIBDIR@") ++import time ++sys.path.append("/usr/share/fence") + from fencing import * + from fencing import fail, run_delay, EC_LOGIN_DENIED, EC_STATUS + +@@ -14,16 +15,30 @@ + "ERROR": "unknown" + } + ++def get_token(conn, options): ++ ++ try: ++ command = "identity/token" ++ action = "grant_type=urn%3Aibm%3Aparams%3Aoauth%3Agrant-type%3Aapikey&apikey={}".format(options["--token"]) ++ res = send_command(conn, command, "POST", action, printResult=False) ++ except Exception as e: ++ logging.debug("Failed: {}".format(e)) ++ return "TOKEN_IS_MISSING_OR_WRONG" ++ ++ #if "--verbose" in options: ++ # logging.debug(json.dumps(res, indent=2)) ++ ++ return res["access_token"] ++ + def get_list(conn, options): + outlets = {} +- ++ + try: + command = "cloud-instances/{}/pvm-instances".format(options["--instance"]) + res = send_command(conn, command) + except Exception as e: + logging.debug("Failed: {}".format(e)) + return outlets +- + for r in res["pvmInstances"]: + if "--verbose" in options: + logging.debug(json.dumps(r, indent=2)) +@@ -32,6 +47,7 @@ def get_list(conn, options): + return outlets + + def get_power_status(conn, options): ++ + try: + command = "cloud-instances/{}/pvm-instances/{}".format( + options["--instance"], options["--plug"]) +@@ -40,10 +56,11 @@ def get_power_status(conn, options): + except KeyError as e: + logging.debug("Failed: Unable to get status for {}".format(e)) + fail(EC_STATUS) +- ++ + return result + + def set_power_status(conn, options): ++ + action = { + "on" : '{"action" : "start"}', + "off" : '{"action" : "immediate-shutdown"}', +@@ -56,35 +73,63 @@ def set_power_status(conn, options): + logging.debug("Failed: Unable to set power to {} for {}".format(options["--action"], e)) + fail(EC_STATUS) + +-def connect(opt): ++def connect(opt, token): + conn = pycurl.Curl() + + ## setup correct URL +- conn.base_url = "https://" + opt["--region"] + ".power-iaas.cloud.ibm.com/pcloud/v1/" ++ conn.base_url = "https://private." + opt["--region"] + ".power-iaas.cloud.ibm.com/pcloud/v1/" ++ if opt["--api-type"] == "public": ++ conn.base_url = "https://" + opt["--region"] + ".power-iaas.cloud.ibm.com/pcloud/v1/" + + if opt["--verbose-level"] > 1: +- conn.setopt(pycurl.VERBOSE, 1) ++ conn.setopt(pycurl.VERBOSE, 0) + ++ conn.setopt(pycurl.CONNECTTIMEOUT,int(opt["--shell-timeout"])) + conn.setopt(pycurl.TIMEOUT, int(opt["--shell-timeout"])) + conn.setopt(pycurl.SSL_VERIFYPEER, 1) + conn.setopt(pycurl.SSL_VERIFYHOST, 2) ++ conn.setopt(pycurl.PROXY, "{}".format(opt["--proxy"])) + + # set auth token for later requests + conn.setopt(pycurl.HTTPHEADER, [ + "Content-Type: application/json", +- "Authorization: Bearer {}".format(opt["--token"]), ++ "Authorization: Bearer {}".format(token), + "CRN: {}".format(opt["--crn"]), + "User-Agent: curl", + ]) ++ ++ return conn ++ ++def auth_connect(opt): ++ conn = pycurl.Curl() ++ ++ # setup correct URL ++ conn.base_url = "https://iam.cloud.ibm.com/" ++ ++ if opt["--verbose-level"] > 1: ++ conn.setopt(pycurl.VERBOSE, 1) ++ ++ conn.setopt(pycurl.CONNECTTIMEOUT,int(opt["--shell-timeout"])) ++ conn.setopt(pycurl.TIMEOUT, int(opt["--shell-timeout"])) ++ conn.setopt(pycurl.SSL_VERIFYPEER, 1) ++ conn.setopt(pycurl.SSL_VERIFYHOST, 2) ++ conn.setopt(pycurl.PROXY, "{}".format(opt["--proxy"])) ++ ++ # set auth token for later requests ++ conn.setopt(pycurl.HTTPHEADER, [ ++ "Content-type: application/x-www-form-urlencoded", ++ "Accept: application/json", ++ "User-Agent: curl", ++ ]) + + return conn + + def disconnect(conn): + conn.close() + +-def send_command(conn, command, method="GET", action=None): ++def send_command(conn, command, method="GET", action=None, printResult=True): + url = conn.base_url + command +- ++ + conn.setopt(pycurl.URL, url.encode("ascii")) + + web_buffer = io.BytesIO() +@@ -99,8 +144,10 @@ def send_command(conn, command, method="GET", action=None): + conn.setopt(pycurl.WRITEFUNCTION, web_buffer.write) + + try: ++ time.sleep(3) + conn.perform() + except Exception as e: ++ logging.error("ADD_DEBUG: {}".format(e)) + raise(e) + + rc = conn.getinfo(pycurl.HTTP_CODE) +@@ -110,8 +157,7 @@ def send_command(conn, command, method="GET", action=None): + + if rc != 200: + if len(result) > 0: +- raise Exception("{}: {}".format(rc, +- result["value"]["messages"][0]["default_message"])) ++ raise Exception("{}: {}".format(rc,result)) + else: + raise Exception("Remote returned {} for request to {}".format(rc, url)) + +@@ -121,7 +167,8 @@ def send_command(conn, command, method="GET", action=None): + logging.debug("url: {}".format(url)) + logging.debug("method: {}".format(method)) + logging.debug("response code: {}".format(rc)) +- logging.debug("result: {}\n".format(result)) ++ if printResult: ++ logging.debug("result: {}\n".format(result)) + + return result + +@@ -129,9 +176,9 @@ def define_new_opts(): + all_opt["token"] = { + "getopt" : ":", + "longopt" : "token", +- "help" : "--token=[token] Bearer Token", ++ "help" : "--token=[token] API Token", + "required" : "1", +- "shortdesc" : "Bearer Token", ++ "shortdesc" : "API Token", + "order" : 0 + } + all_opt["crn"] = { +@@ -158,6 +205,22 @@ def define_new_opts(): + "shortdesc" : "Region", + "order" : 0 + } ++ all_opt["api-type"] = { ++ "getopt" : ":", ++ "longopt" : "api-type", ++ "help" : "--api-type=[private|public] API-type: 'private' (default) or 'public'", ++ "required" : "0", ++ "shortdesc" : "API-type (private|public)", ++ "order" : 0 ++ } ++ all_opt["proxy"] = { ++ "getopt" : ":", ++ "longopt" : "proxy", ++ "help" : "--proxy=[http://:] Proxy: 'http://:'", ++ "required" : "0", ++ "shortdesc" : "Network proxy", ++ "order" : 0 ++ } + + + def main(): +@@ -166,6 +229,8 @@ def main(): + "crn", + "instance", + "region", ++ "api-type", ++ "proxy", + "port", + "no_password", + ] +@@ -173,9 +238,11 @@ def main(): + atexit.register(atexit_handler) + define_new_opts() + +- all_opt["shell_timeout"]["default"] = "15" ++ all_opt["shell_timeout"]["default"] = "500" + all_opt["power_timeout"]["default"] = "30" + all_opt["power_wait"]["default"] = "1" ++ all_opt["api-type"]["default"] = "private" ++ all_opt["proxy"]["default"] = "" + + options = check_input(device_opt, process_input(device_opt)) + +@@ -190,8 +257,11 @@ def main(): + ## Fence operations + #### + run_delay(options) +- +- conn = connect(options) ++ ++ auth_conn = auth_connect(options) ++ token = get_token(auth_conn, options) ++ disconnect(auth_conn) ++ conn = connect(options, token) + atexit.register(disconnect, conn) + + result = fence_action(conn, options, set_power_status, get_power_status, get_list) + +From fbe9a539ac8f40686a8027b7e768d9f7b799e485 Mon Sep 17 00:00:00 2001 +From: Oyvind Albrigtsen +Date: Fri, 6 May 2022 11:22:47 +0200 +Subject: [PATCH 2/2] fence_ibm_powervs: cleanup and fixes + +--- + agents/ibm_powervs/fence_ibm_powervs.py | 37 ++++++++++------------- + tests/data/metadata/fence_ibm_powervs.xml | 19 ++++++++++-- + 2 files changed, 33 insertions(+), 23 deletions(-) + +diff --git a/agents/ibm_powervs/fence_ibm_powervs.py b/agents/ibm_powervs/fence_ibm_powervs.py +index 727009220..819ab8896 100755 +--- a/agents/ibm_powervs/fence_ibm_powervs.py ++++ b/agents/ibm_powervs/fence_ibm_powervs.py +@@ -1,11 +1,11 @@ +-#!/usr/libexec/platform-python -tt ++#!@PYTHON@ -tt + + import sys + import pycurl, io, json + import logging + import atexit + import time +-sys.path.append("/usr/share/fence") ++sys.path.append("@FENCEAGENTSLIBDIR@") + from fencing import * + from fencing import fail, run_delay, EC_LOGIN_DENIED, EC_STATUS + +@@ -16,7 +16,6 @@ + } + + def get_token(conn, options): +- + try: + command = "identity/token" + action = "grant_type=urn%3Aibm%3Aparams%3Aoauth%3Agrant-type%3Aapikey&apikey={}".format(options["--token"]) +@@ -25,20 +24,18 @@ def get_token(conn, options): + logging.debug("Failed: {}".format(e)) + return "TOKEN_IS_MISSING_OR_WRONG" + +- #if "--verbose" in options: +- # logging.debug(json.dumps(res, indent=2)) +- + return res["access_token"] + + def get_list(conn, options): + outlets = {} +- ++ + try: + command = "cloud-instances/{}/pvm-instances".format(options["--instance"]) + res = send_command(conn, command) + except Exception as e: + logging.debug("Failed: {}".format(e)) + return outlets ++ + for r in res["pvmInstances"]: + if "--verbose" in options: + logging.debug(json.dumps(r, indent=2)) +@@ -47,7 +44,6 @@ def get_list(conn, options): + return outlets + + def get_power_status(conn, options): +- + try: + command = "cloud-instances/{}/pvm-instances/{}".format( + options["--instance"], options["--plug"]) +@@ -56,11 +52,10 @@ def get_power_status(conn, options): + except KeyError as e: + logging.debug("Failed: Unable to get status for {}".format(e)) + fail(EC_STATUS) +- ++ + return result + + def set_power_status(conn, options): +- + action = { + "on" : '{"action" : "start"}', + "off" : '{"action" : "immediate-shutdown"}', +@@ -77,11 +72,11 @@ def connect(opt, token): + conn = pycurl.Curl() + + ## setup correct URL +- conn.base_url = "https://private." + opt["--region"] + ".power-iaas.cloud.ibm.com/pcloud/v1/" +- if opt["--api-type"] == "public": +- conn.base_url = "https://" + opt["--region"] + ".power-iaas.cloud.ibm.com/pcloud/v1/" ++ conn.base_url = "https://" + opt["--region"] + ".power-iaas.cloud.ibm.com/pcloud/v1/" ++ if opt["--api-type"] == "private": ++ conn.base_url = "https://private." + opt["--region"] + ".power-iaas.cloud.ibm.com/pcloud/v1/" + +- if opt["--verbose-level"] > 1: ++ if opt["--verbose-level"] < 3: + conn.setopt(pycurl.VERBOSE, 0) + + conn.setopt(pycurl.CONNECTTIMEOUT,int(opt["--shell-timeout"])) +@@ -129,7 +124,7 @@ def disconnect(conn): + + def send_command(conn, command, method="GET", action=None, printResult=True): + url = conn.base_url + command +- ++ + conn.setopt(pycurl.URL, url.encode("ascii")) + + web_buffer = io.BytesIO() +@@ -144,10 +139,9 @@ def send_command(conn, command, method="GET", action=None, printResult=True): + conn.setopt(pycurl.WRITEFUNCTION, web_buffer.write) + + try: +- time.sleep(3) + conn.perform() + except Exception as e: +- logging.error("ADD_DEBUG: {}".format(e)) ++ logging.error("send_command(): {}".format(e)) + raise(e) + + rc = conn.getinfo(pycurl.HTTP_CODE) +@@ -208,9 +202,9 @@ def define_new_opts(): + all_opt["api-type"] = { + "getopt" : ":", + "longopt" : "api-type", +- "help" : "--api-type=[private|public] API-type: 'private' (default) or 'public'", ++ "help" : "--api-type=[public|private] API-type: 'public' (default) or 'private'", + "required" : "0", +- "shortdesc" : "API-type (private|public)", ++ "shortdesc" : "API-type (public|private)", + "order" : 0 + } + all_opt["proxy"] = { +@@ -238,9 +232,10 @@ def main(): + atexit.register(atexit_handler) + define_new_opts() + +- all_opt["shell_timeout"]["default"] = "500" ++ all_opt["shell_timeout"]["default"] = "15" + all_opt["power_timeout"]["default"] = "30" + all_opt["power_wait"]["default"] = "1" ++ all_opt["stonith_status_sleep"]["default"] = "3" + all_opt["api-type"]["default"] = "private" + all_opt["proxy"]["default"] = "" + +@@ -257,7 +252,7 @@ def main(): + ## Fence operations + #### + run_delay(options) +- ++ + auth_conn = auth_connect(options) + token = get_token(auth_conn, options) + disconnect(auth_conn) +diff --git a/tests/data/metadata/fence_ibm_powervs.xml b/tests/data/metadata/fence_ibm_powervs.xml +index fe86331bd..81cea4379 100644 +--- a/tests/data/metadata/fence_ibm_powervs.xml ++++ b/tests/data/metadata/fence_ibm_powervs.xml +@@ -3,6 +3,16 @@ + fence_ibm_powervs is an I/O Fencing agent which can be used with IBM PowerVS to fence virtual machines. + https://www.ibm.com + ++ ++ ++ ++ API-type (public|private) ++ ++ ++ ++ ++ API-type (public|private) ++ + + + +@@ -13,6 +23,11 @@ + + PowerVS Instance + ++ ++ ++ ++ Network proxy ++ + + + +@@ -21,7 +36,7 @@ + + + +- Bearer Token ++ API Token + + + +@@ -110,7 +125,7 @@ + + + +- ++ + Sleep X seconds between status calls during a STONITH action + + diff --git a/bz2123010-fence_ibm_vpc-add-proxy-support.patch b/bz2123010-fence_ibm_vpc-add-proxy-support.patch new file mode 100644 index 0000000000000000000000000000000000000000..39a2e2ef0b39afe2c91f55a8bcbf74d8af850aef --- /dev/null +++ b/bz2123010-fence_ibm_vpc-add-proxy-support.patch @@ -0,0 +1,62 @@ +From be409554bbc99df2bba22cb01e8a6df634af896d Mon Sep 17 00:00:00 2001 +From: Oyvind Albrigtsen +Date: Tue, 31 May 2022 15:46:40 +0200 +Subject: [PATCH] fence_ibm_vpc: add proxy support + +--- + agents/ibm_vpc/fence_ibm_vpc.py | 11 +++++++++++ + tests/data/metadata/fence_ibm_vpc.xml | 5 +++++ + 2 files changed, 16 insertions(+) + +diff --git a/agents/ibm_vpc/fence_ibm_vpc.py b/agents/ibm_vpc/fence_ibm_vpc.py +index 9e38e8301..3da3ce056 100755 +--- a/agents/ibm_vpc/fence_ibm_vpc.py ++++ b/agents/ibm_vpc/fence_ibm_vpc.py +@@ -88,6 +88,7 @@ def connect(opt): + conn.setopt(pycurl.TIMEOUT, int(opt["--shell-timeout"])) + conn.setopt(pycurl.SSL_VERIFYPEER, 1) + conn.setopt(pycurl.SSL_VERIFYHOST, 2) ++ conn.setopt(pycurl.PROXY, "{}".format(opt["--proxy"])) + + # get bearer token + bearer_token = get_bearer_token(conn, opt) +@@ -169,6 +170,15 @@ def define_new_opts(): + "shortdesc" : "Region", + "order" : 0 + } ++ all_opt["proxy"] = { ++ "getopt" : ":", ++ "longopt" : "proxy", ++ "help" : "--proxy=[http://:] Proxy: 'http://:'", ++ "required" : "0", ++ "default": "", ++ "shortdesc" : "Network proxy", ++ "order" : 0 ++ } + all_opt["limit"] = { + "getopt" : ":", + "longopt" : "limit", +@@ -185,6 +195,7 @@ def main(): + "apikey", + "region", + "limit", ++ "proxy", + "port", + "no_password", + ] +diff --git a/tests/data/metadata/fence_ibm_vpc.xml b/tests/data/metadata/fence_ibm_vpc.xml +index ee7151673..09da0e303 100644 +--- a/tests/data/metadata/fence_ibm_vpc.xml ++++ b/tests/data/metadata/fence_ibm_vpc.xml +@@ -13,6 +13,11 @@ + + Number of nodes returned by API + ++ ++ ++ ++ Network proxy ++ + + + diff --git a/bz2123465-fence_ibm_vpc-remove-unused-instance-parameter-limit-optional.patch b/bz2123465-fence_ibm_vpc-remove-unused-instance-parameter-limit-optional.patch new file mode 100644 index 0000000000000000000000000000000000000000..5e031ad40df3ef7e4329ed7f6a33f0f7cabf103c --- /dev/null +++ b/bz2123465-fence_ibm_vpc-remove-unused-instance-parameter-limit-optional.patch @@ -0,0 +1,65 @@ +From d0254345472c9415af1e06e9e8df2fe0ce464db0 Mon Sep 17 00:00:00 2001 +From: Oyvind Albrigtsen +Date: Mon, 2 May 2022 11:14:42 +0200 +Subject: [PATCH] fence_ibm_vpc: remove unused instance parameter and make + limit optional + +--- + agents/ibm_vpc/fence_ibm_vpc.py | 11 +---------- + tests/data/metadata/fence_ibm_vpc.xml | 7 +------ + 2 files changed, 2 insertions(+), 16 deletions(-) + +diff --git a/agents/ibm_vpc/fence_ibm_vpc.py b/agents/ibm_vpc/fence_ibm_vpc.py +index 9f84f7b2d..9e38e8301 100755 +--- a/agents/ibm_vpc/fence_ibm_vpc.py ++++ b/agents/ibm_vpc/fence_ibm_vpc.py +@@ -161,14 +161,6 @@ def define_new_opts(): + "shortdesc" : "API Key", + "order" : 0 + } +- all_opt["instance"] = { +- "getopt" : ":", +- "longopt" : "instance", +- "help" : "--instance=[instance] Cloud Instance", +- "required" : "1", +- "shortdesc" : "Cloud Instance", +- "order" : 0 +- } + all_opt["region"] = { + "getopt" : ":", + "longopt" : "region", +@@ -181,7 +173,7 @@ def define_new_opts(): + "getopt" : ":", + "longopt" : "limit", + "help" : "--limit=[number] Limit number of nodes returned by API", +- "required" : "1", ++ "required" : "0", + "default": 50, + "shortdesc" : "Number of nodes returned by API", + "order" : 0 +@@ -191,7 +183,6 @@ def define_new_opts(): + def main(): + device_opt = [ + "apikey", +- "instance", + "region", + "limit", + "port", +diff --git a/tests/data/metadata/fence_ibm_vpc.xml b/tests/data/metadata/fence_ibm_vpc.xml +index 926efcaa0..ee7151673 100644 +--- a/tests/data/metadata/fence_ibm_vpc.xml ++++ b/tests/data/metadata/fence_ibm_vpc.xml +@@ -8,12 +8,7 @@ + + API Key + +- +- +- +- Cloud Instance +- +- ++ + + + Number of nodes returned by API diff --git a/bz2127872-fence_ibm_vpc-add-token-cache-support.patch b/bz2127872-fence_ibm_vpc-add-token-cache-support.patch new file mode 100644 index 0000000000000000000000000000000000000000..a3002a7b446fff32771624a6370a9c7e19a7a9d1 --- /dev/null +++ b/bz2127872-fence_ibm_vpc-add-token-cache-support.patch @@ -0,0 +1,432 @@ +From bccac64a5135815ada30d385ab573409f1176905 Mon Sep 17 00:00:00 2001 +From: Oyvind Albrigtsen +Date: Thu, 7 Jul 2022 14:18:21 +0200 +Subject: [PATCH 1/3] build: make xml-check: ignore detected paths in *_file + parameters not matching saved metadata + +--- + make/agentpycheck.mk | 2 +- + 83 files changed, 1 insertion(+), 108 deletions(-) + +diff --git a/make/agentpycheck.mk b/make/agentpycheck.mk +index f686c4c89..4044dbad3 100644 +--- a/make/agentpycheck.mk ++++ b/make/agentpycheck.mk +@@ -1,5 +1,5 @@ + DATADIR:=$(abs_top_srcdir)/tests/data/metadata +-AWK_VAL='BEGIN {store=-1} /name=".*_path"/ {store=2} {if (store!=0) {print}; store--}' ++AWK_VAL='BEGIN {store=-1} /name=".*_path"/ || /name=".*_file"/ {store=2} {if (store!=0) {print}; store--}' + + TEST_TARGET=$(filter-out $(TEST_TARGET_SKIP),$(TARGET)) + +From 1b7f3cc431ca53962506e6d96e7a4938c4388416 Mon Sep 17 00:00:00 2001 +From: Oyvind Albrigtsen +Date: Fri, 1 Jul 2022 13:29:16 +0200 +Subject: [PATCH 2/3] build: add FENCETMPDIR for state files + +--- + Makefile.am | 3 ++- + configure.ac | 30 ++++++++++++++++++++++++++++++ + m4/PKG_CHECK_VAR.m4 | 24 ++++++++++++++++++++++++ + make/fencebuild.mk | 1 + + systemd/Makefile.am | 24 ++++++++++++++++++++++++ + systemd/fence-agents.conf.in | 1 + + 7 files changed, 97 insertions(+), 2 deletions(-) + create mode 100644 m4/PKG_CHECK_VAR.m4 + create mode 100644 systemd/Makefile.am + create mode 100644 systemd/fence-agents.conf.in + +diff --git a/Makefile.am b/Makefile.am +index c1091b93a..1d115e5aa 100644 +--- a/Makefile.am ++++ b/Makefile.am +@@ -23,7 +23,7 @@ TARFILES = $(PACKAGE_NAME)-$(VERSION).tar.bz2 \ + + ACLOCAL_AMFLAGS = -I m4 + +-SUBDIRS = lib agents doc ++SUBDIRS = lib agents doc systemd + + .PHONY: $(SUBDIRS) + +@@ -34,6 +34,7 @@ doc: agents + install-exec-local: + $(INSTALL) -d $(DESTDIR)/$(LOGDIR) + $(INSTALL) -d $(DESTDIR)/$(CLUSTERVARRUN) ++ $(INSTALL) -d -m 1755 $(DESTDIR)$(FENCETMPDIR) + + uninstall-local: + rmdir $(DESTDIR)/$(LOGDIR) || :; +diff --git a/configure.ac b/configure.ac +index 1bad8e3b0..d7afb8dbe 100644 +--- a/configure.ac ++++ b/configure.ac +@@ -135,10 +135,38 @@ AC_ARG_WITH([agents], + [ AGENTS_LIST="$withval" ], + [ AGENTS_LIST="all" ]) + ++FENCETMPDIR=${localstatedir}/run/fence-agents ++AC_ARG_WITH(fencetmpdir, ++ [ --with-fencetmpdir=DIR directory for fence agents state files [${FENCETMPDIR}]], ++ [ FENCETMPDIR="$withval" ]) ++ ++# Expand $prefix ++eval FENCETMPDIR="`eval echo ${FENCETMPDIR}`" ++AC_DEFINE_UNQUOTED(FENCETMPDIR,"$FENCETMPDIR", Where Fence agents keep state files) ++AC_SUBST(FENCETMPDIR) ++ ++ + if test "x$AGENTS_LIST" = x; then + AC_ERROR([No agents selected]) + fi + ++# PKG_CHECK_MODULES will fail if systemd is not found by default, so make sure ++# we set the proper vars and deal with it ++PKG_CHECK_MODULES([systemd], [systemd], [HAS_SYSTEMD=yes], [HAS_SYSTEMD=no]) ++if test "x$HAS_SYSTEMD" == "xyes"; then ++ PKG_CHECK_VAR([SYSTEMD_TMPFILES_DIR], [systemd], [tmpfilesdir]) ++ if test "x$SYSTEMD_TMPFILES_DIR" == "x"; then ++ AC_MSG_ERROR([Unable to detect systemd tmpfiles directory automatically]) ++ fi ++ ++ # sanitize systed vars when using non standard prefix ++ if test "$prefix" != "/usr"; then ++ SYSTEMD_TMPFILES_DIR="$prefix/$SYSTEMD_TMPFILES_DIR" ++ AC_SUBST([SYSTEMD_TMPFILES_DIR]) ++ fi ++fi ++AM_CONDITIONAL(HAVE_SYSTEMD, [test "x$HAS_SYSTEMD" == xyes ]) ++ + FENCE_KDUMP=0 + if echo "$AGENTS_LIST" | grep -q -E "all|kdump"; then + case "$host_os" in +@@ -552,6 +580,8 @@ AC_CONFIG_FILES([Makefile + agents/Makefile + lib/Makefile + doc/Makefile ++ systemd/Makefile ++ systemd/fence-agents.conf + agents/virt/Makefile + agents/virt/config/Makefile + agents/virt/common/Makefile +diff --git a/m4/PKG_CHECK_VAR.m4 b/m4/PKG_CHECK_VAR.m4 +new file mode 100644 +index 000000000..2221a69eb +--- /dev/null ++++ b/m4/PKG_CHECK_VAR.m4 +@@ -0,0 +1,24 @@ ++dnl PKG_CHECK_VAR(VARIABLE, MODULE, CONFIG-VARIABLE, ++dnl [ACTION-IF-FOUND], [ACTION-IF-NOT-FOUND]) ++dnl ------------------------------------------- ++dnl Since: 0.28 ++dnl ++dnl Retrieves the value of the pkg-config variable for the given module. ++dnl ++dnl Origin (declared license: GPLv2+ with less restrictive exception): ++dnl https://cgit.freedesktop.org/pkg-config/tree/pkg.m4.in?h=pkg-config-0.29.1#n261 ++dnl (AS_VAR_COPY replaced with backward-compatible equivalent and guard ++dnl to prefer system-wide variant by Jan Pokorny ) ++ ++m4_ifndef([PKG_CHECK_VAR],[ ++AC_DEFUN([PKG_CHECK_VAR], ++[AC_REQUIRE([PKG_PROG_PKG_CONFIG])dnl ++AC_ARG_VAR([$1], [value of $3 for $2, overriding pkg-config])dnl ++ ++_PKG_CONFIG([$1], [variable="][$3]["], [$2]) ++dnl AS_VAR_COPY([$1], [pkg_cv_][$1]) ++$1=AS_VAR_GET([pkg_cv_][$1]) ++ ++AS_VAR_IF([$1], [""], [$5], [$4])dnl ++])dnl PKG_CHECK_VAR ++])dnl m4_ifndef +diff --git a/make/fencebuild.mk b/make/fencebuild.mk +index 762db62c4..9a3c6d6dd 100644 +--- a/make/fencebuild.mk ++++ b/make/fencebuild.mk +@@ -8,6 +8,7 @@ define gen_agent_from_py + -e 's#@''LOGDIR@#${LOGDIR}#g' \ + -e 's#@''SBINDIR@#${sbindir}#g' \ + -e 's#@''LIBEXECDIR@#${libexecdir}#g' \ ++ -e 's#@''FENCETMPDIR@#${FENCETMPDIR}#g' \ + -e 's#@''IPMITOOL_PATH@#${IPMITOOL_PATH}#g' \ + -e 's#@''OPENSTACK_PATH@#${OPENSTACK_PATH}#g' \ + -e 's#@''AMTTOOL_PATH@#${AMTTOOL_PATH}#g' \ +diff --git a/systemd/Makefile.am b/systemd/Makefile.am +new file mode 100644 +index 000000000..aa3a01679 +--- /dev/null ++++ b/systemd/Makefile.am +@@ -0,0 +1,24 @@ ++# ++# Copyright (C) 2017 Oyvind Albrigtsen ++# ++# This program is free software; you can redistribute it and/or ++# modify it under the terms of the GNU General Public License ++# as published by the Free Software Foundation; either version 2 ++# of the License, or (at your option) any later version. ++# ++# This program is distributed in the hope that it will be useful, ++# but WITHOUT ANY WARRANTY; without even the implied warranty of ++# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ++# GNU General Public License for more details. ++# ++# You should have received a copy of the GNU General Public License ++# along with this program; if not, write to the Free Software ++# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. ++# ++ ++MAINTAINERCLEANFILES = Makefile.in ++ ++if HAVE_SYSTEMD ++tmpfilesdir = $(SYSTEMD_TMPFILES_DIR) ++tmpfiles_DATA = fence-agents.conf ++endif +diff --git a/systemd/fence-agents.conf.in b/systemd/fence-agents.conf.in +new file mode 100644 +index 000000000..4181287da +--- /dev/null ++++ b/systemd/fence-agents.conf.in +@@ -0,0 +1 @@ ++d @FENCETMPDIR@ 1755 root root + +From d5a12d9c30b66eb8720e037c4dce5fe0f3ad7dbb Mon Sep 17 00:00:00 2001 +From: Oyvind Albrigtsen +Date: Thu, 30 Jun 2022 13:20:37 +0200 +Subject: [PATCH 3/3] fence_ibm_vpc: add token cache support + +--- + agents/ibm_vpc/fence_ibm_vpc.py | 126 ++++++++++++++++++++---- + tests/data/metadata/fence_ibm_vpc.xml | 4 + + 3 files changed, 110 insertions(+), 22 deletions(-) + + def auth_connect(opt): +diff --git a/agents/ibm_vpc/fence_ibm_vpc.py b/agents/ibm_vpc/fence_ibm_vpc.py +index 3da3ce056..847010584 100755 +--- a/agents/ibm_vpc/fence_ibm_vpc.py ++++ b/agents/ibm_vpc/fence_ibm_vpc.py +@@ -4,9 +4,10 @@ + import pycurl, io, json + import logging + import atexit ++import hashlib + sys.path.append("@FENCEAGENTSLIBDIR@") + from fencing import * +-from fencing import fail, run_delay, EC_LOGIN_DENIED, EC_STATUS ++from fencing import fail, run_delay, EC_LOGIN_DENIED, EC_STATUS, EC_GENERIC_ERROR + + state = { + "running": "on", +@@ -22,7 +23,7 @@ def get_list(conn, options): + + try: + command = "instances?version=2021-05-25&generation=2&limit={}".format(options["--limit"]) +- res = send_command(conn, command) ++ res = send_command(conn, options, command) + except Exception as e: + logging.debug("Failed: Unable to get list: {}".format(e)) + return outlets +@@ -38,7 +39,7 @@ def get_list(conn, options): + def get_power_status(conn, options): + try: + command = "instances/{}?version=2021-05-25&generation=2".format(options["--plug"]) +- res = send_command(conn, command) ++ res = send_command(conn, options, command) + result = state[res["status"]] + if options["--verbose-level"] > 1: + logging.debug("Result:\n{}".format(json.dumps(res, indent=2))) +@@ -57,27 +58,71 @@ def set_power_status(conn, options): + + try: + command = "instances/{}/actions?version=2021-05-25&generation=2".format(options["--plug"]) +- send_command(conn, command, "POST", action, 201) ++ send_command(conn, options, command, "POST", action, 201) + except Exception as e: + logging.debug("Failed: Unable to set power to {} for {}".format(options["--action"], e)) + fail(EC_STATUS) + + def get_bearer_token(conn, options): ++ import os, errno ++ ++ try: ++ # FIPS requires usedforsecurity=False and might not be ++ # available on all distros: https://bugs.python.org/issue9216 ++ hash = hashlib.sha256(options["--apikey"].encode("utf-8"), usedforsecurity=False).hexdigest() ++ except (AttributeError, TypeError): ++ hash = hashlib.sha256(options["--apikey"].encode("utf-8")).hexdigest() ++ file_path = options["--token-file"].replace("[hash]", hash) + token = None ++ ++ if not os.path.isdir(os.path.dirname(file_path)): ++ os.makedirs(os.path.dirname(file_path)) ++ ++ # For security, remove file with potentially elevated mode + try: +- conn.setopt(pycurl.HTTPHEADER, [ +- "Content-Type: application/x-www-form-urlencoded", +- "User-Agent: curl", +- ]) +- token = send_command(conn, "https://iam.cloud.ibm.com/identity/token", "POST", "grant_type=urn:ibm:params:oauth:grant-type:apikey&apikey={}".format(options["--apikey"]))["access_token"] +- except Exception: +- logging.error("Failed: Unable to authenticate") +- fail(EC_LOGIN_DENIED) ++ os.remove(file_path) ++ except OSError: ++ pass ++ ++ try: ++ oldumask = os.umask(0) ++ file_handle = os.open(file_path, os.O_CREAT | os.O_EXCL | os.O_WRONLY, 0o600) ++ except OSError as e: ++ if e.errno == errno.EEXIST: # Failed as the file already exists. ++ logging.error("Failed: File already exists: {}".format(e)) ++ sys.exit(EC_GENERIC_ERROR) ++ else: # Something unexpected went wrong ++ logging.error("Failed: Unable to open file: {}".format(e)) ++ sys.exit(EC_GENERIC_ERROR) ++ else: # No exception, so the file must have been created successfully. ++ with os.fdopen(file_handle, 'w') as file_obj: ++ try: ++ conn.setopt(pycurl.HTTPHEADER, [ ++ "Content-Type: application/x-www-form-urlencoded", ++ "User-Agent: curl", ++ ]) ++ token = send_command(conn, options, "https://iam.cloud.ibm.com/identity/token", "POST", "grant_type=urn:ibm:params:oauth:grant-type:apikey&apikey={}".format(options["--apikey"]))["access_token"] ++ except Exception as e: ++ logging.error("Failed: Unable to authenticate: {}".format(e)) ++ fail(EC_LOGIN_DENIED) ++ file_obj.write(token) ++ finally: ++ os.umask(oldumask) + + return token + ++def set_bearer_token(conn, bearer_token): ++ conn.setopt(pycurl.HTTPHEADER, [ ++ "Content-Type: application/json", ++ "Authorization: Bearer {}".format(bearer_token), ++ "User-Agent: curl", ++ ]) ++ ++ return conn ++ + def connect(opt): + conn = pycurl.Curl() ++ bearer_token = "" + + ## setup correct URL + conn.base_url = "https://" + opt["--region"] + ".iaas.cloud.ibm.com/v1/" +@@ -91,21 +136,28 @@ def connect(opt): + conn.setopt(pycurl.PROXY, "{}".format(opt["--proxy"])) + + # get bearer token +- bearer_token = get_bearer_token(conn, opt) ++ try: ++ try: ++ # FIPS requires usedforsecurity=False and might not be ++ # available on all distros: https://bugs.python.org/issue9216 ++ hash = hashlib.sha256(opt["--apikey"].encode("utf-8"), usedforsecurity=False).hexdigest() ++ except (AttributeError, TypeError): ++ hash = hashlib.sha256(opt["--apikey"].encode("utf-8")).hexdigest() ++ f = open(opt["--token-file"].replace("[hash]", hash)) ++ bearer_token = f.read() ++ f.close() ++ except IOError: ++ bearer_token = get_bearer_token(conn, opt) + + # set auth token for later requests +- conn.setopt(pycurl.HTTPHEADER, [ +- "Content-Type: application/json", +- "Authorization: Bearer {}".format(bearer_token), +- "User-Agent: curl", +- ]) ++ conn = set_bearer_token(conn, bearer_token) + + return conn + + def disconnect(conn): + conn.close() + +-def send_command(conn, command, method="GET", action=None, expected_rc=200): ++def send_command(conn, options, command, method="GET", action=None, expected_rc=200): + if not command.startswith("https"): + url = conn.base_url + command + else: +@@ -130,6 +182,26 @@ def send_command(conn, command, method="GET", action=None, expected_rc=200): + raise(e) + + rc = conn.getinfo(pycurl.HTTP_CODE) ++ ++ # auth if token has expired ++ if rc in [400, 401, 415]: ++ tokenconn = pycurl.Curl() ++ token = get_bearer_token(tokenconn, options) ++ tokenconn.close() ++ conn = set_bearer_token(conn, token) ++ ++ # flush web_buffer ++ web_buffer.close() ++ web_buffer = io.BytesIO() ++ conn.setopt(pycurl.WRITEFUNCTION, web_buffer.write) ++ ++ try: ++ conn.perform() ++ except Exception as e: ++ raise(e) ++ ++ rc = conn.getinfo(pycurl.HTTP_CODE) ++ + result = web_buffer.getvalue().decode("UTF-8") + + web_buffer.close() +@@ -173,7 +245,7 @@ def define_new_opts(): + all_opt["proxy"] = { + "getopt" : ":", + "longopt" : "proxy", +- "help" : "--proxy=[http://:] Proxy: 'http://:'", ++ "help" : "--proxy=[http://:] Proxy: 'http://:'", + "required" : "0", + "default": "", + "shortdesc" : "Network proxy", +@@ -188,14 +260,26 @@ def define_new_opts(): + "shortdesc" : "Number of nodes returned by API", + "order" : 0 + } ++ all_opt["token_file"] = { ++ "getopt" : ":", ++ "longopt" : "token-file", ++ "help" : "--token-file=[path] Path to the token cache file\n" ++ "\t\t\t\t (Default: @FENCETMPDIR@/fence_ibm_vpc/[hash].token)\n" ++ "\t\t\t\t [hash] will be replaced by a hashed value", ++ "required" : "0", ++ "default": "@FENCETMPDIR@/fence_ibm_vpc/[hash].token", ++ "shortdesc" : "Path to the token cache file", ++ "order" : 0 ++ } + + + def main(): + device_opt = [ + "apikey", + "region", +- "limit", + "proxy", ++ "limit", ++ "token_file", + "port", + "no_password", + ] +diff --git a/tests/data/metadata/fence_ibm_vpc.xml b/tests/data/metadata/fence_ibm_vpc.xml +index acf4925fc..c35bc4619 100644 +--- a/tests/data/metadata/fence_ibm_vpc.xml ++++ b/tests/data/metadata/fence_ibm_vpc.xml +@@ -23,6 +23,10 @@ + + Region + ++ ++ ++ Path to the token cache file ++ + + + diff --git a/bz2136200-fence_gce-update.patch b/bz2136200-fence_gce-update.patch new file mode 100644 index 0000000000000000000000000000000000000000..011371c0c8fcb54c1bb5aa008e6007cf504259d9 --- /dev/null +++ b/bz2136200-fence_gce-update.patch @@ -0,0 +1,410 @@ +--- a/agents/gce/fence_gce.py 2022-04-29 10:13:50.317888041 +0200 ++++ b/agents/gce/fence_gce.py 2022-04-29 10:17:54.813248566 +0200 +@@ -2,10 +2,10 @@ + + # + # Requires the googleapiclient and oauth2client +-# RHEL 7.x: google-api-python-client==1.6.7 python-gflags==2.0 pyasn1==0.4.8 rsa==3.4.2 +-# RHEL 8.x: nothing additional needed +-# SLES 12.x: python-google-api-python-client python-oauth2client python-oauth2client-gce +-# SLES 15.x: python3-google-api-python-client python3-oauth2client python3-oauth2client-gce ++# RHEL 7.x: google-api-python-client==1.6.7 python-gflags==2.0 pyasn1==0.4.8 rsa==3.4.2 pysocks==1.7.1 httplib2==0.19.0 ++# RHEL 8.x: pysocks==1.7.1 httplib2==0.19.0 ++# SLES 12.x: python-google-api-python-client python-oauth2client python-oauth2client-gce pysocks==1.7.1 httplib2==0.19.0 ++# SLES 15.x: python3-google-api-python-client python3-oauth2client pysocks==1.7.1 httplib2==0.19.0 + # + + import atexit +@@ -27,7 +27,7 @@ + import urllib2 as urlrequest + sys.path.append("@FENCEAGENTSLIBDIR@") + +-from fencing import fail_usage, run_delay, all_opt, atexit_handler, check_input, process_input, show_docs, fence_action ++from fencing import fail_usage, run_delay, all_opt, atexit_handler, check_input, process_input, show_docs, fence_action, run_command + try: + sys.path.insert(0, '/usr/lib/fence-agents/support/google') + import httplib2 +@@ -42,6 +42,19 @@ + + METADATA_SERVER = 'http://metadata.google.internal/computeMetadata/v1/' + METADATA_HEADERS = {'Metadata-Flavor': 'Google'} ++INSTANCE_LINK = 'https://www.googleapis.com/compute/v1/projects/{}/zones/{}/instances/{}' ++ ++def run_on_fail(options): ++ if "--runonfail" in options: ++ run_command(options, options["--runonfail"]) ++ ++def fail_fence_agent(options, message): ++ run_on_fail(options) ++ fail_usage(message) ++ ++def raise_fence_agent(options, message): ++ run_on_fail(options) ++ raise Exception(message) + + # + # Will use baremetalsolution setting or the environment variable +@@ -66,7 +79,7 @@ + { + "matchlength": 4, + "match": "https://compute.googleapis.com/compute/v1/projects/(.*)/zones/(.*)/instances/(.*)/reset(.*)", +- "replace": "https://baremetalsolution.googleapis.com/v1alpha1/projects/\\1/locations/\\2/instances/\\3:resetInstance\\4" ++ "replace": "https://baremetalsolution.googleapis.com/v1/projects/\\1/locations/\\2/instances/\\3:resetInstance\\4" + }) + for uri_replacement in uri_replacements: + # each uri_replacement should have matchlength, match, and replace +@@ -121,14 +134,17 @@ + + def get_nodes_list(conn, options): + result = {} ++ if "--zone" not in options: ++ fail_fence_agent(options, "Failed: get_nodes_list: Please specify the --zone in the command") + try: +- instanceList = retry_api_execute(options, conn.instances().list( +- project=options["--project"], +- zone=options["--zone"])) +- for instance in instanceList["items"]: +- result[instance["id"]] = (instance["name"], translate_status(instance["status"])) ++ for zone in options["--zone"].split(","): ++ instanceList = retry_api_execute(options, conn.instances().list( ++ project=options["--project"], ++ zone=zone)) ++ for instance in instanceList["items"]: ++ result[instance["id"]] = (instance["name"], translate_status(instance["status"])) + except Exception as err: +- fail_usage("Failed: get_nodes_list: {}".format(str(err))) ++ fail_fence_agent(options, "Failed: get_nodes_list: {}".format(str(err))) + + return result + +@@ -142,23 +158,54 @@ + return "off" + else: + return "on" ++ # If zone is not listed for an entry we attempt to get it automatically ++ instance = options["--plug"] ++ zone = get_zone(conn, options, instance) if "--plugzonemap" not in options else options["--plugzonemap"][instance] ++ instance_status = get_instance_power_status(conn, options, instance, zone) ++ # If any of the instances do not match the intended status we return the ++ # the opposite status so that the fence agent can change it. ++ if instance_status != options.get("--action"): ++ return instance_status ++ ++ return options.get("--action") ++ ++ ++def get_instance_power_status(conn, options, instance, zone): + try: +- instance = retry_api_execute(options, conn.instances().get( +- project=options["--project"], +- zone=options["--zone"], +- instance=options["--plug"])) ++ instance = retry_api_execute( ++ options, ++ conn.instances().get(project=options["--project"], zone=zone, instance=instance)) + return translate_status(instance["status"]) + except Exception as err: +- fail_usage("Failed: get_power_status: {}".format(str(err))) ++ fail_fence_agent(options, "Failed: get_instance_power_status: {}".format(str(err))) + + +-def wait_for_operation(conn, options, operation): ++def check_for_existing_operation(conn, options, instance, zone, operation_type): ++ logging.debug("check_for_existing_operation") ++ if "--baremetalsolution" in options: ++ # There is no API for checking in progress operations ++ return False ++ ++ project = options["--project"] ++ target_link = INSTANCE_LINK.format(project, zone, instance) ++ query_filter = '(targetLink = "{}") AND (operationType = "{}") AND (status = "RUNNING")'.format(target_link, operation_type) ++ result = retry_api_execute( ++ options, ++ conn.zoneOperations().list(project=project, zone=zone, filter=query_filter, maxResults=1)) ++ ++ if "items" in result and result["items"]: ++ logging.info("Existing %s operation found", operation_type) ++ return result["items"][0] ++ ++ ++def wait_for_operation(conn, options, zone, operation): + if 'name' not in operation: + logging.warning('Cannot wait for operation to complete, the' + ' requested operation will continue asynchronously') +- return ++ return False ++ ++ wait_time = 0 + project = options["--project"] +- zone = options["--zone"] + while True: + result = retry_api_execute(options, conn.zoneOperations().get( + project=project, +@@ -166,56 +213,93 @@ + operation=operation['name'])) + if result['status'] == 'DONE': + if 'error' in result: +- raise Exception(result['error']) +- return ++ raise_fence_agent(options, result['error']) ++ return True ++ ++ if "--errortimeout" in options and wait_time > int(options["--errortimeout"]): ++ raise_fence_agent(options, "Operation did not complete before the timeout.") ++ ++ if "--warntimeout" in options and wait_time > int(options["--warntimeout"]): ++ logging.warning("Operation did not complete before the timeout.") ++ if "--runonwarn" in options: ++ run_command(options, options["--runonwarn"]) ++ return False ++ ++ wait_time = wait_time + 1 + time.sleep(1) + + + def set_power_status(conn, options): +- logging.debug("set_power_status"); ++ logging.debug("set_power_status") ++ instance = options["--plug"] ++ # If zone is not listed for an entry we attempt to get it automatically ++ zone = get_zone(conn, options, instance) if "--plugzonemap" not in options else options["--plugzonemap"][instance] ++ set_instance_power_status(conn, options, instance, zone, options["--action"]) ++ ++ ++def set_instance_power_status(conn, options, instance, zone, action): ++ logging.info("Setting power status of %s in zone %s", instance, zone) ++ project = options["--project"] ++ + try: +- if options["--action"] == "off": +- logging.info("Issuing poweroff of %s in zone %s" % (options["--plug"], options["--zone"])) +- operation = retry_api_execute(options, conn.instances().stop( +- project=options["--project"], +- zone=options["--zone"], +- instance=options["--plug"])) ++ if action == "off": ++ logging.info("Issuing poweroff of %s in zone %s", instance, zone) ++ operation = check_for_existing_operation(conn, options, instance, zone, "stop") ++ if operation and "--earlyexit" in options: ++ return ++ if not operation: ++ operation = retry_api_execute( ++ options, ++ conn.instances().stop(project=project, zone=zone, instance=instance)) + logging.info("Poweroff command completed, waiting for the operation to complete") +- wait_for_operation(conn, options, operation) +- logging.info("Poweroff of %s in zone %s complete" % (options["--plug"], options["--zone"])) +- elif options["--action"] == "on": +- logging.info("Issuing poweron of %s in zone %s" % (options["--plug"], options["--zone"])) +- operation = retry_api_execute(options, conn.instances().start( +- project=options["--project"], +- zone=options["--zone"], +- instance=options["--plug"])) +- wait_for_operation(conn, options, operation) +- logging.info("Poweron of %s in zone %s complete" % (options["--plug"], options["--zone"])) ++ if wait_for_operation(conn, options, zone, operation): ++ logging.info("Poweroff of %s in zone %s complete", instance, zone) ++ elif action == "on": ++ logging.info("Issuing poweron of %s in zone %s", instance, zone) ++ operation = check_for_existing_operation(conn, options, instance, zone, "start") ++ if operation and "--earlyexit" in options: ++ return ++ if not operation: ++ operation = retry_api_execute( ++ options, ++ conn.instances().start(project=project, zone=zone, instance=instance)) ++ if wait_for_operation(conn, options, zone, operation): ++ logging.info("Poweron of %s in zone %s complete", instance, zone) + except Exception as err: +- fail_usage("Failed: set_power_status: {}".format(str(err))) +- ++ fail_fence_agent(options, "Failed: set_instance_power_status: {}".format(str(err))) + + def power_cycle(conn, options): +- logging.debug("power_cycle"); ++ logging.debug("power_cycle") ++ instance = options["--plug"] ++ # If zone is not listed for an entry we attempt to get it automatically ++ zone = get_zone(conn, options, instance) if "--plugzonemap" not in options else options["--plugzonemap"][instance] ++ return power_cycle_instance(conn, options, instance, zone) ++ ++ ++def power_cycle_instance(conn, options, instance, zone): ++ logging.info("Issuing reset of %s in zone %s", instance, zone) ++ project = options["--project"] ++ + try: +- logging.info('Issuing reset of %s in zone %s' % (options["--plug"], options["--zone"])) +- operation = retry_api_execute(options, conn.instances().reset( +- project=options["--project"], +- zone=options["--zone"], +- instance=options["--plug"])) +- logging.info("Reset command completed, waiting for the operation to complete") +- wait_for_operation(conn, options, operation) +- logging.info('Reset of %s in zone %s complete' % (options["--plug"], options["--zone"])) ++ operation = check_for_existing_operation(conn, options, instance, zone, "reset") ++ if operation and "--earlyexit" in options: ++ return True ++ if not operation: ++ operation = retry_api_execute( ++ options, ++ conn.instances().reset(project=project, zone=zone, instance=instance)) ++ logging.info("Reset command sent, waiting for the operation to complete") ++ if wait_for_operation(conn, options, zone, operation): ++ logging.info("Reset of %s in zone %s complete", instance, zone) + return True + except Exception as err: +- logging.error("Failed: power_cycle: {}".format(str(err))) +- return False ++ logging.exception("Failed: power_cycle") ++ raise err + + +-def get_zone(conn, options): ++def get_zone(conn, options, instance): + logging.debug("get_zone"); + project = options['--project'] +- instance = options['--plug'] + fl = 'name="%s"' % instance + request = replace_api_uri(options, conn.instances().aggregatedList(project=project, filter=fl)) + while request is not None: +@@ -227,7 +311,7 @@ + return inst['zone'].split("/")[-1] + request = replace_api_uri(options, conn.instances().aggregatedList_next( + previous_request=request, previous_response=response)) +- raise Exception("Unable to find instance %s" % (instance)) ++ raise_fence_agent(options, "Unable to find instance %s" % (instance)) + + + def get_metadata(metadata_key, params=None, timeout=None): +@@ -326,13 +410,21 @@ + "required" : "0", + "order" : 9 + } ++ all_opt["plugzonemap"] = { ++ "getopt" : ":", ++ "longopt" : "plugzonemap", ++ "help" : "--plugzonemap=[plugzonemap] Comma separated zone map when fencing multiple plugs", ++ "shortdesc" : "Comma separated zone map when fencing multiple plugs.", ++ "required" : "0", ++ "order" : 10 ++ } + all_opt["proxyhost"] = { + "getopt" : ":", + "longopt" : "proxyhost", + "help" : "--proxyhost=[proxy_host] The proxy host to use, if one is needed to access the internet (Example: 10.122.0.33)", + "shortdesc" : "If a proxy is used for internet access, the proxy host should be specified.", + "required" : "0", +- "order" : 10 ++ "order" : 11 + } + all_opt["proxyport"] = { + "getopt" : ":", +@@ -341,7 +433,49 @@ + "help" : "--proxyport=[proxy_port] The proxy port to use, if one is needed to access the internet (Example: 3127)", + "shortdesc" : "If a proxy is used for internet access, the proxy port should be specified.", + "required" : "0", +- "order" : 11 ++ "order" : 12 ++ } ++ all_opt["earlyexit"] = { ++ "getopt" : "", ++ "longopt" : "earlyexit", ++ "help" : "--earlyexit Return early if reset is already in progress", ++ "shortdesc" : "If an existing reset operation is detected, the fence agent will return before the operation completes with a 0 return code.", ++ "required" : "0", ++ "order" : 13 ++ } ++ all_opt["warntimeout"] = { ++ "getopt" : ":", ++ "type" : "second", ++ "longopt" : "warntimeout", ++ "help" : "--warntimeout=[warn_timeout] Timeout seconds before logging a warning and returning a 0 status code", ++ "shortdesc" : "If the operation is not completed within the timeout, the cluster operations are allowed to continue.", ++ "required" : "0", ++ "order" : 14 ++ } ++ all_opt["errortimeout"] = { ++ "getopt" : ":", ++ "type" : "second", ++ "longopt" : "errortimeout", ++ "help" : "--errortimeout=[error_timeout] Timeout seconds before failing and returning a non-zero status code", ++ "shortdesc" : "If the operation is not completed within the timeout, cluster is notified of the operation failure.", ++ "required" : "0", ++ "order" : 15 ++ } ++ all_opt["runonwarn"] = { ++ "getopt" : ":", ++ "longopt" : "runonwarn", ++ "help" : "--runonwarn=[run_on_warn] If a timeout occurs and warning is generated, run the supplied command", ++ "shortdesc" : "If a timeout would occur while running the agent, then the supplied command is run.", ++ "required" : "0", ++ "order" : 16 ++ } ++ all_opt["runonfail"] = { ++ "getopt" : ":", ++ "longopt" : "runonfail", ++ "help" : "--runonfail=[run_on_fail] If a failure occurs, run the supplied command", ++ "shortdesc" : "If a failure would occur while running the agent, then the supplied command is run.", ++ "required" : "0", ++ "order" : 17 + } + + +@@ -350,7 +484,8 @@ + + device_opt = ["port", "no_password", "zone", "project", "stackdriver-logging", + "method", "baremetalsolution", "apitimeout", "retries", "retrysleep", +- "serviceaccount", "proxyhost", "proxyport"] ++ "serviceaccount", "plugzonemap", "proxyhost", "proxyport", "earlyexit", ++ "warntimeout", "errortimeout", "runonwarn", "runonfail"] + + atexit.register(atexit_handler) + +@@ -431,22 +566,39 @@ + conn = googleapiclient.discovery.build( + 'compute', 'v1', credentials=credentials, cache_discovery=False) + except Exception as err: +- fail_usage("Failed: Create GCE compute v1 connection: {}".format(str(err))) ++ fail_fence_agent(options, "Failed: Create GCE compute v1 connection: {}".format(str(err))) + + # Get project and zone + if not options.get("--project"): + try: + options["--project"] = get_metadata('project/project-id') + except Exception as err: +- fail_usage("Failed retrieving GCE project. Please provide --project option: {}".format(str(err))) ++ fail_fence_agent(options, "Failed retrieving GCE project. Please provide --project option: {}".format(str(err))) + + if "--baremetalsolution" in options: + options["--zone"] = "none" +- if not options.get("--zone"): +- try: +- options["--zone"] = get_zone(conn, options) +- except Exception as err: +- fail_usage("Failed retrieving GCE zone. Please provide --zone option: {}".format(str(err))) ++ ++ # Populates zone automatically if missing from the command ++ zones = [] if not "--zone" in options else options["--zone"].split(",") ++ options["--plugzonemap"] = {} ++ if "--plug" in options: ++ for i, instance in enumerate(options["--plug"].split(",")): ++ if len(zones) == 1: ++ # If only one zone is specified, use it across all plugs ++ options["--plugzonemap"][instance] = zones[0] ++ continue ++ ++ if len(zones) - 1 >= i: ++ # If we have enough zones specified with the --zone flag use the zone at ++ # the same index as the plug ++ options["--plugzonemap"][instance] = zones[i] ++ continue ++ ++ try: ++ # In this case we do not have a zone specified so we attempt to detect it ++ options["--plugzonemap"][instance] = get_zone(conn, options, instance) ++ except Exception as err: ++ fail_fence_agent(options, "Failed retrieving GCE zone. Please provide --zone option: {}".format(str(err))) + + # Operate the fencing device + result = fence_action(conn, options, set_power_status, get_power_status, get_nodes_list, power_cycle) diff --git a/bz2149691-1-all-agents-unify-ssl-parameters.patch b/bz2149691-1-all-agents-unify-ssl-parameters.patch new file mode 100644 index 0000000000000000000000000000000000000000..6f8f0af1ac0ae039614f02949460bac3683957dd --- /dev/null +++ b/bz2149691-1-all-agents-unify-ssl-parameters.patch @@ -0,0 +1,291 @@ +From 999f2f8b4dc7d258679daf8c3f13d9b317ff4435 Mon Sep 17 00:00:00 2001 +From: Oyvind Albrigtsen +Date: Thu, 7 Apr 2022 13:11:12 +0200 +Subject: [PATCH] all agents: unify ssl parameters to avoid having to use --ssl + when using --ssl-secure/--ssl-insecure for some agents + +THIS MIGHT BREAK SETUPS USING fence_docker or fence_pve! +--- + agents/cisco_ucs/fence_cisco_ucs.py | 9 +++++---- + agents/docker/fence_docker.py | 9 ++++++--- + agents/ibmz/fence_ibmz.py | 4 ++-- + agents/rhevm/fence_rhevm.py | 8 ++++---- + agents/skalar/fence_skalar.py | 2 +- + agents/vmware_rest/fence_vmware_rest.py | 8 ++++---- + agents/vmware_soap/fence_vmware_soap.py | 2 +- + agents/vmware_vcloud/fence_vmware_vcloud.py | 4 ++-- + agents/zvm/fence_zvmip.py | 8 +++++--- + lib/fencing.py.py | 6 ++++++ + tests/data/metadata/fence_docker.xml | 4 ++-- + 13 files changed, 64 insertions(+), 31 deletions(-) + +diff --git a/agents/cisco_ucs/fence_cisco_ucs.py b/agents/cisco_ucs/fence_cisco_ucs.py +index 2280dbbc7..b85379a73 100644 +--- a/agents/cisco_ucs/fence_cisco_ucs.py ++++ b/agents/cisco_ucs/fence_cisco_ucs.py +@@ -99,7 +99,7 @@ def get_list(conn, options): + + def send_command(opt, command, timeout): + ## setup correct URL +- if "--ssl" in opt or "--ssl-secure" in opt or "--ssl-insecure" in opt: ++ if "--ssl-secure" in opt or "--ssl-insecure" in opt: + url = "https:" + else: + url = "http:" +@@ -114,13 +114,14 @@ def send_command(opt, command, timeout): + conn.setopt(pycurl.POSTFIELDS, command.encode("ascii")) + conn.setopt(pycurl.WRITEFUNCTION, web_buffer.write) + conn.setopt(pycurl.TIMEOUT, timeout) +- if "--ssl" in opt or "--ssl-secure" in opt: ++ ++ if "--ssl-secure" in opt: + conn.setopt(pycurl.SSL_VERIFYPEER, 1) + conn.setopt(pycurl.SSL_VERIFYHOST, 2) +- +- if "--ssl-insecure" in opt: ++ elif "--ssl-insecure" in opt: + conn.setopt(pycurl.SSL_VERIFYPEER, 0) + conn.setopt(pycurl.SSL_VERIFYHOST, 0) ++ + conn.perform() + result = web_buffer.getvalue().decode() + +diff --git a/agents/docker/fence_docker.py b/agents/docker/fence_docker.py +index fef87da86..004402518 100644 +--- a/agents/docker/fence_docker.py ++++ b/agents/docker/fence_docker.py +@@ -43,7 +43,7 @@ def get_list(conn, options): + + + def send_cmd(options, cmd, post = False): +- url = "http%s://%s:%s/v%s/%s" % ("s" if "--ssl" in options else "", options["--ip"], options["--ipport"], options["--api-version"], cmd) ++ url = "http%s://%s:%s/v%s/%s" % ("s" if "--ssl-secure" in options or "--ssl-insecure" in options else "", options["--ip"], options["--ipport"], options["--api-version"], cmd) + conn = pycurl.Curl() + output_buffer = io.BytesIO() + if logging.getLogger().getEffectiveLevel() < logging.WARNING: +@@ -55,7 +55,8 @@ def send_cmd(options, cmd, post = False): + conn.setopt(pycurl.POSTFIELDSIZE, 0) + conn.setopt(pycurl.WRITEFUNCTION, output_buffer.write) + conn.setopt(pycurl.TIMEOUT, int(options["--shell-timeout"])) +- if "--ssl" in options: ++ ++ if "--ssl-secure" in options: + if not (set(("--tlscert", "--tlskey", "--tlscacert")) <= set(options)): + fail_usage("Failed. If --ssl option is used, You have to also \ + specify: --tlscert, --tlskey and --tlscacert") +@@ -63,7 +64,7 @@ def send_cmd(options, cmd, post = False): + conn.setopt(pycurl.SSLCERT, options["--tlscert"]) + conn.setopt(pycurl.SSLKEY, options["--tlskey"]) + conn.setopt(pycurl.CAINFO, options["--tlscacert"]) +- else: ++ elif "--ssl-insecure" in options: + conn.setopt(pycurl.SSL_VERIFYPEER, 0) + conn.setopt(pycurl.SSL_VERIFYHOST, 0) + +@@ -136,6 +137,8 @@ def main(): + + device_opt = ["ipaddr", "no_password", "no_login", "port", "method", "web", "tlscert", "tlskey", "tlscacert", "ssl", "api_version"] + ++ all_opt["ssl"]["default"] = "1" ++ + options = check_input(device_opt, process_input(device_opt)) + + docs = { } +diff --git a/agents/ibmz/fence_ibmz.py b/agents/ibmz/fence_ibmz.py +index 47408ccf4..d477adeb9 100644 +--- a/agents/ibmz/fence_ibmz.py ++++ b/agents/ibmz/fence_ibmz.py +@@ -534,7 +534,7 @@ def main(): + requests_log.propagate = True + if "--verbose" in options: + requests_log.setLevel(logging.DEBUG) +- if "--ssl-secure" not in options: ++ if "--ssl-insecure" in options: + urllib3.disable_warnings( + category=urllib3.exceptions.InsecureRequestWarning) + +@@ -548,7 +548,7 @@ def main(): + 'connect_timeout': int(options['--connect-timeout']), + 'read_timeout': int(options['--read-timeout']), + 'port': int(options['--ipport']), +- 'ssl_verify': bool('--ssl-secure' in options), ++ 'ssl_verify': bool('--ssl-insecure' not in options), + } + try: + conn = APIClient(hmc_address, hmc_userid, hmc_password, config) +diff --git a/agents/rhevm/fence_rhevm.py b/agents/rhevm/fence_rhevm.py +index 25aecbe58..5f74d06f6 100644 +--- a/agents/rhevm/fence_rhevm.py ++++ b/agents/rhevm/fence_rhevm.py +@@ -85,7 +85,7 @@ def send_command(opt, command, method="GET"): + logging.debug("auto-detected API version: " + opt["--api-version"]) + + ## setup correct URL +- if "--ssl" in opt or "--ssl-secure" in opt or "--ssl-insecure" in opt: ++ if "--ssl-secure" in opt or "--ssl-insecure" in opt: + url = "https:" + else: + url = "http:" +@@ -126,11 +126,11 @@ def send_command(opt, command, method="GET"): + conn.setopt(pycurl.COOKIEJAR, cookie_file) + + conn.setopt(pycurl.TIMEOUT, int(opt["--shell-timeout"])) +- if "--ssl" in opt or "--ssl-secure" in opt: ++ ++ if "--ssl-secure" in opt: + conn.setopt(pycurl.SSL_VERIFYPEER, 1) + conn.setopt(pycurl.SSL_VERIFYHOST, 2) +- +- if "--ssl-insecure" in opt: ++ elif "--ssl-insecure" in opt: + conn.setopt(pycurl.SSL_VERIFYPEER, 0) + conn.setopt(pycurl.SSL_VERIFYHOST, 0) + +diff --git a/agents/skalar/fence_skalar.py b/agents/skalar/fence_skalar.py +index 959527411..0e11d83f9 100644 +--- a/agents/skalar/fence_skalar.py ++++ b/agents/skalar/fence_skalar.py +@@ -200,7 +200,7 @@ def main(): + run_delay(options) + + proto = "https://" +- if "--ssl" in options or "--ssl-secure" in options: ++ if "--ssl-secure" in options: + ssl_verify = True + elif "--ssl-insecure" in options: + ssl_verify = False +diff --git a/agents/vmware_rest/fence_vmware_rest.py b/agents/vmware_rest/fence_vmware_rest.py +index e49fd5663..4b884fc62 100644 +--- a/agents/vmware_rest/fence_vmware_rest.py ++++ b/agents/vmware_rest/fence_vmware_rest.py +@@ -69,7 +69,7 @@ def connect(opt): + conn = pycurl.Curl() + + ## setup correct URL +- if "--ssl" in opt or "--ssl-secure" in opt or "--ssl-insecure" in opt: ++ if "--ssl-secure" in opt or "--ssl-insecure" in opt: + conn.base_url = "https:" + else: + conn.base_url = "http:" +@@ -89,11 +89,11 @@ def connect(opt): + conn.setopt(pycurl.USERPWD, opt["--username"] + ":" + opt["--password"]) + + conn.setopt(pycurl.TIMEOUT, int(opt["--shell-timeout"])) +- if "--ssl" in opt or "--ssl-secure" in opt: ++ ++ if "--ssl-secure" in opt: + conn.setopt(pycurl.SSL_VERIFYPEER, 1) + conn.setopt(pycurl.SSL_VERIFYHOST, 2) +- +- if "--ssl-insecure" in opt: ++ elif "--ssl-insecure" in opt: + conn.setopt(pycurl.SSL_VERIFYPEER, 0) + conn.setopt(pycurl.SSL_VERIFYHOST, 0) + +diff --git a/agents/vmware_soap/fence_vmware_soap.py b/agents/vmware_soap/fence_vmware_soap.py +index 2cd45e0b3..51fb0f147 100644 +--- a/agents/vmware_soap/fence_vmware_soap.py ++++ b/agents/vmware_soap/fence_vmware_soap.py +@@ -34,7 +34,7 @@ def send(self, request): + def soap_login(options): + run_delay(options) + +- if "--ssl" in options or "--ssl-secure" in options or "--ssl-insecure" in options: ++ if "--ssl-secure" in options or "--ssl-insecure" in options: + if "--ssl-insecure" in options: + import ssl + import urllib3 +diff --git a/agents/vmware_vcloud/fence_vmware_vcloud.py b/agents/vmware_vcloud/fence_vmware_vcloud.py +index 42372a83d..7626b82bb 100644 +--- a/agents/vmware_vcloud/fence_vmware_vcloud.py ++++ b/agents/vmware_vcloud/fence_vmware_vcloud.py +@@ -60,7 +60,7 @@ def connect(opt): + conn = pycurl.Curl() + + ## setup correct URL +- if "--ssl" in opt or "--ssl-secure" in opt or "--ssl-insecure" in opt: ++ if "--ssl-secure" in opt or "--ssl-insecure" in opt: + conn.base_url = "https:" + else: + conn.base_url = "http:" +@@ -76,7 +76,7 @@ def connect(opt): + conn.setopt(pycurl.USERPWD, opt["--username"] + ":" + opt["--password"]) + + conn.setopt(pycurl.TIMEOUT, int(opt["--shell-timeout"])) +- if "--ssl" in opt or "--ssl-secure" in opt: ++ if "--ssl-secure" in opt: + conn.setopt(pycurl.SSL_VERIFYPEER, 1) + conn.setopt(pycurl.SSL_VERIFYHOST, 2) + elif "--ssl-insecure" in opt: +diff --git a/agents/zvm/fence_zvmip.py b/agents/zvm/fence_zvmip.py +index e8f849eda..90ca95d45 100644 +--- a/agents/zvm/fence_zvmip.py ++++ b/agents/zvm/fence_zvmip.py +@@ -26,7 +26,7 @@ def open_socket(options): + except socket.gaierror: + fail(EC_LOGIN_DENIED) + +- if "--ssl" in options: ++ if "--ssl-secure" in options or "--ssl-insecure" in options: + import ssl + sock = socket.socket() + sslcx = ssl.create_default_context() +@@ -132,7 +132,7 @@ def get_list_of_images(options, command, data_as_plug): + images = set() + + if output_len > 3*INT4: +- recvflag = socket.MSG_WAITALL if "--ssl" not in options else 0 ++ recvflag = socket.MSG_WAITALL if "--ssl-secure" not in options and "--ssl-insecure" not in options else 0 + array_len = struct.unpack("!i", conn.recv(INT4))[0] + data = "" + +@@ -182,7 +182,9 @@ def main(): + options = check_input(device_opt, process_input(device_opt), other_conditions=True) + + if "--disable-ssl" in options or options["--ssl"] == "0": +- del options["--ssl"] ++ for k in ["--ssl", "--ssl-secure", "--ssl-insecure"]: ++ if k in options: ++ del options[k] + + if len(options.get("--plug", "")) > 8: + fail_usage("Failed: Name of image can not be longer than 8 characters") +diff --git a/lib/fencing.py.py b/lib/fencing.py.py +index 696388d55..b746ede8b 100644 +--- a/lib/fencing.py.py ++++ b/lib/fencing.py.py +@@ -789,6 +789,12 @@ def check_input(device_opt, opt, other_conditions = False): + if "--password-script" in options: + options["--password"] = os.popen(options["--password-script"]).read().rstrip() + ++ if "--ssl-secure" in options or "--ssl-insecure" in options: ++ options["--ssl"] = "" ++ ++ if "--ssl" in options and "--ssl-insecure" not in options: ++ options["--ssl-secure"] = "" ++ + if os.environ.get("PCMK_service") == "pacemaker-fenced" and "--disable-timeout" not in options: + options["--disable-timeout"] = "1" + +diff --git a/tests/data/metadata/fence_docker.xml b/tests/data/metadata/fence_docker.xml +index 723e72280..51c7c470a 100644 +--- a/tests/data/metadata/fence_docker.xml ++++ b/tests/data/metadata/fence_docker.xml +@@ -20,7 +20,7 @@ + + + +- ++ + TCP/UDP port to use for connection with device + + +@@ -43,7 +43,7 @@ + + + +- ++ + Use SSL connection with verifying certificate + + diff --git a/bz2149691-2-fence_zvmip-connect-error.patch b/bz2149691-2-fence_zvmip-connect-error.patch new file mode 100644 index 0000000000000000000000000000000000000000..1a1bd972bc7f2db886e65fab454ea5e988746818 --- /dev/null +++ b/bz2149691-2-fence_zvmip-connect-error.patch @@ -0,0 +1,30 @@ +From 6430104318b4bf349425b08636183bf839812e04 Mon Sep 17 00:00:00 2001 +From: Oyvind Albrigtsen +Date: Tue, 31 May 2022 08:55:25 +0200 +Subject: [PATCH] fence_zvmip: show unable to connect error instead of full + stacktrace, e.g. when not using --ssl for SSL devices + +--- + agents/zvm/fence_zvmip.py | 9 +++++++-- + 1 file changed, 7 insertions(+), 2 deletions(-) + +diff --git a/agents/zvm/fence_zvmip.py b/agents/zvm/fence_zvmip.py +index 90ca95d45..4f538e10d 100644 +--- a/agents/zvm/fence_zvmip.py ++++ b/agents/zvm/fence_zvmip.py +@@ -127,8 +127,13 @@ def get_list_of_images(options, command, data_as_plug): + + conn.send(packet) + +- request_id = struct.unpack("!i", conn.recv(INT4))[0] +- (output_len, request_id, return_code, reason_code) = struct.unpack("!iiii", conn.recv(INT4 * 4)) ++ try: ++ request_id = struct.unpack("!i", conn.recv(INT4))[0] ++ (output_len, request_id, return_code, reason_code) = struct.unpack("!iiii", conn.recv(INT4 * 4)) ++ except struct.error: ++ logging.debug(sys.exc_info()) ++ fail_usage("Failed: Unable to connect to {} port: {} SSL: {} \n".format(options["--ip"], options["--ipport"], bool("--ssl" in options))) ++ + images = set() + + if output_len > 3*INT4: diff --git a/cachetools-4.2.4.tar.gz b/cachetools-4.2.4.tar.gz deleted file mode 100644 index c475518965d39deced60eba1edfd71f2506d20f7..0000000000000000000000000000000000000000 Binary files a/cachetools-4.2.4.tar.gz and /dev/null differ diff --git a/certifi-2021.10.8.tar.gz b/certifi-2021.10.8.tar.gz deleted file mode 100644 index 9e1581b8e08fbbaad11e4413dac9324c03104754..0000000000000000000000000000000000000000 Binary files a/certifi-2021.10.8.tar.gz and /dev/null differ diff --git a/charset-normalizer-2.0.7.tar.gz b/charset-normalizer-2.0.7.tar.gz deleted file mode 100644 index 61df022ad86c0d3726c53d4b47560061d8465d8d..0000000000000000000000000000000000000000 Binary files a/charset-normalizer-2.0.7.tar.gz and /dev/null differ diff --git a/colorama-0.3.3.tar.gz b/colorama-0.3.3.tar.gz deleted file mode 100644 index a926e8bcc6654a34e37ebf1f9db73d7b55e9e264..0000000000000000000000000000000000000000 Binary files a/colorama-0.3.3.tar.gz and /dev/null differ diff --git a/dist b/dist new file mode 100644 index 0000000000000000000000000000000000000000..80139a041832c9091cefa2a01d8df0045a1689df --- /dev/null +++ b/dist @@ -0,0 +1 @@ +an9_0 diff --git a/download b/download new file mode 100644 index 0000000000000000000000000000000000000000..a0b503994581b44170c9cbe1b1692f3c1bcc7068 --- /dev/null +++ b/download @@ -0,0 +1,47 @@ +832fbc4db8822fcb0099edb7158ddf81 aliyun-python-sdk-core-2.11.5.tar.gz +7c2d43fbfb0faeddec259a7f26adb8dc awscli-2.2.15.tar.gz +c64f38a505b122a2ecf2b7d93c0ec4b7 cachetools-4.2.4.tar.gz +880ed9e5d04aff8f46f5ff82a3a3e395 certifi-2021.10.8.tar.gz +b28e4463613ff3911d5a2dc62b96233f charset-normalizer-2.0.7.tar.gz +a56b8dc55158a41ab3c89c4c8feb8824 colorama-0.3.3.tar.gz +62655d4b45872572f243d0eb7e9dd1f9 fence-agents-4.10.0.tar.gz +a61b1015a213f1a9cf27252fbac579ee google-auth-2.3.0.tar.gz +5856306eac5f25db8249e37a4c6ee3e7 idna-3.3.tar.gz +059f89375d7ea60eb7013f341f0b89e7 Jinja2-3.0.2.tar.gz +d44bf469fcc16312e12fe8548cb177ee kubernetes-12.0.1.tar.gz +892e0fefa3c488387e5cc0cad2daa523 MarkupSafe-2.0.1.tar.gz +e46e2af1ad29245ddbd93972770f528b msal-1.18.0.tar.gz +93f47277871a06956432af604c543cb2 msal-extensions-1.0.0.tar.gz +68d5804254642905ba87ede509e68970 msgpack-1.0.2.tar.gz +3146dcb3297dd018ae5eb9a52b440419 netifaces-0.11.0.tar.gz +9201e30a4eacf3ecfa15503b241ad5e3 oauthlib-3.1.1.tar.gz +6aef637aec8c21ae1c41f02aa731fa29 openshift-0.12.1.tar.gz +26909d08551f369fcde80f43529a1f92 poetry-core-1.0.7.tar.gz +3c4c381a4cecfd21f9f3259b7617efeb portalocker-2.5.1.tar.gz +dffae4ff9f997a83324b3f33fe62be54 pyasn1-0.4.8.tar.gz +107e1ece7d0a41d782f69f8a95a4d9bc pyasn1-modules-0.2.8.tar.gz +e1a8c5ecb51dd87472362ff6ce575675 pyparsing-3.0.1.tar.gz +fe5b62f042e66f971e527d66beb18267 pyroute2-0.6.4.tar.gz +c71887abb338291469aff2ada3384900 pyroute2.core-0.6.4.tar.gz +4f256b16bb0a4516566c2424301c56ff pyroute2.ethtool-0.6.4.tar.gz +b78eb0a604c5d99db8c7a890a21f4c74 pyroute2.ipdb-0.6.4.tar.gz +999dd68a0a54b396ad43f4f056f119f4 pyroute2.ipset-0.6.4.tar.gz +6d85ad856fa6fc8a3ea0276fefea3df7 pyroute2.ndb-0.6.4.tar.gz +7f73cda2ca895ea8bea84308000fd568 pyroute2.nftables-0.6.4.tar.gz +27730cf2d33786aa89903efd782b4864 pyroute2.nslink-0.6.4.tar.gz +70ef5c5e6b05badc8675dcc3106d90cc python-string-utils-1.0.0.tar.gz +3b07eb596071bac75c886129de881d22 PyYAML-5.1.tar.gz +1d19c798f25e58e3e582f0f8c977dbb8 PyYAML-6.0.tar.gz +8c745949ad3e9ae83d9927fed213db8a requests-2.26.0.tar.gz +1ebcd55f1b1b9281940b4bc33010e2ba requests-oauthlib-1.3.0.tar.gz +c21701cdd75c170f8d690f704a362c44 rsa-4.7.2.tar.gz +dd811a8f09dc0e622ad19a42508da7c1 ruamel.yaml-0.15.100.tar.gz +ef2af87b5f265163700b12165a541406 ruamel.yaml-0.17.16.tar.gz +e2397bedcd1f40b2f22b3696175082aa ruamel.yaml.clib-0.2.6.tar.gz +7a2c32ef46b0f91acc8c2756af56a711 setuptools-58.3.0.tar.gz +32918d8ac566360c21411e0b3556c695 setuptools_scm-6.3.2.tar.gz +a7c927740e4964dd29b72cebfc1429bb six-1.16.0.tar.gz +36fd182000c721cf495d4dc673a6f9e9 tomli-1.0.1.tar.gz +e0051a87a956e618a6bb514a07fa7773 urllib3-1.26.7.tar.gz +a043b9a04dc10a7c9f333cf55f6222df websocket-client-1.2.1.tar.gz +6d56ed0de4336462a73350341462f45e wrapt-1.12.1.tar.gz diff --git a/fence-agents-4.10.0.tar.gz b/fence-agents-4.10.0.tar.gz deleted file mode 100644 index fc6ec00678394e3a5713dc3b1ac5d5cf96612926..0000000000000000000000000000000000000000 Binary files a/fence-agents-4.10.0.tar.gz and /dev/null differ diff --git a/fence-agents.spec b/fence-agents.spec index 793d76f7fe57b59fe10ebc20b6d24e8d3e77d975..9a67f691539422e3b92ff748e1cb9454ba9cbb00 100644 --- a/fence-agents.spec +++ b/fence-agents.spec @@ -1,3 +1,4 @@ +%define anolis_release .0.1 # Copyright 2004-2011 Red Hat, Inc. # This copyrighted material is made available to anyone wishing to use, # modify, copy, or redistribute it subject to the terms and conditions @@ -59,7 +60,7 @@ Name: fence-agents Summary: Set of unified programs capable of host isolation ("fencing") Version: 4.10.0 -Release: 20%{?alphatag:.%{alphatag}}%{?dist}.2 +Release: 20%{?alphatag:.%{alphatag}}%{anolis_release}%{?dist}.6 License: GPLv2+ and LGPLv2+ URL: https://github.com/ClusterLabs/fence-agents Source0: https://fedorahosted.org/releases/f/e/fence-agents/%{name}-%{version}.tar.gz @@ -109,118 +110,122 @@ Source1024: azure_core-1.15.0-py2.py3-none-any.whl Source1025: azure_mgmt_compute-21.0.0-py2.py3-none-any.whl Source1026: azure_mgmt_core-1.2.2-py2.py3-none-any.whl Source1027: azure_mgmt_network-19.0.0-py2.py3-none-any.whl -Source1028: certifi-2021.5.30-py2.py3-none-any.whl -Source1029: chardet-4.0.0-py2.py3-none-any.whl -Source1030: idna-2.10-py2.py3-none-any.whl -Source1031: isodate-0.6.0-py2.py3-none-any.whl -Source1032: msrest-0.6.21-py2.py3-none-any.whl -Source1033: msrestazure-0.6.4-py2.py3-none-any.whl -Source1034: oauthlib-3.1.1-py2.py3-none-any.whl -Source1035: PyJWT-2.1.0-py3-none-any.whl -Source1036: requests-2.25.1-py2.py3-none-any.whl -Source1037: requests_oauthlib-1.3.0-py2.py3-none-any.whl +Source1028: azure-identity-1.10.0.zip +Source1029: certifi-2021.5.30-py2.py3-none-any.whl +Source1030: chardet-4.0.0-py2.py3-none-any.whl +Source1031: idna-2.10-py2.py3-none-any.whl +Source1032: isodate-0.6.0-py2.py3-none-any.whl +Source1033: msrest-0.6.21-py2.py3-none-any.whl +Source1034: msrestazure-0.6.4-py2.py3-none-any.whl +Source1035: oauthlib-3.1.1-py2.py3-none-any.whl +Source1036: PyJWT-2.1.0-py3-none-any.whl +Source1037: requests-2.25.1-py2.py3-none-any.whl +Source1038: requests_oauthlib-1.3.0-py2.py3-none-any.whl +Source1139: msal-1.18.0.tar.gz +Source1140: msal-extensions-1.0.0.tar.gz +Source1141: portalocker-2.5.1.tar.gz # google -Source1038: cachetools-4.2.2-py3-none-any.whl -Source1039: chardet-3.0.4-py2.py3-none-any.whl -Source1040: google_api_core-1.30.0-py2.py3-none-any.whl -Source1041: google_api_python_client-1.12.8-py2.py3-none-any.whl -Source1042: googleapis_common_protos-1.53.0-py2.py3-none-any.whl -Source1043: google_auth-1.32.0-py2.py3-none-any.whl -Source1044: google_auth_httplib2-0.1.0-py2.py3-none-any.whl -Source1045: httplib2-0.19.1-py3-none-any.whl -Source1046: packaging-20.9-py2.py3-none-any.whl -Source1047: protobuf-3.17.3-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.whl -Source1048: pyasn1-0.4.8-py2.py3-none-any.whl -Source1049: pyasn1_modules-0.2.8-py2.py3-none-any.whl -Source1050: pyparsing-2.4.7-py2.py3-none-any.whl -Source1051: pyroute2-0.6.4.tar.gz -Source1052: pyroute2.core-0.6.4.tar.gz -Source1053: pyroute2.ethtool-0.6.4.tar.gz -Source1054: pyroute2.ipdb-0.6.4.tar.gz -Source1055: pyroute2.ipset-0.6.4.tar.gz -Source1056: pyroute2.ndb-0.6.4.tar.gz -Source1057: pyroute2.nftables-0.6.4.tar.gz -Source1058: pyroute2.nslink-0.6.4.tar.gz -Source1059: pytz-2021.1-py2.py3-none-any.whl -Source1060: rsa-4.7.2-py3-none-any.whl -Source1061: setuptools-57.0.0-py3-none-any.whl -Source1062: uritemplate-3.0.1-py2.py3-none-any.whl -# openstack -Source1063: PyYAML-5.1.tar.gz -Source1064: charset_normalizer-2.0.4-py3-none-any.whl -Source1065: debtcollector-2.2.0-py3-none-any.whl -Source1066: idna-3.2-py3-none-any.whl -Source1067: iso8601-0.1.16-py2.py3-none-any.whl -Source1068: keystoneauth1-4.3.1-py3-none-any.whl -Source1069: msgpack-1.0.2.tar.gz -Source1070: netaddr-0.8.0-py2.py3-none-any.whl -Source1071: netifaces-0.11.0.tar.gz -Source1072: oslo.config-8.7.1-py3-none-any.whl -Source1073: oslo.i18n-5.0.1-py3-none-any.whl -Source1074: oslo.serialization-4.2.0-py3-none-any.whl -Source1075: oslo.utils-4.10.0-py3-none-any.whl -Source1076: os_service_types-1.7.0-py2.py3-none-any.whl -Source1077: pbr-5.6.0-py2.py3-none-any.whl -Source1078: packaging-21.0-py3-none-any.whl -Source1079: prettytable-2.2.0-py3-none-any.whl -Source1080: python_keystoneclient-4.2.0-py3-none-any.whl -Source1081: python_novaclient-17.5.0-py3-none-any.whl -Source1082: requests-2.26.0-py2.py3-none-any.whl -Source1083: rfc3986-1.5.0-py2.py3-none-any.whl -Source1084: stevedore-3.4.0-py3-none-any.whl -Source1085: wcwidth-0.2.5-py2.py3-none-any.whl -Source1086: wheel-0.37.0-py2.py3-none-any.whl -Source1087: wrapt-1.12.1.tar.gz +Source1042: cachetools-4.2.2-py3-none-any.whl +Source1043: chardet-3.0.4-py2.py3-none-any.whl +Source1044: google_api_core-1.30.0-py2.py3-none-any.whl +Source1045: google_api_python_client-1.12.8-py2.py3-none-any.whl +Source1046: googleapis_common_protos-1.53.0-py2.py3-none-any.whl +Source1047: google_auth-1.32.0-py2.py3-none-any.whl +Source1048: google_auth_httplib2-0.1.0-py2.py3-none-any.whl +Source1049: httplib2-0.19.1-py3-none-any.whl +Source1050: packaging-20.9-py2.py3-none-any.whl +Source1051: protobuf-3.17.3-cp39-cp39-manylinux_2_5_x86_64.manylinux1_x86_64.whl +Source1052: pyasn1-0.4.8-py2.py3-none-any.whl +Source1053: pyasn1_modules-0.2.8-py2.py3-none-any.whl +Source1054: pyparsing-2.4.7-py2.py3-none-any.whl +Source1055: pyroute2-0.6.4.tar.gz +Source1056: pyroute2.core-0.6.4.tar.gz +Source1057: pyroute2.ethtool-0.6.4.tar.gz +Source1058: pyroute2.ipdb-0.6.4.tar.gz +Source1059: pyroute2.ipset-0.6.4.tar.gz +Source1060: pyroute2.ndb-0.6.4.tar.gz +Source1061: pyroute2.nftables-0.6.4.tar.gz +Source1062: pyroute2.nslink-0.6.4.tar.gz +Source1063: pytz-2021.1-py2.py3-none-any.whl +Source1064: rsa-4.7.2-py3-none-any.whl +Source1065: setuptools-57.0.0-py3-none-any.whl +Source1066: uritemplate-3.0.1-py2.py3-none-any.whl # common (pexpect / suds) -Source1088: pexpect-4.8.0-py2.py3-none-any.whl -Source1089: ptyprocess-0.7.0-py2.py3-none-any.whl -Source1090: suds_community-0.8.5-py3-none-any.whl +Source1067: pexpect-4.8.0-py2.py3-none-any.whl +Source1068: ptyprocess-0.7.0-py2.py3-none-any.whl +Source1069: suds_community-0.8.5-py3-none-any.whl ### END ### # kubevirt ## pip download --no-binary :all: openshift "ruamel.yaml.clib>=0.1.2" ### BEGIN -Source1091: %{openshift}-%{openshift_version}.tar.gz -Source1092: %{ruamelyamlclib}-%{ruamelyamlclib_version}.tar.gz -Source1093: %{kubernetes}-%{kubernetes_version}.tar.gz -Source1094: %{certifi}-%{certifi_version}.tar.gz -Source1095: %{googleauth}-%{googleauth_version}.tar.gz -Source1096: %{cachetools}-%{cachetools_version}.tar.gz -Source1097: %{pyasn1modules}-%{pyasn1modules_version}.tar.gz -Source1098: %{pyasn1}-%{pyasn1_version}.tar.gz -Source1100: %{pyyaml}-%{pyyaml_version}.tar.gz +Source1070: %{openshift}-%{openshift_version}.tar.gz +Source1071: %{ruamelyamlclib}-%{ruamelyamlclib_version}.tar.gz +Source1072: %{kubernetes}-%{kubernetes_version}.tar.gz +Source1073: %{certifi}-%{certifi_version}.tar.gz +Source1074: %{googleauth}-%{googleauth_version}.tar.gz +Source1075: %{cachetools}-%{cachetools_version}.tar.gz +Source1076: %{pyasn1modules}-%{pyasn1modules_version}.tar.gz +Source1077: %{pyasn1}-%{pyasn1_version}.tar.gz +Source1079: %{pyyaml}-%{pyyaml_version}.tar.gz ## rsa is dependency for "pip install", ## but gets removed to use cryptography lib instead -Source1101: rsa-4.7.2.tar.gz -Source1102: %{six}-%{six_version}.tar.gz -Source1103: %{urllib3}-%{urllib3_version}.tar.gz -Source1104: %{websocketclient}-%{websocketclient_version}.tar.gz -Source1105: %{jinja2}-%{jinja2_version}.tar.gz -Source1106: %{markupsafe}-%{markupsafe_version}.tar.gz -Source1107: python-%{stringutils}-%{stringutils_version}.tar.gz -Source1108: %{requests}-%{requests_version}.tar.gz -Source1109: %{chrstnormalizer}-%{chrstnormalizer_version}.tar.gz -Source1110: %{idna}-%{idna_version}.tar.gz -Source1111: %{reqstsoauthlib}-%{reqstsoauthlib_version}.tar.gz -Source1112: %{oauthlib}-%{oauthlib_version}.tar.gz -Source1113: %{ruamelyaml}-%{ruamelyaml_version}.tar.gz -Source1114: %{setuptools}-%{setuptools_version}.tar.gz +Source1080: rsa-4.7.2.tar.gz +Source1081: %{six}-%{six_version}.tar.gz +Source1082: %{urllib3}-%{urllib3_version}.tar.gz +Source1083: %{websocketclient}-%{websocketclient_version}.tar.gz +Source1084: %{jinja2}-%{jinja2_version}.tar.gz +Source1085: %{markupsafe}-%{markupsafe_version}.tar.gz +Source1086: python-%{stringutils}-%{stringutils_version}.tar.gz +Source1087: %{requests}-%{requests_version}.tar.gz +Source1088: %{chrstnormalizer}-%{chrstnormalizer_version}.tar.gz +Source1089: %{idna}-%{idna_version}.tar.gz +Source1090: %{reqstsoauthlib}-%{reqstsoauthlib_version}.tar.gz +Source1091: %{oauthlib}-%{oauthlib_version}.tar.gz +Source1092: %{ruamelyaml}-%{ruamelyaml_version}.tar.gz +Source1093: %{setuptools}-%{setuptools_version}.tar.gz ## required for installation -Source1115: setuptools_scm-6.3.2.tar.gz -Source1116: packaging-21.2-py3-none-any.whl -Source1117: poetry-core-1.0.7.tar.gz -Source1118: pyparsing-3.0.1.tar.gz -Source1119: tomli-1.0.1.tar.gz -Source1120: pycryptodome-3.10.1.tar.gz -Source1121: cryptography-3.3.2-cp36-abi3-manylinux1_x86_64.whl -Source1122: awscrt-0.11.13-cp36-cp36m-manylinux1_x86_64.whl -Source1123: cffi-1.14.5-cp36-cp36m-manylinux1_x86_64.whl -Source1124: urllib3-1.24.3-py2.py3-none-any.whl -Source1125: importlib_metadata-4.8.1-py3-none-any.whl -Source1126: protobuf-3.17.3-cp36-cp36m-manylinux_2_5_x86_64.manylinux1_x86_64.whl -Source1127: zipp-3.5.0-py3-none-any.whl -Source1128: typing_extensions-3.10.0.2-py3-none-any.whl -Source1129: importlib_resources-5.2.2-py3-none-any.whl -Source1130: MarkupSafe-2.0.1-cp36-cp36m-manylinux1_x86_64.whl +Source1094: setuptools_scm-6.3.2.tar.gz +Source1095: packaging-21.2-py3-none-any.whl +Source1096: poetry-core-1.0.7.tar.gz +Source1097: pyparsing-3.0.1.tar.gz +Source1098: tomli-1.0.1.tar.gz +Source1099: wheel-0.37.0-py2.py3-none-any.whl +# openstack +Source1100: PyYAML-5.1.tar.gz +Source1101: charset_normalizer-2.0.4-py3-none-any.whl +Source1102: debtcollector-2.2.0-py3-none-any.whl +Source1103: idna-3.2-py3-none-any.whl +Source1104: iso8601-0.1.16-py2.py3-none-any.whl +Source1105: keystoneauth1-4.3.1-py3-none-any.whl +Source1106: msgpack-1.0.2.tar.gz +Source1107: netaddr-0.8.0-py2.py3-none-any.whl +Source1108: netifaces-0.11.0.tar.gz +Source1109: oslo.config-8.7.1-py3-none-any.whl +Source1110: oslo.i18n-5.0.1-py3-none-any.whl +Source1111: oslo.serialization-4.2.0-py3-none-any.whl +Source1112: oslo.utils-4.10.0-py3-none-any.whl +Source1113: os_service_types-1.7.0-py2.py3-none-any.whl +Source1114: pbr-5.6.0-py2.py3-none-any.whl +Source1115: packaging-21.0-py3-none-any.whl +Source1116: prettytable-2.2.0-py3-none-any.whl +Source1117: python_keystoneclient-4.2.0-py3-none-any.whl +Source1118: python_novaclient-17.5.0-py3-none-any.whl +Source1119: requests-2.26.0-py2.py3-none-any.whl +Source1120: rfc3986-1.5.0-py2.py3-none-any.whl +Source1121: stevedore-3.4.0-py3-none-any.whl +Source1122: wcwidth-0.2.5-py2.py3-none-any.whl +Source1123: wrapt-1.12.1.tar.gz +Source2000: pycryptodome-3.10.1.tar.gz +Source2001: cryptography-3.3.2-cp36-abi3-manylinux1_x86_64.whl +Source2002: awscrt-0.11.13-cp36-cp36m-manylinux1_x86_64.whl +Source2003: cffi-1.14.5-cp36-cp36m-manylinux1_x86_64.whl +Source2004: urllib3-1.24.3-py2.py3-none-any.whl +Source2005: importlib_metadata-4.8.1-py3-none-any.whl +Source2006: protobuf-3.17.3-cp36-cp36m-manylinux_2_5_x86_64.manylinux1_x86_64.whl +Source2007: zipp-3.5.0-py3-none-any.whl +Source2008: typing_extensions-3.10.0.2-py3-none-any.whl +Source2009: importlib_resources-5.2.2-py3-none-any.whl +Source2010: MarkupSafe-2.0.1-cp36-cp36m-manylinux1_x86_64.whl ### END Patch0: ha-cloud-support-aliyun.patch @@ -244,6 +249,13 @@ Patch17: bz2042496-fence_ibm_vpc-fence_ibm_powervs.patch Patch18: bz2022334-fence_zvmip-add-disable-ssl.patch Patch19: bz2086839-1-fence_apc-fence_ilo_moonshot-import-logging.patch Patch20: bz2086839-2-fence_lpar-fix-import-fail_usage.patch +Patch21: bz2123009-fence_ibm_powervs-proxy-private-api-servers.patch +Patch22: bz2123465-fence_ibm_vpc-remove-unused-instance-parameter-limit-optional.patch +Patch23: bz2123010-fence_ibm_vpc-add-proxy-support.patch +Patch24: bz2127872-fence_ibm_vpc-add-token-cache-support.patch +Patch25: bz2136200-fence_gce-update.patch +Patch26: bz2149691-1-all-agents-unify-ssl-parameters.patch +Patch27: bz2149691-2-fence_zvmip-connect-error.patch %global supportedagents amt_ws apc apc_snmp bladecenter brocade cisco_mds cisco_ucs compute drac5 eaton_snmp emerson eps evacuate hpblade ibmblade ibm_powervs ibm_vpc ifmib ilo ilo_moonshot ilo_mp ilo_ssh intelmodular ipdu ipmilan kdump kubevirt lpar mpath redfish rhevm rsa rsb sbd scsi vmware_rest vmware_soap wti %ifarch x86_64 @@ -376,6 +388,13 @@ BuildRequires: %{systemd_units} %patch18 -p1 %patch19 -p1 %patch20 -p1 +%patch21 -p1 +%patch22 -p1 +%patch23 -p1 +%patch24 -p1 +%patch25 -p1 +%patch26 -p1 +%patch27 -p1 # prevent compilation of something that won't get used anyway sed -i.orig 's|FENCE_ZVM=1|FENCE_ZVM=0|' configure.ac @@ -411,7 +430,13 @@ done # %endif ./autogen.sh -%{configure} --disable-libvirt-qmf-plugin PYTHONPATH="support/aliyun:support/aws:support/azure:support/google:support/openstack:support/common" --with-agents='%{supportedagents} %{testagents}' +%{configure} --disable-libvirt-qmf-plugin PYTHONPATH="support/aliyun:support/aws:support/azure:support/google:support/common" \ +%if %{defined _tmpfilesdir} + SYSTEMD_TMPFILES_DIR=%{_tmpfilesdir} \ + --with-fencetmpdir=/run/fence-agents \ +%endif + --with-agents='%{supportedagents} %{testagents}' + CFLAGS="$(echo '%{optflags}')" make %{_smp_mflags} %install @@ -516,6 +541,14 @@ This package contains support files including the Python fencing library. %{_datadir}/pkgconfig/%{name}.pc %exclude %{_sbindir}/* %exclude %{_mandir}/man8/* +%if %{defined _tmpfilesdir} +%{_tmpfilesdir}/%{name}.conf +%endif +%if %{defined _tmpfilesdir} +%dir %attr (1755, root, root) /run/%{name} +%else +%dir %attr (1755, root, root) %{_var}/run/%{name} +%endif %dir %{_usr}/lib/%{name} %{_usr}/lib/%{name}/support/common @@ -1468,6 +1501,32 @@ are located on corosync cluster nodes. %endif %changelog +* Fri May 19 2023 Chang Gao - 4.10.0-20.0.1.6 +- Replace some packages with build env + +* Thu Dec 1 2022 Oyvind Albrigtsen - 4.10.0-20.6 +- all agents: unify ssl parameters to avoid having to use --ssl when + using --ssl-secure/--ssl-insecure for some agents + Resolves: rhbz#2149691 + +* Thu Oct 20 2022 Oyvind Albrigtsen - 4.10.0-20.5 +- fence_gce: update fence agent + Resolves: rhbz#2136200 + +* Mon Sep 19 2022 Oyvind Albrigtsen - 4.10.0-20.4 +- fence_ibm_powervs: add support for proxy, private API servers and + get token via API key + Resolves: rhbz#2123009 +- fence_ibm_vpc: add proxy support + Resolves: rhbz#2123010 +- fence_ibm_vpc: add token cache support + Resolves: rhbz#2127872 +- fence_ibm_vpc: remove unused instance parameter and make limit + optional + Resolves: rhbz#2123465 +- add azure-identity and dependencies + Resolves: rhbz#2127876 + * Tue May 17 2022 Oyvind Albrigtsen - 4.10.0-20.2 - fence_apc/fence_ilo_moonshot/fence_lpar: add missing "import logging" Resolves: rhbz#2086839 diff --git a/google-auth-2.3.0.tar.gz b/google-auth-2.3.0.tar.gz deleted file mode 100644 index d098ae491d20f10fdb1b351ac44c846d33fcfd83..0000000000000000000000000000000000000000 Binary files a/google-auth-2.3.0.tar.gz and /dev/null differ diff --git a/idna-3.3.tar.gz b/idna-3.3.tar.gz deleted file mode 100644 index ff2bcbf0e10555b42a098bd3a0dbbfcc80b0bfbc..0000000000000000000000000000000000000000 Binary files a/idna-3.3.tar.gz and /dev/null differ diff --git a/kubernetes-12.0.1.tar.gz b/kubernetes-12.0.1.tar.gz deleted file mode 100644 index b05ac5043b08b48ef28ca9ed22b57e485df7105d..0000000000000000000000000000000000000000 Binary files a/kubernetes-12.0.1.tar.gz and /dev/null differ diff --git a/msgpack-1.0.2.tar.gz b/msgpack-1.0.2.tar.gz deleted file mode 100644 index db1b5d19e0d4d927d312dace5fc8ea439c6a79a6..0000000000000000000000000000000000000000 Binary files a/msgpack-1.0.2.tar.gz and /dev/null differ diff --git a/netifaces-0.11.0.tar.gz b/netifaces-0.11.0.tar.gz deleted file mode 100644 index 3a35596a416364861289f59b08277af3950fab75..0000000000000000000000000000000000000000 Binary files a/netifaces-0.11.0.tar.gz and /dev/null differ diff --git a/oauthlib-3.1.1.tar.gz b/oauthlib-3.1.1.tar.gz deleted file mode 100644 index 8bbe54662ead8ae8b24c6baf6ffa3657f0ace928..0000000000000000000000000000000000000000 Binary files a/oauthlib-3.1.1.tar.gz and /dev/null differ diff --git a/openshift-0.12.1.tar.gz b/openshift-0.12.1.tar.gz deleted file mode 100644 index 05fa11211711cf21bd1cc43f4e71bde8c7e746ab..0000000000000000000000000000000000000000 Binary files a/openshift-0.12.1.tar.gz and /dev/null differ diff --git a/poetry-core-1.0.7.tar.gz b/poetry-core-1.0.7.tar.gz deleted file mode 100644 index 0f47032347f90578ab9a34e4f2a13d71a6b4a0f8..0000000000000000000000000000000000000000 Binary files a/poetry-core-1.0.7.tar.gz and /dev/null differ diff --git a/pyasn1-0.4.8.tar.gz b/pyasn1-0.4.8.tar.gz deleted file mode 100644 index c45347e4103dd56ae59e8a87cf4defa5e1df40a4..0000000000000000000000000000000000000000 Binary files a/pyasn1-0.4.8.tar.gz and /dev/null differ diff --git a/pyasn1-modules-0.2.8.tar.gz b/pyasn1-modules-0.2.8.tar.gz deleted file mode 100644 index d06837eeb603b9be1bcdafa07cc74f008007cd63..0000000000000000000000000000000000000000 Binary files a/pyasn1-modules-0.2.8.tar.gz and /dev/null differ diff --git a/pyparsing-3.0.1.tar.gz b/pyparsing-3.0.1.tar.gz deleted file mode 100644 index e6dd830e80023faea5181caaa4dc328cb76d0568..0000000000000000000000000000000000000000 Binary files a/pyparsing-3.0.1.tar.gz and /dev/null differ diff --git a/pyroute2-0.6.4.tar.gz b/pyroute2-0.6.4.tar.gz deleted file mode 100644 index a207c44584988cf13bb4c6a0d0ff7abff652735d..0000000000000000000000000000000000000000 Binary files a/pyroute2-0.6.4.tar.gz and /dev/null differ diff --git a/pyroute2.core-0.6.4.tar.gz b/pyroute2.core-0.6.4.tar.gz deleted file mode 100644 index d158979eb6e768f6cec9b041792cc6c727d34a34..0000000000000000000000000000000000000000 Binary files a/pyroute2.core-0.6.4.tar.gz and /dev/null differ diff --git a/pyroute2.ethtool-0.6.4.tar.gz b/pyroute2.ethtool-0.6.4.tar.gz deleted file mode 100644 index 5d70f6e6461707631c32c9137c207de16f2d7be2..0000000000000000000000000000000000000000 Binary files a/pyroute2.ethtool-0.6.4.tar.gz and /dev/null differ diff --git a/pyroute2.ipdb-0.6.4.tar.gz b/pyroute2.ipdb-0.6.4.tar.gz deleted file mode 100644 index 3efff171398dbe7c08bb5cd1e45f013c00426f76..0000000000000000000000000000000000000000 Binary files a/pyroute2.ipdb-0.6.4.tar.gz and /dev/null differ diff --git a/pyroute2.ipset-0.6.4.tar.gz b/pyroute2.ipset-0.6.4.tar.gz deleted file mode 100644 index cd23157203fcb1fbda01ae0efbabced7438c054c..0000000000000000000000000000000000000000 Binary files a/pyroute2.ipset-0.6.4.tar.gz and /dev/null differ diff --git a/pyroute2.ndb-0.6.4.tar.gz b/pyroute2.ndb-0.6.4.tar.gz deleted file mode 100644 index 6ee89c06bb47c7f7058301fc09460193c311ed32..0000000000000000000000000000000000000000 Binary files a/pyroute2.ndb-0.6.4.tar.gz and /dev/null differ diff --git a/pyroute2.nftables-0.6.4.tar.gz b/pyroute2.nftables-0.6.4.tar.gz deleted file mode 100644 index 6045f8630602295b0b4ee861cb576d8f9a537d12..0000000000000000000000000000000000000000 Binary files a/pyroute2.nftables-0.6.4.tar.gz and /dev/null differ diff --git a/pyroute2.nslink-0.6.4.tar.gz b/pyroute2.nslink-0.6.4.tar.gz deleted file mode 100644 index e7423bb9464a23bd3be803dd08dda31a5af56d50..0000000000000000000000000000000000000000 Binary files a/pyroute2.nslink-0.6.4.tar.gz and /dev/null differ diff --git a/python-string-utils-1.0.0.tar.gz b/python-string-utils-1.0.0.tar.gz deleted file mode 100644 index 75cbb52420ff192b4c2666b5f6380b900bf93e10..0000000000000000000000000000000000000000 Binary files a/python-string-utils-1.0.0.tar.gz and /dev/null differ diff --git a/requests-2.26.0.tar.gz b/requests-2.26.0.tar.gz deleted file mode 100644 index 101dc7923b10585656cc5567a80fbb16622ad600..0000000000000000000000000000000000000000 Binary files a/requests-2.26.0.tar.gz and /dev/null differ diff --git a/requests-oauthlib-1.3.0.tar.gz b/requests-oauthlib-1.3.0.tar.gz deleted file mode 100644 index 9ae846e29bd94875a02989bb382bf5fcb8764aab..0000000000000000000000000000000000000000 Binary files a/requests-oauthlib-1.3.0.tar.gz and /dev/null differ diff --git a/requirements-azure.txt b/requirements-azure.txt index 3aa79bcfedf687b60e0ede62f237f1f6b00fd5b4..8e4b2b79f5c2e5adacf4941255eac51310d61b19 100644 --- a/requirements-azure.txt +++ b/requirements-azure.txt @@ -1,3 +1,4 @@ azure-mgmt-compute azure-mgmt-network +azure-identity msrestazure diff --git a/rsa-4.7.2.tar.gz b/rsa-4.7.2.tar.gz deleted file mode 100644 index a7cab9ba2a1b9e6de56a09b4bdd619143f30bf06..0000000000000000000000000000000000000000 Binary files a/rsa-4.7.2.tar.gz and /dev/null differ diff --git a/ruamel.yaml-0.15.100.tar.gz b/ruamel.yaml-0.15.100.tar.gz deleted file mode 100644 index 46deab9484247d121f144ec3fe12b43c4e7b399d..0000000000000000000000000000000000000000 Binary files a/ruamel.yaml-0.15.100.tar.gz and /dev/null differ diff --git a/ruamel.yaml-0.17.16.tar.gz b/ruamel.yaml-0.17.16.tar.gz deleted file mode 100644 index 1ec21f1401794ff7eeeb78d96df27d5746607323..0000000000000000000000000000000000000000 Binary files a/ruamel.yaml-0.17.16.tar.gz and /dev/null differ diff --git a/ruamel.yaml.clib-0.2.6.tar.gz b/ruamel.yaml.clib-0.2.6.tar.gz deleted file mode 100644 index 9ea482d17cf5ce8a6c3dfc9bdf1f19b59e4c1188..0000000000000000000000000000000000000000 Binary files a/ruamel.yaml.clib-0.2.6.tar.gz and /dev/null differ diff --git a/setuptools-58.3.0.tar.gz b/setuptools-58.3.0.tar.gz deleted file mode 100644 index f6cb08cd9efa9dd563cf738a3232b84a54475790..0000000000000000000000000000000000000000 Binary files a/setuptools-58.3.0.tar.gz and /dev/null differ diff --git a/setuptools_scm-6.3.2.tar.gz b/setuptools_scm-6.3.2.tar.gz deleted file mode 100644 index 7666317cd732bcc4b7c64ed176b0cc3cb6262528..0000000000000000000000000000000000000000 Binary files a/setuptools_scm-6.3.2.tar.gz and /dev/null differ diff --git a/six-1.16.0.tar.gz b/six-1.16.0.tar.gz deleted file mode 100644 index 5bf3a27710e7dcaad5f93208643e7049103e3186..0000000000000000000000000000000000000000 Binary files a/six-1.16.0.tar.gz and /dev/null differ diff --git a/tomli-1.0.1.tar.gz b/tomli-1.0.1.tar.gz deleted file mode 100644 index e5e8770bc55ac04443bbbc3cfcd8f03a6c8a65cd..0000000000000000000000000000000000000000 Binary files a/tomli-1.0.1.tar.gz and /dev/null differ diff --git a/urllib3-1.26.7.tar.gz b/urllib3-1.26.7.tar.gz deleted file mode 100644 index 990abe6a84d601699f0a67869335a338a28d54c9..0000000000000000000000000000000000000000 Binary files a/urllib3-1.26.7.tar.gz and /dev/null differ diff --git a/websocket-client-1.2.1.tar.gz b/websocket-client-1.2.1.tar.gz deleted file mode 100644 index ade68dcbf5bf5df3d50977cf18f02c3b41b88caa..0000000000000000000000000000000000000000 Binary files a/websocket-client-1.2.1.tar.gz and /dev/null differ diff --git a/wrapt-1.12.1.tar.gz b/wrapt-1.12.1.tar.gz deleted file mode 100644 index 0e54678b76a1d613f331ee15c4b0bc6f7196e172..0000000000000000000000000000000000000000 Binary files a/wrapt-1.12.1.tar.gz and /dev/null differ