mirror of
https://github.com/moby/moby.git
synced 2022-11-09 12:21:53 -05:00
Add init process for zombie fighting
This adds a small C binary for fighting zombies. It is mounted under `/dev/init` and is prepended to the args specified by the user. You enable it via a daemon flag, `dockerd --init`, as it is disable by default for backwards compat. You can also override the daemon option or specify this on a per container basis with `docker run --init=true|false`. You can test this by running a process like this as the pid 1 in a container and see the extra zombie that appears in the container as it is running. ```c int main(int argc, char ** argv) { pid_t pid = fork(); if (pid == 0) { pid = fork(); if (pid == 0) { exit(0); } sleep(3); exit(0); } printf("got pid %d and exited\n", pid); sleep(20); } ``` Signed-off-by: Michael Crosby <crosbymichael@gmail.com>
This commit is contained in:
parent
d8c9951707
commit
ee3ac3aa66
22 changed files with 112 additions and 68 deletions
10
Dockerfile
10
Dockerfile
|
@ -255,6 +255,16 @@ RUN set -x \
|
||||||
&& cp bin/ctr /usr/local/bin/docker-containerd-ctr \
|
&& cp bin/ctr /usr/local/bin/docker-containerd-ctr \
|
||||||
&& rm -rf "$GOPATH"
|
&& rm -rf "$GOPATH"
|
||||||
|
|
||||||
|
ENV GRIMES_COMMIT f207601a8d19a534cc90d9e26e037e9931ccb9db
|
||||||
|
RUN set -x \
|
||||||
|
&& export GOPATH="$(mktemp -d)" \
|
||||||
|
&& git clone https://github.com/crosbymichael/grimes.git "$GOPATH/grimes" \
|
||||||
|
&& cd "$GOPATH/grimes" \
|
||||||
|
&& git checkout -q "$GRIMES_COMMIT" \
|
||||||
|
&& make \
|
||||||
|
&& cp init /usr/local/bin/docker-init \
|
||||||
|
&& rm -rf "$GOPATH"
|
||||||
|
|
||||||
# Wrap all commands in the "docker-in-docker" script to allow nested containers
|
# Wrap all commands in the "docker-in-docker" script to allow nested containers
|
||||||
ENTRYPOINT ["hack/dind"]
|
ENTRYPOINT ["hack/dind"]
|
||||||
|
|
||||||
|
|
|
@ -198,6 +198,16 @@ RUN set -x \
|
||||||
&& cp bin/ctr /usr/local/bin/docker-containerd-ctr \
|
&& cp bin/ctr /usr/local/bin/docker-containerd-ctr \
|
||||||
&& rm -rf "$GOPATH"
|
&& rm -rf "$GOPATH"
|
||||||
|
|
||||||
|
ENV GRIMES_COMMIT f207601a8d19a534cc90d9e26e037e9931ccb9db
|
||||||
|
RUN set -x \
|
||||||
|
&& export GOPATH="$(mktemp -d)" \
|
||||||
|
&& git clone https://github.com/crosbymichael/grimes.git "$GOPATH/grimes" \
|
||||||
|
&& cd "$GOPATH/grimes" \
|
||||||
|
&& git checkout -q "$GRIMES_COMMIT" \
|
||||||
|
&& make \
|
||||||
|
&& cp init /usr/local/bin/docker-init \
|
||||||
|
&& rm -rf "$GOPATH"
|
||||||
|
|
||||||
# Wrap all commands in the "docker-in-docker" script to allow nested containers
|
# Wrap all commands in the "docker-in-docker" script to allow nested containers
|
||||||
ENTRYPOINT ["hack/dind"]
|
ENTRYPOINT ["hack/dind"]
|
||||||
|
|
||||||
|
|
|
@ -196,6 +196,16 @@ RUN set -x \
|
||||||
&& cp bin/ctr /usr/local/bin/docker-containerd-ctr \
|
&& cp bin/ctr /usr/local/bin/docker-containerd-ctr \
|
||||||
&& rm -rf "$GOPATH"
|
&& rm -rf "$GOPATH"
|
||||||
|
|
||||||
|
ENV GRIMES_COMMIT f207601a8d19a534cc90d9e26e037e9931ccb9db
|
||||||
|
RUN set -x \
|
||||||
|
&& export GOPATH="$(mktemp -d)" \
|
||||||
|
&& git clone https://github.com/crosbymichael/grimes.git "$GOPATH/grimes" \
|
||||||
|
&& cd "$GOPATH/grimes" \
|
||||||
|
&& git checkout -q "$GRIMES_COMMIT" \
|
||||||
|
&& make \
|
||||||
|
&& cp init /usr/local/bin/docker-init \
|
||||||
|
&& rm -rf "$GOPATH"
|
||||||
|
|
||||||
ENTRYPOINT ["hack/dind"]
|
ENTRYPOINT ["hack/dind"]
|
||||||
|
|
||||||
# Upload docker source
|
# Upload docker source
|
||||||
|
|
|
@ -216,6 +216,16 @@ RUN set -x \
|
||||||
&& cp bin/ctr /usr/local/bin/docker-containerd-ctr \
|
&& cp bin/ctr /usr/local/bin/docker-containerd-ctr \
|
||||||
&& rm -rf "$GOPATH"
|
&& rm -rf "$GOPATH"
|
||||||
|
|
||||||
|
ENV GRIMES_COMMIT f207601a8d19a534cc90d9e26e037e9931ccb9db
|
||||||
|
RUN set -x \
|
||||||
|
&& export GOPATH="$(mktemp -d)" \
|
||||||
|
&& git clone https://github.com/crosbymichael/grimes.git "$GOPATH/grimes" \
|
||||||
|
&& cd "$GOPATH/grimes" \
|
||||||
|
&& git checkout -q "$GRIMES_COMMIT" \
|
||||||
|
&& make \
|
||||||
|
&& cp init /usr/local/bin/docker-init \
|
||||||
|
&& rm -rf "$GOPATH"
|
||||||
|
|
||||||
# Wrap all commands in the "docker-in-docker" script to allow nested containers
|
# Wrap all commands in the "docker-in-docker" script to allow nested containers
|
||||||
ENTRYPOINT ["hack/dind"]
|
ENTRYPOINT ["hack/dind"]
|
||||||
|
|
||||||
|
|
|
@ -208,6 +208,16 @@ RUN set -x \
|
||||||
&& cp bin/ctr /usr/local/bin/docker-containerd-ctr \
|
&& cp bin/ctr /usr/local/bin/docker-containerd-ctr \
|
||||||
&& rm -rf "$GOPATH"
|
&& rm -rf "$GOPATH"
|
||||||
|
|
||||||
|
ENV GRIMES_COMMIT f207601a8d19a534cc90d9e26e037e9931ccb9db
|
||||||
|
RUN set -x \
|
||||||
|
&& export GOPATH="$(mktemp -d)" \
|
||||||
|
&& git clone https://github.com/crosbymichael/grimes.git "$GOPATH/grimes" \
|
||||||
|
&& cd "$GOPATH/grimes" \
|
||||||
|
&& git checkout -q "$GRIMES_COMMIT" \
|
||||||
|
&& make \
|
||||||
|
&& cp init /usr/local/bin/docker-init \
|
||||||
|
&& rm -rf "$GOPATH"
|
||||||
|
|
||||||
# Wrap all commands in the "docker-in-docker" script to allow nested containers
|
# Wrap all commands in the "docker-in-docker" script to allow nested containers
|
||||||
ENTRYPOINT ["hack/dind"]
|
ENTRYPOINT ["hack/dind"]
|
||||||
|
|
||||||
|
|
|
@ -80,6 +80,16 @@ RUN set -x \
|
||||||
&& cp bin/ctr /usr/local/bin/docker-containerd-ctr \
|
&& cp bin/ctr /usr/local/bin/docker-containerd-ctr \
|
||||||
&& rm -rf "$GOPATH"
|
&& rm -rf "$GOPATH"
|
||||||
|
|
||||||
|
ENV GRIMES_COMMIT f207601a8d19a534cc90d9e26e037e9931ccb9db
|
||||||
|
RUN set -x \
|
||||||
|
&& export GOPATH="$(mktemp -d)" \
|
||||||
|
&& git clone https://github.com/crosbymichael/grimes.git "$GOPATH/grimes" \
|
||||||
|
&& cd "$GOPATH/grimes" \
|
||||||
|
&& git checkout -q "$GRIMES_COMMIT" \
|
||||||
|
&& make \
|
||||||
|
&& cp init /usr/local/bin/docker-init \
|
||||||
|
&& rm -rf "$GOPATH"
|
||||||
|
|
||||||
ENV AUTO_GOPATH 1
|
ENV AUTO_GOPATH 1
|
||||||
WORKDIR /usr/src/docker
|
WORKDIR /usr/src/docker
|
||||||
COPY . /usr/src/docker
|
COPY . /usr/src/docker
|
||||||
|
|
|
@ -321,6 +321,9 @@ type HostConfig struct {
|
||||||
|
|
||||||
// Mounts specs used by the container
|
// Mounts specs used by the container
|
||||||
Mounts []mount.Mount `json:",omitempty"`
|
Mounts []mount.Mount `json:",omitempty"`
|
||||||
|
|
||||||
|
// Run a custom init inside the container, if null, use the daemon's configured settings
|
||||||
|
Init *bool `json:",om itempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
// Box specifies height and width dimensions. Used for sizing of a console.
|
// Box specifies height and width dimensions. Used for sizing of a console.
|
||||||
|
|
|
@ -35,6 +35,7 @@ type Config struct {
|
||||||
Runtimes map[string]types.Runtime `json:"runtimes,omitempty"`
|
Runtimes map[string]types.Runtime `json:"runtimes,omitempty"`
|
||||||
DefaultRuntime string `json:"default-runtime,omitempty"`
|
DefaultRuntime string `json:"default-runtime,omitempty"`
|
||||||
OOMScoreAdjust int `json:"oom-score-adjust,omitempty"`
|
OOMScoreAdjust int `json:"oom-score-adjust,omitempty"`
|
||||||
|
Init bool `json:"init,omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
// bridgeConfig stores all the bridge driver specific
|
// bridgeConfig stores all the bridge driver specific
|
||||||
|
@ -91,6 +92,7 @@ func (config *Config) InstallFlags(flags *pflag.FlagSet) {
|
||||||
flags.Var(runconfigopts.NewNamedRuntimeOpt("runtimes", &config.Runtimes, stockRuntimeName), "add-runtime", "Register an additional OCI compatible runtime")
|
flags.Var(runconfigopts.NewNamedRuntimeOpt("runtimes", &config.Runtimes, stockRuntimeName), "add-runtime", "Register an additional OCI compatible runtime")
|
||||||
flags.StringVar(&config.DefaultRuntime, "default-runtime", stockRuntimeName, "Default OCI runtime for containers")
|
flags.StringVar(&config.DefaultRuntime, "default-runtime", stockRuntimeName, "Default OCI runtime for containers")
|
||||||
flags.IntVar(&config.OOMScoreAdjust, "oom-score-adjust", -500, "Set the oom_score_adj for the daemon")
|
flags.IntVar(&config.OOMScoreAdjust, "oom-score-adjust", -500, "Set the oom_score_adj for the daemon")
|
||||||
|
flags.BoolVar(&config.Init, "init", false, "Run an init in the container to forward signals and reap processes")
|
||||||
|
|
||||||
config.attachExperimentalFlags(flags)
|
config.attachExperimentalFlags(flags)
|
||||||
}
|
}
|
||||||
|
|
|
@ -4,6 +4,7 @@ import (
|
||||||
"fmt"
|
"fmt"
|
||||||
"io"
|
"io"
|
||||||
"os"
|
"os"
|
||||||
|
"os/exec"
|
||||||
"path/filepath"
|
"path/filepath"
|
||||||
"sort"
|
"sort"
|
||||||
"strconv"
|
"strconv"
|
||||||
|
@ -585,6 +586,26 @@ func (daemon *Daemon) populateCommonSpec(s *specs.Spec, c *container.Container)
|
||||||
cwd = "/"
|
cwd = "/"
|
||||||
}
|
}
|
||||||
s.Process.Args = append([]string{c.Path}, c.Args...)
|
s.Process.Args = append([]string{c.Path}, c.Args...)
|
||||||
|
|
||||||
|
// only add the custom init if it is specified and the container is running in its
|
||||||
|
// own private pid namespace. It does not make sense to add if it is running in the
|
||||||
|
// host namespace or another container's pid namespace where we already have an init
|
||||||
|
if c.HostConfig.PidMode.IsPrivate() {
|
||||||
|
if (c.HostConfig.Init != nil && *c.HostConfig.Init) ||
|
||||||
|
(c.HostConfig.Init == nil && daemon.configStore.Init) {
|
||||||
|
s.Process.Args = append([]string{"/dev/init", c.Path}, c.Args...)
|
||||||
|
path, err := exec.LookPath("docker-init")
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
s.Mounts = append(s.Mounts, specs.Mount{
|
||||||
|
Destination: "/dev/init",
|
||||||
|
Type: "bind",
|
||||||
|
Source: path,
|
||||||
|
Options: []string{"bind", "ro"},
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
s.Process.Cwd = cwd
|
s.Process.Cwd = cwd
|
||||||
s.Process.Env = c.CreateDaemonEnvironment(linkedEnv)
|
s.Process.Env = c.CreateDaemonEnvironment(linkedEnv)
|
||||||
s.Process.Terminal = c.Config.Tty
|
s.Process.Terminal = c.Config.Tty
|
||||||
|
|
|
@ -48,6 +48,7 @@ Options:
|
||||||
-H, --host=[] Daemon socket(s) to connect to
|
-H, --host=[] Daemon socket(s) to connect to
|
||||||
--help Print usage
|
--help Print usage
|
||||||
--icc=true Enable inter-container communication
|
--icc=true Enable inter-container communication
|
||||||
|
--init Run an init inside containers to forward signals and reap processes
|
||||||
--insecure-registry=[] Enable insecure registry communication
|
--insecure-registry=[] Enable insecure registry communication
|
||||||
--ip=0.0.0.0 Default IP when binding container ports
|
--ip=0.0.0.0 Default IP when binding container ports
|
||||||
--ip-forward=true Enable net.ipv4.ip_forward
|
--ip-forward=true Enable net.ipv4.ip_forward
|
||||||
|
@ -1140,6 +1141,7 @@ This is a full example of the allowed configuration options on Linux:
|
||||||
"group": "",
|
"group": "",
|
||||||
"cgroup-parent": "",
|
"cgroup-parent": "",
|
||||||
"default-ulimits": {},
|
"default-ulimits": {},
|
||||||
|
"init": false,
|
||||||
"ipv6": false,
|
"ipv6": false,
|
||||||
"iptables": false,
|
"iptables": false,
|
||||||
"ip-forward": false,
|
"ip-forward": false,
|
||||||
|
|
|
@ -255,7 +255,7 @@ bundle() {
|
||||||
source "$SCRIPTDIR/make/$bundle" "$@"
|
source "$SCRIPTDIR/make/$bundle" "$@"
|
||||||
}
|
}
|
||||||
|
|
||||||
copy_containerd() {
|
copy_binaries() {
|
||||||
dir="$1"
|
dir="$1"
|
||||||
# Add nested executables to bundle dir so we have complete set of
|
# Add nested executables to bundle dir so we have complete set of
|
||||||
# them available, but only if the native OS/ARCH is the same as the
|
# them available, but only if the native OS/ARCH is the same as the
|
||||||
|
@ -263,7 +263,7 @@ copy_containerd() {
|
||||||
if [ "$(go env GOOS)/$(go env GOARCH)" == "$(go env GOHOSTOS)/$(go env GOHOSTARCH)" ]; then
|
if [ "$(go env GOOS)/$(go env GOARCH)" == "$(go env GOHOSTOS)/$(go env GOHOSTARCH)" ]; then
|
||||||
if [ -x /usr/local/bin/docker-runc ]; then
|
if [ -x /usr/local/bin/docker-runc ]; then
|
||||||
echo "Copying nested executables into $dir"
|
echo "Copying nested executables into $dir"
|
||||||
for file in containerd containerd-shim containerd-ctr runc; do
|
for file in containerd containerd-shim containerd-ctr runc init; do
|
||||||
cp `which "docker-$file"` "$dir/"
|
cp `which "docker-$file"` "$dir/"
|
||||||
if [ "$2" == "hash" ]; then
|
if [ "$2" == "hash" ]; then
|
||||||
hash_files "$dir/docker-$file"
|
hash_files "$dir/docker-$file"
|
||||||
|
|
|
@ -7,3 +7,4 @@ DOCKER_CONTAINERD_BINARY_NAME='docker-containerd'
|
||||||
DOCKER_CONTAINERD_CTR_BINARY_NAME='docker-containerd-ctr'
|
DOCKER_CONTAINERD_CTR_BINARY_NAME='docker-containerd-ctr'
|
||||||
DOCKER_CONTAINERD_SHIM_BINARY_NAME='docker-containerd-shim'
|
DOCKER_CONTAINERD_SHIM_BINARY_NAME='docker-containerd-shim'
|
||||||
DOCKER_PROXY_BINARY_NAME='docker-proxy'
|
DOCKER_PROXY_BINARY_NAME='docker-proxy'
|
||||||
|
DOCKER_INIT_BINARY_NAME='docker-init'
|
||||||
|
|
|
@ -12,5 +12,5 @@ set -e
|
||||||
export BINARY_SHORT_NAME="$DOCKER_PROXY_BINARY_NAME"
|
export BINARY_SHORT_NAME="$DOCKER_PROXY_BINARY_NAME"
|
||||||
export SOURCE_PATH='./vendor/src/github.com/docker/libnetwork/cmd/proxy'
|
export SOURCE_PATH='./vendor/src/github.com/docker/libnetwork/cmd/proxy'
|
||||||
source "${MAKEDIR}/.binary"
|
source "${MAKEDIR}/.binary"
|
||||||
copy_containerd "$DEST" 'hash'
|
copy_binaries "$DEST" 'hash'
|
||||||
)
|
)
|
||||||
|
|
|
@ -12,4 +12,5 @@ rm -rf "$DEST"
|
||||||
install_binary "${DEST}/${DOCKER_CONTAINERD_CTR_BINARY_NAME}"
|
install_binary "${DEST}/${DOCKER_CONTAINERD_CTR_BINARY_NAME}"
|
||||||
install_binary "${DEST}/${DOCKER_CONTAINERD_SHIM_BINARY_NAME}"
|
install_binary "${DEST}/${DOCKER_CONTAINERD_SHIM_BINARY_NAME}"
|
||||||
install_binary "${DEST}/${DOCKER_PROXY_BINARY_NAME}"
|
install_binary "${DEST}/${DOCKER_PROXY_BINARY_NAME}"
|
||||||
|
install_binary "${DEST}/${DOCKER_INIT_BINARY_NAME}"
|
||||||
)
|
)
|
||||||
|
|
|
@ -53,8 +53,8 @@ for d in "$CROSS/"*/*; do
|
||||||
cp -L "$d/$PROXY_BINARY_FULLNAME" "$TAR_PATH/${DOCKER_PROXY_BINARY_NAME}${BINARY_EXTENSION}"
|
cp -L "$d/$PROXY_BINARY_FULLNAME" "$TAR_PATH/${DOCKER_PROXY_BINARY_NAME}${BINARY_EXTENSION}"
|
||||||
fi
|
fi
|
||||||
|
|
||||||
# copy over all the containerd binaries
|
# copy over all the extra binaries
|
||||||
copy_containerd $TAR_PATH
|
copy_binaries $TAR_PATH
|
||||||
|
|
||||||
if [ "$IS_TAR" == "true" ]; then
|
if [ "$IS_TAR" == "true" ]; then
|
||||||
echo "Creating tgz from $BUILD_PATH and naming it $TGZ"
|
echo "Creating tgz from $BUILD_PATH and naming it $TGZ"
|
||||||
|
|
|
@ -78,40 +78,6 @@ func (s *DockerSuite) TestEventsUntag(c *check.C) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *DockerSuite) TestEventsContainerFailStartDie(c *check.C) {
|
|
||||||
_, _, err := dockerCmdWithError("run", "--name", "testeventdie", "busybox", "blerg")
|
|
||||||
c.Assert(err, checker.NotNil, check.Commentf("Container run with command blerg should have failed, but it did not"))
|
|
||||||
|
|
||||||
out, _ := dockerCmd(c, "events", "--since=0", "--until", daemonUnixTime(c))
|
|
||||||
events := strings.Split(strings.TrimSpace(out), "\n")
|
|
||||||
|
|
||||||
nEvents := len(events)
|
|
||||||
c.Assert(nEvents, checker.GreaterOrEqualThan, 1) //Missing expected event
|
|
||||||
|
|
||||||
actions := eventActionsByIDAndType(c, events, "testeventdie", "container")
|
|
||||||
|
|
||||||
var startEvent bool
|
|
||||||
var dieEvent bool
|
|
||||||
for _, a := range actions {
|
|
||||||
switch a {
|
|
||||||
case "start":
|
|
||||||
startEvent = true
|
|
||||||
case "die":
|
|
||||||
dieEvent = true
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Windows platform is different from Linux, it will start container whatever
|
|
||||||
// so Windows can get start/die event but Linux can't
|
|
||||||
if daemonPlatform == "windows" {
|
|
||||||
c.Assert(startEvent, checker.True, check.Commentf("Start event not found: %v\n%v", actions, events))
|
|
||||||
c.Assert(dieEvent, checker.True, check.Commentf("Die event not found: %v\n%v", actions, events))
|
|
||||||
} else {
|
|
||||||
c.Assert(startEvent, checker.False, check.Commentf("Start event not expected: %v\n%v", actions, events))
|
|
||||||
c.Assert(dieEvent, checker.False, check.Commentf("Die event not expected: %v\n%v", actions, events))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *DockerSuite) TestEventsLimit(c *check.C) {
|
func (s *DockerSuite) TestEventsLimit(c *check.C) {
|
||||||
var waitGroup sync.WaitGroup
|
var waitGroup sync.WaitGroup
|
||||||
errChan := make(chan error, 17)
|
errChan := make(chan error, 17)
|
||||||
|
|
|
@ -2403,30 +2403,6 @@ func (s *DockerSuite) TestRunExposePort(c *check.C) {
|
||||||
c.Assert(out, checker.Contains, "invalid range format for --expose")
|
c.Assert(out, checker.Contains, "invalid range format for --expose")
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *DockerSuite) TestRunUnknownCommand(c *check.C) {
|
|
||||||
out, _, _ := dockerCmdWithStdoutStderr(c, "create", "busybox", "/bin/nada")
|
|
||||||
|
|
||||||
cID := strings.TrimSpace(out)
|
|
||||||
_, _, err := dockerCmdWithError("start", cID)
|
|
||||||
|
|
||||||
// Windows and Linux are different here by architectural design. Linux will
|
|
||||||
// fail to start the container, so an error is expected. Windows will
|
|
||||||
// successfully start the container, and once started attempt to execute
|
|
||||||
// the command which will fail.
|
|
||||||
if daemonPlatform == "windows" {
|
|
||||||
// Wait for it to exit.
|
|
||||||
waitExited(cID, 30*time.Second)
|
|
||||||
c.Assert(err, check.IsNil)
|
|
||||||
} else {
|
|
||||||
c.Assert(err, check.NotNil)
|
|
||||||
}
|
|
||||||
|
|
||||||
rc := inspectField(c, cID, "State.ExitCode")
|
|
||||||
if rc == "0" {
|
|
||||||
c.Fatalf("ExitCode(%v) cannot be 0", rc)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
func (s *DockerSuite) TestRunModeIpcHost(c *check.C) {
|
func (s *DockerSuite) TestRunModeIpcHost(c *check.C) {
|
||||||
// Not applicable on Windows as uses Unix-specific capabilities
|
// Not applicable on Windows as uses Unix-specific capabilities
|
||||||
testRequires(c, SameHostDaemon, DaemonIsLinux, NotUserNamespace)
|
testRequires(c, SameHostDaemon, DaemonIsLinux, NotUserNamespace)
|
||||||
|
|
|
@ -1234,11 +1234,11 @@ func (s *DockerSuite) TestRunPidsLimit(c *check.C) {
|
||||||
testRequires(c, pidsLimit)
|
testRequires(c, pidsLimit)
|
||||||
|
|
||||||
file := "/sys/fs/cgroup/pids/pids.max"
|
file := "/sys/fs/cgroup/pids/pids.max"
|
||||||
out, _ := dockerCmd(c, "run", "--name", "skittles", "--pids-limit", "2", "busybox", "cat", file)
|
out, _ := dockerCmd(c, "run", "--name", "skittles", "--pids-limit", "4", "busybox", "cat", file)
|
||||||
c.Assert(strings.TrimSpace(out), checker.Equals, "2")
|
c.Assert(strings.TrimSpace(out), checker.Equals, "4")
|
||||||
|
|
||||||
out = inspectField(c, "skittles", "HostConfig.PidsLimit")
|
out = inspectField(c, "skittles", "HostConfig.PidsLimit")
|
||||||
c.Assert(out, checker.Equals, "2", check.Commentf("setting the pids limit failed"))
|
c.Assert(out, checker.Equals, "4", check.Commentf("setting the pids limit failed"))
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *DockerSuite) TestRunPrivilegedAllowedDevices(c *check.C) {
|
func (s *DockerSuite) TestRunPrivilegedAllowedDevices(c *check.C) {
|
||||||
|
|
|
@ -34,6 +34,7 @@ dockerd - Enable daemon mode
|
||||||
[**-H**|**--host**[=*[]*]]
|
[**-H**|**--host**[=*[]*]]
|
||||||
[**--help**]
|
[**--help**]
|
||||||
[**--icc**[=*true*]]
|
[**--icc**[=*true*]]
|
||||||
|
[**--init**[=*false*]]
|
||||||
[**--insecure-registry**[=*[]*]]
|
[**--insecure-registry**[=*[]*]]
|
||||||
[**--ip**[=*0.0.0.0*]]
|
[**--ip**[=*0.0.0.0*]]
|
||||||
[**--ip-forward**[=*true*]]
|
[**--ip-forward**[=*true*]]
|
||||||
|
@ -166,6 +167,9 @@ unix://[/path/to/socket] to use.
|
||||||
**--icc**=*true*|*false*
|
**--icc**=*true*|*false*
|
||||||
Allow unrestricted inter\-container and Docker daemon host communication. If disabled, containers can still be linked together using the **--link** option (see **docker-run(1)**). Default is true.
|
Allow unrestricted inter\-container and Docker daemon host communication. If disabled, containers can still be linked together using the **--link** option (see **docker-run(1)**). Default is true.
|
||||||
|
|
||||||
|
**--init**
|
||||||
|
Run an init process inside containers for signal forwarding and process reaping.
|
||||||
|
|
||||||
**--insecure-registry**=[]
|
**--insecure-registry**=[]
|
||||||
Enable insecure registry communication, i.e., enable un-encrypted and/or untrusted communication.
|
Enable insecure registry communication, i.e., enable un-encrypted and/or untrusted communication.
|
||||||
|
|
||||||
|
|
|
@ -59,7 +59,6 @@ func DefaultSpec() specs.Spec {
|
||||||
Options: []string{"nosuid", "noexec", "nodev"},
|
Options: []string{"nosuid", "noexec", "nodev"},
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
s.Process.Capabilities = []string{
|
s.Process.Capabilities = []string{
|
||||||
"CAP_CHOWN",
|
"CAP_CHOWN",
|
||||||
"CAP_DAC_OVERRIDE",
|
"CAP_DAC_OVERRIDE",
|
||||||
|
|
|
@ -2,10 +2,11 @@ package opts
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
"fmt"
|
||||||
fopts "github.com/docker/docker/opts"
|
|
||||||
"net"
|
"net"
|
||||||
"os"
|
"os"
|
||||||
"strings"
|
"strings"
|
||||||
|
|
||||||
|
fopts "github.com/docker/docker/opts"
|
||||||
)
|
)
|
||||||
|
|
||||||
// ValidateAttach validates that the specified string is a valid attach option.
|
// ValidateAttach validates that the specified string is a valid attach option.
|
||||||
|
|
|
@ -103,6 +103,7 @@ type ContainerOptions struct {
|
||||||
healthRetries int
|
healthRetries int
|
||||||
runtime string
|
runtime string
|
||||||
autoRemove bool
|
autoRemove bool
|
||||||
|
init bool
|
||||||
|
|
||||||
Image string
|
Image string
|
||||||
Args []string
|
Args []string
|
||||||
|
@ -243,6 +244,8 @@ func AddFlags(flags *pflag.FlagSet) *ContainerOptions {
|
||||||
flags.StringVar(&copts.shmSize, "shm-size", "", "Size of /dev/shm, default value is 64MB")
|
flags.StringVar(&copts.shmSize, "shm-size", "", "Size of /dev/shm, default value is 64MB")
|
||||||
flags.StringVar(&copts.utsMode, "uts", "", "UTS namespace to use")
|
flags.StringVar(&copts.utsMode, "uts", "", "UTS namespace to use")
|
||||||
flags.StringVar(&copts.runtime, "runtime", "", "Runtime to use for this container")
|
flags.StringVar(&copts.runtime, "runtime", "", "Runtime to use for this container")
|
||||||
|
|
||||||
|
flags.BoolVar(&copts.init, "init", false, "Run an init inside the container that forwards signals and reaps processes")
|
||||||
return copts
|
return copts
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -593,6 +596,11 @@ func Parse(flags *pflag.FlagSet, copts *ContainerOptions) (*container.Config, *c
|
||||||
Runtime: copts.runtime,
|
Runtime: copts.runtime,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// only set this value if the user provided the flag, else it should default to nil
|
||||||
|
if flags.Changed("init") {
|
||||||
|
hostConfig.Init = &copts.init
|
||||||
|
}
|
||||||
|
|
||||||
// When allocating stdin in attached mode, close stdin at client disconnect
|
// When allocating stdin in attached mode, close stdin at client disconnect
|
||||||
if config.OpenStdin && config.AttachStdin {
|
if config.OpenStdin && config.AttachStdin {
|
||||||
config.StdinOnce = true
|
config.StdinOnce = true
|
||||||
|
|
Loading…
Reference in a new issue