Files
gocage/cmd/stop.go

174 lines
3.3 KiB
Go

package cmd
import (
"fmt"
// "log"
// "strings"
"os/exec"
)
// TODO : Use SYS_RCTL_GET_RACCT syscall
func removeRctlRules(jail string, rules []string) error {
var cmd []string
if len(rules) == 0 {
rules[0] = ""
}
for _, r := range rules {
if gUseSudo {
cmd = append(cmd, "sudo")
}
cmd = append(cmd, "/usr/bin/rctl")
cmd = append(cmd, "-r")
cmd = append(cmd, fmt.Sprintf("jail:%s:%s", jail, r))
// TODO : Log in another channel than stdout (will scramble diusplay)
//log.Println(fmt.Sprintf("Removing all rules for jail %s: %s", jail, cmd))
//out, err := exec.Command(cmd[0], cmd[1:]...).Output()
_, err := exec.Command(cmd[0], cmd[1:]...).Output()
return err
}
return nil
}
/* Moved into cmd/utils.go
func executeCommand(cmdline string) (string, error) {
var cmd []string
var out []byte
var err error
if gUseSudo {
cmd = append(cmd, "sudo")
}
cs := strings.Split(cmdline, " ")
cmd = append(cmd, cs...)
if len (cmd) > 1 {
out, err = exec.Command(cmd[0], cmd[1:]...).Output()
} else {
out, err = exec.Command(cmd[0]).Output()
}
return string(out), err
}
func executeCommandInJail(jail *Jail, cmdline string) (string, error) {
var cmd []string
if gUseSudo {
cmd = append(cmd, "sudo")
}
cmd = append(cmd, "setfib")
if len(jail.Config.Exec_fib) > 0 {
cmd = append(cmd, jail.Config.Exec_fib)
} else {
cmd = append(cmd, "0")
}
cmd = append(cmd, "jexec", jail.InternalName)
cs := strings.Split(cmdline, " ")
cmd = append(cmd, cs...)
out, err := exec.Command(cmd[0], cmd[1:]...).Output()
return string(out), err
}
*/
// TODO
func umountJailedZFS(jail *Jail) error {
/*
for _, zd := range jail.Config.Jail_zfs_dataset {
}
*/
return nil
}
/*
Stop jail:
Remove rctl rules
Execute prestop if set (jailhost perimeter)
Execute stop if set (inside jail)
Umount ZFS dataset
Unmount mountpoint
Delete devfs ruleset
Use setfib for each command
Shouldnt rctl rules be removed last, when jail is stopped?
*/
func stopJail(args []string) {
// Current jail were stopping
var cj *Jail
for _, j := range args {
fmt.Printf("> Stopping jail %s\n", j)
for _, rj := range gJails {
if rj.Name == j {
cj = &rj
break
}
}
if cj == nil {
fmt.Printf("Jail not found: %s\n", j)
continue
}
if cj.Running == false {
fmt.Printf("Jail %s is not running!\n", cj.Name)
continue
}
fmt.Printf(" > Remove RCTL rules: ")
err := removeRctlRules(cj.InternalName, []string{""})
if err != nil {
fmt.Printf("ERROR: %s\n", err.Error())
} else {
fmt.Printf("OK\n")
}
if len (cj.Config.Exec_prestop) > 0 {
fmt.Printf(" > Execute prestop: ")
out, err := executeCommand(cj.Config.Exec_prestop)
if err != nil {
fmt.Printf("ERROR: %s\n", err.Error())
} else {
fmt.Printf("OK\n")
fmt.Printf("%s\n", out)
}
}
if len (cj.Config.Exec_stop) > 0 {
fmt.Printf(" > Execute stop: ")
out, err := executeCommandInJail(cj, cj.Config.Exec_stop)
if err != nil {
fmt.Printf("ERROR: %s\n", err.Error())
} else {
fmt.Printf("OK\n")
fmt.Printf("%s\n", out)
}
}
if cj.Config.Jail_zfs > 0 {
fmt.Printf(" > Umount jailed ZFS: ")
err := umountJailedZFS(cj)
if err != nil {
fmt.Printf("ERROR: %s\n", err.Error())
} else {
fmt.Printf("OK\n")
}
}
}
}