Skip to content

Commit

Permalink
Amend logind's behaviour (bsc#1031355, bsc#1039309, bsc#1043844)
Browse files Browse the repository at this point in the history
  • Loading branch information
angelabriel committed Jun 27, 2017
1 parent 40eb28d commit 43d75e4
Show file tree
Hide file tree
Showing 4 changed files with 112 additions and 16 deletions.
9 changes: 9 additions & 0 deletions main.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,8 @@ import (
"github.com/HouzuoGuo/saptune/sap/note"
"github.com/HouzuoGuo/saptune/sap/solution"
"github.com/HouzuoGuo/saptune/system"
"io"
"log"
"os"
"runtime"
"sort"
Expand Down Expand Up @@ -62,6 +64,13 @@ func main() {
errorExit("Please run saptune with root privilege.")
return
}
var saptune_log io.Writer
saptune_log, err := os.OpenFile("/var/log/tuned/tuned.log", os.O_CREATE | os.O_APPEND | os.O_RDWR, 0644)
if err != nil {
panic(err.Error())
}
saptune_writer := io.MultiWriter(os.Stdout, saptune_log)
log.SetOutput(saptune_writer)
archSolutions, exist := solution.AllSolutions[runtime.GOARCH]
if !exist {
errorExit("The system architecture (%s) is not supported.", runtime.GOARCH)
Expand Down
98 changes: 91 additions & 7 deletions sap/note/common.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,13 +5,20 @@ import (
"github.com/HouzuoGuo/saptune/sap/param"
"github.com/HouzuoGuo/saptune/system"
"github.com/HouzuoGuo/saptune/txtparser"
"io/ioutil"
"log"
"os"
"os/exec"
"path"
"regexp"
"strings"
)

const (
ARCH_X86 = "amd64" // GOARCH for 64-bit X86
ARCH_PPC = "ppc64le" // GOARCH for 64-bit PowerPC little endian
ARCH_X86 = "amd64" // GOARCH for 64-bit X86
ARCH_PPC = "ppc64le" // GOARCH for 64-bit PowerPC little endian
LOGIND_DIR = "/etc/systemd/logind.conf.d"
SAP_LOGIN_FILE = "sap.conf"
)

// 1275776 - Linux: Preparing SLES for SAP environments
Expand Down Expand Up @@ -148,22 +155,99 @@ func (prepare PrepareForSAPEnvironments) Apply() error {
// 1984787 - SUSE LINUX Enterprise Server 12: Installation notes
type AfterInstallation struct {
UuiddSocket bool
UserTasksMax bool
}

func (inst AfterInstallation) Name() string {
return "SUSE LINUX Enterprise Server 12: Installation notes"
}
func (inst AfterInstallation) Initialise() (Note, error) {
return AfterInstallation{UuiddSocket: system.SystemctlIsRunning("uuidd.socket")}, nil
return AfterInstallation{UuiddSocket: system.SystemctlIsRunning("uuidd.socket"), UserTasksMax: CheckSapLogindFile()}, nil
}
func (inst AfterInstallation) Optimise() (Note, error) {
// Unconditionally enable uuid socket
return AfterInstallation{UuiddSocket: true}, nil
if CheckSapLogindFile() {
// print message fork bomb
log.Print("ATTENTION UserTasksMax set to infinity. With this setting your system is vulnerable to fork bomb attacks.")
}
return AfterInstallation{UuiddSocket: true, UserTasksMax: true}, nil
}
func (inst AfterInstallation) Apply() error {
var err error
if CheckSapLogindFile() {
// print message fork bomb
log.Print("ATTENTION UserTasksMax set to infinity. With this setting your system is vulnerable to fork bomb attacks.")
} else {
// create directory /etc/systemd/logind.conf.d, if it does not exists
if err = os.MkdirAll(LOGIND_DIR, 0755); err != nil {
fmt.Printf("Error: Can't create directory '%s'\n", LOGIND_DIR)
return err
}
// create file /etc/systemd/logind.conf.d/sap.conf
err = ioutil.WriteFile(path.Join(LOGIND_DIR, SAP_LOGIN_FILE),[]byte("[Login]\nUserTasksMax=infinity\n"), 0644)
if err != nil {
fmt.Printf("Error: Can't create file '%s'\n", path.Join(LOGIND_DIR, SAP_LOGIN_FILE))
return err
}
// print reboot
log.Print("ATTENTION UserTasksMax is now set to infinity. Please reboot the system for the changes to take effect.")
}
if IsVM() {
//skip uuidd, does not work in VMs
return err
}
if inst.UuiddSocket {
return system.SystemctlEnableStart("uuidd.socket")
err = system.SystemctlEnableStart("uuidd.socket")
} else {
return system.SystemctlDisableStop("uuidd.socket")
err = system.SystemctlDisableStop("uuidd.socket")
}
return err
}
func CheckSapLogindFile() bool {
_ , err := os.Stat(path.Join(LOGIND_DIR, SAP_LOGIN_FILE))
if os.IsNotExist(err) {
// file does not exists, create it later
return false
}
if err == nil {
// file does exists, check value of UserTasksMax
content, err := ioutil.ReadFile(path.Join(LOGIND_DIR, SAP_LOGIN_FILE))
if err != nil {
fmt.Printf("Error: Can't read file '%s'. Continue anyway.\n", path.Join(LOGIND_DIR, SAP_LOGIN_FILE))
return false
}
for _, line := range strings.Split(string(content), "\n") {
matched, _ := regexp.MatchString("^[[:blank:]]*UserTasksMax[[:blank:]]*=[[:blank:]]*infinity", line)
if matched {
return true
}
}
// value of UserTasksMax does not match our needs
err = os.Rename(path.Join(LOGIND_DIR, SAP_LOGIN_FILE), path.Join(LOGIND_DIR, SAP_LOGIN_FILE + ".sav"))
if err != nil {
fmt.Printf("Error: Can't move file '%s' to '%s'. Continue anyway.\n", path.Join(LOGIND_DIR, SAP_LOGIN_FILE), path.Join(LOGIND_DIR, SAP_LOGIN_FILE + ".sav"))
}
return false
}
// another error concerning the file occured
return false
}
func IsVM() bool {
// true - system is vm, false - system is phys.
_ , err := os.Stat("/usr/bin/systemd-detect-virt")
if err == nil {
//systemd-detect-virt err=0 is VM, err=1 is phys.
cmd := exec.Command("/usr/bin/systemd-detect-virt")
_, err := cmd.Output()
if err == nil {
return true
} else {
return false
}
}
out, err := exec.Command("/usr/sbin/dmidecode", "-s", "system-manufacturer").Output()
switch strings.TrimSpace(string(out)) {
case "QEMU", "Xen", "VirtualBox", "VMware, Inc.":
return true
}
return false
}
3 changes: 3 additions & 0 deletions sap/note/common_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -51,4 +51,7 @@ func TestAfterInstallation(t *testing.T) {
if !optimised.(AfterInstallation).UuiddSocket {
t.Fatal(optimised)
}
if !optimised.(AfterInstallation).UserTasksMax {
t.Fatal(optimised)
}
}
18 changes: 9 additions & 9 deletions sap/note/ini.go
Original file line number Diff line number Diff line change
Expand Up @@ -67,15 +67,15 @@ type BlockDeviceQueue struct {
BlockDeviceNrRequests param.BlockDeviceNrRequests
}

func GetBlockVal(key string) string {
func GetBlockVal(key string) (string, error) {
newQueue := make(map[string]string)
newReq := make(map[string]int)
ret_val := ""
switch key {
case "IO_SCHEDULER":
newIOQ, err := BlockDeviceQueue{}.BlockDeviceSchedulers.Inspect()
if err != nil {
return "0"
return "", err
}
newQueue = newIOQ.(param.BlockDeviceSchedulers).SchedulerChoice
for k, v := range newQueue {
Expand All @@ -84,14 +84,14 @@ func GetBlockVal(key string) string {
case "NRREQ":
newNrR, err := BlockDeviceQueue{}.BlockDeviceNrRequests.Inspect()
if err != nil {
return "0"
return "", err
}
newReq = newNrR.(param.BlockDeviceNrRequests).NrRequests
for k, v := range newReq {
ret_val = ret_val + fmt.Sprintf("%s@%s ", k, strconv.Itoa(v))
}
}
return ret_val
return ret_val, nil
}

func OptBlkVal(parameter, act_value, cfg_value string) string {
Expand Down Expand Up @@ -164,12 +164,12 @@ func SetBlkVal(key, value string) error {
}

// section [limits]
func GetLimitsVal(key string) string {
func GetLimitsVal(key string) (string, error) {
// Find out current memlock limits
LimitMemlock := 0
secLimits, err := system.ParseSecLimitsFile()
if err != nil {
return "0"
return "", err
}
switch key {
case "MEMLOCK_HARD":
Expand All @@ -178,7 +178,7 @@ func GetLimitsVal(key string) string {
LimitMemlock, _ = secLimits.Get("sybase", "soft", "memlock")

}
return strconv.Itoa(LimitMemlock)
return strconv.Itoa(LimitMemlock), nil
}

func OptLimitsVal(act_value, cfg_value string) string {
Expand Down Expand Up @@ -268,9 +268,9 @@ func (vend INISettings) Initialise() (Note, error) {
case INISectionVM:
vend.SysctlParams[param.Key] = GetVmVal(param.Key)
case INISectionBlock:
vend.SysctlParams[param.Key] = GetBlockVal(param.Key)
vend.SysctlParams[param.Key], _ = GetBlockVal(param.Key)
case INISectionLimits:
vend.SysctlParams[param.Key] = GetLimitsVal(param.Key)
vend.SysctlParams[param.Key], _ = GetLimitsVal(param.Key)
default:
// saptune does not yet understand settings outside of [sysctl] section
log.Printf("3rdPartyTuningOption %s: skip unknown section %s", vend.ConfFilePath, param.Section)
Expand Down

0 comments on commit 43d75e4

Please sign in to comment.