summaryrefslogtreecommitdiff
path: root/cmd/kpod
diff options
context:
space:
mode:
Diffstat (limited to 'cmd/kpod')
-rw-r--r--cmd/kpod/create.go363
-rw-r--r--cmd/kpod/create_cli.go106
-rw-r--r--cmd/kpod/images.go33
-rw-r--r--cmd/kpod/inspect.go308
-rw-r--r--cmd/kpod/run.go12
-rw-r--r--cmd/kpod/spec.go162
-rw-r--r--cmd/kpod/spec_test.go4
7 files changed, 620 insertions, 368 deletions
diff --git a/cmd/kpod/create.go b/cmd/kpod/create.go
index fc6e519fa..3548ad7df 100644
--- a/cmd/kpod/create.go
+++ b/cmd/kpod/create.go
@@ -1,6 +1,7 @@
package main
import (
+ "encoding/json"
"fmt"
"os"
"strconv"
@@ -36,91 +37,92 @@ var (
)
type createResourceConfig struct {
- blkioWeight uint16 // blkio-weight
- blkioWeightDevice []string // blkio-weight-device
- cpuPeriod uint64 // cpu-period
- cpuQuota int64 // cpu-quota
- cpuRtPeriod uint64 // cpu-rt-period
- cpuRtRuntime int64 // cpu-rt-runtime
- cpuShares uint64 // cpu-shares
- cpus string // cpus
- cpusetCpus string
- cpusetMems string // cpuset-mems
- deviceReadBps []string // device-read-bps
- deviceReadIOps []string // device-read-iops
- deviceWriteBps []string // device-write-bps
- deviceWriteIOps []string // device-write-iops
- disableOomKiller bool // oom-kill-disable
- kernelMemory int64 // kernel-memory
- memory int64 //memory
- memoryReservation int64 // memory-reservation
- memorySwap int64 //memory-swap
- memorySwappiness int // memory-swappiness
- oomScoreAdj int //oom-score-adj
- pidsLimit int64 // pids-limit
- shmSize string
- ulimit []string //ulimit
+ BlkioWeight uint16 // blkio-weight
+ BlkioWeightDevice []string // blkio-weight-device
+ CpuPeriod uint64 // cpu-period
+ CpuQuota int64 // cpu-quota
+ CpuRtPeriod uint64 // cpu-rt-period
+ CpuRtRuntime int64 // cpu-rt-runtime
+ CpuShares uint64 // cpu-shares
+ Cpus string // cpus
+ CpusetCpus string
+ CpusetMems string // cpuset-mems
+ DeviceReadBps []string // device-read-bps
+ DeviceReadIOps []string // device-read-iops
+ DeviceWriteBps []string // device-write-bps
+ DeviceWriteIOps []string // device-write-iops
+ DisableOomKiller bool // oom-kill-disable
+ KernelMemory int64 // kernel-memory
+ Memory int64 //memory
+ MemoryReservation int64 // memory-reservation
+ MemorySwap int64 //memory-swap
+ MemorySwappiness int // memory-swappiness
+ OomScoreAdj int //oom-score-adj
+ PidsLimit int64 // pids-limit
+ ShmSize string
+ Ulimit []string //ulimit
}
type createConfig struct {
- runtime *libpod.Runtime
- args []string
- capAdd []string // cap-add
- capDrop []string // cap-drop
- cidFile string
- cgroupParent string // cgroup-parent
- command []string
- detach bool // detach
- devices []*pb.Device // device
- dnsOpt []string //dns-opt
- dnsSearch []string //dns-search
- dnsServers []string //dns
- entrypoint string //entrypoint
- env map[string]string //env
- expose []string //expose
- groupAdd []uint32 // group-add
- hostname string //hostname
- image string
- interactive bool //interactive
- ipcMode container.IpcMode //ipc
- ip6Address string //ipv6
- ipAddress string //ip
- labels map[string]string //label
- linkLocalIP []string // link-local-ip
- logDriver string // log-driver
- logDriverOpt []string // log-opt
- macAddress string //mac-address
- name string //name
- netMode container.NetworkMode //net
- network string //network
- networkAlias []string //network-alias
- pidMode container.PidMode //pid
- nsUser string
- pod string //pod
- privileged bool //privileged
- publish []string //publish
- publishAll bool //publish-all
- readOnlyRootfs bool //read-only
- resources createResourceConfig
- rm bool //rm
- shmDir string
- sigProxy bool //sig-proxy
- stopSignal string // stop-signal
- stopTimeout int64 // stop-timeout
- storageOpts []string //storage-opt
- sysctl map[string]string //sysctl
- tmpfs []string // tmpfs
- tty bool //tty
- user uint32 //user
- group uint32 // group
- utsMode container.UTSMode //uts
- volumes []string //volume
- workDir string //workdir
- mountLabel string //SecurityOpts
- processLabel string //SecurityOpts
- noNewPrivileges bool //SecurityOpts
- apparmorProfile string //SecurityOpts
- seccompProfilePath string //SecurityOpts
+ Runtime *libpod.Runtime
+ Args []string
+ CapAdd []string // cap-add
+ CapDrop []string // cap-drop
+ CidFile string
+ CgroupParent string // cgroup-parent
+ Command []string
+ Detach bool // detach
+ Devices []*pb.Device // device
+ DnsOpt []string //dns-opt
+ DnsSearch []string //dns-search
+ DnsServers []string //dns
+ Entrypoint string //entrypoint
+ Env map[string]string //env
+ Expose []string //expose
+ GroupAdd []uint32 // group-add
+ Hostname string //hostname
+ Image string
+ Interactive bool //interactive
+ IpcMode container.IpcMode //ipc
+ Ip6Address string //ipv6
+ IpAddress string //ip
+ Labels map[string]string //label
+ LinkLocalIP []string // link-local-ip
+ LogDriver string // log-driver
+ LogDriverOpt []string // log-opt
+ MacAddress string //mac-address
+ Name string //name
+ NetMode container.NetworkMode //net
+ Network string //network
+ NetworkAlias []string //network-alias
+ PidMode container.PidMode //pid
+ NsUser string
+ Pod string //pod
+ Privileged bool //privileged
+ Publish []string //publish
+ PublishAll bool //publish-all
+ ReadOnlyRootfs bool //read-only
+ Resources createResourceConfig
+ Rm bool //rm
+ ShmDir string
+ SigProxy bool //sig-proxy
+ StopSignal string // stop-signal
+ StopTimeout int64 // stop-timeout
+ StorageOpts []string //storage-opt
+ Sysctl map[string]string //sysctl
+ Tmpfs []string // tmpfs
+ Tty bool //tty
+ User uint32 //user
+ Group uint32 // group
+ UtsMode container.UTSMode //uts
+ Volumes []string //volume
+ WorkDir string //workdir
+ MountLabel string //SecurityOpts
+ ProcessLabel string //SecurityOpts
+ NoNewPrivileges bool //SecurityOpts
+ ApparmorProfile string //SecurityOpts
+ SeccompProfilePath string //SecurityOpts
+ SecurityOpts []string
}
var createDescription = "Creates a new container from the given image or" +
@@ -160,7 +162,7 @@ func createCmd(c *cli.Context) error {
}
// Deal with the image after all the args have been checked
- createImage := runtime.NewImage(createConfig.image)
+ createImage := runtime.NewImage(createConfig.Image)
createImage.LocalName, _ = createImage.GetLocalImageName()
if createImage.LocalName == "" {
// The image wasnt found by the user input'd name or its fqname
@@ -203,13 +205,21 @@ func createCmd(c *cli.Context) error {
}
// Gather up the options for NewContainer which consist of With... funcs
options = append(options, libpod.WithRootFSFromImage(imageID, imageName, false))
- options = append(options, libpod.WithSELinuxLabels(createConfig.processLabel, createConfig.mountLabel))
- options = append(options, libpod.WithShmDir(createConfig.shmDir))
+ options = append(options, libpod.WithSELinuxLabels(createConfig.ProcessLabel, createConfig.MountLabel))
+ options = append(options, libpod.WithShmDir(createConfig.ShmDir))
ctr, err := runtime.NewContainer(runtimeSpec, options...)
if err != nil {
return err
}
+ createConfigJSON, err := json.Marshal(createConfig)
+ if err != nil {
+ return err
+ }
+ if err := ctr.AddArtifact("create-config", createConfigJSON); err != nil {
+ return err
+ }
+
logrus.Debug("new container created ", ctr.ID())
if c.String("cidfile") != "" {
@@ -229,29 +239,29 @@ func parseSecurityOpt(config *createConfig, securityOpts []string) error {
err error
)
- if config.pidMode.IsHost() {
+ if config.PidMode.IsHost() {
labelOpts = append(labelOpts, label.DisableSecOpt()...)
- } else if config.pidMode.IsContainer() {
- ctr, err := config.runtime.LookupContainer(config.pidMode.Container())
+ } else if config.PidMode.IsContainer() {
+ ctr, err := config.Runtime.LookupContainer(config.PidMode.Container())
if err != nil {
- return errors.Wrapf(err, "container %q not found", config.pidMode.Container())
+ return errors.Wrapf(err, "container %q not found", config.PidMode.Container())
}
labelOpts = append(labelOpts, label.DupSecOpt(ctr.ProcessLabel())...)
}
- if config.ipcMode.IsHost() {
+ if config.IpcMode.IsHost() {
labelOpts = append(labelOpts, label.DisableSecOpt()...)
- } else if config.ipcMode.IsContainer() {
- ctr, err := config.runtime.LookupContainer(config.ipcMode.Container())
+ } else if config.IpcMode.IsContainer() {
+ ctr, err := config.Runtime.LookupContainer(config.IpcMode.Container())
if err != nil {
- return errors.Wrapf(err, "container %q not found", config.ipcMode.Container())
+ return errors.Wrapf(err, "container %q not found", config.IpcMode.Container())
}
labelOpts = append(labelOpts, label.DupSecOpt(ctr.ProcessLabel())...)
}
for _, opt := range securityOpts {
if opt == "no-new-privileges" {
- config.noNewPrivileges = true
+ config.NoNewPrivileges = true
} else {
con := strings.SplitN(opt, "=", 2)
if len(con) != 2 {
@@ -262,25 +272,25 @@ func parseSecurityOpt(config *createConfig, securityOpts []string) error {
case "label":
labelOpts = append(labelOpts, con[1])
case "apparmor":
- config.apparmorProfile = con[1]
+ config.ApparmorProfile = con[1]
case "seccomp":
- config.seccompProfilePath = con[1]
+ config.SeccompProfilePath = con[1]
default:
return fmt.Errorf("Invalid --security-opt 2: %q", opt)
}
}
}
- if config.seccompProfilePath == "" {
+ if config.SeccompProfilePath == "" {
if _, err := os.Stat(seccompDefaultPath); err != nil {
if !os.IsNotExist(err) {
return errors.Wrapf(err, "can't check if %q exists", seccompDefaultPath)
}
} else {
- config.seccompProfilePath = seccompDefaultPath
+ config.SeccompProfilePath = seccompDefaultPath
}
}
- config.processLabel, config.mountLabel, err = label.InitLabels(labelOpts)
+ config.ProcessLabel, config.MountLabel, err = label.InitLabels(labelOpts)
return err
}
@@ -403,88 +413,89 @@ func parseCreateOpts(c *cli.Context, runtime *libpod.Runtime) (*createConfig, er
}
config := &createConfig{
- runtime: runtime,
- capAdd: c.StringSlice("cap-add"),
- capDrop: c.StringSlice("cap-drop"),
- cgroupParent: c.String("cgroup-parent"),
- command: command,
- detach: c.Bool("detach"),
- dnsOpt: c.StringSlice("dns-opt"),
- dnsSearch: c.StringSlice("dns-search"),
- dnsServers: c.StringSlice("dns"),
- entrypoint: c.String("entrypoint"),
- env: env,
- expose: c.StringSlice("expose"),
- groupAdd: groupAdd,
- hostname: c.String("hostname"),
- image: image,
- interactive: c.Bool("interactive"),
- ip6Address: c.String("ipv6"),
- ipAddress: c.String("ip"),
- labels: labels,
- linkLocalIP: c.StringSlice("link-local-ip"),
- logDriver: c.String("log-driver"),
- logDriverOpt: c.StringSlice("log-opt"),
- macAddress: c.String("mac-address"),
- name: c.String("name"),
- network: c.String("network"),
- networkAlias: c.StringSlice("network-alias"),
- ipcMode: ipcMode,
- netMode: container.NetworkMode(c.String("network")),
- utsMode: utsMode,
- pidMode: pidMode,
- pod: c.String("pod"),
- privileged: c.Bool("privileged"),
- publish: c.StringSlice("publish"),
- publishAll: c.Bool("publish-all"),
- readOnlyRootfs: c.Bool("read-only"),
- resources: createResourceConfig{
- blkioWeight: blkioWeight,
- blkioWeightDevice: c.StringSlice("blkio-weight-device"),
- cpuShares: c.Uint64("cpu-shares"),
- cpuPeriod: c.Uint64("cpu-period"),
- cpusetCpus: c.String("cpu-period"),
- cpusetMems: c.String("cpuset-mems"),
- cpuQuota: c.Int64("cpu-quota"),
- cpuRtPeriod: c.Uint64("cpu-rt-period"),
- cpuRtRuntime: c.Int64("cpu-rt-runtime"),
- cpus: c.String("cpus"),
- deviceReadBps: c.StringSlice("device-read-bps"),
- deviceReadIOps: c.StringSlice("device-read-iops"),
- deviceWriteBps: c.StringSlice("device-write-bps"),
- deviceWriteIOps: c.StringSlice("device-write-iops"),
- disableOomKiller: c.Bool("oom-kill-disable"),
- shmSize: c.String("shm-size"),
- memory: memoryLimit,
- memoryReservation: memoryReservation,
- memorySwap: memorySwap,
- memorySwappiness: c.Int("memory-swappiness"),
- kernelMemory: memoryKernel,
- oomScoreAdj: c.Int("oom-score-adj"),
-
- pidsLimit: c.Int64("pids-limit"),
- ulimit: c.StringSlice("ulimit"),
+ Runtime: runtime,
+ CapAdd: c.StringSlice("cap-add"),
+ CapDrop: c.StringSlice("cap-drop"),
+ CgroupParent: c.String("cgroup-parent"),
+ Command: command,
+ Detach: c.Bool("detach"),
+ DnsOpt: c.StringSlice("dns-opt"),
+ DnsSearch: c.StringSlice("dns-search"),
+ DnsServers: c.StringSlice("dns"),
+ Entrypoint: c.String("entrypoint"),
+ Env: env,
+ Expose: c.StringSlice("expose"),
+ GroupAdd: groupAdd,
+ Hostname: c.String("hostname"),
+ Image: image,
+ Interactive: c.Bool("interactive"),
+ Ip6Address: c.String("ipv6"),
+ IpAddress: c.String("ip"),
+ Labels: labels,
+ LinkLocalIP: c.StringSlice("link-local-ip"),
+ LogDriver: c.String("log-driver"),
+ LogDriverOpt: c.StringSlice("log-opt"),
+ MacAddress: c.String("mac-address"),
+ Name: c.String("name"),
+ Network: c.String("network"),
+ NetworkAlias: c.StringSlice("network-alias"),
+ IpcMode: ipcMode,
+ NetMode: container.NetworkMode(c.String("network")),
+ UtsMode: utsMode,
+ PidMode: pidMode,
+ Pod: c.String("pod"),
+ Privileged: c.Bool("privileged"),
+ Publish: c.StringSlice("publish"),
+ PublishAll: c.Bool("publish-all"),
+ ReadOnlyRootfs: c.Bool("read-only"),
+ Resources: createResourceConfig{
+ BlkioWeight: blkioWeight,
+ BlkioWeightDevice: c.StringSlice("blkio-weight-device"),
+ CpuShares: c.Uint64("cpu-shares"),
+ CpuPeriod: c.Uint64("cpu-period"),
+ CpusetCpus: c.String("cpu-period"),
+ CpusetMems: c.String("cpuset-mems"),
+ CpuQuota: c.Int64("cpu-quota"),
+ CpuRtPeriod: c.Uint64("cpu-rt-period"),
+ CpuRtRuntime: c.Int64("cpu-rt-runtime"),
+ Cpus: c.String("cpus"),
+ DeviceReadBps: c.StringSlice("device-read-bps"),
+ DeviceReadIOps: c.StringSlice("device-read-iops"),
+ DeviceWriteBps: c.StringSlice("device-write-bps"),
+ DeviceWriteIOps: c.StringSlice("device-write-iops"),
+ DisableOomKiller: c.Bool("oom-kill-disable"),
+ ShmSize: c.String("shm-size"),
+ Memory: memoryLimit,
+ MemoryReservation: memoryReservation,
+ MemorySwap: memorySwap,
+ MemorySwappiness: c.Int("memory-swappiness"),
+ KernelMemory: memoryKernel,
+ OomScoreAdj: c.Int("oom-score-adj"),
+
+ PidsLimit: c.Int64("pids-limit"),
+ Ulimit: c.StringSlice("ulimit"),
},
- rm: c.Bool("rm"),
- shmDir: shmDir,
- sigProxy: c.Bool("sig-proxy"),
- stopSignal: c.String("stop-signal"),
- stopTimeout: c.Int64("stop-timeout"),
- storageOpts: c.StringSlice("storage-opt"),
- sysctl: sysctl,
- tmpfs: c.StringSlice("tmpfs"),
- tty: tty,
- user: uid,
- group: gid,
- volumes: c.StringSlice("volume"),
- workDir: c.String("workdir"),
- }
-
- if !config.privileged {
+ Rm: c.Bool("rm"),
+ ShmDir: shmDir,
+ SigProxy: c.Bool("sig-proxy"),
+ StopSignal: c.String("stop-signal"),
+ StopTimeout: c.Int64("stop-timeout"),
+ StorageOpts: c.StringSlice("storage-opt"),
+ Sysctl: sysctl,
+ Tmpfs: c.StringSlice("tmpfs"),
+ Tty: tty,
+ User: uid,
+ Group: gid,
+ Volumes: c.StringSlice("volume"),
+ WorkDir: c.String("workdir"),
+ }
+
+ if !config.Privileged {
if err := parseSecurityOpt(config, c.StringSlice("security-opt")); err != nil {
return nil, err
}
}
+ config.SecurityOpts = c.StringSlice("security-opt")
warnings, err := verifyContainerResources(config, false)
if err != nil {
return nil, err
diff --git a/cmd/kpod/create_cli.go b/cmd/kpod/create_cli.go
index 9686b89a7..a162cb319 100644
--- a/cmd/kpod/create_cli.go
+++ b/cmd/kpod/create_cli.go
@@ -111,131 +111,131 @@ func verifyContainerResources(config *createConfig, update bool) ([]string, erro
sysInfo := sysinfo.New(true)
// memory subsystem checks and adjustments
- if config.resources.memory != 0 && config.resources.memory < linuxMinMemory {
+ if config.Resources.Memory != 0 && config.Resources.Memory < linuxMinMemory {
return warnings, fmt.Errorf("minimum memory limit allowed is 4MB")
}
- if config.resources.memory > 0 && !sysInfo.MemoryLimit {
+ if config.Resources.Memory > 0 && !sysInfo.MemoryLimit {
warnings = addWarning(warnings, "Your kernel does not support memory limit capabilities or the cgroup is not mounted. Limitation discarded.")
- config.resources.memory = 0
- config.resources.memorySwap = -1
+ config.Resources.Memory = 0
+ config.Resources.MemorySwap = -1
}
- if config.resources.memory > 0 && config.resources.memorySwap != -1 && !sysInfo.SwapLimit {
+ if config.Resources.Memory > 0 && config.Resources.MemorySwap != -1 && !sysInfo.SwapLimit {
warnings = addWarning(warnings, "Your kernel does not support swap limit capabilities,or the cgroup is not mounted. Memory limited without swap.")
- config.resources.memorySwap = -1
+ config.Resources.MemorySwap = -1
}
- if config.resources.memory > 0 && config.resources.memorySwap > 0 && config.resources.memorySwap < config.resources.memory {
+ if config.Resources.Memory > 0 && config.Resources.MemorySwap > 0 && config.Resources.MemorySwap < config.Resources.Memory {
return warnings, fmt.Errorf("minimum memoryswap limit should be larger than memory limit, see usage")
}
- if config.resources.memory == 0 && config.resources.memorySwap > 0 && !update {
- return warnings, fmt.Errorf("you should always set the Memory limit when using Memoryswap limit, see usage")
+ if config.Resources.Memory == 0 && config.Resources.MemorySwap > 0 && !update {
+ return warnings, fmt.Errorf("you should always set the memory limit when using memoryswap limit, see usage")
}
- if config.resources.memorySwappiness != -1 {
+ if config.Resources.MemorySwappiness != -1 {
if !sysInfo.MemorySwappiness {
msg := "Your kernel does not support memory swappiness capabilities, or the cgroup is not mounted. Memory swappiness discarded."
warnings = addWarning(warnings, msg)
- config.resources.memorySwappiness = -1
+ config.Resources.MemorySwappiness = -1
} else {
- swappiness := config.resources.memorySwappiness
+ swappiness := config.Resources.MemorySwappiness
if swappiness < -1 || swappiness > 100 {
return warnings, fmt.Errorf("invalid value: %v, valid memory swappiness range is 0-100", swappiness)
}
}
}
- if config.resources.memoryReservation > 0 && !sysInfo.MemoryReservation {
+ if config.Resources.MemoryReservation > 0 && !sysInfo.MemoryReservation {
warnings = addWarning(warnings, "Your kernel does not support memory soft limit capabilities or the cgroup is not mounted. Limitation discarded.")
- config.resources.memoryReservation = 0
+ config.Resources.MemoryReservation = 0
}
- if config.resources.memoryReservation > 0 && config.resources.memoryReservation < linuxMinMemory {
+ if config.Resources.MemoryReservation > 0 && config.Resources.MemoryReservation < linuxMinMemory {
return warnings, fmt.Errorf("minimum memory reservation allowed is 4MB")
}
- if config.resources.memory > 0 && config.resources.memoryReservation > 0 && config.resources.memory < config.resources.memoryReservation {
+ if config.Resources.Memory > 0 && config.Resources.MemoryReservation > 0 && config.Resources.Memory < config.Resources.MemoryReservation {
return warnings, fmt.Errorf("minimum memory limit can not be less than memory reservation limit, see usage")
}
- if config.resources.kernelMemory > 0 && !sysInfo.KernelMemory {
+ if config.Resources.KernelMemory > 0 && !sysInfo.KernelMemory {
warnings = addWarning(warnings, "Your kernel does not support kernel memory limit capabilities or the cgroup is not mounted. Limitation discarded.")
- config.resources.kernelMemory = 0
+ config.Resources.KernelMemory = 0
}
- if config.resources.kernelMemory > 0 && config.resources.kernelMemory < linuxMinMemory {
+ if config.Resources.KernelMemory > 0 && config.Resources.KernelMemory < linuxMinMemory {
return warnings, fmt.Errorf("minimum kernel memory limit allowed is 4MB")
}
- if config.resources.disableOomKiller == true && !sysInfo.OomKillDisable {
+ if config.Resources.DisableOomKiller == true && !sysInfo.OomKillDisable {
// only produce warnings if the setting wasn't to *disable* the OOM Kill; no point
// warning the caller if they already wanted the feature to be off
warnings = addWarning(warnings, "Your kernel does not support OomKillDisable. OomKillDisable discarded.")
- config.resources.disableOomKiller = false
+ config.Resources.DisableOomKiller = false
}
- if config.resources.pidsLimit != 0 && !sysInfo.PidsLimit {
+ if config.Resources.PidsLimit != 0 && !sysInfo.PidsLimit {
warnings = addWarning(warnings, "Your kernel does not support pids limit capabilities or the cgroup is not mounted. PIDs limit discarded.")
- config.resources.pidsLimit = 0
+ config.Resources.PidsLimit = 0
}
- if config.resources.cpuShares > 0 && !sysInfo.CPUShares {
+ if config.Resources.CpuShares > 0 && !sysInfo.CPUShares {
warnings = addWarning(warnings, "Your kernel does not support CPU shares or the cgroup is not mounted. Shares discarded.")
- config.resources.cpuShares = 0
+ config.Resources.CpuShares = 0
}
- if config.resources.cpuPeriod > 0 && !sysInfo.CPUCfsPeriod {
+ if config.Resources.CpuPeriod > 0 && !sysInfo.CPUCfsPeriod {
warnings = addWarning(warnings, "Your kernel does not support CPU cfs period or the cgroup is not mounted. Period discarded.")
- config.resources.cpuPeriod = 0
+ config.Resources.CpuPeriod = 0
}
- if config.resources.cpuPeriod != 0 && (config.resources.cpuPeriod < 1000 || config.resources.cpuPeriod > 1000000) {
+ if config.Resources.CpuPeriod != 0 && (config.Resources.CpuPeriod < 1000 || config.Resources.CpuPeriod > 1000000) {
return warnings, fmt.Errorf("CPU cfs period can not be less than 1ms (i.e. 1000) or larger than 1s (i.e. 1000000)")
}
- if config.resources.cpuQuota > 0 && !sysInfo.CPUCfsQuota {
+ if config.Resources.CpuQuota > 0 && !sysInfo.CPUCfsQuota {
warnings = addWarning(warnings, "Your kernel does not support CPU cfs quota or the cgroup is not mounted. Quota discarded.")
- config.resources.cpuQuota = 0
+ config.Resources.CpuQuota = 0
}
- if config.resources.cpuQuota > 0 && config.resources.cpuQuota < 1000 {
+ if config.Resources.CpuQuota > 0 && config.Resources.CpuQuota < 1000 {
return warnings, fmt.Errorf("CPU cfs quota can not be less than 1ms (i.e. 1000)")
}
// cpuset subsystem checks and adjustments
- if (config.resources.cpusetCpus != "" || config.resources.cpusetMems != "") && !sysInfo.Cpuset {
+ if (config.Resources.CpusetCpus != "" || config.Resources.CpusetMems != "") && !sysInfo.Cpuset {
warnings = addWarning(warnings, "Your kernel does not support cpuset or the cgroup is not mounted. Cpuset discarded.")
- config.resources.cpusetCpus = ""
- config.resources.cpusetMems = ""
+ config.Resources.CpusetCpus = ""
+ config.Resources.CpusetMems = ""
}
- cpusAvailable, err := sysInfo.IsCpusetCpusAvailable(config.resources.cpusetCpus)
+ cpusAvailable, err := sysInfo.IsCpusetCpusAvailable(config.Resources.CpusetCpus)
if err != nil {
- return warnings, fmt.Errorf("invalid value %s for cpuset cpus", config.resources.cpusetCpus)
+ return warnings, fmt.Errorf("invalid value %s for cpuset cpus", config.Resources.CpusetCpus)
}
if !cpusAvailable {
- return warnings, fmt.Errorf("requested CPUs are not available - requested %s, available: %s", config.resources.cpusetCpus, sysInfo.Cpus)
+ return warnings, fmt.Errorf("requested CPUs are not available - requested %s, available: %s", config.Resources.CpusetCpus, sysInfo.Cpus)
}
- memsAvailable, err := sysInfo.IsCpusetMemsAvailable(config.resources.cpusetMems)
+ memsAvailable, err := sysInfo.IsCpusetMemsAvailable(config.Resources.CpusetMems)
if err != nil {
- return warnings, fmt.Errorf("invalid value %s for cpuset mems", config.resources.cpusetMems)
+ return warnings, fmt.Errorf("invalid value %s for cpuset mems", config.Resources.CpusetMems)
}
if !memsAvailable {
- return warnings, fmt.Errorf("requested memory nodes are not available - requested %s, available: %s", config.resources.cpusetMems, sysInfo.Mems)
+ return warnings, fmt.Errorf("requested memory nodes are not available - requested %s, available: %s", config.Resources.CpusetMems, sysInfo.Mems)
}
// blkio subsystem checks and adjustments
- if config.resources.blkioWeight > 0 && !sysInfo.BlkioWeight {
+ if config.Resources.BlkioWeight > 0 && !sysInfo.BlkioWeight {
warnings = addWarning(warnings, "Your kernel does not support Block I/O weight or the cgroup is not mounted. Weight discarded.")
- config.resources.blkioWeight = 0
+ config.Resources.BlkioWeight = 0
}
- if config.resources.blkioWeight > 0 && (config.resources.blkioWeight < 10 || config.resources.blkioWeight > 1000) {
+ if config.Resources.BlkioWeight > 0 && (config.Resources.BlkioWeight < 10 || config.Resources.BlkioWeight > 1000) {
return warnings, fmt.Errorf("range of blkio weight is from 10 to 1000")
}
- if len(config.resources.blkioWeightDevice) > 0 && !sysInfo.BlkioWeightDevice {
+ if len(config.Resources.BlkioWeightDevice) > 0 && !sysInfo.BlkioWeightDevice {
warnings = addWarning(warnings, "Your kernel does not support Block I/O weight_device or the cgroup is not mounted. Weight-device discarded.")
- config.resources.blkioWeightDevice = []string{}
+ config.Resources.BlkioWeightDevice = []string{}
}
- if len(config.resources.deviceReadBps) > 0 && !sysInfo.BlkioReadBpsDevice {
+ if len(config.Resources.DeviceReadBps) > 0 && !sysInfo.BlkioReadBpsDevice {
warnings = addWarning(warnings, "Your kernel does not support BPS Block I/O read limit or the cgroup is not mounted. Block I/O BPS read limit discarded")
- config.resources.deviceReadBps = []string{}
+ config.Resources.DeviceReadBps = []string{}
}
- if len(config.resources.deviceWriteBps) > 0 && !sysInfo.BlkioWriteBpsDevice {
+ if len(config.Resources.DeviceWriteBps) > 0 && !sysInfo.BlkioWriteBpsDevice {
warnings = addWarning(warnings, "Your kernel does not support BPS Block I/O write limit or the cgroup is not mounted. Block I/O BPS write limit discarded.")
- config.resources.deviceWriteBps = []string{}
+ config.Resources.DeviceWriteBps = []string{}
}
- if len(config.resources.deviceReadIOps) > 0 && !sysInfo.BlkioReadIOpsDevice {
+ if len(config.Resources.DeviceReadIOps) > 0 && !sysInfo.BlkioReadIOpsDevice {
warnings = addWarning(warnings, "Your kernel does not support IOPS Block read limit or the cgroup is not mounted. Block I/O IOPS read limit discarded.")
- config.resources.deviceReadIOps = []string{}
+ config.Resources.DeviceReadIOps = []string{}
}
- if len(config.resources.deviceWriteIOps) > 0 && !sysInfo.BlkioWriteIOpsDevice {
+ if len(config.Resources.DeviceWriteIOps) > 0 && !sysInfo.BlkioWriteIOpsDevice {
warnings = addWarning(warnings, "Your kernel does not support IOPS Block I/O write limit or the cgroup is not mounted. Block I/O IOPS write limit discarded.")
- config.resources.deviceWriteIOps = []string{}
+ config.Resources.DeviceWriteIOps = []string{}
}
return warnings, nil
diff --git a/cmd/kpod/images.go b/cmd/kpod/images.go
index 7b020c984..1cf69c96d 100644
--- a/cmd/kpod/images.go
+++ b/cmd/kpod/images.go
@@ -6,7 +6,6 @@ import (
"strings"
"time"
- "github.com/containers/image/types"
"github.com/containers/storage"
"github.com/docker/go-units"
digest "github.com/opencontainers/go-digest"
@@ -208,18 +207,18 @@ func getImagesTemplateOutput(runtime *libpod.Runtime, images []*storage.Image, o
}
}
- info, imageDigest, size, _ := runtime.InfoAndDigestAndSize(*img)
- if info != nil {
- createdTime = info.Created
+ imgData, _ := runtime.GetImageInspectInfo(*img)
+ if imgData != nil {
+ createdTime = *imgData.Created
}
params := imagesTemplateParams{
Repository: repository,
Tag: tag,
ID: imageID,
- Digest: imageDigest,
+ Digest: imgData.Digest,
Created: units.HumanDuration(time.Since((createdTime))) + " ago",
- Size: units.HumanSizeWithPrecision(float64(size), 3),
+ Size: units.HumanSizeWithPrecision(float64(imgData.Size), 3),
}
imagesOutput = append(imagesOutput, params)
}
@@ -231,17 +230,17 @@ func getImagesJSONOutput(runtime *libpod.Runtime, images []*storage.Image) (imag
for _, img := range images {
createdTime := img.Created
- info, imageDigest, size, _ := runtime.InfoAndDigestAndSize(*img)
- if info != nil {
- createdTime = info.Created
+ imgData, _ := runtime.GetImageInspectInfo(*img)
+ if imgData != nil {
+ createdTime = *imgData.Created
}
params := imagesJSONParams{
ID: img.ID,
Name: img.Names,
- Digest: imageDigest,
+ Digest: imgData.Digest,
Created: createdTime,
- Size: size,
+ Size: imgData.Size,
}
imagesOutput = append(imagesOutput, params)
}
@@ -274,7 +273,7 @@ func generateImagesOutput(runtime *libpod.Runtime, images []*storage.Image, opts
func generateImagesFilter(params *libpod.ImageFilterParams, filterType string) libpod.ImageFilter {
switch filterType {
case "label":
- return func(image *storage.Image, info *types.ImageInspectInfo) bool {
+ return func(image *storage.Image, info *libpod.ImageData) bool {
if params == nil || params.Label == "" {
return true
}
@@ -291,21 +290,21 @@ func generateImagesFilter(params *libpod.ImageFilterParams, filterType string) l
return false
}
case "before-image":
- return func(image *storage.Image, info *types.ImageInspectInfo) bool {
+ return func(image *storage.Image, info *libpod.ImageData) bool {
if params == nil || params.BeforeImage.IsZero() {
return true
}
return info.Created.Before(params.BeforeImage)
}
case "since-image":
- return func(image *storage.Image, info *types.ImageInspectInfo) bool {
+ return func(image *storage.Image, info *libpod.ImageData) bool {
if params == nil || params.SinceImage.IsZero() {
return true
}
return info.Created.After(params.SinceImage)
}
case "dangling":
- return func(image *storage.Image, info *types.ImageInspectInfo) bool {
+ return func(image *storage.Image, info *libpod.ImageData) bool {
if params == nil || params.Dangling == "" {
return true
}
@@ -318,14 +317,14 @@ func generateImagesFilter(params *libpod.ImageFilterParams, filterType string) l
return false
}
case "reference":
- return func(image *storage.Image, info *types.ImageInspectInfo) bool {
+ return func(image *storage.Image, info *libpod.ImageData) bool {
if params == nil || params.ReferencePattern == "" {
return true
}
return libpod.MatchesReference(params.ImageName, params.ReferencePattern)
}
case "image-input":
- return func(image *storage.Image, info *types.ImageInspectInfo) bool {
+ return func(image *storage.Image, info *libpod.ImageData) bool {
if params == nil || params.ImageInput == "" {
return true
}
diff --git a/cmd/kpod/inspect.go b/cmd/kpod/inspect.go
index a70e285ac..e2f9ec97e 100644
--- a/cmd/kpod/inspect.go
+++ b/cmd/kpod/inspect.go
@@ -1,10 +1,12 @@
package main
import (
+ "encoding/json"
+
+ specs "github.com/opencontainers/runtime-spec/specs-go"
"github.com/pkg/errors"
"github.com/projectatomic/libpod/cmd/kpod/formats"
- "github.com/projectatomic/libpod/libkpod"
- "github.com/projectatomic/libpod/libpod/images"
+ "github.com/projectatomic/libpod/libpod"
"github.com/urfave/cli"
)
@@ -53,56 +55,63 @@ func inspectCmd(c *cli.Context) error {
return err
}
- itemType := c.String("type")
- size := c.Bool("size")
+ runtime, err := getRuntime(c)
+ if err != nil {
+ return errors.Wrapf(err, "error creating libpod runtime")
+ }
+ defer runtime.Shutdown(false)
- switch itemType {
- case inspectTypeContainer:
- case inspectTypeImage:
- case inspectAll:
- default:
+ if c.String("type") != inspectTypeContainer && c.String("type") != inspectTypeImage && c.String("type") != inspectAll {
return errors.Errorf("the only recognized types are %q, %q, and %q", inspectTypeContainer, inspectTypeImage, inspectAll)
}
name := args[0]
- config, err := getConfig(c)
- if err != nil {
- return errors.Wrapf(err, "Could not get config")
- }
- server, err := libkpod.New(config)
- if err != nil {
- return errors.Wrapf(err, "could not get container server")
- }
- defer server.Shutdown()
- if err = server.Update(); err != nil {
- return errors.Wrapf(err, "could not update list of containers")
- }
-
outputFormat := c.String("format")
var data interface{}
- switch itemType {
+ switch c.String("type") {
case inspectTypeContainer:
- data, err = server.GetContainerData(name, size)
+ ctr, err := runtime.LookupContainer(name)
+ if err != nil {
+ return errors.Wrapf(err, "error looking up container %q", name)
+ }
+ libpodInspectData, err := ctr.Inspect(c.Bool("size"))
+ if err != nil {
+ return errors.Wrapf(err, "error getting libpod container inspect data %q", ctr.ID)
+ }
+ data, err = getCtrInspectInfo(ctr, libpodInspectData)
if err != nil {
- return errors.Wrapf(err, "error parsing container data")
+ return errors.Wrapf(err, "error parsing container data %q", ctr.ID())
}
case inspectTypeImage:
- data, err = images.GetData(server.Store(), name)
+ image, err := runtime.GetImage(name)
if err != nil {
- return errors.Wrapf(err, "error parsing image data")
+ return errors.Wrapf(err, "error getting image %q", name)
+ }
+ data, err = runtime.GetImageInspectInfo(*image)
+ if err != nil {
+ return errors.Wrapf(err, "error parsing image data %q", image.ID)
}
case inspectAll:
- ctrData, err := server.GetContainerData(name, size)
+ ctr, err := runtime.LookupContainer(name)
if err != nil {
- imgData, err := images.GetData(server.Store(), name)
+ image, err := runtime.GetImage(name)
if err != nil {
- return errors.Wrapf(err, "error parsing container or image data")
+ return errors.Wrapf(err, "error getting image %q", name)
+ }
+ data, err = runtime.GetImageInspectInfo(*image)
+ if err != nil {
+ return errors.Wrapf(err, "error parsing image data %q", image.ID)
}
- data = imgData
-
} else {
- data = ctrData
+ libpodInspectData, err := ctr.Inspect(c.Bool("size"))
+ if err != nil {
+ return errors.Wrapf(err, "error getting libpod container inspect data %q", ctr.ID)
+ }
+ data, err = getCtrInspectInfo(ctr, libpodInspectData)
+ if err != nil {
+ return errors.Wrapf(err, "error parsing container data %q", ctr.ID)
+ }
}
}
@@ -118,3 +127,236 @@ func inspectCmd(c *cli.Context) error {
formats.Writer(out).Out()
return nil
}
+
+func getCtrInspectInfo(ctr *libpod.Container, ctrInspectData *libpod.ContainerInspectData) (*ContainerData, error) {
+ config := ctr.Config()
+ spec := config.Spec
+
+ cpus, mems, period, quota, realtimePeriod, realtimeRuntime, shares := getCPUInfo(spec)
+ blkioWeight, blkioWeightDevice, blkioReadBps, blkioWriteBps, blkioReadIOPS, blkioeWriteIOPS := getBLKIOInfo(spec)
+ memKernel, memReservation, memSwap, memSwappiness, memDisableOOMKiller := getMemoryInfo(spec)
+ pidsLimit := getPidsInfo(spec)
+ cgroup := getCgroup(spec)
+
+ artifact, err := ctr.GetArtifact("create-config")
+ if err != nil {
+ return nil, errors.Wrapf(err, "error getting artifact %q", ctr.ID())
+ }
+ var createArtifact createConfig
+ if err := json.Unmarshal(artifact, &createArtifact); err != nil {
+ return nil, err
+ }
+
+ data := &ContainerData{
+ CtrInspectData: ctrInspectData,
+ HostConfig: &HostConfig{
+ ConsoleSize: spec.Process.ConsoleSize,
+ OomScoreAdj: spec.Process.OOMScoreAdj,
+ CPUShares: shares,
+ BlkioWeight: blkioWeight,
+ BlkioWeightDevice: blkioWeightDevice,
+ BlkioDeviceReadBps: blkioReadBps,
+ BlkioDeviceWriteBps: blkioWriteBps,
+ BlkioDeviceReadIOps: blkioReadIOPS,
+ BlkioDeviceWriteIOps: blkioeWriteIOPS,
+ CPUPeriod: period,
+ CPUQuota: quota,
+ CPURealtimePeriod: realtimePeriod,
+ CPURealtimeRuntime: realtimeRuntime,
+ CPUSetCpus: cpus,
+ CPUSetMems: mems,
+ Devices: spec.Linux.Devices,
+ KernelMemory: memKernel,
+ MemoryReservation: memReservation,
+ MemorySwap: memSwap,
+ MemorySwappiness: memSwappiness,
+ OomKillDisable: memDisableOOMKiller,
+ PidsLimit: pidsLimit,
+ Privileged: spec.Process.NoNewPrivileges,
+ ReadonlyRootfs: spec.Root.Readonly,
+ Runtime: ctr.RuntimeName(),
+ NetworkMode: string(createArtifact.NetMode),
+ IpcMode: string(createArtifact.IpcMode),
+ Cgroup: cgroup,
+ UTSMode: string(createArtifact.UtsMode),
+ UsernsMode: createArtifact.NsUser,
+ GroupAdd: spec.Process.User.AdditionalGids,
+ ContainerIDFile: createArtifact.CidFile,
+ AutoRemove: createArtifact.Rm,
+ CapAdd: createArtifact.CapAdd,
+ CapDrop: createArtifact.CapDrop,
+ DNS: createArtifact.DnsServers,
+ DNSOptions: createArtifact.DnsOpt,
+ DNSSearch: createArtifact.DnsSearch,
+ PidMode: string(createArtifact.PidMode),
+ CgroupParent: createArtifact.CgroupParent,
+ ShmSize: createArtifact.Resources.ShmSize,
+ Memory: createArtifact.Resources.Memory,
+ Ulimits: createArtifact.Resources.Ulimit,
+ SecurityOpt: createArtifact.SecurityOpts,
+ },
+ Config: &CtrConfig{
+ Hostname: spec.Hostname,
+ User: spec.Process.User,
+ Env: spec.Process.Env,
+ Image: config.RootfsImageName,
+ WorkingDir: spec.Process.Cwd,
+ Labels: config.Labels,
+ Annotations: spec.Annotations,
+ Tty: spec.Process.Terminal,
+ OpenStdin: config.Stdin,
+ StopSignal: config.StopSignal,
+ Cmd: config.Spec.Process.Args,
+ Entrypoint: createArtifact.Entrypoint,
+ },
+ }
+ return data, nil
+}
+
+func getCPUInfo(spec *specs.Spec) (string, string, *uint64, *int64, *uint64, *int64, *uint64) {
+ if spec.Linux.Resources == nil {
+ return "", "", nil, nil, nil, nil, nil
+ }
+ cpu := spec.Linux.Resources.CPU
+ if cpu == nil {
+ return "", "", nil, nil, nil, nil, nil
+ }
+ return cpu.Cpus, cpu.Mems, cpu.Period, cpu.Quota, cpu.RealtimePeriod, cpu.RealtimeRuntime, cpu.Shares
+}
+
+func getBLKIOInfo(spec *specs.Spec) (*uint16, []specs.LinuxWeightDevice, []specs.LinuxThrottleDevice, []specs.LinuxThrottleDevice, []specs.LinuxThrottleDevice, []specs.LinuxThrottleDevice) {
+ if spec.Linux.Resources == nil {
+ return nil, nil, nil, nil, nil, nil
+ }
+ blkio := spec.Linux.Resources.BlockIO
+ if blkio == nil {
+ return nil, nil, nil, nil, nil, nil
+ }
+ return blkio.Weight, blkio.WeightDevice, blkio.ThrottleReadBpsDevice, blkio.ThrottleWriteBpsDevice, blkio.ThrottleReadIOPSDevice, blkio.ThrottleWriteIOPSDevice
+}
+
+func getMemoryInfo(spec *specs.Spec) (*int64, *int64, *int64, *uint64, *bool) {
+ if spec.Linux.Resources == nil {
+ return nil, nil, nil, nil, nil
+ }
+ memory := spec.Linux.Resources.Memory
+ if memory == nil {
+ return nil, nil, nil, nil, nil
+ }
+ return memory.Kernel, memory.Reservation, memory.Swap, memory.Swappiness, memory.DisableOOMKiller
+}
+
+func getPidsInfo(spec *specs.Spec) *int64 {
+ if spec.Linux.Resources == nil {
+ return nil
+ }
+ pids := spec.Linux.Resources.Pids
+ if pids == nil {
+ return nil
+ }
+ return &pids.Limit
+}
+
+func getCgroup(spec *specs.Spec) string {
+ cgroup := "host"
+ for _, ns := range spec.Linux.Namespaces {
+ if ns.Type == specs.CgroupNamespace && ns.Path != "" {
+ cgroup = "container"
+ }
+ }
+ return cgroup
+}
+
+// ContainerData holds the kpod inspect data for a container
+type ContainerData struct {
+ CtrInspectData *libpod.ContainerInspectData `json:"CtrInspectData"`
+ HostConfig *HostConfig `json:"HostConfig"`
+ Config *CtrConfig `json:"Config"`
+}
+
+// LogConfig holds the log information for a container
+type LogConfig struct {
+ Type string `json:"Type"` // TODO
+ Config map[string]string `json:"Config"` //idk type, TODO
+}
+
+// HostConfig represents the host configuration for the container
+type HostConfig struct {
+ ContainerIDFile string `json:"ContainerIDFile"`
+ LogConfig *LogConfig `json:"LogConfig"` //TODO
+ NetworkMode string `json:"NetworkMode"`
+ PortBindings map[string]struct{} `json:"PortBindings"` //TODO
+ AutoRemove bool `json:"AutoRemove"`
+ CapAdd []string `json:"CapAdd"`
+ CapDrop []string `json:"CapDrop"`
+ DNS []string `json:"DNS"`
+ DNSOptions []string `json:"DNSOptions"`
+ DNSSearch []string `json:"DNSSearch"`
+ ExtraHosts []string `json:"ExtraHosts"`
+ GroupAdd []uint32 `json:"GroupAdd"`
+ IpcMode string `json:"IpcMode"`
+ Cgroup string `json:"Cgroup"`
+ OomScoreAdj *int `json:"OomScoreAdj"`
+ PidMode string `json:"PidMode"`
+ Privileged bool `json:"Privileged"`
+ PublishAllPorts bool `json:"PublishAllPorts"` //TODO
+ ReadonlyRootfs bool `json:"ReadonlyRootfs"`
+ SecurityOpt []string `json:"SecurityOpt"`
+ UTSMode string `json:"UTSMode"`
+ UsernsMode string `json:"UsernsMode"`
+ ShmSize string `json:"ShmSize"`
+ Runtime string `json:"Runtime"`
+ ConsoleSize *specs.Box `json:"ConsoleSize"`
+ Isolation string `json:"Isolation"` //TODO
+ CPUShares *uint64 `json:"CPUSShares"`
+ Memory int64 `json:"Memory"`
+ NanoCpus int `json:"NanoCpus"` //check type, TODO
+ CgroupParent string `json:"CgroupParent"`
+ BlkioWeight *uint16 `json:"BlkioWeight"`
+ BlkioWeightDevice []specs.LinuxWeightDevice `json:"BlkioWeightDevice"`
+ BlkioDeviceReadBps []specs.LinuxThrottleDevice `json:"BlkioDeviceReadBps"`
+ BlkioDeviceWriteBps []specs.LinuxThrottleDevice `json:"BlkioDeviceWriteBps"`
+ BlkioDeviceReadIOps []specs.LinuxThrottleDevice `json:"BlkioDeviceReadIOps"`
+ BlkioDeviceWriteIOps []specs.LinuxThrottleDevice `json:"BlkioDeviceWriteIOps"`
+ CPUPeriod *uint64 `json:"CPUPeriod"`
+ CPUQuota *int64 `json:"CPUQuota"`
+ CPURealtimePeriod *uint64 `json:"CPURealtimePeriod"`
+ CPURealtimeRuntime *int64 `json:"CPURealtimeRuntime"`
+ CPUSetCpus string `json:"CPUSetCpus"`
+ CPUSetMems string `json:"CPUSetMems"`
+ Devices []specs.LinuxDevice `json:"Devices"`
+ DiskQuota int `json:"DiskQuota"` //check type, TODO
+ KernelMemory *int64 `json:"KernelMemory"`
+ MemoryReservation *int64 `json:"MemoryReservation"`
+ MemorySwap *int64 `json:"MemorySwap"`
+ MemorySwappiness *uint64 `json:"MemorySwappiness"`
+ OomKillDisable *bool `json:"OomKillDisable"`
+ PidsLimit *int64 `json:"PidsLimit"`
+ Ulimits []string `json:"Ulimits"`
+ CPUCount int `json:"CPUCount"` //check type, TODO
+ CPUPercent int `json:"CPUPercent"` //check type, TODO
+ IOMaximumIOps int `json:"IOMaximumIOps"` //check type, TODO
+ IOMaximumBandwidth int `json:"IOMaximumBandwidth"` //check type, TODO
+}
+
+// CtrConfig holds information about the container configuration
+type CtrConfig struct {
+ Hostname string `json:"Hostname"`
+ DomainName string `json:"Domainname"` //TODO
+ User specs.User `json:"User"`
+ AttachStdin bool `json:"AttachStdin"` //TODO
+ AttachStdout bool `json:"AttachStdout"` //TODO
+ AttachStderr bool `json:"AttachStderr"` //TODO
+ Tty bool `json:"Tty"`
+ OpenStdin bool `json:"OpenStdin"`
+ StdinOnce bool `json:"StdinOnce"` //TODO
+ Env []string `json:"Env"`
+ Cmd []string `json:"Cmd"`
+ Image string `json:"Image"`
+ Volumes map[string]struct{} `json:"Volumes"`
+ WorkingDir string `json:"WorkingDir"`
+ Entrypoint string `json:"Entrypoint"`
+ Labels map[string]string `json:"Labels"`
+ Annotations map[string]string `json:"Annotations"`
+ StopSignal uint `json:"StopSignal"`
+}
diff --git a/cmd/kpod/run.go b/cmd/kpod/run.go
index 7e078f66a..6142983ad 100644
--- a/cmd/kpod/run.go
+++ b/cmd/kpod/run.go
@@ -39,7 +39,7 @@ func runCmd(c *cli.Context) error {
return err
}
- createImage := runtime.NewImage(createConfig.image)
+ createImage := runtime.NewImage(createConfig.Image)
createImage.LocalName, _ = createImage.GetLocalImageName()
if createImage.LocalName == "" {
// The image wasnt found by the user input'd name or its fqname
@@ -89,8 +89,8 @@ func runCmd(c *cli.Context) error {
// Gather up the options for NewContainer which consist of With... funcs
options = append(options, libpod.WithRootFSFromImage(imageID, imageName, false))
- options = append(options, libpod.WithSELinuxLabels(createConfig.processLabel, createConfig.mountLabel))
- options = append(options, libpod.WithShmDir(createConfig.shmDir))
+ options = append(options, libpod.WithSELinuxLabels(createConfig.ProcessLabel, createConfig.MountLabel))
+ options = append(options, libpod.WithShmDir(createConfig.ShmDir))
ctr, err := runtime.NewContainer(runtimeSpec, options...)
if err != nil {
return err
@@ -114,7 +114,7 @@ func runCmd(c *cli.Context) error {
// to finish before exiting main
var wg sync.WaitGroup
- if !createConfig.detach {
+ if !createConfig.Detach {
// We increment the wg counter because we need to do the attach
wg.Add(1)
// Attach to the running container
@@ -133,13 +133,13 @@ func runCmd(c *cli.Context) error {
if err := ctr.Start(); err != nil {
return errors.Wrapf(err, "unable to start container %q", ctr.ID())
}
- if createConfig.detach {
+ if createConfig.Detach {
fmt.Printf("%s\n", ctr.ID())
return nil
}
wg.Wait()
- if createConfig.rm {
+ if createConfig.Rm {
return runtime.RemoveContainer(ctr, true)
}
return ctr.CleanupStorage()
diff --git a/cmd/kpod/spec.go b/cmd/kpod/spec.go
index b200ed77a..4e00f04ff 100644
--- a/cmd/kpod/spec.go
+++ b/cmd/kpod/spec.go
@@ -20,7 +20,7 @@ import (
)
func blockAccessToKernelFilesystems(config *createConfig, g *generate.Generator) {
- if !config.privileged {
+ if !config.Privileged {
for _, mp := range []string{
"/proc/kcore",
"/proc/latency_stats",
@@ -47,12 +47,12 @@ func blockAccessToKernelFilesystems(config *createConfig, g *generate.Generator)
}
func addPidNS(config *createConfig, g *generate.Generator) error {
- pidMode := config.pidMode
+ pidMode := config.PidMode
if pidMode.IsHost() {
return g.RemoveLinuxNamespace(libpod.PIDNamespace)
}
if pidMode.IsContainer() {
- ctr, err := config.runtime.LookupContainer(pidMode.Container())
+ ctr, err := config.Runtime.LookupContainer(pidMode.Container())
if err != nil {
return errors.Wrapf(err, "container %q not found", pidMode.Container())
}
@@ -69,7 +69,7 @@ func addPidNS(config *createConfig, g *generate.Generator) error {
}
func addNetNS(config *createConfig, g *generate.Generator) error {
- netMode := config.netMode
+ netMode := config.NetMode
if netMode.IsHost() {
return g.RemoveLinuxNamespace(libpod.NetNamespace)
}
@@ -80,7 +80,7 @@ func addNetNS(config *createConfig, g *generate.Generator) error {
return libpod.ErrNotImplemented
}
if netMode.IsContainer() {
- ctr, err := config.runtime.LookupContainer(netMode.ConnectedContainer())
+ ctr, err := config.Runtime.LookupContainer(netMode.ConnectedContainer())
if err != nil {
return errors.Wrapf(err, "container %q not found", netMode.ConnectedContainer())
}
@@ -97,7 +97,7 @@ func addNetNS(config *createConfig, g *generate.Generator) error {
}
func addUTSNS(config *createConfig, g *generate.Generator) error {
- utsMode := config.utsMode
+ utsMode := config.UtsMode
if utsMode.IsHost() {
return g.RemoveLinuxNamespace(libpod.UTSNamespace)
}
@@ -105,12 +105,12 @@ func addUTSNS(config *createConfig, g *generate.Generator) error {
}
func addIpcNS(config *createConfig, g *generate.Generator) error {
- ipcMode := config.ipcMode
+ ipcMode := config.IpcMode
if ipcMode.IsHost() {
return g.RemoveLinuxNamespace(libpod.IPCNamespace)
}
if ipcMode.IsContainer() {
- ctr, err := config.runtime.LookupContainer(ipcMode.Container())
+ ctr, err := config.Runtime.LookupContainer(ipcMode.Container())
if err != nil {
return errors.Wrapf(err, "container %q not found", ipcMode.Container())
}
@@ -133,7 +133,7 @@ func addRlimits(config *createConfig, g *generate.Generator) error {
err error
)
- for _, u := range config.resources.ulimit {
+ for _, u := range config.Resources.Ulimit {
if ul, err = units.ParseUlimit(u); err != nil {
return errors.Wrapf(err, "ulimit option %q requires name=SOFT:HARD, failed to be parsed", u)
}
@@ -146,10 +146,10 @@ func addRlimits(config *createConfig, g *generate.Generator) error {
func setupCapabilities(config *createConfig, configSpec *spec.Spec) error {
var err error
var caplist []string
- if config.privileged {
+ if config.Privileged {
caplist = caps.GetAllCapabilities()
} else {
- caplist, err = caps.TweakCapabilities(configSpec.Process.Capabilities.Bounding, config.capAdd, config.capDrop)
+ caplist, err = caps.TweakCapabilities(configSpec.Process.Capabilities.Bounding, config.CapAdd, config.CapDrop)
if err != nil {
return err
}
@@ -166,85 +166,85 @@ func setupCapabilities(config *createConfig, configSpec *spec.Spec) error {
func createConfigToOCISpec(config *createConfig) (*spec.Spec, error) {
g := generate.New()
g.AddCgroupsMount("ro")
- g.SetProcessCwd(config.workDir)
- g.SetProcessArgs(config.command)
- g.SetProcessTerminal(config.tty)
+ g.SetProcessCwd(config.WorkDir)
+ g.SetProcessArgs(config.Command)
+ g.SetProcessTerminal(config.Tty)
// User and Group must go together
- g.SetProcessUID(config.user)
- g.SetProcessGID(config.group)
- for _, gid := range config.groupAdd {
+ g.SetProcessUID(config.User)
+ g.SetProcessGID(config.Group)
+ for _, gid := range config.GroupAdd {
g.AddProcessAdditionalGid(gid)
}
for key, val := range config.GetAnnotations() {
g.AddAnnotation(key, val)
}
- g.SetRootReadonly(config.readOnlyRootfs)
- g.SetHostname(config.hostname)
- if config.hostname != "" {
- g.AddProcessEnv("HOSTNAME", config.hostname)
+ g.SetRootReadonly(config.ReadOnlyRootfs)
+ g.SetHostname(config.Hostname)
+ if config.Hostname != "" {
+ g.AddProcessEnv("HOSTNAME", config.Hostname)
}
- for _, sysctl := range config.sysctl {
+ for _, sysctl := range config.Sysctl {
s := strings.SplitN(sysctl, "=", 2)
g.AddLinuxSysctl(s[0], s[1])
}
// RESOURCES - MEMORY
- if config.resources.memory != 0 {
- g.SetLinuxResourcesMemoryLimit(config.resources.memory)
+ if config.Resources.Memory != 0 {
+ g.SetLinuxResourcesMemoryLimit(config.Resources.Memory)
}
- if config.resources.memoryReservation != 0 {
- g.SetLinuxResourcesMemoryReservation(config.resources.memoryReservation)
+ if config.Resources.MemoryReservation != 0 {
+ g.SetLinuxResourcesMemoryReservation(config.Resources.MemoryReservation)
}
- if config.resources.memorySwap != 0 {
- g.SetLinuxResourcesMemorySwap(config.resources.memorySwap)
+ if config.Resources.MemorySwap != 0 {
+ g.SetLinuxResourcesMemorySwap(config.Resources.MemorySwap)
}
- if config.resources.kernelMemory != 0 {
- g.SetLinuxResourcesMemoryKernel(config.resources.kernelMemory)
+ if config.Resources.KernelMemory != 0 {
+ g.SetLinuxResourcesMemoryKernel(config.Resources.KernelMemory)
}
- if config.resources.memorySwappiness != -1 {
- g.SetLinuxResourcesMemorySwappiness(uint64(config.resources.memorySwappiness))
+ if config.Resources.MemorySwappiness != -1 {
+ g.SetLinuxResourcesMemorySwappiness(uint64(config.Resources.MemorySwappiness))
}
- g.SetLinuxResourcesMemoryDisableOOMKiller(config.resources.disableOomKiller)
- g.SetProcessOOMScoreAdj(config.resources.oomScoreAdj)
+ g.SetLinuxResourcesMemoryDisableOOMKiller(config.Resources.DisableOomKiller)
+ g.SetProcessOOMScoreAdj(config.Resources.OomScoreAdj)
// RESOURCES - CPU
- if config.resources.cpuShares != 0 {
- g.SetLinuxResourcesCPUShares(config.resources.cpuShares)
+ if config.Resources.CpuShares != 0 {
+ g.SetLinuxResourcesCPUShares(config.Resources.CpuShares)
}
- if config.resources.cpuQuota != 0 {
- g.SetLinuxResourcesCPUQuota(config.resources.cpuQuota)
+ if config.Resources.CpuQuota != 0 {
+ g.SetLinuxResourcesCPUQuota(config.Resources.CpuQuota)
}
- if config.resources.cpuPeriod != 0 {
- g.SetLinuxResourcesCPUPeriod(config.resources.cpuPeriod)
+ if config.Resources.CpuPeriod != 0 {
+ g.SetLinuxResourcesCPUPeriod(config.Resources.CpuPeriod)
}
- if config.resources.cpuRtRuntime != 0 {
- g.SetLinuxResourcesCPURealtimeRuntime(config.resources.cpuRtRuntime)
+ if config.Resources.CpuRtRuntime != 0 {
+ g.SetLinuxResourcesCPURealtimeRuntime(config.Resources.CpuRtRuntime)
}
- if config.resources.cpuRtPeriod != 0 {
- g.SetLinuxResourcesCPURealtimePeriod(config.resources.cpuRtPeriod)
+ if config.Resources.CpuRtPeriod != 0 {
+ g.SetLinuxResourcesCPURealtimePeriod(config.Resources.CpuRtPeriod)
}
- if config.resources.cpus != "" {
- g.SetLinuxResourcesCPUCpus(config.resources.cpus)
+ if config.Resources.Cpus != "" {
+ g.SetLinuxResourcesCPUCpus(config.Resources.Cpus)
}
- if config.resources.cpusetMems != "" {
- g.SetLinuxResourcesCPUMems(config.resources.cpusetMems)
+ if config.Resources.CpusetMems != "" {
+ g.SetLinuxResourcesCPUMems(config.Resources.CpusetMems)
}
// SECURITY OPTS
- g.SetProcessNoNewPrivileges(config.noNewPrivileges)
- g.SetProcessApparmorProfile(config.apparmorProfile)
- g.SetProcessSelinuxLabel(config.processLabel)
- g.SetLinuxMountLabel(config.mountLabel)
+ g.SetProcessNoNewPrivileges(config.NoNewPrivileges)
+ g.SetProcessApparmorProfile(config.ApparmorProfile)
+ g.SetProcessSelinuxLabel(config.ProcessLabel)
+ g.SetLinuxMountLabel(config.MountLabel)
blockAccessToKernelFilesystems(config, &g)
// RESOURCES - PIDS
- if config.resources.pidsLimit != 0 {
- g.SetLinuxResourcesPidsLimit(config.resources.pidsLimit)
+ if config.Resources.PidsLimit != 0 {
+ g.SetLinuxResourcesPidsLimit(config.Resources.PidsLimit)
}
- for _, i := range config.tmpfs {
+ for _, i := range config.Tmpfs {
options := []string{"rw", "noexec", "nosuid", "nodev", "size=65536k"}
spliti := strings.SplitN(i, ":", 2)
if len(spliti) > 1 {
@@ -257,7 +257,7 @@ func createConfigToOCISpec(config *createConfig) (*spec.Spec, error) {
g.AddTmpfsMount(spliti[0], options)
}
- for name, val := range config.env {
+ for name, val := range config.Env {
g.AddProcessEnv(name, val)
}
@@ -282,14 +282,14 @@ func createConfigToOCISpec(config *createConfig) (*spec.Spec, error) {
}
configSpec := g.Spec()
- if config.seccompProfilePath != "" && config.seccompProfilePath != "unconfined" {
- seccompProfile, err := ioutil.ReadFile(config.seccompProfilePath)
+ if config.SeccompProfilePath != "" && config.SeccompProfilePath != "unconfined" {
+ seccompProfile, err := ioutil.ReadFile(config.SeccompProfilePath)
if err != nil {
- return nil, errors.Wrapf(err, "opening seccomp profile (%s) failed", config.seccompProfilePath)
+ return nil, errors.Wrapf(err, "opening seccomp profile (%s) failed", config.SeccompProfilePath)
}
var seccompConfig spec.LinuxSeccomp
if err := json.Unmarshal(seccompProfile, &seccompConfig); err != nil {
- return nil, errors.Wrapf(err, "decoding seccomp profile (%s) failed", config.seccompProfilePath)
+ return nil, errors.Wrapf(err, "decoding seccomp profile (%s) failed", config.SeccompProfilePath)
}
configSpec.Linux.Seccomp = &seccompConfig
}
@@ -347,10 +347,10 @@ func createConfigToOCISpec(config *createConfig) (*spec.Spec, error) {
func (c *createConfig) CreateBlockIO() (spec.LinuxBlockIO, error) {
bio := spec.LinuxBlockIO{}
- bio.Weight = &c.resources.blkioWeight
- if len(c.resources.blkioWeightDevice) > 0 {
+ bio.Weight = &c.Resources.BlkioWeight
+ if len(c.Resources.BlkioWeightDevice) > 0 {
var lwds []spec.LinuxWeightDevice
- for _, i := range c.resources.blkioWeightDevice {
+ for _, i := range c.Resources.BlkioWeightDevice {
wd, err := validateweightDevice(i)
if err != nil {
return bio, errors.Wrapf(err, "invalid values for blkio-weight-device")
@@ -364,29 +364,29 @@ func (c *createConfig) CreateBlockIO() (spec.LinuxBlockIO, error) {
lwds = append(lwds, lwd)
}
}
- if len(c.resources.deviceReadBps) > 0 {
- readBps, err := makeThrottleArray(c.resources.deviceReadBps)
+ if len(c.Resources.DeviceReadBps) > 0 {
+ readBps, err := makeThrottleArray(c.Resources.DeviceReadBps)
if err != nil {
return bio, err
}
bio.ThrottleReadBpsDevice = readBps
}
- if len(c.resources.deviceWriteBps) > 0 {
- writeBpds, err := makeThrottleArray(c.resources.deviceWriteBps)
+ if len(c.Resources.DeviceWriteBps) > 0 {
+ writeBpds, err := makeThrottleArray(c.Resources.DeviceWriteBps)
if err != nil {
return bio, err
}
bio.ThrottleWriteBpsDevice = writeBpds
}
- if len(c.resources.deviceReadIOps) > 0 {
- readIOps, err := makeThrottleArray(c.resources.deviceReadIOps)
+ if len(c.Resources.DeviceReadIOps) > 0 {
+ readIOps, err := makeThrottleArray(c.Resources.DeviceReadIOps)
if err != nil {
return bio, err
}
bio.ThrottleReadIOPSDevice = readIOps
}
- if len(c.resources.deviceWriteIOps) > 0 {
- writeIOps, err := makeThrottleArray(c.resources.deviceWriteIOps)
+ if len(c.Resources.DeviceWriteIOps) > 0 {
+ writeIOps, err := makeThrottleArray(c.Resources.DeviceWriteIOps)
if err != nil {
return bio, err
}
@@ -401,7 +401,7 @@ func (c *createConfig) GetAnnotations() map[string]string {
a := getDefaultAnnotations()
// TODO - Which annotations do we want added by default
// TODO - This should be added to the DB long term
- if c.tty {
+ if c.Tty {
a["io.kubernetes.cri-o.TTY"] = "true"
}
return a
@@ -445,7 +445,7 @@ func getDefaultAnnotations() map[string]string {
func (c *createConfig) GetVolumeMounts() ([]spec.Mount, error) {
var m []spec.Mount
var options []string
- for _, i := range c.volumes {
+ for _, i := range c.Volumes {
// We need to handle SELinux options better here, specifically :Z
spliti := strings.Split(i, ":")
if len(spliti) > 2 {
@@ -472,12 +472,12 @@ func (c *createConfig) GetVolumeMounts() ([]spec.Mount, error) {
options = append(options, "rw")
}
if foundz {
- if err := label.Relabel(spliti[0], c.mountLabel, true); err != nil {
+ if err := label.Relabel(spliti[0], c.MountLabel, true); err != nil {
return nil, errors.Wrapf(err, "relabel failed %q", spliti[0])
}
}
if foundZ {
- if err := label.Relabel(spliti[0], c.mountLabel, false); err != nil {
+ if err := label.Relabel(spliti[0], c.MountLabel, false); err != nil {
return nil, errors.Wrapf(err, "relabel failed %q", spliti[0])
}
}
@@ -495,10 +495,10 @@ func (c *createConfig) GetVolumeMounts() ([]spec.Mount, error) {
return m, nil
}
-//GetTmpfsMounts takes user provided input for tmpfs mounts and creates Mount structs
+//GetTmpfsMounts takes user provided input for Tmpfs mounts and creates Mount structs
func (c *createConfig) GetTmpfsMounts() []spec.Mount {
var m []spec.Mount
- for _, i := range c.tmpfs {
+ for _, i := range c.Tmpfs {
// Default options if nothing passed
options := []string{"rw", "noexec", "nosuid", "nodev", "size=65536k"}
spliti := strings.Split(i, ":")
@@ -522,12 +522,12 @@ func (c *createConfig) GetContainerCreateOptions() ([]libpod.CtrCreateOption, er
// Uncomment after talking to mheon about unimplemented funcs
// options = append(options, libpod.WithLabels(c.labels))
- if c.interactive {
+ if c.Interactive {
options = append(options, libpod.WithStdin())
}
- if c.name != "" {
- logrus.Debugf("appending name %s", c.name)
- options = append(options, libpod.WithName(c.name))
+ if c.Name != "" {
+ logrus.Debugf("appending name %s", c.Name)
+ options = append(options, libpod.WithName(c.Name))
}
return options, nil
diff --git a/cmd/kpod/spec_test.go b/cmd/kpod/spec_test.go
index 799d6b235..01e1a4ad3 100644
--- a/cmd/kpod/spec_test.go
+++ b/cmd/kpod/spec_test.go
@@ -16,7 +16,7 @@ func TestCreateConfig_GetVolumeMounts(t *testing.T) {
Options: []string{"ro", "rbind", "rprivate"},
}
config := createConfig{
- volumes: []string{"foobar:/foobar:ro"},
+ Volumes: []string{"foobar:/foobar:ro"},
}
specMount, err := config.GetVolumeMounts()
assert.NoError(t, err)
@@ -31,7 +31,7 @@ func TestCreateConfig_GetTmpfsMounts(t *testing.T) {
Options: []string{"rw", "size=787448k", "mode=1777"},
}
config := createConfig{
- tmpfs: []string{"/homer:rw,size=787448k,mode=1777"},
+ Tmpfs: []string{"/homer:rw,size=787448k,mode=1777"},
}
tmpfsMount := config.GetTmpfsMounts()
assert.True(t, reflect.DeepEqual(data, tmpfsMount[0]))