aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--docs/source/markdown/.gitignore1
-rw-r--r--docs/source/markdown/options/interactive.md3
-rw-r--r--docs/source/markdown/options/preserve-fds.md5
-rw-r--r--docs/source/markdown/options/tty.md9
-rw-r--r--docs/source/markdown/podman-create.1.md.in15
-rw-r--r--docs/source/markdown/podman-exec.1.md.in12
-rw-r--r--docs/source/markdown/podman-run.1.md.in19
-rw-r--r--docs/source/markdown/podman-start.1.md.in (renamed from docs/source/markdown/podman-start.1.md)4
-rw-r--r--libpod/container_internal_common.go4
-rw-r--r--libpod/container_path_resolution.go30
-rw-r--r--libpod/container_path_resolution_test.go28
-rw-r--r--test/e2e/run_working_dir_test.go9
12 files changed, 90 insertions, 49 deletions
diff --git a/docs/source/markdown/.gitignore b/docs/source/markdown/.gitignore
index 552e6f520..69911b5b8 100644
--- a/docs/source/markdown/.gitignore
+++ b/docs/source/markdown/.gitignore
@@ -26,6 +26,7 @@ podman-push.1.md
podman-rm.1.md
podman-run.1.md
podman-search.1.md
+podman-start.1.md
podman-stop.1.md
podman-unpause.1.md
podman-update.1.md
diff --git a/docs/source/markdown/options/interactive.md b/docs/source/markdown/options/interactive.md
new file mode 100644
index 000000000..a28088368
--- /dev/null
+++ b/docs/source/markdown/options/interactive.md
@@ -0,0 +1,3 @@
+#### **--interactive**, **-i**
+
+When set to **true**, keep stdin open even if not attached. The default is **false**.
diff --git a/docs/source/markdown/options/preserve-fds.md b/docs/source/markdown/options/preserve-fds.md
new file mode 100644
index 000000000..61e33bdf4
--- /dev/null
+++ b/docs/source/markdown/options/preserve-fds.md
@@ -0,0 +1,5 @@
+#### **--preserve-fds**=*N*
+
+Pass down to the process N additional file descriptors (in addition to 0, 1, 2).
+The total FDs will be 3+N.
+(This option is not available with the remote Podman client, including Mac and Windows (excluding WSL2) machines)
diff --git a/docs/source/markdown/options/tty.md b/docs/source/markdown/options/tty.md
new file mode 100644
index 000000000..04bd8af2c
--- /dev/null
+++ b/docs/source/markdown/options/tty.md
@@ -0,0 +1,9 @@
+#### **--tty**, **-t**
+
+Allocate a pseudo-TTY. The default is **false**.
+
+When set to **true**, Podman will allocate a pseudo-tty and attach to the standard
+input of the container. This can be used, for example, to run a throwaway
+interactive shell.
+
+**NOTE**: The --tty flag prevents redirection of standard output. It combines STDOUT and STDERR, it can insert control characters, and it can hang pipes. This option should only be used when run interactively in a terminal. When feeding input to Podman, use -i only, not -it.
diff --git a/docs/source/markdown/podman-create.1.md.in b/docs/source/markdown/podman-create.1.md.in
index e407ff4d4..44e524dd6 100644
--- a/docs/source/markdown/podman-create.1.md.in
+++ b/docs/source/markdown/podman-create.1.md.in
@@ -224,9 +224,7 @@ pod when that pod is not running.
@@option init-path
-#### **--interactive**, **-i**
-
-Keep STDIN open even if not attached. The default is *false*.
+@@option interactive
@@option ip
@@ -438,16 +436,7 @@ When size is `0`, there is no limit on the amount of memory used for IPC by the
@@option tmpfs
-#### **--tty**, **-t**
-
-Allocate a pseudo-TTY. The default is *false*.
-
-When set to true Podman will allocate a pseudo-tty and attach to the standard
-input of the container. This can be used, for example, to run a throwaway
-interactive shell. The default is false.
-
-Note: The **-t** option is incompatible with a redirection of the Podman client
-standard input.
+@@option tty
@@option tz
diff --git a/docs/source/markdown/podman-exec.1.md.in b/docs/source/markdown/podman-exec.1.md.in
index 0d161ef66..a3931df1d 100644
--- a/docs/source/markdown/podman-exec.1.md.in
+++ b/docs/source/markdown/podman-exec.1.md.in
@@ -31,24 +31,18 @@ This option allows arbitrary environment variables that are available for the pr
Read in a line delimited file of environment variables.
-#### **--interactive**, **-i**
-
-When set to true, keep stdin open even if not attached. The default is *false*.
+@@option interactive
#### **--latest**, **-l**
Instead of providing the container name or ID, use the last created container. If you use methods other than Podman
to run containers such as CRI-O, the last started container could be from either of those methods. (This option is not available with the remote Podman client, including Mac and Windows (excluding WSL2) machines)
-#### **--preserve-fds**=*N*
-
-Pass down to the process N additional file descriptors (in addition to 0, 1, 2). The total FDs will be 3+N.
+@@option preserve-fds
@@option privileged
-#### **--tty**, **-t**
-
-Allocate a pseudo-TTY.
+@@option tty
#### **--user**, **-u**
diff --git a/docs/source/markdown/podman-run.1.md.in b/docs/source/markdown/podman-run.1.md.in
index d9dcd60f9..96605ee3f 100644
--- a/docs/source/markdown/podman-run.1.md.in
+++ b/docs/source/markdown/podman-run.1.md.in
@@ -245,9 +245,7 @@ Print usage statement
@@option init-path
-#### **--interactive**, **-i**
-
-When set to **true**, keep stdin open even if not attached. The default is **false**.
+@@option interactive
@@option ip
@@ -366,10 +364,7 @@ If a container is run with a pod, and the pod has an infra-container, the infra-
@@option pod-id-file.container
-#### **--preserve-fds**=*N*
-
-Pass down to the process N additional file descriptors (in addition to 0, 1, 2).
-The total FDs will be 3+N. (This option is not available with the remote Podman client, including Mac and Windows (excluding WSL2) machines)
+@@option preserve-fds
@@option privileged
@@ -478,15 +473,7 @@ Sets whether the signals sent to the **podman run** command are proxied to the c
@@option tmpfs
-#### **--tty**, **-t**
-
-Allocate a pseudo-TTY. The default is **false**.
-
-When set to **true**, Podman will allocate a pseudo-tty and attach to the standard
-input of the container. This can be used, for example, to run a throwaway
-interactive shell. The default is **false**.
-
-**NOTE**: The --tty flag prevents redirection of standard output. It combines STDOUT and STDERR, it can insert control characters, and it can hang pipes. This option should only be used when run interactively in a terminal. When feeding input to Podman, use -i only, not -it.
+@@option tty
```
echo "asdf" | podman run --rm -i someimage /bin/cat
diff --git a/docs/source/markdown/podman-start.1.md b/docs/source/markdown/podman-start.1.md.in
index fd24c6bf4..6fa41018b 100644
--- a/docs/source/markdown/podman-start.1.md
+++ b/docs/source/markdown/podman-start.1.md.in
@@ -53,9 +53,7 @@ Valid filters are listed below:
| pod | [Pod] name or full or partial ID of pod |
| network | [Network] name or full ID of network |
-#### **--interactive**, **-i**
-
-Attach container's STDIN. The default is false.
+@@option interactive
#### **--latest**, **-l**
diff --git a/libpod/container_internal_common.go b/libpod/container_internal_common.go
index c7f59aba5..9c4a3bb67 100644
--- a/libpod/container_internal_common.go
+++ b/libpod/container_internal_common.go
@@ -531,7 +531,7 @@ func (c *Container) isWorkDirSymlink(resolvedPath string) bool {
}
if resolvedSymlink != "" {
_, resolvedSymlinkWorkdir, err := c.resolvePath(c.state.Mountpoint, resolvedSymlink)
- if isPathOnVolume(c, resolvedSymlinkWorkdir) || isPathOnBindMount(c, resolvedSymlinkWorkdir) {
+ if isPathOnVolume(c, resolvedSymlinkWorkdir) || isPathOnMount(c, resolvedSymlinkWorkdir) {
// Resolved symlink exists on external volume or mount
return true
}
@@ -564,7 +564,7 @@ func (c *Container) resolveWorkDir() error {
// If the specified workdir is a subdir of a volume or mount,
// we don't need to do anything. The runtime is taking care of
// that.
- if isPathOnVolume(c, workdir) || isPathOnBindMount(c, workdir) {
+ if isPathOnVolume(c, workdir) || isPathOnMount(c, workdir) {
logrus.Debugf("Workdir %q resolved to a volume or mount", workdir)
return nil
}
diff --git a/libpod/container_path_resolution.go b/libpod/container_path_resolution.go
index 35622d623..cd86df540 100644
--- a/libpod/container_path_resolution.go
+++ b/libpod/container_path_resolution.go
@@ -119,15 +119,29 @@ func findVolume(c *Container, containerPath string) (*Volume, error) {
return nil, nil
}
+// isSubDir checks whether path is a subdirectory of root.
+func isSubDir(path, root string) bool {
+ // check if the specified container path is below a bind mount.
+ rel, err := filepath.Rel(root, path)
+ if err != nil {
+ return false
+ }
+ return rel != ".." && !strings.HasPrefix(rel, "../")
+}
+
// isPathOnVolume returns true if the specified containerPath is a subdir of any
// Volume's destination.
func isPathOnVolume(c *Container, containerPath string) bool {
cleanedContainerPath := filepath.Clean(containerPath)
for _, vol := range c.config.NamedVolumes {
- if cleanedContainerPath == filepath.Clean(vol.Dest) {
+ cleanedDestination := filepath.Clean(vol.Dest)
+ if cleanedContainerPath == cleanedDestination {
return true
}
- for dest := vol.Dest; dest != "/" && dest != "."; dest = filepath.Dir(dest) {
+ if isSubDir(cleanedContainerPath, cleanedDestination) {
+ return true
+ }
+ for dest := cleanedDestination; dest != "/" && dest != "."; dest = filepath.Dir(dest) {
if cleanedContainerPath == dest {
return true
}
@@ -152,15 +166,19 @@ func findBindMount(c *Container, containerPath string) *specs.Mount {
return nil
}
-/// isPathOnBindMount returns true if the specified containerPath is a subdir of any
+/// isPathOnMount returns true if the specified containerPath is a subdir of any
// Mount's destination.
-func isPathOnBindMount(c *Container, containerPath string) bool {
+func isPathOnMount(c *Container, containerPath string) bool {
cleanedContainerPath := filepath.Clean(containerPath)
for _, m := range c.config.Spec.Mounts {
- if cleanedContainerPath == filepath.Clean(m.Destination) {
+ cleanedDestination := filepath.Clean(m.Destination)
+ if cleanedContainerPath == cleanedDestination {
+ return true
+ }
+ if isSubDir(cleanedContainerPath, cleanedDestination) {
return true
}
- for dest := m.Destination; dest != "/" && dest != "."; dest = filepath.Dir(dest) {
+ for dest := cleanedDestination; dest != "/" && dest != "."; dest = filepath.Dir(dest) {
if cleanedContainerPath == dest {
return true
}
diff --git a/libpod/container_path_resolution_test.go b/libpod/container_path_resolution_test.go
new file mode 100644
index 000000000..f906c752d
--- /dev/null
+++ b/libpod/container_path_resolution_test.go
@@ -0,0 +1,28 @@
+package libpod
+
+import (
+ "testing"
+
+ "github.com/stretchr/testify/assert"
+)
+
+func TestIsSubDir(t *testing.T) {
+ assert.True(t, isSubDir("/foo", "/foo"))
+ assert.True(t, isSubDir("/foo/bar", "/foo"))
+ assert.True(t, isSubDir("/foo/bar", "/foo/"))
+ assert.True(t, isSubDir("/foo/bar", "/foo//"))
+ assert.True(t, isSubDir("/foo/bar/", "/foo"))
+ assert.True(t, isSubDir("/foo/bar/baz/", "/foo"))
+ assert.True(t, isSubDir("/foo/bar/baz/", "/foo/bar"))
+ assert.True(t, isSubDir("/foo/bar/baz/", "/foo/bar/"))
+ assert.False(t, isSubDir("/foo/bar/baz/", "/foobar/"))
+ assert.False(t, isSubDir("/foo/bar/baz/../../", "/foobar/"))
+ assert.False(t, isSubDir("/foo/bar/baz/", "../foo/bar"))
+ assert.False(t, isSubDir("/foo/bar/baz/", "../foo/"))
+ assert.False(t, isSubDir("/foo/bar/baz/", "../foo"))
+ assert.False(t, isSubDir("/", ".."))
+ assert.False(t, isSubDir("//", ".."))
+ assert.False(t, isSubDir("//", "../"))
+ assert.False(t, isSubDir("//", "..//"))
+ assert.True(t, isSubDir("/foo/bar/baz/../../", "/foo/"))
+}
diff --git a/test/e2e/run_working_dir_test.go b/test/e2e/run_working_dir_test.go
index ff91a420f..84792481f 100644
--- a/test/e2e/run_working_dir_test.go
+++ b/test/e2e/run_working_dir_test.go
@@ -46,6 +46,15 @@ var _ = Describe("Podman run", func() {
Expect(session).Should(Exit(126))
})
+ It("podman run a container using a --workdir under a bind mount", func() {
+ volume, err := CreateTempDirInTempDir()
+ Expect(err).To(BeNil())
+
+ session := podmanTest.Podman([]string{"run", "--volume", fmt.Sprintf("%s:/var_ovl/:O", volume), "--workdir", "/var_ovl/log", ALPINE, "true"})
+ session.WaitWithDefaultTimeout()
+ Expect(session).Should(Exit(0))
+ })
+
It("podman run a container on an image with a workdir", func() {
dockerfile := fmt.Sprintf(`FROM %s
RUN mkdir -p /home/foobar /etc/foobar; chown bin:bin /etc/foobar