From d599caafc3d504dbf92dd7514307dc45f1cbacb7 Mon Sep 17 00:00:00 2001 From: Veerabhadrarao Damisetti Date: Thu, 31 Oct 2024 18:23:14 +0530 Subject: [PATCH] ACM-15078: Fixing agents reuse problem in z/VM after reclaim (#817) * ACM-15078: Updated bootLoaderConfigTemplateS390x for making IP and nameserver persistent for agents Signed-off-by: DAMISETTI-VEERABHADRARAO * ACM-15078: Updated paramaters for zipl for s390x Signed-off-by: DAMISETTI-VEERABHADRARAO * ACM-15078: Created new function extractCmdlineParams and updated unit test case for the same Signed-off-by: DAMISETTI-VEERABHADRARAO --------- Signed-off-by: DAMISETTI-VEERABHADRARAO --- .../actions/download_boot_artifacts_cmd.go | 2 +- src/commands/actions/reboot_for_reclaim.go | 64 ++++++++++++++++++- .../actions/reboot_for_reclaim_test.go | 21 ++++++ 3 files changed, 83 insertions(+), 4 deletions(-) diff --git a/src/commands/actions/download_boot_artifacts_cmd.go b/src/commands/actions/download_boot_artifacts_cmd.go index b25be3ac2..9d385a3ee 100644 --- a/src/commands/actions/download_boot_artifacts_cmd.go +++ b/src/commands/actions/download_boot_artifacts_cmd.go @@ -54,7 +54,7 @@ const ( bootLoaderConfigFileName string = "/00-assisted-discovery.conf" bootLoaderConfigTemplateS390x string = `title Assisted Installer Discovery version 999 -options random.trust_cpu=on ignition.firstboot ignition.platform.id=metal coreos.live.rootfs_url=%s +options random.trust_cpu=on ai.ip_cfg_override=1 ignition.firstboot ignition.platform.id=metal coreos.live.rootfs_url=%s linux %s initrd %s` bootLoaderConfigTemplate string = `title Assisted Installer Discovery diff --git a/src/commands/actions/reboot_for_reclaim.go b/src/commands/actions/reboot_for_reclaim.go index f88e6d869..c153c62a1 100644 --- a/src/commands/actions/reboot_for_reclaim.go +++ b/src/commands/actions/reboot_for_reclaim.go @@ -3,7 +3,9 @@ package actions import ( "encoding/json" "fmt" + "regexp" "runtime" + "strings" "syscall" "github.com/openshift/assisted-installer-agent/src/util" @@ -29,25 +31,81 @@ func (a *rebootForReclaim) Run() (stdout, stderr string, exitCode int) { } if runtime.GOARCH == "s390x" { + var options string + var requiredCmdline string + + stdout, stderr, exitCode = util.Execute("cat", "/boot/loader/entries/00-assisted-discovery.conf") + if exitCode != 0 { + return stdout, stderr, exitCode + } + lines := strings.Split(stdout, "\n") + for _, line := range lines { + if strings.HasPrefix(line, "options") { + options = strings.TrimSpace(strings.TrimPrefix(line, "options")) + break + } + } + stdout, stderr, exitCode := util.Execute("cat", "/proc/cmdline") + if exitCode != 0 { + return stdout, stderr, exitCode + } + + // Parameters to extract from cmdline for agents + paramsToExtract := []string{ + "ip", + "nameserver", + "rd.znet", + "zfcp.allow_lun_scan", + "rd.zfcp", + "rd.dasd", + } + + requiredCmdline = extractCmdlineParams(stdout, paramsToExtract) + unshareCommand := "unshare" unshareArgs := []string{ "--mount", "bash", "-c", - fmt.Sprintf("mount -o remount,rw /boot && zipl -V -t /boot -i %s/%s -r %s/%s -c /boot/loader/entries%s -p /boot/loader/entries%s", + fmt.Sprintf("mount -o remount,rw /boot && zipl -V -t /boot -i %s/%s -r %s/%s -P '%s %s'", artifactsFolder, kernelFile, artifactsFolder, initrdFile, - bootLoaderConfigFileName, - bootLoaderConfigFileName), + options, + requiredCmdline), } stdout, stderr, exitCode = util.Execute(unshareCommand, unshareArgs...) if exitCode != 0 { return stdout, stderr, exitCode } + } return util.Execute("systemctl", "reboot") } +// Returns the paramsToExtract parameters which are present in cmdlineOutput, if no paramter matched then returns any empty string '' + +func extractCmdlineParams(cmdlineOutput string, paramsToExtract []string) string { + cmdlineParams := make(map[string]string) + var requiredCmdline string + + // Matches the exact param from paramsToExtract followed by an = sign, and then capture the non-whitespace value after the = + for _, param := range paramsToExtract { + regex := regexp.MustCompile(fmt.Sprintf(`\b%s=([^\s]+)`, param)) + match := regex.FindStringSubmatch(cmdlineOutput) + if len(match) > 1 { + cmdlineParams[param] = match[1] + } + } + + // Convert the key value pairs in map to string with predefined order which is in paramsToExtract + for _, key := range paramsToExtract { + if value, exists := cmdlineParams[key]; exists { + requiredCmdline += fmt.Sprintf("%s=%s ", key, value) + } + } + return requiredCmdline +} + // Unused, but required as part of ActionInterface func (a *rebootForReclaim) Command() string { return "systemctl" diff --git a/src/commands/actions/reboot_for_reclaim_test.go b/src/commands/actions/reboot_for_reclaim_test.go index 7ae6bcfc8..ea60ee239 100644 --- a/src/commands/actions/reboot_for_reclaim_test.go +++ b/src/commands/actions/reboot_for_reclaim_test.go @@ -21,4 +21,25 @@ var _ = Describe("reboot_for_reclaim", func() { It("fails when given bad input", func() { badParamsCommonTests(models.StepTypeRebootForReclaim, []string{}) }) + + Context("extractCmdlineParams", func() { + It("returns the expected parameters when valid cmdline output is given", func() { + cmdlineOutput := "ip=192.168.1.1 nameserver=8.8.8.8 rd.znet=enabled zfcp.allow_lun_scan=0 rd.zfcp=xyz rd.dasd=abc" + paramsToExtract := []string{"ip", "nameserver", "rd.znet", "zfcp.allow_lun_scan", "rd.zfcp", "rd.dasd"} + + expectedCmdline := "ip=192.168.1.1 nameserver=8.8.8.8 rd.znet=enabled zfcp.allow_lun_scan=0 rd.zfcp=xyz rd.dasd=abc " + requiredCmdline := extractCmdlineParams(cmdlineOutput, paramsToExtract) + + Expect(requiredCmdline).To(Equal(expectedCmdline)) + }) + + It("returns an empty string when no parameters match", func() { + cmdlineOutput := "other_param=value" + paramsToExtract := []string{"ip", "nameserver"} + + requiredCmdline := extractCmdlineParams(cmdlineOutput, paramsToExtract) + + Expect(requiredCmdline).To(Equal("")) + }) + }) })