From 22bb3010e5fad43e8937553939467868650e31b3 Mon Sep 17 00:00:00 2001 From: "Carl D. Roth" Date: Tue, 26 Dec 2017 17:47:11 -0800 Subject: [PATCH 1/7] Add installer support for using onie-sysinfo instead of /etc/machine.conf --- .../src/python/onl/install/App.py | 17 ++- .../src/python/onl/install/ShellApp.py | 106 +++++++++++++++++- .../src/python/onl/install/SystemInstall.py | 5 +- 3 files changed, 118 insertions(+), 10 deletions(-) diff --git a/packages/base/all/vendor-config-onl/src/python/onl/install/App.py b/packages/base/all/vendor-config-onl/src/python/onl/install/App.py index 69b83f8f5f..13465b90f5 100644 --- a/packages/base/all/vendor-config-onl/src/python/onl/install/App.py +++ b/packages/base/all/vendor-config-onl/src/python/onl/install/App.py @@ -17,7 +17,7 @@ from InstallUtils import InitrdContext from InstallUtils import SubprocessMixin from InstallUtils import ProcMountsParser -from ShellApp import OnieBootContext +from ShellApp import OnieBootContext, OnieSysinfo import ConfUtils, BaseInstall class App(SubprocessMixin, object): @@ -129,7 +129,7 @@ def reporthook(blocks, bsz, sz): def runLocalOrChroot(self): if self.machineConf is None: - self.log.error("missing machine.conf") + self.log.error("missing onie-sysinfo or machine.conf") return 1 if self.installerConf is None: self.log.error("missing installer.conf") @@ -230,10 +230,17 @@ def runLocalOrChroot(self): def runLocal(self): self.log.info("getting installer configuration") - if os.path.exists(ConfUtils.MachineConf.PATH): + osi = OnieSysinfo(log=self.log.getChild("onie-sysinfo")) + try: + halp = osi.help + except AttributeError: + halp = None + if halp is not None: + self.machineConf = osi + elif os.path.exists(ConfUtils.MachineConf.PATH): self.machineConf = ConfUtils.MachineConf() else: - self.log.warn("missing /etc/machine.conf from ONIE runtime") + self.log.warn("missing onie-sysinfo or /etc/machine.conf from ONIE runtime") self.machineConf = ConfUtils.MachineConf(path='/dev/null') self.installerConf = ConfUtils.InstallerConf() @@ -243,7 +250,7 @@ def runLocal(self): def findPlatform(self): plat = arch = None - if os.path.exists(ConfUtils.MachineConf.PATH): + if self.machineConf is not None: plat = getattr(self.machineConf, 'onie_platform', None) arch = getattr(self.machineConf, 'onie_arch', None) if plat and arch: diff --git a/packages/base/all/vendor-config-onl/src/python/onl/install/ShellApp.py b/packages/base/all/vendor-config-onl/src/python/onl/install/ShellApp.py index 7c5f2c6c32..fcf7f93d6f 100644 --- a/packages/base/all/vendor-config-onl/src/python/onl/install/ShellApp.py +++ b/packages/base/all/vendor-config-onl/src/python/onl/install/ShellApp.py @@ -15,9 +15,6 @@ from InstallUtils import BlkidParser from InstallUtils import UbootInitrdContext -import onl.platform.current -from onl.sysconfig import sysconfig - class AppBase(SubprocessMixin, object): @property @@ -228,6 +225,105 @@ def run(self): with OnieBootContext(log=self.log) as ctx: return self._runInitrdShell(ctx.initrd) +class OnieSysinfoApp(SubprocessMixin, object): + + PROG = "onie-sysinfo" + + def __init__(self, args=[], log=None): + + if log is not None: + self.log = log + else: + self.log = logging.getLogger(self.__class__.__name__) + self.args = args or ['-p',] + self.output = None + + def _runInitrdShell(self, initrd): + with InitrdContext(initrd=initrd, log=self.log) as ctx: + cmd = ['onie-sysinfo',] + cmd.extend(self.args) + cmd = ('chroot', ctx.dir, + '/bin/sh', '-c', 'IFS=;' + " ".join(cmd)) + try: + self.output = self.check_output(cmd) + ret = 0 + except subprocess.CalledProcessError, what: + self.log.error("failed command: %s", " ".join(what.cmd)) + for line in (what.output or "").splitlines(): + self.log.error(">>> %s", line) + ret = what.returncode + return ret + + def run(self): + with OnieBootContext(log=self.log) as ctx: + ret = self._runInitrdShell(ctx.initrd) + if self.output is not None: + sys.stdout.write(self.output) + return ret + + def shutdown(self): + pass + + @classmethod + def main(cls): + + logging.basicConfig() + logger = logging.getLogger(cls.PROG) + logger.setLevel(logging.INFO) + + args = list(sys.argv[1:]) + sysinfoArgs = [] + while args: + + if args[0] in ('-v', '--verbose',): + logger.setLevel(logging.DEBUG) + args.pop(0) + continue + + if args[0] in ('-q', '--quiet',): + logger.setLevel(logging.ERROR) + args.pop(0) + continue + + sysinfoArgs.append(args.pop(0)) + + app = cls(args=sysinfoArgs, log=logger) + try: + code = app.run() + except: + logger.exception("runner failed") + code = 1 + app.shutdown() + sys.exit(code) + +class OnieSysinfo(OnieSysinfoApp): + + def _runArgs(self, *args): + self.args = args + with OnieBootContext(log=self.log) as ctx: + ret = self._runInitrdShell(ctx.initrd) + if self.output is not None: + return self.output.rstrip() + raise AttributeError("cannot retrieve onie-sysinfo attribute via %s" % str(args)) + + @property + def help(self): + return self._runArgs('-h') + + @property + def onie_platform(self): + return self._runArgs('-p') + + @property + def onie_arch(self): + return self._runArgs('-c') + + @property + def onie_version(self): + return self._runArgs('-v') + + # XXX roth other switches too + class Loader(AppBase): """Application shell that uses the (installed) loader runtime.""" @@ -331,6 +427,7 @@ def runUboot(self): def run(self): + import onl.platform.current self.platform = onl.platform.current.OnlPlatform() self.pc = self.platform.platform_config @@ -353,6 +450,7 @@ class Upgrader(AppBase): def runGrub(self): + from onl.sysconfig import sysconfig d = sysconfig.upgrade.loader.package.dir for b in sysconfig.upgrade.loader.package.grub: p = os.path.join(d, b) @@ -365,6 +463,7 @@ def runGrub(self): def runUboot(self): + from onl.sysconfig import sysconfig d = sysconfig.upgrade.loader.package.dir for b in sysconfig.upgrade.loader.package.fit: p = os.path.join(d, b) @@ -377,6 +476,7 @@ def runUboot(self): def run(self): + import onl.platform.current self.platform = onl.platform.current.OnlPlatform() self.pc = self.platform.platform_config diff --git a/packages/base/all/vendor-config-onl/src/python/onl/install/SystemInstall.py b/packages/base/all/vendor-config-onl/src/python/onl/install/SystemInstall.py index ad6ce72e69..09348f52c6 100644 --- a/packages/base/all/vendor-config-onl/src/python/onl/install/SystemInstall.py +++ b/packages/base/all/vendor-config-onl/src/python/onl/install/SystemInstall.py @@ -60,8 +60,9 @@ def _runInitrd(self, helper, path): src = os.path.join(octx.initrdDir, "etc/machine.conf") dst = os.path.join(ctx.dir, "etc/machine.conf") - self.log.debug("+ /bin/cp %s %s", src, dst) - shutil.copy2(src, dst) + if os.path.exists(src): + self.log.debug("+ /bin/cp %s %s", src, dst) + shutil.copy2(src, dst) src = "/etc/fw_env.config" if os.path.exists(src): From feeb3c333060fa026f0f41862c74fc302ac6a4ac Mon Sep 17 00:00:00 2001 From: "Carl D. Roth" Date: Tue, 26 Dec 2017 17:47:35 -0800 Subject: [PATCH 2/7] Wrap access to ONIE's sysinfo tool --- packages/base/all/vendor-config-onl/src/bin/onie-sysinfo | 7 +++++++ 1 file changed, 7 insertions(+) create mode 100755 packages/base/all/vendor-config-onl/src/bin/onie-sysinfo diff --git a/packages/base/all/vendor-config-onl/src/bin/onie-sysinfo b/packages/base/all/vendor-config-onl/src/bin/onie-sysinfo new file mode 100755 index 0000000000..fabd202687 --- /dev/null +++ b/packages/base/all/vendor-config-onl/src/bin/onie-sysinfo @@ -0,0 +1,7 @@ +#!/usr/bin/python + +"""Run native onie-sysinfo +""" + +import onl.install.ShellApp +onl.install.ShellApp.OnieSysinfoApp.main() From 1fdf13b5067e7e6758671ecbe7adcfbabc773394 Mon Sep 17 00:00:00 2001 From: "Carl D. Roth" Date: Tue, 26 Dec 2017 17:47:58 -0800 Subject: [PATCH 3/7] Loader should use onie-sysinfo --- .../vendor-config-onl/src/python/onl/upgrade/loader.py | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/packages/base/all/vendor-config-onl/src/python/onl/upgrade/loader.py b/packages/base/all/vendor-config-onl/src/python/onl/upgrade/loader.py index 29128db986..9ebec5b5d1 100755 --- a/packages/base/all/vendor-config-onl/src/python/onl/upgrade/loader.py +++ b/packages/base/all/vendor-config-onl/src/python/onl/upgrade/loader.py @@ -12,7 +12,7 @@ from onl.sysconfig import sysconfig from onl.mounts import OnlMountManager, OnlMountContextReadOnly, OnlMountContextReadWrite from onl.install import BaseInstall, ConfUtils, InstallUtils -from onl.install.ShellApp import OnieBootContext +from onl.install.ShellApp import OnieBootContext, OnieSysinfo import onl.platform.current import onl.versions @@ -83,8 +83,12 @@ def do_upgrade(self, forced=False): onlPlatform = onl.platform.current.OnlPlatform() with OnieBootContext(log=self.logger) as octx: - path = os.path.join(octx.initrdDir, "etc/machine.conf") - machineConf = ConfUtils.MachineConf(path=path) + if os.path.exists("/usr/bin/onie-shell"): + machineConf = OnieSysinfo(log=self.logger.getChild("onie-sysinfo")) + else: + path = os.path.join(octx.initrdDir, "etc/machine.conf") + if os.path.exists(path): + machineConf = ConfUtils.MachineConf(path=path) installerConf = ConfUtils.InstallerConf(path="/dev/null") # start with an empty installerConf, fill it in piece by piece From 7550367afb584aab6026c34034567006d80dbb95 Mon Sep 17 00:00:00 2001 From: "Carl D. Roth" Date: Tue, 26 Dec 2017 17:48:08 -0800 Subject: [PATCH 4/7] Platform ident should use onie-sysinfo --- .../src/python/onl/platform/current.py | 19 ++++++++++++++++++- 1 file changed, 18 insertions(+), 1 deletion(-) diff --git a/packages/base/all/vendor-config-onl/src/python/onl/platform/current.py b/packages/base/all/vendor-config-onl/src/python/onl/platform/current.py index bdf4c91553..36e9e4573a 100644 --- a/packages/base/all/vendor-config-onl/src/python/onl/platform/current.py +++ b/packages/base/all/vendor-config-onl/src/python/onl/platform/current.py @@ -14,8 +14,9 @@ # platform-config packages. # ############################################################ -import os +import os, sys import importlib +import subprocess def platform_name_get(): # Determine the current platform name. @@ -23,6 +24,22 @@ def platform_name_get(): if os.path.exists("/etc/onl/platform"): with open("/etc/onl/platform", 'r') as f: platform=f.read().strip() + elif os.path.exists("/bin/onie-sysinfo"): + try: + platform = subprocess.check_output(('/bin/onie-sysinfo', '-p',)).strip() + except subprocess.CalledProcessError as what: + for line in (what.output or "").splitlines(): + sys.stderr.write(">>> %s\n" % line) + sys.stderr.write("onie-sysinfo failed with code %d\n" % what.returncode) + platform = None + elif os.path.exists("/usr/bin/onie-shell"): + try: + platform = subprocess.check_output(('/usr/bin/onie-shell', '-c', "onie-sysinfo -p",)).strip() + except subprocess.CalledProcessError as what: + for line in (what.output or "").splitlines(): + sys.stderr.write(">>> %s\n" % line) + sys.stderr.write("onie-sysinfo (onie-shell) failed with code %d\n" % what.returncode) + platform = None elif os.path.exists("/etc/machine.conf"): with open("/etc/machine.conf", 'r') as f: lines = f.readlines(False) From 8e1577f4cbe1662da47548fa2aaa709a3decf994 Mon Sep 17 00:00:00 2001 From: "Carl D. Roth" Date: Tue, 26 Dec 2017 17:48:18 -0800 Subject: [PATCH 5/7] deprecated --- .../mellanox/vendor-config/src/python/mellanox/__init__.py | 1 + 1 file changed, 1 insertion(+) diff --git a/packages/platforms/mellanox/vendor-config/src/python/mellanox/__init__.py b/packages/platforms/mellanox/vendor-config/src/python/mellanox/__init__.py index 56cd4d71fa..db5e2d0677 100644 --- a/packages/platforms/mellanox/vendor-config/src/python/mellanox/__init__.py +++ b/packages/platforms/mellanox/vendor-config/src/python/mellanox/__init__.py @@ -14,6 +14,7 @@ def syseeprom_export(self): print "Caching ONIE System EEPROM..." onie = self.onie_syseeprom_get() mc = self.onie_machine_get() + # XXX roth -- deprecated if 'onie_version' in mc: onie['0x29'] = mc['onie_version'] self.onie_syseeprom_set(onie) From 8e31b248e938c623a55982834e119d9ccb6764e6 Mon Sep 17 00:00:00 2001 From: "Carl D. Roth" Date: Tue, 26 Dec 2017 17:48:26 -0800 Subject: [PATCH 6/7] Updated comment --- packages/base/all/vendor-config-onl/src/lib/install/lib.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/base/all/vendor-config-onl/src/lib/install/lib.sh b/packages/base/all/vendor-config-onl/src/lib/install/lib.sh index 0a5ea18420..3835580f90 100644 --- a/packages/base/all/vendor-config-onl/src/lib/install/lib.sh +++ b/packages/base/all/vendor-config-onl/src/lib/install/lib.sh @@ -122,7 +122,7 @@ installer_mkchroot() { mkdir -p "${rootdir}${TMPDIR}" fi - # export ONIE defines to the installer + # export ONIE defines to the installer, if they exist if test -r /etc/machine.conf; then cp /etc/machine.conf "${rootdir}/etc/machine.conf" fi From 19d289c45694468c655b4f92a6e60c286343f19b Mon Sep 17 00:00:00 2001 From: "Carl D. Roth" Date: Tue, 26 Dec 2017 17:48:39 -0800 Subject: [PATCH 7/7] Use onie-sysinfo rather than /etc/machine.conf --- builds/any/installer/installer.sh.in | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/builds/any/installer/installer.sh.in b/builds/any/installer/installer.sh.in index e3d968aa00..6711709dbb 100644 --- a/builds/any/installer/installer.sh.in +++ b/builds/any/installer/installer.sh.in @@ -144,7 +144,14 @@ if test "$installer_debug"; then fi # Pickup ONIE defines for this machine. -if test -r /etc/machine.conf; then +if test "$onie_platform"; then + : +else + onie_platform=$(onie-sysinfo -p 2>/dev/null) || : +fi +if test "$onie_platform"; then + : +elif test -r /etc/machine.conf; then . /etc/machine.conf fi @@ -252,7 +259,7 @@ if test "${onie_platform}"; then } else if test "$ARCH_X86"; then - echo "Missing onie_platform (invalid /etc/machine.conf)" 1>&2 + echo "Missing onie_platform (invalid or missing onie-sysinfo or /etc/machine.conf)" 1>&2 exit 1 fi #