diff options
-rw-r--r-- | Makefile | 4 | ||||
-rw-r--r-- | cmd/podman/containers/stats.go | 9 | ||||
-rw-r--r-- | contrib/gate/Dockerfile | 2 | ||||
-rw-r--r-- | docs/source/index.rst | 2 | ||||
-rw-r--r-- | docs/tutorials/rootless_tutorial.md | 6 | ||||
-rw-r--r-- | go.mod | 2 | ||||
-rw-r--r-- | go.sum | 2 | ||||
-rwxr-xr-x | hack/podman-registry | 17 | ||||
-rw-r--r-- | pkg/bindings/connection.go | 14 | ||||
-rw-r--r-- | pkg/bindings/containers/containers.go | 61 | ||||
-rw-r--r-- | pkg/bindings/containers/logs.go | 1 | ||||
-rw-r--r-- | pkg/domain/infra/abi/containers.go | 1 | ||||
-rw-r--r-- | test/e2e/attach_test.go | 1 | ||||
-rw-r--r-- | vendor/github.com/opencontainers/selinux/go-selinux/label/label.go | 22 | ||||
-rw-r--r-- | vendor/github.com/opencontainers/selinux/go-selinux/label/label_selinux.go | 34 | ||||
-rw-r--r-- | vendor/github.com/opencontainers/selinux/go-selinux/label/label_stub.go | 4 | ||||
-rw-r--r-- | vendor/modules.txt | 2 |
17 files changed, 110 insertions, 74 deletions
@@ -318,7 +318,7 @@ localunit: test/goecho/goecho varlink_generate ginkgo \ -r \ $(TESTFLAGS) \ - --skipPackage test/e2e,pkg/apparmor,test/endpoint,pkg/bindings \ + --skipPackage test/e2e,pkg/apparmor,test/endpoint,pkg/bindings,hack \ --cover \ --covermode atomic \ --tags "$(BUILDTAGS)" \ @@ -326,7 +326,7 @@ localunit: test/goecho/goecho varlink_generate .PHONY: ginkgo ginkgo: - ginkgo -v $(TESTFLAGS) -tags "$(BUILDTAGS)" $(GINKGOTIMEOUT) -cover -flakeAttempts 3 -progress -trace -noColor -nodes 3 -debug test/e2e/. + ginkgo -v $(TESTFLAGS) -tags "$(BUILDTAGS)" $(GINKGOTIMEOUT) -cover -flakeAttempts 3 -progress -trace -noColor -nodes 3 -debug test/e2e/. hack/. .PHONY: ginkgo-remote ginkgo-remote: diff --git a/cmd/podman/containers/stats.go b/cmd/podman/containers/stats.go index 5b7f52cc7..c61b161e4 100644 --- a/cmd/podman/containers/stats.go +++ b/cmd/podman/containers/stats.go @@ -4,6 +4,7 @@ import ( "fmt" "os" "strings" + "sync" "text/tabwriter" "text/template" @@ -111,14 +112,20 @@ func stats(cmd *cobra.Command, args []string) error { } } statsOptions.StatChan = make(chan []*define.ContainerStats, 1) + wg := sync.WaitGroup{} + wg.Add(1) go func() { for reports := range statsOptions.StatChan { if err := outputStats(reports); err != nil { logrus.Error(err) } } + wg.Done() + }() - return registry.ContainerEngine().ContainerStats(registry.Context(), args, statsOptions) + err := registry.ContainerEngine().ContainerStats(registry.Context(), args, statsOptions) + wg.Wait() + return err } func outputStats(reports []*define.ContainerStats) error { diff --git a/contrib/gate/Dockerfile b/contrib/gate/Dockerfile index aa827c385..f86709b00 100644 --- a/contrib/gate/Dockerfile +++ b/contrib/gate/Dockerfile @@ -12,7 +12,7 @@ COPY . $GOSRC # Install packages from dependencies.txt, ignoring commented lines # Note: adding conmon and crun so podman command checks will work RUN dnf -y install \ - $(grep "^[^#]" $GOSRC/contrib/dependencies.txt) diffutils containers-common fuse-overlayfs conmon crun runc --exclude container-selinux \ + $(grep "^[^#]" $GOSRC/contrib/dependencies.txt) diffutils containers-common fuse-overlayfs conmon crun runc --exclude container-selinux; \ sed -i -e 's|^#mount_program|mount_program|g' /etc/containers/storage.conf \ && dnf clean all diff --git a/docs/source/index.rst b/docs/source/index.rst index 9cc8e7af8..1c46f1c8a 100644 --- a/docs/source/index.rst +++ b/docs/source/index.rst @@ -2,7 +2,7 @@ What is Podman? ================================== -Podman_ is a daemonless, open source, Linux native tool designed to make it easy to find, run, build, share and deploy applications using Open Containers Initiative (OCI_) Containers_ and `Container Images`_. Podman provides a command line interface (CLI) familiar to anyone who has used the Docker `Container Engine`_. Most users can simply alias Docker to Podman (`alias docker=podman`) without any problems. Similiar other common `Container Engines`_ (Docker, CRI-O, containerd), Podman relies on an OCI compliant `Container Runtime`_ (runc, crun, runv, etc) to interface with the operating system and create the running containers.This makes the running containers created by Podman nearly indistinguishable from those created by any other common container engine. +Podman_ is a daemonless, open source, Linux native tool designed to make it easy to find, run, build, share and deploy applications using Open Containers Initiative (OCI_) Containers_ and `Container Images`_. Podman provides a command line interface (CLI) familiar to anyone who has used the Docker `Container Engine`_. Most users can simply alias Docker to Podman (`alias docker=podman`) without any problems. Similar to other common `Container Engines`_ (Docker, CRI-O, containerd), Podman relies on an OCI compliant `Container Runtime`_ (runc, crun, runv, etc) to interface with the operating system and create the running containers.This makes the running containers created by Podman nearly indistinguishable from those created by any other common container engine. Containers under the control of Podman can either be run by root or by a non-privileged user. Podman manages the entire container ecosystem which includes pods, containers, container images, and container volumes using the libpod_ library. Podman specializes in all of the commands and functions that help you to maintain and modify OCI container images, such as pulling and tagging. It allows you to create, run, and maintain those containers and container images in a production environment. diff --git a/docs/tutorials/rootless_tutorial.md b/docs/tutorials/rootless_tutorial.md index 93726b3b1..440e12062 100644 --- a/docs/tutorials/rootless_tutorial.md +++ b/docs/tutorials/rootless_tutorial.md @@ -58,7 +58,7 @@ The number of user namespaces that are allowed on the system is specified in the ### /etc/subuid and /etc/subgid configuration -Rootless podman requires the user running it to have a range of UIDs listed in /etc/subuid and /etc/subgid files. The `shadows-utils` or `newuid` package provides these files on different distributions and they must be installed on the system. These files will need someone with root privileges on the system to add or update the entries within them. The following is a summarization from the [How does rootless Podman work?](https://opensource.com/article/19/2/how-does-rootless-podman-work) article by Dan Walsh on [opensource.com](https://opensource.com) +Rootless Podman requires the user running it to have a range of UIDs listed in /etc/subuid and /etc/subgid files. The `shadows-utils` or `newuid` package provides these files on different distributions and they must be installed on the system. These files will need someone with root privileges on the system to add or update the entries within them. The following is a summarization from the [How does rootless Podman work?](https://opensource.com/article/19/2/how-does-rootless-podman-work) article by Dan Walsh on [opensource.com](https://opensource.com) Update the /etc/subuid and /etc/subgid with fields for each user that will be allowed to create containers that look like the following. Note that the values for each user must be unique and without any overlap. If there is an overlap, there is a potential for a user to use another’s namespace and they could corrupt it. @@ -112,7 +112,7 @@ The default authorization file used by the `podman login` and `podman logout` co ### Using volumes -Rootless Podman is not, and will never be, root; it's not a setuid binary, and gains no privileges when it runs. Instead, Podman makes use of a user namespace to shift the UIDs and GIDs of a block of users it is given access to on the host (via the newuidmap and newgidmap executables) and your own user within the containers that podman creates. +Rootless Podman is not, and will never be, root; it's not a setuid binary, and gains no privileges when it runs. Instead, Podman makes use of a user namespace to shift the UIDs and GIDs of a block of users it is given access to on the host (via the newuidmap and newgidmap executables) and your own user within the containers that Podman creates. If your container runs with the root user, then `root` in the container is actually your user on the host. UID/GID 1 is the first UID/GID specified in your user's mapping in `/etc/subuid` and `/etc/subgid`, etc. If you mount a directory from the host into a container as a rootless user, and create a file in that directory as root in the container, you'll see it's actually owned by your user on the host. @@ -143,7 +143,7 @@ total 0 We do recognize that this doesn't really match how many people intend to use rootless Podman - they want their UID inside and outside the container to match. Thus, we provide the `--userns=keep-id` flag, which ensures that your user is mapped to its own UID and GID inside the container. -It is also helpful to distinguish between running podman as a rootless user, and a container which is built to run rootless. If the container you're trying you run has a `USER` which is not root, then when mounting volumes you **must** use `--userns=keep-id`. This is because the container user would not be able to become `root` and access the mounted volumes. +It is also helpful to distinguish between running Podman as a rootless user, and a container which is built to run rootless. If the container you're trying you run has a `USER` which is not root, then when mounting volumes you **must** use `--userns=keep-id`. This is because the container user would not be able to become `root` and access the mounted volumes. Other considerations in regards to volumes: @@ -42,7 +42,7 @@ require ( github.com/opencontainers/runc v1.0.0-rc9 github.com/opencontainers/runtime-spec v1.0.3-0.20200520003142-237cc4f519e2 github.com/opencontainers/runtime-tools v0.9.0 - github.com/opencontainers/selinux v1.5.1 + github.com/opencontainers/selinux v1.5.2 github.com/opentracing/opentracing-go v1.1.0 github.com/pkg/errors v0.9.1 github.com/pmezard/go-difflib v1.0.0 @@ -343,6 +343,8 @@ github.com/opencontainers/selinux v1.3.0/go.mod h1:+BLncwf63G4dgOzykXAxcmnFlUaOl github.com/opencontainers/selinux v1.4.0/go.mod h1:yTcKuYAh6R95iDpefGLQaPaRwJFwyzAJufJyiTt7s0g= github.com/opencontainers/selinux v1.5.1 h1:jskKwSMFYqyTrHEuJgQoUlTcId0av64S6EWObrIfn5Y= github.com/opencontainers/selinux v1.5.1/go.mod h1:yTcKuYAh6R95iDpefGLQaPaRwJFwyzAJufJyiTt7s0g= +github.com/opencontainers/selinux v1.5.2 h1:F6DgIsjgBIcDksLW4D5RG9bXok6oqZ3nvMwj4ZoFu/Q= +github.com/opencontainers/selinux v1.5.2/go.mod h1:yTcKuYAh6R95iDpefGLQaPaRwJFwyzAJufJyiTt7s0g= github.com/openshift/imagebuilder v1.1.4 h1:LUg8aTjyXMtlDx6IbtvaqofFGZ6aYqe+VIeATE735LM= github.com/openshift/imagebuilder v1.1.4/go.mod h1:9aJRczxCH0mvT6XQ+5STAQaPWz7OsWcU5/mRkt8IWeo= github.com/opentracing/opentracing-go v1.1.0 h1:pWlfV3Bxv7k65HYwkikxat0+s3pV4bsqf19k25Ur8rU= diff --git a/hack/podman-registry b/hack/podman-registry index 79dff8b70..fe79b7d9d 100755 --- a/hack/podman-registry +++ b/hack/podman-registry @@ -14,7 +14,7 @@ PODMAN_REGISTRY_PASS= PODMAN_REGISTRY_PORT= # Podman binary to run -PODMAN=${PODMAN:-$(type -p podman)} +PODMAN=${PODMAN:-$(dirname $0)/../bin/podman} # END defaults ############################################################################### @@ -176,11 +176,16 @@ function do_start() { -out ${AUTHDIR}/domain.crt \ -subj "/C=US/ST=Foo/L=Bar/O=Red Hat, Inc./CN=localhost" - # Store credentials where container will see them - must_pass podman run --rm \ - --entrypoint htpasswd ${PODMAN_REGISTRY_IMAGE} \ - -Bbn ${PODMAN_REGISTRY_USER} ${PODMAN_REGISTRY_PASS} \ - > $AUTHDIR/htpasswd + # Store credentials where container will see them. We can't run + # this one via must_pass because we need its stdout. + podman run --rm \ + --entrypoint htpasswd ${PODMAN_REGISTRY_IMAGE} \ + -Bbn ${PODMAN_REGISTRY_USER} ${PODMAN_REGISTRY_PASS} \ + > $AUTHDIR/htpasswd + if [ $? -ne 0 ]; then + rm -rf ${PODMAN_REGISTRY_WORKDIR} + die "Command failed: podman run [htpasswd]" + fi # In case someone needs to debug echo "${PODMAN_REGISTRY_USER}:${PODMAN_REGISTRY_PASS}" \ diff --git a/pkg/bindings/connection.go b/pkg/bindings/connection.go index d21d55beb..d30698c1d 100644 --- a/pkg/bindings/connection.go +++ b/pkg/bindings/connection.go @@ -16,7 +16,6 @@ import ( "time" "github.com/blang/semver" - "github.com/containers/libpod/pkg/api/types" jsoniter "github.com/json-iterator/go" "github.com/pkg/errors" "github.com/sirupsen/logrus" @@ -28,7 +27,7 @@ var ( basePath = &url.URL{ Scheme: "http", Host: "d", - Path: "/v" + types.MinimalAPIVersion + "/libpod", + Path: "/v" + APIVersion.String() + "/libpod", } ) @@ -157,17 +156,22 @@ func pingNewConnection(ctx context.Context) error { } if response.StatusCode == http.StatusOK { - v, err := semver.ParseTolerant(response.Header.Get("Libpod-API-Version")) + versionHdr := response.Header.Get("Libpod-API-Version") + if versionHdr == "" { + logrus.Info("Service did not provide Libpod-API-Version Header") + return nil + } + versionSrv, err := semver.ParseTolerant(versionHdr) if err != nil { return err } - switch APIVersion.Compare(v) { + switch APIVersion.Compare(versionSrv) { case 1, 0: // Server's job when client version is equal or older return nil case -1: - return errors.Errorf("server API version is too old. client %q server %q", APIVersion.String(), v.String()) + return errors.Errorf("server API version is too old. client %q server %q", APIVersion.String(), versionSrv.String()) } } return errors.Errorf("ping response was %q", response.StatusCode) diff --git a/pkg/bindings/containers/containers.go b/pkg/bindings/containers/containers.go index 39a077f36..81e213d2b 100644 --- a/pkg/bindings/containers/containers.go +++ b/pkg/bindings/containers/containers.go @@ -9,6 +9,7 @@ import ( "net/url" "os" "os/signal" + "reflect" "strconv" "strings" @@ -347,6 +348,26 @@ func ContainerInit(ctx context.Context, nameOrID string) error { // Attach attaches to a running container func Attach(ctx context.Context, nameOrId string, detachKeys *string, logs, stream *bool, stdin io.Reader, stdout io.Writer, stderr io.Writer, attachReady chan bool) error { + isSet := struct { + stdin bool + stdout bool + stderr bool + }{ + stdin: !(stdin == nil || reflect.ValueOf(stdin).IsNil()), + stdout: !(stdout == nil || reflect.ValueOf(stdout).IsNil()), + stderr: !(stderr == nil || reflect.ValueOf(stderr).IsNil()), + } + // Ensure golang can determine that interfaces are "really" nil + if !isSet.stdin { + stdin = (io.Reader)(nil) + } + if !isSet.stdout { + stdout = (io.Writer)(nil) + } + if !isSet.stderr { + stderr = (io.Writer)(nil) + } + conn, err := bindings.GetClient(ctx) if err != nil { return err @@ -368,13 +389,13 @@ func Attach(ctx context.Context, nameOrId string, detachKeys *string, logs, stre if stream != nil { params.Add("stream", fmt.Sprintf("%t", *stream)) } - if stdin != nil { + if isSet.stdin { params.Add("stdin", "true") } - if stdout != nil { + if isSet.stdout { params.Add("stdout", "true") } - if stderr != nil { + if isSet.stderr { params.Add("stderr", "true") } @@ -422,32 +443,26 @@ func Attach(ctx context.Context, nameOrId string, detachKeys *string, logs, stre }() } - response, err := conn.DoRequest(nil, http.MethodPost, "/containers/%s/attach", params, nameOrId) + response, err := conn.DoRequest(stdin, http.MethodPost, "/containers/%s/attach", params, nameOrId) if err != nil { return err } - defer response.Body.Close() + if !(response.IsSuccess() || response.IsInformational()) { + return response.Process(nil) + } + // If we are attaching around a start, we need to "signal" // back that we are in fact attached so that started does // not execute before we can attach. if attachReady != nil { attachReady <- true } - if !(response.IsSuccess() || response.IsInformational()) { - return response.Process(nil) - } - - if stdin != nil { - go func() { - _, err := io.Copy(conn, stdin) - if err != nil { - logrus.Error("failed to write input to service: " + err.Error()) - } - }() - } buffer := make([]byte, 1024) if ctnr.Config.Tty { + if !isSet.stdout { + return fmt.Errorf("container %q requires stdout to be set", ctnr.ID) + } // If not multiplex'ed, read from server and write to stdout _, err := io.Copy(stdout, response.Body) if err != nil { @@ -469,25 +484,25 @@ func Attach(ctx context.Context, nameOrId string, detachKeys *string, logs, stre } switch { - case fd == 0 && stdin != nil: + case fd == 0 && isSet.stdout: _, err := stdout.Write(frame[0:l]) if err != nil { return err } - case fd == 1 && stdout != nil: + case fd == 1 && isSet.stdout: _, err := stdout.Write(frame[0:l]) if err != nil { return err } - case fd == 2 && stderr != nil: + case fd == 2 && isSet.stderr: _, err := stderr.Write(frame[0:l]) if err != nil { return err } case fd == 3: - return errors.New("error from service in stream: " + string(frame)) + return fmt.Errorf("error from service from stream: %s", frame) default: - return fmt.Errorf("unrecognized input header: %d", fd) + return fmt.Errorf("unrecognized channel in header: %d, 0-3 supported", fd) } } } @@ -520,6 +535,7 @@ func DemuxFrame(r io.Reader, buffer []byte, length int) (frame []byte, err error if len(buffer) < length { buffer = append(buffer, make([]byte, length-len(buffer)+1)...) } + n, err := io.ReadFull(r, buffer[0:length]) if err != nil { return nil, nil @@ -528,6 +544,7 @@ func DemuxFrame(r io.Reader, buffer []byte, length int) (frame []byte, err error err = io.ErrUnexpectedEOF return } + return buffer[0:length], nil } diff --git a/pkg/bindings/containers/logs.go b/pkg/bindings/containers/logs.go index 20c8b4292..7fea30003 100644 --- a/pkg/bindings/containers/logs.go +++ b/pkg/bindings/containers/logs.go @@ -50,7 +50,6 @@ func Logs(ctx context.Context, nameOrID string, opts LogOptions, stdoutChan, std if err != nil { return err } - defer response.Body.Close() buffer := make([]byte, 1024) for { diff --git a/pkg/domain/infra/abi/containers.go b/pkg/domain/infra/abi/containers.go index b4e38ca23..e982c7c11 100644 --- a/pkg/domain/infra/abi/containers.go +++ b/pkg/domain/infra/abi/containers.go @@ -1087,6 +1087,7 @@ func (ic *ContainerEngine) Shutdown(_ context.Context) { } func (ic *ContainerEngine) ContainerStats(ctx context.Context, namesOrIds []string, options entities.ContainerStatsOptions) error { + defer close(options.StatChan) containerFunc := ic.Libpod.GetRunningContainers switch { case len(namesOrIds) > 0: diff --git a/test/e2e/attach_test.go b/test/e2e/attach_test.go index 7233d169c..e9050b53b 100644 --- a/test/e2e/attach_test.go +++ b/test/e2e/attach_test.go @@ -33,7 +33,6 @@ var _ = Describe("Podman attach", func() { podmanTest.Cleanup() f := CurrentGinkgoTestDescription() processTestResult(f) - }) It("podman attach to bogus container", func() { diff --git a/vendor/github.com/opencontainers/selinux/go-selinux/label/label.go b/vendor/github.com/opencontainers/selinux/go-selinux/label/label.go index 6e38d3d32..fea096c18 100644 --- a/vendor/github.com/opencontainers/selinux/go-selinux/label/label.go +++ b/vendor/github.com/opencontainers/selinux/go-selinux/label/label.go @@ -1,6 +1,8 @@ package label import ( + "fmt" + "github.com/opencontainers/selinux/go-selinux" ) @@ -46,7 +48,7 @@ var PidLabel = selinux.PidLabel // Init initialises the labeling system func Init() { - selinux.GetEnabled() + _ = selinux.GetEnabled() } // ClearLabels will clear all reserved labels @@ -75,3 +77,21 @@ func ReleaseLabel(label string) error { // can be used to set duplicate labels on future container processes // Deprecated: use selinux.DupSecOpt var DupSecOpt = selinux.DupSecOpt + +// FormatMountLabel returns a string to be used by the mount command. +// The format of this string will be used to alter the labeling of the mountpoint. +// The string returned is suitable to be used as the options field of the mount command. +// If you need to have additional mount point options, you can pass them in as +// the first parameter. Second parameter is the label that you wish to apply +// to all content in the mount point. +func FormatMountLabel(src, mountLabel string) string { + if mountLabel != "" { + switch src { + case "": + src = fmt.Sprintf("context=%q", mountLabel) + default: + src = fmt.Sprintf("%s,context=%q", src, mountLabel) + } + } + return src +} diff --git a/vendor/github.com/opencontainers/selinux/go-selinux/label/label_selinux.go b/vendor/github.com/opencontainers/selinux/go-selinux/label/label_selinux.go index 903829958..779e2e3a8 100644 --- a/vendor/github.com/opencontainers/selinux/go-selinux/label/label_selinux.go +++ b/vendor/github.com/opencontainers/selinux/go-selinux/label/label_selinux.go @@ -3,7 +3,6 @@ package label import ( - "fmt" "os" "os/user" "strings" @@ -43,7 +42,7 @@ func InitLabels(options []string) (plabel string, mlabel string, Err error) { if err != nil { return "", "", err } - + mcsLevel := pcon["level"] mcon, err := selinux.NewContext(mountLabel) if err != nil { return "", "", err @@ -62,16 +61,21 @@ func InitLabels(options []string) (plabel string, mlabel string, Err error) { } if con[0] == "filetype" { mcon["type"] = con[1] + continue } pcon[con[0]] = con[1] if con[0] == "level" || con[0] == "user" { mcon[con[0]] = con[1] } } - selinux.ReleaseLabel(processLabel) - processLabel = pcon.Get() - mountLabel = mcon.Get() - selinux.ReserveLabel(processLabel) + if pcon.Get() != processLabel { + if pcon["level"] != mcsLevel { + selinux.ReleaseLabel(processLabel) + } + processLabel = pcon.Get() + mountLabel = mcon.Get() + selinux.ReserveLabel(processLabel) + } } return processLabel, mountLabel, nil } @@ -82,24 +86,6 @@ func GenLabels(options string) (string, string, error) { return InitLabels(strings.Fields(options)) } -// FormatMountLabel returns a string to be used by the mount command. -// The format of this string will be used to alter the labeling of the mountpoint. -// The string returned is suitable to be used as the options field of the mount command. -// If you need to have additional mount point options, you can pass them in as -// the first parameter. Second parameter is the label that you wish to apply -// to all content in the mount point. -func FormatMountLabel(src, mountLabel string) string { - if mountLabel != "" { - switch src { - case "": - src = fmt.Sprintf("context=%q", mountLabel) - default: - src = fmt.Sprintf("%s,context=%q", src, mountLabel) - } - } - return src -} - // SetFileLabel modifies the "path" label to the specified file label func SetFileLabel(path string, fileLabel string) error { if !selinux.GetEnabled() || fileLabel == "" { diff --git a/vendor/github.com/opencontainers/selinux/go-selinux/label/label_stub.go b/vendor/github.com/opencontainers/selinux/go-selinux/label/label_stub.go index cda59d671..c2bdd35d7 100644 --- a/vendor/github.com/opencontainers/selinux/go-selinux/label/label_stub.go +++ b/vendor/github.com/opencontainers/selinux/go-selinux/label/label_stub.go @@ -15,10 +15,6 @@ func GenLabels(options string) (string, string, error) { return "", "", nil } -func FormatMountLabel(src string, mountLabel string) string { - return src -} - func SetFileLabel(path string, fileLabel string) error { return nil } diff --git a/vendor/modules.txt b/vendor/modules.txt index 2bb46598f..b3c8b96ae 100644 --- a/vendor/modules.txt +++ b/vendor/modules.txt @@ -421,7 +421,7 @@ github.com/opencontainers/runtime-tools/generate github.com/opencontainers/runtime-tools/generate/seccomp github.com/opencontainers/runtime-tools/specerror github.com/opencontainers/runtime-tools/validate -# github.com/opencontainers/selinux v1.5.1 +# github.com/opencontainers/selinux v1.5.2 github.com/opencontainers/selinux/go-selinux github.com/opencontainers/selinux/go-selinux/label github.com/opencontainers/selinux/pkg/pwalk |