From d2e64247e6dfd3257a7d015890aa2f168ff643a0 Mon Sep 17 00:00:00 2001 From: Vincent Demeester Date: Mon, 24 Oct 2016 11:10:14 -0700 Subject: [PATCH] Taking stop-signal into account when docker kill If a container sets a stop-signal, taking it into account to disable or not the restart policy. Signed-off-by: Vincent Demeester --- daemon/kill.go | 12 +++++++++- integration-cli/docker_cli_kill_test.go | 32 ++++++++++++++++++++++++- 2 files changed, 42 insertions(+), 2 deletions(-) diff --git a/daemon/kill.go b/daemon/kill.go index 84186a9390..18d5bbb4e5 100644 --- a/daemon/kill.go +++ b/daemon/kill.go @@ -68,7 +68,17 @@ func (daemon *Daemon) killWithSignal(container *container.Container, sig int) er return errNotRunning{container.ID} } - container.ExitOnNext() + if container.Config.StopSignal != "" { + containerStopSignal, err := signal.ParseSignal(container.Config.StopSignal) + if err != nil { + return err + } + if containerStopSignal == syscall.Signal(sig) { + container.ExitOnNext() + } + } else { + container.ExitOnNext() + } if !daemon.IsShuttingDown() { container.HasBeenManuallyStopped = true diff --git a/integration-cli/docker_cli_kill_test.go b/integration-cli/docker_cli_kill_test.go index 05d9a55879..7a9f12f0c6 100644 --- a/integration-cli/docker_cli_kill_test.go +++ b/integration-cli/docker_cli_kill_test.go @@ -47,7 +47,7 @@ func (s *DockerSuite) TestKillDifferentUserContainer(c *check.C) { // regression test about correct signal parsing see #13665 func (s *DockerSuite) TestKillWithSignal(c *check.C) { - // Cannot port to Windows - does not support signals in the same was a Linux does + // Cannot port to Windows - does not support signals in the same way Linux does testRequires(c, DaemonIsLinux) out, _ := dockerCmd(c, "run", "-d", "busybox", "top") cid := strings.TrimSpace(out) @@ -60,6 +60,36 @@ func (s *DockerSuite) TestKillWithSignal(c *check.C) { c.Assert(running, checker.Equals, "true", check.Commentf("Container should be in running state after SIGWINCH")) } +func (s *DockerSuite) TestKillWithStopSignalWithSameSignalShouldDisableRestartPolicy(c *check.C) { + // Cannot port to Windows - does not support signals int the same way as Linux does + testRequires(c, DaemonIsLinux) + out, _ := dockerCmd(c, "run", "-d", "--stop-signal=TERM", "busybox", "top") + cid := strings.TrimSpace(out) + c.Assert(waitRun(cid), check.IsNil) + + // Let's docker send a CONT signal to the container + dockerCmd(c, "kill", "-s", "TERM", cid) + + out, _ = dockerCmd(c, "ps", "-q") + c.Assert(out, checker.Not(checker.Contains), cid, check.Commentf("killed container is still running")) +} + +func (s *DockerSuite) TestKillWithStopSignalWithDifferentSignalShouldKeepRestartPolicy(c *check.C) { + // Cannot port to Windows - does not support signals int the same way as Linux does + testRequires(c, DaemonIsLinux) + out, _ := dockerCmd(c, "run", "-d", "--stop-signal=CONT", "busybox", "top") + cid := strings.TrimSpace(out) + c.Assert(waitRun(cid), check.IsNil) + + // Let's docker send a TERM signal to the container + // It will kill the process, but not disable the restart policy + dockerCmd(c, "kill", "-s", "TERM", cid) + + // Restart policy should still be in place, so it should be still running + c.Assert(waitRun(cid), check.IsNil) +} + +// FIXME(vdemeester) should be a unit test func (s *DockerSuite) TestKillWithInvalidSignal(c *check.C) { out, _ := runSleepingContainer(c, "-d") cid := strings.TrimSpace(out)