зеркало из https://github.com/microsoft/docker.git
Fix ulimits in `docker inspect` when daemon default exists
This fix tries to fix 26326 where `docker inspect` will not show ulimit even when daemon default ulimit has been set. This fix merge the HostConfig's ulimit with daemon default in `docker inspect`, so that when daemon is started with `default-ulimit` and HostConfig's ulimit is not set, `docker inspect` will output the daemon default. An integration test has been added to cover the changes. This fix fixes 26326. Signed-off-by: Yong Tang <yong.tang.github@outlook.com>
This commit is contained in:
Родитель
5be6ccc433
Коммит
7d705a7355
|
@ -110,6 +110,9 @@ func (daemon *Daemon) getInspectData(container *container.Container, size bool)
|
|||
hostConfig.Links = append(hostConfig.Links, fmt.Sprintf("%s:%s", child.Name, linkAlias))
|
||||
}
|
||||
|
||||
// We merge the Ulimits from hostConfig with daemon default
|
||||
daemon.mergeUlimits(&hostConfig)
|
||||
|
||||
var containerHealth *types.Health
|
||||
if container.State.Health != nil {
|
||||
containerHealth = &types.Health{
|
||||
|
|
|
@ -115,19 +115,11 @@ func setDevices(s *specs.Spec, c *container.Container) error {
|
|||
func setRlimits(daemon *Daemon, s *specs.Spec, c *container.Container) error {
|
||||
var rlimits []specs.Rlimit
|
||||
|
||||
ulimits := c.HostConfig.Ulimits
|
||||
// Merge ulimits with daemon defaults
|
||||
ulIdx := make(map[string]struct{})
|
||||
for _, ul := range ulimits {
|
||||
ulIdx[ul.Name] = struct{}{}
|
||||
}
|
||||
for name, ul := range daemon.configStore.Ulimits {
|
||||
if _, exists := ulIdx[name]; !exists {
|
||||
ulimits = append(ulimits, ul)
|
||||
}
|
||||
}
|
||||
|
||||
for _, ul := range ulimits {
|
||||
// We want to leave the original HostConfig alone so make a copy here
|
||||
hostConfig := *c.HostConfig
|
||||
// Merge with the daemon defaults
|
||||
daemon.mergeUlimits(&hostConfig)
|
||||
for _, ul := range hostConfig.Ulimits {
|
||||
rlimits = append(rlimits, specs.Rlimit{
|
||||
Type: "RLIMIT_" + strings.ToUpper(ul.Name),
|
||||
Soft: uint64(ul.Soft),
|
||||
|
@ -709,3 +701,19 @@ func clearReadOnly(m *specs.Mount) {
|
|||
}
|
||||
m.Options = opt
|
||||
}
|
||||
|
||||
// mergeUlimits merge the Ulimits from HostConfig with daemon defaults, and update HostConfig
|
||||
func (daemon *Daemon) mergeUlimits(c *containertypes.HostConfig) {
|
||||
ulimits := c.Ulimits
|
||||
// Merge ulimits with daemon defaults
|
||||
ulIdx := make(map[string]struct{})
|
||||
for _, ul := range ulimits {
|
||||
ulIdx[ul.Name] = struct{}{}
|
||||
}
|
||||
for name, ul := range daemon.configStore.Ulimits {
|
||||
if _, exists := ulIdx[name]; !exists {
|
||||
ulimits = append(ulimits, ul)
|
||||
}
|
||||
}
|
||||
c.Ulimits = ulimits
|
||||
}
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
package daemon
|
||||
|
||||
import (
|
||||
containertypes "github.com/docker/docker/api/types/container"
|
||||
"github.com/docker/docker/container"
|
||||
"github.com/docker/docker/libcontainerd"
|
||||
"github.com/docker/docker/oci"
|
||||
|
@ -10,3 +11,9 @@ func (daemon *Daemon) createSpec(c *container.Container) (*libcontainerd.Spec, e
|
|||
s := oci.DefaultSpec()
|
||||
return (*libcontainerd.Spec)(&s), nil
|
||||
}
|
||||
|
||||
// mergeUlimits merge the Ulimits from HostConfig with daemon defaults, and update HostConfig
|
||||
// It will do nothing on non-Linux platform
|
||||
func (daemon *Daemon) mergeUlimits(c *containertypes.HostConfig) {
|
||||
return
|
||||
}
|
||||
|
|
|
@ -7,6 +7,7 @@ import (
|
|||
"path/filepath"
|
||||
"syscall"
|
||||
|
||||
containertypes "github.com/docker/docker/api/types/container"
|
||||
"github.com/docker/docker/container"
|
||||
"github.com/docker/docker/image"
|
||||
"github.com/docker/docker/layer"
|
||||
|
@ -192,3 +193,9 @@ func escapeArgs(args []string) []string {
|
|||
}
|
||||
return escapedArgs
|
||||
}
|
||||
|
||||
// mergeUlimits merge the Ulimits from HostConfig with daemon defaults, and update HostConfig
|
||||
// It will do nothing on non-Linux platform
|
||||
func (daemon *Daemon) mergeUlimits(c *containertypes.HostConfig) {
|
||||
return
|
||||
}
|
||||
|
|
|
@ -4518,3 +4518,25 @@ exec "$@"`,
|
|||
c.Assert(err, check.NotNil)
|
||||
c.Assert(err.Error(), checker.Contains, "No command specified")
|
||||
}
|
||||
|
||||
func (s *DockerDaemonSuite) TestRunWithUlimitAndDaemonDefault(c *check.C) {
|
||||
c.Assert(s.d.StartWithBusybox("--debug", "--default-ulimit=nofile=65535"), checker.IsNil)
|
||||
|
||||
name := "test-A"
|
||||
_, err := s.d.Cmd("run", "--name", name, "-d", "busybox", "top")
|
||||
c.Assert(err, checker.IsNil)
|
||||
c.Assert(s.d.waitRun(name), check.IsNil)
|
||||
|
||||
out, err := s.d.Cmd("inspect", "--format", "{{.HostConfig.Ulimits}}", name)
|
||||
c.Assert(err, checker.IsNil)
|
||||
c.Assert(out, checker.Contains, "[nofile=65535:65535]")
|
||||
|
||||
name = "test-B"
|
||||
_, err = s.d.Cmd("run", "--name", name, "--ulimit=nofile=42", "-d", "busybox", "top")
|
||||
c.Assert(err, checker.IsNil)
|
||||
c.Assert(s.d.waitRun(name), check.IsNil)
|
||||
|
||||
out, err = s.d.Cmd("inspect", "--format", "{{.HostConfig.Ulimits}}", name)
|
||||
c.Assert(err, checker.IsNil)
|
||||
c.Assert(out, checker.Contains, "[nofile=42:42]")
|
||||
}
|
||||
|
|
Загрузка…
Ссылка в новой задаче