diff --git a/xCAT-openbmc-py/lib/python/agent/hwctl/bmcconfig.py b/xCAT-openbmc-py/lib/python/agent/hwctl/bmcconfig.py index ec19b596c..76355be85 100644 --- a/xCAT-openbmc-py/lib/python/agent/hwctl/bmcconfig.py +++ b/xCAT-openbmc-py/lib/python/agent/hwctl/bmcconfig.py @@ -25,6 +25,9 @@ class BmcConfigInterface(object): def dump_process(self, task): return task.run("dump_process") + def gard_clear(self, task): + return task.run("gard_clear") + def set_sshcfg(self, task): return task.run("set_sshcfg") diff --git a/xCAT-openbmc-py/lib/python/agent/hwctl/executor/openbmc_bmcconfig.py b/xCAT-openbmc-py/lib/python/agent/hwctl/executor/openbmc_bmcconfig.py index a3240bc48..aa91a56be 100644 --- a/xCAT-openbmc-py/lib/python/agent/hwctl/executor/openbmc_bmcconfig.py +++ b/xCAT-openbmc-py/lib/python/agent/hwctl/executor/openbmc_bmcconfig.py @@ -23,7 +23,7 @@ from scp import SCPClient import logging logger = logging.getLogger('xcatagent') -RSPCONFIG_GET_NETINFO=['ip', 'netmask', 'gateway', 'vlan', 'ipsrc', 'hostname'] +RSPCONFIG_GET_NETINFO=['ip', 'netmask', 'gateway', 'vlan', 'ipsrc', 'hostname', 'ntpservers'] RSPCONFIG_SET_NETINFO=['ip', 'netmask', 'gateway', 'vlan'] XCAT_LOG_DUMP_DIR = "/var/log/xcat/dump/" @@ -179,6 +179,20 @@ class OpenBMCBmcConfigTask(ParallelNodesCommand): except SelfServerException as e: self.callback.info('%s: %s' % (node, e.message)) + def gard_clear(self, **kw): + + node = kw['node'] + obmc = openbmc.OpenBMCRest(name=node, nodeinfo=kw['nodeinfo'], messager=self.callback, + debugmode=self.debugmode, verbose=self.verbose) + + try: + obmc.login() + obmc.clear_gard() + self.callback.info('%s: GARD cleared' % node) + + except SelfServerException as e: + self.callback.info('%s: %s' % (node, e.message)) + def pre_set_sshcfg(self, *arg, **kw): local_home_dir=os.path.expanduser('~') self.local_ssh_dir = local_home_dir + "/.ssh/" @@ -261,7 +275,8 @@ rmdir \"/tmp/$userid\" \n") if len(netinfo_dict): self._get_netinfo(ip=netinfo_dict.get('ip', False), ipsrc=netinfo_dict.get('ipsrc', False), netmask=netinfo_dict.get('netmask', False), gateway=netinfo_dict.get('gateway', False),vlan= netinfo_dict.get('vlan', False), - hostname=netinfo_dict.get('hostname', False), **kw) + hostname=netinfo_dict.get('hostname', False), + ntpservers=netinfo_dict.get('ntpservers', False), **kw) def set_attributes(self, attributes, **kw): netinfo_dict={'vlan':False} @@ -271,6 +286,10 @@ rmdir \"/tmp/$userid\" \n") netinfo_dict[k] = v elif k == 'hostname': self._set_hostname(v, **kw) + elif k == 'admin_passwd': + self._set_admin_password(v, **kw) + elif k == 'ntpservers': + self._set_ntp_servers(v, **kw) elif k in openbmc.RSPCONFIG_APIS: self._set_apis_values(k, v, **kw) else: @@ -292,7 +311,66 @@ rmdir \"/tmp/$userid\" \n") self._set_apis_values("hostname", hostname, **kw) self._get_netinfo(hostname=True, ntpserver=False, **kw) return - + + def _set_ntp_servers(self, servers, **kw): + node = kw['node'] + node_info = kw['nodeinfo'] + obmc = openbmc.OpenBMCRest(name=node, nodeinfo=node_info, messager=self.callback, + debugmode=self.debugmode, verbose=self.verbose) + + try: + obmc.login() + netinfo = obmc.get_netinfo() + except (SelfServerException, SelfClientException) as e: + self.callback.info('%s: %s' % (node, e.message)) + return + + if not netinfo: + return self.callback.error("%s: No network information get" % node) + + bmcip = node_info['bmcip'] + nic = self._get_facing_nic(bmcip, netinfo) + if not nic: + return self.callback.error('%s: Can not get facing NIC for %s' % (node, bmcip)) + + try: + obmc.set_ntp_servers(nic, servers) + self.callback.info('%s: BMC Setting NTPServers...' % node) + netinfo = obmc.get_netinfo() + except (SelfServerException, SelfClientException) as e: + self.callback.info('%s: %s' % (node, e.message)) + return + + ntpservers = None + if nic in netinfo: + ntpservers = netinfo[nic]['ntpservers'] + self.callback.info('%s: BMC NTP Servers: %s' % (node, ntpservers)) + + def _get_facing_nic(self, bmcip, netinfo): + for k,v in netinfo.items(): + if 'ip' in v and v['ip'] == bmcip: + return k + return None + + def _set_admin_password(self, admin_passwd, **kw): + node = kw['node'] + node_info = kw['nodeinfo'] + + origin_passwd, new_passwd = admin_passwd.split(',') + + if origin_passwd != node_info['password']: + self.callback.info('%s: Current BMC password is incorrect, cannot set the new password.' % node) + return + + obmc = openbmc.OpenBMCRest(name=node, nodeinfo=node_info, messager=self.callback, + debugmode=self.debugmode, verbose=self.verbose) + try: + obmc.login() + obmc.set_admin_passwd(new_passwd) + self.callback.info("%s: BMC Setting Password..." % node) + except (SelfServerException, SelfClientException) as e: + self.callback.info("%s: %s" % (node, e.message)) + def _set_apis_values(self, key, value, **kw): node = kw['node'] obmc = openbmc.OpenBMCRest(name=node, nodeinfo=kw['nodeinfo'], messager=self.callback, @@ -327,7 +405,7 @@ rmdir \"/tmp/$userid\" \n") result = "set net(%s, %s, %s) for eth0" % (ip, netmask, gateway) return self.callback.info("set_netinfo %s" % result) - def _get_netinfo(self, ip=False, ipsrc=False, netmask=False, gateway=False, vlan=False, hostname=False, ntpserver=True, **kw): + def _get_netinfo(self, ip=False, ipsrc=False, netmask=False, gateway=False, vlan=False, hostname=False, ntpservers=False, **kw): node = kw['node'] obmc = openbmc.OpenBMCRest(name=node, nodeinfo=kw['nodeinfo'], messager=self.callback, debugmode=self.debugmode, verbose=self.verbose) @@ -352,7 +430,7 @@ rmdir \"/tmp/$userid\" \n") self.callback.info("%s: BMC Hostname: %s" %(node, bmchostname)) dic_length = len(netinfo) netinfodict = {'ip':[], 'netmask':[], 'gateway':[], - 'vlan':[], 'ipsrc':[], 'ntpserver':[]} + 'vlan':[], 'ipsrc':[], 'ntpservers':[]} for nic,attrs in netinfo.items(): addon_string = '' if dic_length > 1: @@ -362,7 +440,7 @@ rmdir \"/tmp/$userid\" \n") netinfodict['gateway'].append("BMC Gateway"+addon_string+": %s (default: %s)" % (attrs["gateway"], defaultgateway)) netinfodict['vlan'].append("BMC VLAN ID"+addon_string+": %s" % attrs["vlanid"]) netinfodict['ipsrc'].append("BMC IP Source"+addon_string+": %s" % attrs["ipsrc"]) - netinfodict['ntpserver'].append("BMC NTP Servers"+addon_string+": %s" % attrs["ntpservers"]) + netinfodict['ntpservers'].append("BMC NTP Servers"+addon_string+": %s" % attrs["ntpservers"]) if ip: for i in netinfodict['ip']: self.callback.info("%s: %s" % (node, i)) @@ -378,7 +456,7 @@ rmdir \"/tmp/$userid\" \n") if vlan: for i in netinfodict['vlan']: self.callback.info("%s: %s" % (node, i)) - if ntpserver: - for i in netinfodict['netserver']: + if ntpservers: + for i in netinfodict['ntpservers']: self.callback.info("%s: %s" % (node, i)) return netinfo diff --git a/xCAT-openbmc-py/lib/python/agent/hwctl/openbmc_client.py b/xCAT-openbmc-py/lib/python/agent/hwctl/openbmc_client.py index 17d377c9f..8b1dc1605 100644 --- a/xCAT-openbmc-py/lib/python/agent/hwctl/openbmc_client.py +++ b/xCAT-openbmc-py/lib/python/agent/hwctl/openbmc_client.py @@ -47,6 +47,8 @@ DUMP_URLS = { "list" : "/dump/enumerate", } +GARD_CLEAR_URL = "/org/open_power/control/gard/action/Reset" + INVENTORY_URL = "/inventory/enumerate" LEDS_URL = "/led/physical/enumerate" @@ -164,9 +166,11 @@ RSPCONFIG_NETINFO_URL = { 'nic_ip': "/network/#NIC#/action/IP", 'vlan': "/network/action/VLAN", 'ipdhcp': "/network/action/Reset", - 'ntpserver': "/network/#NIC#/attr/NTPServers", + 'ntpservers': "/network/#NIC#/attr/NTPServers", } +PASSWD_URL = '/user/root/action/SetPassword' + RSPCONFIG_APIS = { 'hostname': { 'baseurl': "/network/config/", @@ -670,6 +674,17 @@ class OpenBMCRest(object): data={"data": attr_info['get_data']} return self.request(method, get_url, payload=data, cmd="get_%s" % key) + def set_admin_passwd(self, passwd): + + payload = { "data": [passwd] } + self.request('POST', PASSWD_URL, payload=payload, cmd='set_admin_password') + + def set_ntp_servers(self, nic, servers): + + payload = { "data": [servers] } + url = RSPCONFIG_NETINFO_URL['ntpservers'].replace('#NIC#', nic) + self.request('PUT', url, payload=payload, cmd='set_ntp_servers') + def clear_dump(self, clear_arg): if clear_arg == 'all': @@ -711,6 +726,12 @@ class OpenBMCRest(object): path = DUMP_URLS['download'].replace('#ID#', download_id) self.download('GET', path, file_path, headers=headers, cmd='download_dump') + def clear_gard(self): + + payload = { "data": [] } + url = HTTP_PROTOCOL + self.bmcip + GARD_CLEAR_URL + return self.request('POST', url, payload=payload, cmd='clear_gard') + def get_netinfo(self): data = self.request('GET', RSPCONFIG_NETINFO_URL['get_netinfo'], cmd="get_netinfo") try: @@ -743,7 +764,11 @@ class OpenBMCRest(object): info = data[dev] utils.update2Ddict(netinfo, nicid, "vlanid", info.get("Id", "Disable")) utils.update2Ddict(netinfo, nicid, "mac", info["MACAddress"]) - utils.update2Ddict(netinfo, nicid, "ntpservers", info["NTPServers"]) + ntpservers = None + tmp_ntpservers = ''.join(info["NTPServers"]) + if tmp_ntpservers: + ntpservers = tmp_ntpservers + utils.update2Ddict(netinfo, nicid, "ntpservers", ntpservers) return netinfo except KeyError: error = 'Error: Received wrong format response: %s' % data diff --git a/xCAT-openbmc-py/lib/python/agent/xcatagent/openbmc.py b/xCAT-openbmc-py/lib/python/agent/xcatagent/openbmc.py index 84c206bf3..6d382d140 100644 --- a/xCAT-openbmc-py/lib/python/agent/xcatagent/openbmc.py +++ b/xCAT-openbmc-py/lib/python/agent/xcatagent/openbmc.py @@ -82,24 +82,27 @@ RFLASH_URLS = { } } -RSPCONFIG_GET_OPTIONS = ['ip','ipsrc','netmask','gateway','vlan','hostname','bootmode','autoreboot','powersupplyredundancy','powerrestorepolicy'] +RSPCONFIG_GET_OPTIONS = ['ip','ipsrc','netmask','gateway','vlan','ntpservers','hostname','bootmode','autoreboot','powersupplyredundancy','powerrestorepolicy'] RSPCONFIG_SET_OPTIONS = { 'ip':'.*', 'netmask':'.*', 'gateway':'.*', 'vlan':'\d+', 'hostname':"\*|.*", + 'ntpservers':'.*', 'autoreboot':"^0|1$", 'powersupplyredundancy':"^enabled$|^disabled$", 'powerrestorepolicy':"^always_on$|^always_off$|^restore$", 'bootmode':"^regular$|^safe$|^setup$", + 'admin_passwd':'.*,.*', } RSPCONFIG_USAGE = """ Handle rspconfig operations. Usage: rspconfig -h|--help - rspconfig dump [[-l|--list] | [-g|--generate] | [-c|--clear ] | [-d|--download ]] [-V|--verbose] + rspconfig dump [[-l|--list] | [-g|--generate] | [-c|--clear --id ] | [-d|--download --id ]] [-V|--verbose] + rspconfig gard -c|--clear [-V|--verbose] rspconfig sshcfg [-V|--verbose] rspconfig ip=dhcp [-V|--verbose] rspconfig get [...] [-V|--verbose] @@ -109,8 +112,9 @@ Options: -V,--verbose Show verbose message -l,--list List are dump files -g,--generate Trigger a new dump file - -c,--clear The id of file to clear or all if specify 'all' - -d,--download The id of file to download or all if specify 'all' + -c,--clear To clear the specified dump file + -d,--download To download specified dump file + --id The dump file id or 'all' The supported attributes to get are: %s @@ -729,11 +733,14 @@ class OpenBMCManager(base.BaseManager): elif opts['--generate']: DefaultBmcConfigManager().dump_generate(runner) elif opts['--clear']: - DefaultBmcConfigManager().dump_clear(runner, opts['--clear'][0]) + DefaultBmcConfigManager().dump_clear(runner, opts['--id']) elif opts['--download']: - DefaultBmcConfigManager().dump_download(runner, opts['--download'][0]) + DefaultBmcConfigManager().dump_download(runner, opts['--id']) else: DefaultBmcConfigManager().dump_process(runner) + elif opts['gard']: + if opts['--clear']: + DefaultBmcConfigManager().gard_clear(runner) elif opts['sshcfg']: DefaultBmcConfigManager().set_sshcfg(runner) elif opts['ip=dhcp']: diff --git a/xCAT-server/lib/xcat/plugins/openbmc2.pm b/xCAT-server/lib/xcat/plugins/openbmc2.pm index 6cbedeaa9..1bcf513a0 100644 --- a/xCAT-server/lib/xcat/plugins/openbmc2.pm +++ b/xCAT-server/lib/xcat/plugins/openbmc2.pm @@ -367,16 +367,21 @@ sub refactor_args { my $request = shift; my $command = $request->{command}->[0]; my $extrargs = $request->{arg}; - my $subcommand; + my $subcommand; if ($command eq "rspconfig") { $subcommand = $extrargs->[0]; - if ($subcommand !~ /^dump$|^sshcfg$|^ip=dhcp$/) { + if ($subcommand !~ /^dump$|^sshcfg$|^ip=dhcp$|^gard$/) { if (grep /=/, @$extrargs) { unshift @$extrargs, "set"; } else { unshift @$extrargs, "get"; } } + if ($subcommand eq "dump") { + if (defined($extrargs->[1]) and $extrargs->[1] =~ /-c|--clear|-d|--download/){ + splice(@$extrargs, 2, 0, "--id"); + } + } } if ($command eq "reventlog") { if (!defined($extrargs->[0])) {