mirror of
https://github.com/yunionio/cloudpods.git
synced 2026-08-30 17:13:08 +08:00
baremetal: fix build HPSARaid and enable serial console errors
This commit is contained in:
+13
-10
@@ -25,9 +25,11 @@ import (
|
||||
"sync"
|
||||
"time"
|
||||
|
||||
"github.com/pkg/errors"
|
||||
|
||||
"yunion.io/x/jsonutils"
|
||||
"yunion.io/x/log"
|
||||
"yunion.io/x/pkg/util/errors"
|
||||
yerrors "yunion.io/x/pkg/util/errors"
|
||||
"yunion.io/x/pkg/util/regutils"
|
||||
"yunion.io/x/pkg/util/seclib"
|
||||
"yunion.io/x/pkg/util/sets"
|
||||
@@ -120,7 +122,7 @@ func (m *SBaremetalManager) loadConfigs() error {
|
||||
errs = append(errs, <-errsChannel)
|
||||
}
|
||||
}
|
||||
return errors.NewAggregate(errs)
|
||||
return yerrors.NewAggregate(errs)
|
||||
}
|
||||
|
||||
func (m *SBaremetalManager) initBaremetal(session *mcclient.ClientSession, bmId string) error {
|
||||
@@ -1016,6 +1018,7 @@ func (b *SBaremetalInstance) StartNewTask(factory tasks.TaskFactory, taskId stri
|
||||
go func() {
|
||||
task, err := factory(b, taskId, data)
|
||||
if err != nil {
|
||||
log.Errorf("New task %#v error: %v", factory, err)
|
||||
tasks.SetTaskFail(task, err)
|
||||
return
|
||||
}
|
||||
@@ -1328,40 +1331,40 @@ func (s *SBaremetalServer) DoPartitionDisk(term *ssh.Client) ([]*disktool.Partit
|
||||
storages = append(storages, pcie...)
|
||||
confs, err := s.GetDiskConfig()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
return nil, errors.Wrapf(err, "do disk config")
|
||||
}
|
||||
layouts, err := baremetal.CalculateLayout(confs, storages)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
return nil, errors.Wrapf(err, "CalculateLayout")
|
||||
}
|
||||
|
||||
tool := disktool.NewSSHPartitionTool(term)
|
||||
tool.FetchDiskConfs(baremetal.GetDiskConfigurations(layouts))
|
||||
err = tool.RetrieveDiskInfo()
|
||||
if err != nil {
|
||||
return nil, err
|
||||
return nil, errors.Wrapf(err, "RetrieveDiskInfo")
|
||||
}
|
||||
|
||||
disks, _ := s.desc.GetArray("disks")
|
||||
if len(disks) == 0 {
|
||||
return nil, fmt.Errorf("Empty disks in desc")
|
||||
return nil, errors.New("Empty disks in desc")
|
||||
}
|
||||
|
||||
rootDisk := disks[0]
|
||||
rootSize, _ := rootDisk.Int("size")
|
||||
err = s.doCreateRoot(term, tool.GetRootDisk().GetDevName())
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("Failed to create root: %v", err)
|
||||
return nil, errors.Wrapf(err, "Failed to create root")
|
||||
}
|
||||
|
||||
tool.RetrievePartitionInfo()
|
||||
parts := tool.GetPartitions()
|
||||
if len(parts) == 0 {
|
||||
return nil, fmt.Errorf("Root disk create failed, no partitions")
|
||||
return nil, errors.New("Root disk create failed, no partitions")
|
||||
}
|
||||
log.Infof("Resize root to %d MB", rootSize)
|
||||
if err := tool.ResizePartition(0, rootSize); err != nil {
|
||||
return nil, fmt.Errorf("Fail to resize root to %d, err: %v", rootSize, err)
|
||||
return nil, errors.Wrapf(err, "Fail to resize root to %d", rootSize)
|
||||
}
|
||||
if len(disks) > 1 {
|
||||
for _, disk := range disks[1:] {
|
||||
@@ -1374,7 +1377,7 @@ func (s *SBaremetalServer) DoPartitionDisk(term *ssh.Client) ([]*disktool.Partit
|
||||
driver, _ := disk.GetString("driver")
|
||||
log.Infof("Create partition %d %s", sz, fs)
|
||||
if err := tool.CreatePartition(-1, sz, fs, true, driver, uuid); err != nil {
|
||||
return nil, fmt.Errorf("Fail to create disk %s: %v", disk.String(), err)
|
||||
return nil, errors.Wrapf(err, "Fail to create disk %s", disk.String())
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -21,6 +21,8 @@ import (
|
||||
"sync"
|
||||
"time"
|
||||
|
||||
"github.com/pkg/errors"
|
||||
|
||||
"yunion.io/x/jsonutils"
|
||||
"yunion.io/x/log"
|
||||
|
||||
@@ -287,18 +289,18 @@ func (self *SBaremetalTaskBase) EnsurePowerUp() error {
|
||||
log.Infof("EnsurePowerUp: bootdev=pxe")
|
||||
status, err := self.Baremetal.GetPowerStatus()
|
||||
if err != nil {
|
||||
return err
|
||||
return errors.Wrapf(err, "Get power status")
|
||||
}
|
||||
for status == "" || status == types.POWER_STATUS_OFF {
|
||||
if status == types.POWER_STATUS_OFF {
|
||||
err = self.Baremetal.DoPXEBoot()
|
||||
if err != nil {
|
||||
return err
|
||||
return errors.Wrapf(err, "Do PXE boot")
|
||||
}
|
||||
}
|
||||
status, err = self.Baremetal.GetPowerStatus()
|
||||
if err != nil {
|
||||
return err
|
||||
return errors.Wrapf(err, "Get power status")
|
||||
}
|
||||
if status == "" || status == types.POWER_STATUS_OFF {
|
||||
time.Sleep(40 * time.Second)
|
||||
@@ -367,7 +369,7 @@ func (self *SBaremetalPXEBootTaskBase) InitPXEBootTask(pxeBootTask IPXEBootTask,
|
||||
return self, fmt.Errorf("EnsurePowerShutdown: %v", err)
|
||||
}
|
||||
if err := self.EnsurePowerUp(); err != nil {
|
||||
return self, fmt.Errorf("EnsurePowerUp to pxe: %v", err)
|
||||
return self, errors.Wrapf(err, "EnsurePowerUp to pxe")
|
||||
}
|
||||
// this stage will be called by baremetalInstance when pxe start notify
|
||||
self.SetSSHStage(pxeBootTask.OnPXEBoot)
|
||||
|
||||
@@ -17,6 +17,8 @@ package tasks
|
||||
import (
|
||||
"context"
|
||||
|
||||
"github.com/pkg/errors"
|
||||
|
||||
"yunion.io/x/jsonutils"
|
||||
"yunion.io/x/log"
|
||||
"yunion.io/x/pkg/utils"
|
||||
@@ -64,25 +66,25 @@ func (self *SBaremetalServerBaseDeployTask) OnPXEBoot(ctx context.Context, term
|
||||
log.Infof("%s called on stage pxeboot, args: %v", self.GetName(), args)
|
||||
result, err := self.serverDeployTask.DoDeploys(term)
|
||||
if err != nil {
|
||||
return err
|
||||
return errors.Wrap(err, "Do deploy")
|
||||
}
|
||||
_, err = term.Run(
|
||||
"/bin/sync",
|
||||
"/sbin/sysctl -w vm.drop_caches=3",
|
||||
)
|
||||
if err != nil {
|
||||
return err
|
||||
return errors.Wrap(err, "Sync disk")
|
||||
}
|
||||
onFinishAction := self.GetFinishAction()
|
||||
if utils.IsInStringArray(onFinishAction, []string{"restart", "shutdown"}) {
|
||||
err = self.EnsurePowerShutdown(false)
|
||||
if err != nil {
|
||||
return err
|
||||
return errors.Wrap(err, "Ensure power off")
|
||||
}
|
||||
if onFinishAction == "restart" {
|
||||
err = self.EnsurePowerUp()
|
||||
if err != nil {
|
||||
return err
|
||||
return errors.Wrap(err, "Ensure power up")
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -74,6 +74,7 @@ func (self *SBaremetalServerCreateTask) DoDeploys(term *ssh.Client) (jsonutils.J
|
||||
}
|
||||
|
||||
func (self *SBaremetalServerCreateTask) onError(term *ssh.Client, err error) error {
|
||||
log.Errorf("Create server error: %+v", err)
|
||||
if err1 := self.Baremetal.GetServer().DoEraseDisk(term); err1 != nil {
|
||||
log.Warningf("EraseDisk error: %v", err1)
|
||||
}
|
||||
|
||||
@@ -70,8 +70,7 @@ func DetectStorageInfo(term *ssh.Client, wait bool) ([]*baremetal.BaremetalStora
|
||||
raidDrivers = append(raidDrivers, drv.GetName())
|
||||
}
|
||||
|
||||
log.Infof("Get Raid drivers: %v", raidDrivers)
|
||||
|
||||
log.Infof("Get Raid drivers: %v, collecting disks info ...", raidDrivers)
|
||||
pcieRet, err := term.Run("/lib/mos/lsdisk --pcie")
|
||||
if err != nil {
|
||||
return nil, nil, nil, fmt.Errorf("Fail to retrieve PCIE DISK info")
|
||||
|
||||
@@ -21,6 +21,8 @@ import (
|
||||
"strings"
|
||||
"time"
|
||||
|
||||
"github.com/pkg/errors"
|
||||
|
||||
"yunion.io/x/log"
|
||||
"yunion.io/x/pkg/tristate"
|
||||
"yunion.io/x/pkg/util/stringutils"
|
||||
@@ -444,7 +446,7 @@ func DoReboot(exector IPMIExecutor) error {
|
||||
var err error
|
||||
status, err = GetChassisPowerStatus(exector)
|
||||
if err != nil {
|
||||
return err
|
||||
log.Errorf("DoReboot get power status 1st: %v", err)
|
||||
}
|
||||
|
||||
isValidStatus := func(s string) bool {
|
||||
@@ -455,25 +457,24 @@ func DoReboot(exector IPMIExecutor) error {
|
||||
time.Sleep(1 * time.Second)
|
||||
status, err = GetChassisPowerStatus(exector)
|
||||
if err != nil {
|
||||
return err
|
||||
log.Errorf("DoReboot %d tries to get power status: %v", tried, err)
|
||||
}
|
||||
}
|
||||
|
||||
if !isValidStatus(status) {
|
||||
return fmt.Errorf("Unexpected status: %s", status)
|
||||
return fmt.Errorf("Unexpected power status: %q", status)
|
||||
}
|
||||
|
||||
// do shutdown
|
||||
if status == types.POWER_STATUS_ON {
|
||||
err = DoHardShutdown(exector)
|
||||
if err != nil {
|
||||
return err
|
||||
if err := DoHardShutdown(exector); err != nil {
|
||||
log.Errorf("DoHardShutdown: %v", err)
|
||||
}
|
||||
time.Sleep(1 * time.Second)
|
||||
for tried := 0; tried < maxTries; tried++ {
|
||||
status, err = GetChassisPowerStatus(exector)
|
||||
if err != nil {
|
||||
return err
|
||||
log.Errorf("DoReboot %d tries to get power status: %v", tried, err)
|
||||
}
|
||||
if status == types.POWER_STATUS_OFF {
|
||||
break
|
||||
@@ -483,28 +484,24 @@ func DoReboot(exector IPMIExecutor) error {
|
||||
}
|
||||
|
||||
// do power on
|
||||
status, err = GetChassisPowerStatus(exector)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
status, _ = GetChassisPowerStatus(exector)
|
||||
for tried := 0; status != types.POWER_STATUS_ON && tried < maxTries; tried++ {
|
||||
err = DoPowerOn(exector)
|
||||
if err != nil {
|
||||
return err
|
||||
if err := DoPowerOn(exector); err != nil {
|
||||
log.Errorf("DoReboot %d tries to power on: %v", tried, err)
|
||||
}
|
||||
time.Sleep(1 * time.Second)
|
||||
status, err = GetChassisPowerStatus(exector)
|
||||
if err != nil {
|
||||
return err
|
||||
log.Errorf("DoReboot %d tries to get power status: %v", tried, err)
|
||||
}
|
||||
}
|
||||
|
||||
status, err = GetChassisPowerStatus(exector)
|
||||
if err != nil {
|
||||
return err
|
||||
return errors.Wrap(err, "Get power status after power on")
|
||||
}
|
||||
if status != types.POWER_STATUS_ON {
|
||||
return fmt.Errorf("do reboot fail to poweron, current status: %s", status)
|
||||
return errors.Errorf("do reboot fail to poweron, current status: %s", status)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
@@ -20,7 +20,10 @@ import (
|
||||
"strconv"
|
||||
"strings"
|
||||
|
||||
"github.com/pkg/errors"
|
||||
|
||||
"yunion.io/x/log"
|
||||
"yunion.io/x/pkg/tristate"
|
||||
"yunion.io/x/pkg/util/stringutils"
|
||||
"yunion.io/x/pkg/utils"
|
||||
|
||||
@@ -39,6 +42,11 @@ type HPSARaidPhyDev struct {
|
||||
func newHPSARaidPhyDev(addr string, adapter int, rotate bool) *HPSARaidPhyDev {
|
||||
b := raid.NewRaidBasePhyDev(baremetal.DISK_DRIVER_HPSARAID)
|
||||
b.Adapter = adapter
|
||||
if rotate {
|
||||
b.Rotate = tristate.True
|
||||
} else {
|
||||
b.Rotate = tristate.False
|
||||
}
|
||||
return &HPSARaidPhyDev{
|
||||
RaidBasePhyDev: b,
|
||||
addr: addr,
|
||||
@@ -133,16 +141,20 @@ func (adapter *HPSARaidAdaptor) ParsePhyDevs() error {
|
||||
adapter.parsePhyDevs(ret, isRotate)
|
||||
return nil
|
||||
}
|
||||
cmd1 := GetCommand("controller", "slot=%d", fmt.Sprintf("%d", adapter.index), "ssdphysicaldrive", "all", "show", "detail")
|
||||
cmd2 := GetCommand("controller", "slot=%d", fmt.Sprintf("%d", adapter.index), "physicaldrive", "all", "show", "detail")
|
||||
var err error
|
||||
if err = parseByCmd(cmd1, false); err != nil {
|
||||
log.Errorf("parsePhyDevs by cmd %q: %v", cmd1, err)
|
||||
cmd1 := GetCommand("controller", fmt.Sprintf("slot=%d", adapter.index), "ssdphysicaldrive", "all", "show", "detail")
|
||||
cmd2 := GetCommand("controller", fmt.Sprintf("slot=%d", adapter.index), "physicaldrive", "all", "show", "detail")
|
||||
var err1 error
|
||||
var err2 error
|
||||
if err1 = parseByCmd(cmd1, false); err1 != nil {
|
||||
err1 = errors.Errorf("parsePhyDevs by cmd %q: %v", cmd1, err1)
|
||||
}
|
||||
if err = parseByCmd(cmd2, true); err != nil {
|
||||
log.Errorf("parsePhyDevs by cmd %q: %v", cmd1, err)
|
||||
if err2 = parseByCmd(cmd2, true); err2 != nil {
|
||||
err2 = errors.Errorf("parsePhyDevs by cmd %q: %v", cmd1, err2)
|
||||
}
|
||||
return err
|
||||
if err1 != nil && err2 != nil {
|
||||
return errors.Errorf("ssd: %v, hdd: %v", err1, err2)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func (adapter *HPSARaidAdaptor) parsePhyDevs(lines []string, isRotate bool) {
|
||||
@@ -153,7 +165,7 @@ func (adapter *HPSARaidAdaptor) parsePhyDevs(lines []string, isRotate bool) {
|
||||
phydev = newHPSARaidPhyDev(m["addr"], adapter.index, isRotate)
|
||||
} else if phydev != nil && phydev.parseLine(line) && phydev.isComplete() {
|
||||
oldDev := adapter.getPhyDevByAddr(phydev.addr)
|
||||
if oldDev != nil {
|
||||
if oldDev == nil {
|
||||
adapter.devs = append(adapter.devs, phydev)
|
||||
}
|
||||
phydev = nil
|
||||
@@ -263,7 +275,7 @@ func (adapter *HPSARaidAdaptor) BuildRaid5(devs []*baremetal.BaremetalStorage, c
|
||||
}
|
||||
|
||||
func (adapter *HPSARaidAdaptor) BuildRaid10(devs []*baremetal.BaremetalStorage, conf *api.BaremetalDiskConfig) error {
|
||||
return adapter.buildRaid("10", devs, conf)
|
||||
return adapter.buildRaid("1+0", devs, conf)
|
||||
}
|
||||
|
||||
func (adapter *HPSARaidAdaptor) BuildNoneRaid(devs []*baremetal.BaremetalStorage) error {
|
||||
@@ -315,7 +327,7 @@ func (adapter *HPSARaidAdaptor) RemoveLogicVolumes() error {
|
||||
if err != nil {
|
||||
return fmt.Errorf("Failed to get logic volumes: %v", err)
|
||||
}
|
||||
for i := len(lvs) - 1; i >= 0; i-- {
|
||||
for _, i := range raid.ReverseIntArray(lvs) {
|
||||
if err := adapter.removeLogicVolume(i); err != nil {
|
||||
return fmt.Errorf("Remove %d logical volume: %v", i, err)
|
||||
}
|
||||
|
||||
@@ -602,7 +602,7 @@ func (adapter *MegaRaidAdaptor) RemoveLogicVolumes() error {
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
for i := len(lvIdx) - 1; i >= 0; i-- {
|
||||
for _, i := range raiddrivers.ReverseIntArray(lvIdx) {
|
||||
cmd := GetCommand("-CfgLdDel", fmt.Sprintf("-L%d", i), "-Force", fmt.Sprintf("-a%d", adapter.index))
|
||||
cmds = append(cmds, cmd)
|
||||
}
|
||||
|
||||
@@ -186,7 +186,7 @@ func (adapter *MarvelRaidAdaptor) RemoveLogicVolumes() error {
|
||||
if err != nil {
|
||||
return fmt.Errorf("Failed to get logic volumes: %v", err)
|
||||
}
|
||||
for i := len(lvs) - 1; i >= 0; i-- {
|
||||
for _, i := range raid.ReverseIntArray(lvs) {
|
||||
if err := adapter.removeLogicVolume(i); err != nil {
|
||||
return fmt.Errorf("Remove %d logical volume: %v", i, err)
|
||||
}
|
||||
|
||||
@@ -103,3 +103,14 @@ func GetModules(term *ssh.Client) []string {
|
||||
}
|
||||
return ret
|
||||
}
|
||||
|
||||
func ReverseIntArray(input []int) []int {
|
||||
s := make([]int, len(input))
|
||||
for i := range input {
|
||||
s[i] = input[i]
|
||||
}
|
||||
for i, j := 0, len(s)-1; i < j; i, j = i+1, j-1 {
|
||||
s[i], s[j] = s[j], s[i]
|
||||
}
|
||||
return s
|
||||
}
|
||||
|
||||
@@ -0,0 +1,46 @@
|
||||
// Copyright 2019 Yunion
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package raid
|
||||
|
||||
import (
|
||||
"reflect"
|
||||
"testing"
|
||||
)
|
||||
|
||||
func TestReverseIntArray(t *testing.T) {
|
||||
tests := []struct {
|
||||
name string
|
||||
input []int
|
||||
want []int
|
||||
}{
|
||||
{
|
||||
name: "empty input",
|
||||
input: []int{},
|
||||
want: []int{},
|
||||
},
|
||||
{
|
||||
name: "reverse",
|
||||
input: []int{1, 2, 3},
|
||||
want: []int{3, 2, 1},
|
||||
},
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
if got := ReverseIntArray(tt.input); !reflect.DeepEqual(got, tt.want) {
|
||||
t.Errorf("ReverseIntArray() = %v, want %v", got, tt.want)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
@@ -371,7 +371,9 @@ func (l *sLinuxRootFs) getSerialPorts(rootFs IDiskPartition) []string {
|
||||
log.Errorf("Get %s error: %v", confpath, err)
|
||||
return nil
|
||||
}
|
||||
return sysutils.GetSerialPorts(strings.Split(string(content), "\n"))
|
||||
ttys := sysutils.GetSerialPorts(strings.Split(string(content), "\n"))
|
||||
log.Infof("Get serial ports content:\n%s, find serial ttys: %#v", string(content), ttys)
|
||||
return ttys
|
||||
}
|
||||
|
||||
func (l *sLinuxRootFs) enableSerialConsoleInitCentos(rootFs IDiskPartition) error {
|
||||
@@ -390,10 +392,26 @@ exec /sbin/agetty /dev/%s 115200 vt100`, tty, tty, tty)
|
||||
return err
|
||||
}
|
||||
|
||||
func (l *sLinuxRootFs) enableSerialConsoleRootLogin(rootFs IDiskPartition, tty string) error {
|
||||
secureTTYFile := "/etc/securetty"
|
||||
content, err := rootFs.FileGetContents(secureTTYFile, false)
|
||||
if err != nil {
|
||||
return errors.Wrapf(err, "get contents of %s", secureTTYFile)
|
||||
}
|
||||
secureTTYs := sysutils.GetSecureTTYs(strings.Split(string(content), "\n"))
|
||||
if utils.IsInStringArray(tty, secureTTYs) {
|
||||
return nil
|
||||
}
|
||||
return rootFs.FilePutContents(secureTTYFile, fmt.Sprintf("\n%s", tty), true, false)
|
||||
}
|
||||
|
||||
func (l *sLinuxRootFs) enableSerialConsoleInit(rootFs IDiskPartition) error {
|
||||
// https://help.ubuntu.com/community/SerialConsoleHowto
|
||||
var err error
|
||||
for _, tty := range l.getSerialPorts(rootFs) {
|
||||
if err := l.enableSerialConsoleRootLogin(rootFs, tty); err != nil {
|
||||
log.Errorf("Enable %s root login: %v", tty, err)
|
||||
}
|
||||
content := fmt.Sprintf(
|
||||
`start on stopped rc or RUNLEVEL=[12345]
|
||||
stop on runlevel [!12345]
|
||||
@@ -415,6 +433,9 @@ func (l *sLinuxRootFs) disableSerialConsoleInit(rootFs IDiskPartition) {
|
||||
|
||||
func (l *sLinuxRootFs) enableSerialConsoleSystemd(rootFs IDiskPartition) error {
|
||||
for _, tty := range l.getSerialPorts(rootFs) {
|
||||
if err := l.enableSerialConsoleRootLogin(rootFs, tty); err != nil {
|
||||
log.Errorf("Enable %s root login: %v", tty, err)
|
||||
}
|
||||
sPath := fmt.Sprintf("/etc/systemd/system/getty.target.wants/getty@%s.service", tty)
|
||||
if rootFs.Exists(sPath, false) {
|
||||
rootFs.Remove(sPath, false)
|
||||
|
||||
+8
-2
@@ -20,6 +20,7 @@ import (
|
||||
"strings"
|
||||
"time"
|
||||
|
||||
"github.com/pkg/errors"
|
||||
"golang.org/x/crypto/ssh"
|
||||
|
||||
"yunion.io/x/log"
|
||||
@@ -131,8 +132,13 @@ func (s *Client) run(parseOutput bool, cmds ...string) ([]string, error) {
|
||||
session.Stderr = &stdErr
|
||||
err = session.Run(cmd)
|
||||
if err != nil {
|
||||
err = fmt.Errorf("%q error: %v, Stderr: %s", cmd, err, stdErr.String())
|
||||
log.Errorf("%v", err)
|
||||
var outputErr error
|
||||
errMsg := stdErr.String()
|
||||
if len(stdOut.String()) != 0 {
|
||||
errMsg = fmt.Sprintf("%s %s", errMsg, stdOut.String())
|
||||
}
|
||||
outputErr = errors.New(errMsg)
|
||||
err = errors.Errorf("%q error: %v, cmd error: %v", cmd, err, outputErr)
|
||||
return nil, err
|
||||
}
|
||||
if parseOutput {
|
||||
|
||||
@@ -233,10 +233,25 @@ func ParseSCSIDiskInfo(lines []string) []*types.SDiskInfo {
|
||||
return ParseDiskInfo(lines, baremetal.DISK_DRIVER_LINUX)
|
||||
}
|
||||
|
||||
func GetSecureTTYs(lines []string) []string {
|
||||
ttys := []string{}
|
||||
for _, l := range lines {
|
||||
if len(l) == 0 {
|
||||
continue
|
||||
}
|
||||
if strings.HasPrefix(l, "#") {
|
||||
continue
|
||||
}
|
||||
ttys = append(ttys, l)
|
||||
}
|
||||
return ttys
|
||||
}
|
||||
|
||||
func GetSerialPorts(lines []string) []string {
|
||||
// http://wiki.networksecuritytoolkit.org/index.php/Console_Output_and_Serial_Terminals
|
||||
ret := []string{}
|
||||
for _, l := range lines {
|
||||
if strings.Contains(l, "CTS") {
|
||||
if strings.Contains(l, "CTS") || strings.Contains(l, "RTS") {
|
||||
pos := strings.Index(l, ":")
|
||||
if pos < 0 {
|
||||
continue
|
||||
|
||||
@@ -273,3 +273,38 @@ func TestParseNicInfo(t *testing.T) {
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestGetSecureTTYs(t *testing.T) {
|
||||
tests := []struct {
|
||||
name string
|
||||
lines []string
|
||||
want []string
|
||||
}{
|
||||
{
|
||||
name: "empty tty",
|
||||
lines: []string{"", "#comment"},
|
||||
want: []string{},
|
||||
},
|
||||
{
|
||||
name: "ttys",
|
||||
lines: []string{
|
||||
"tty1",
|
||||
"ttyS0",
|
||||
"console",
|
||||
"#tty0",
|
||||
},
|
||||
want: []string{
|
||||
"tty1",
|
||||
"ttyS0",
|
||||
"console",
|
||||
},
|
||||
},
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
if got := GetSecureTTYs(tt.lines); !reflect.DeepEqual(got, tt.want) {
|
||||
t.Errorf("GetSecureTTYs() = %v, want %v", got, tt.want)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user