diff options
25 files changed, 365 insertions, 102 deletions
@@ -5,7 +5,7 @@ Podman (the POD MANager) is a tool for managing containers and images, volumes mounted into those containers, and pods made from groups of containers. Podman is based on libpod, a library for container lifecycle management that is also contained in this repository. The libpod library provides APIs for managing containers, pods, container images, and volumes. -* [Latest Version: 2.1.0](https://github.com/containers/podman/releases/latest) +* [Latest Version: 2.1.1](https://github.com/containers/podman/releases/latest) * Latest Remote client for Windows * Latest Remote client for MacOs * Latest Static Remote client for Linux diff --git a/contrib/cirrus/logformatter b/contrib/cirrus/logformatter index f97638b6f..2ab8aa117 100755 --- a/contrib/cirrus/logformatter +++ b/contrib/cirrus/logformatter @@ -31,6 +31,12 @@ our $CSS = <<'END_CSS'; /* wrap long lines - don't require user to scroll right */ pre { line-break: normal; overflow-wrap: normal; white-space: pre-wrap; } +/* synopsis table at top */ +table.synopsis { border: none; border-collapse: collapse; margin-left: 2em; margin-top: 2ex; } +.synopsis th { font-weight: normal; font-size: 110%; text-align: right; } +.synopsis td { font-weight: bold; font-size: 120%; font-family: monospace; } + +/* test results */ .boring { color: #999; } .timestamp { color: #999; } .log-debug { color: #999; } @@ -171,9 +177,20 @@ window.addEventListener("load", scrollToBottom, false); </script> </head> <body> -<pre> <!-- begin processed output --> END_HTML + # Synopsis of this job: show job environment, links to PR and Cirrus + print { $out_fh } "<h2>Synopsis</h2>\n<hr/>\n", + job_synopsis($test_name), "<hr/>\n"; + + # FOR DEBUGGING: dump environment, but in HTML comments to not clutter + print { $out_fh } "<!-- Environment: -->\n"; + for my $e (sort keys %ENV) { + my $val = escapeHTML($ENV{$e}); + $val =~ s/--/--/g; # double dash not valid in comments + printf { $out_fh } "<!-- %-20s %s -->\n", $e, $val; + } + # State variables my $previous_timestamp = ''; # timestamp of previous line my $cirrus_task; # Cirrus task number, used for linking @@ -185,6 +202,8 @@ END_HTML my $looks_like_bats; # binary flag: for detecting BATS results my %bats_count; # For summary line: count of pass/fail/skip + print { $out_fh } "<pre> <!-- begin processed output -->\n"; + # Main loop: read input, one line at a time, and write out reformatted LINE: while (my $line = <STDIN>) { @@ -232,8 +251,9 @@ END_HTML my $css; # Readability: /long/path/to/podman -> podman (hover for full path) - $line =~ s{^(#\s+(#|\$)\s+)(\S+/)(podman\S*)\s} - {$1<span title="$3$4">$4</span> }; + # Also make it boldface, to make commands stand out + $line =~ s{^(#\s+(#|\$)\s+)(\S+/)(podman\S*)(\s.*)} + {$1<b><span title="$3$4">$4</span>$5</b>}; if ($line =~ /^ok\s.*\s# skip/) { $css = 'skipped' } elsif ($line =~ /^ok\s/) { $css = 'passed' } @@ -470,6 +490,83 @@ sub make_id { } +############################################################################### +# BEGIN job_synopsis and related helpers + +################## +# job_synopsis # Job details, links to github/cirrus +################## +sub job_synopsis { + my $subtest_name = shift; # e.g. integration_test + + my $s = <<"END_SYNOPSIS"; +<table class="synopsis"> +END_SYNOPSIS + + # PR 1234 - title of the pr + my $pr_title = escapeHTML(_env_replace("{CIRRUS_CHANGE_TITLE}")); + $s .= _tr("Github PR", sprintf("%s - %s", + _a("{CIRRUS_PR}", "https://{CIRRUS_REPO_CLONE_HOST}/{CIRRUS_REPO_FULL_NAME}/pull/{CIRRUS_PR}"), + $pr_title)); + + # PR author, if signed-off-by + if (my $msg = _env_replace("{CIRRUS_COMMIT_MESSAGE}")) { + while ($msg =~ /^Signed-off-by:\s+(\S.*\S)$/gmi) { + $s .= _tr("Author", escapeHTML($1)); + } + } + + # eg "test fedora", "special_testing_rootless" + my $test_name = _env_replace("{CIRRUS_TASK_NAME}"); + if (my $rcli = $ENV{RCLI}) { + $test_name .= " [remote]" if $rcli eq 'true'; + } + else { + $test_name .= " [no RCLI; cannot determine remote/local]"; + } + $s .= _tr("Test name", $test_name); + + # Subtest, e.g. system_test + $s .= _tr("Subtest", $subtest_name); + + # Link to further Cirrus results, e.g. other runs. + # Build is mostly boring, it's usually TASK that we want to see. + $s .= _tr("Cirrus Build ID", "<small>" . _a("{CIRRUS_BUILD_ID}", "https://cirrus-ci.com/build/{CIRRUS_BUILD_ID}") . "</small>"); + $s .= _tr("Cirrus <b>Task</b> ID", _a("{CIRRUS_TASK_ID}", "https://cirrus-ci.com/task/{CIRRUS_TASK_ID}")); + + # "none", "rootless" + $s .= _tr("Special mode", _env_replace("{SPECIALMODE}")); + + $s .= "</table>\n"; + return $s; +} + + +sub _tr { + my ($th, $td) = @_; + return "<tr><th>$th:</th><td>$td</td></tr>\n"; +} + +sub _a { + my ($name, $href) = map { _env_replace($_) } @_; + + if ($href =~ /UNDEFINED/) { + return "$name ($href)"; + } + return "<a href='$href'>$name</a>"; +} + +sub _env_replace { + my $s_in = shift; + + $s_in =~ s[\{(.*?)\}][$ENV{$1} || "[$1 UNDEFINED]"]ge; + + return $s_in; +} + +# END job_synopsis and related helpers +############################################################################### +# BEGIN html-formatting helpers sub escapeHTML { my $s = shift; @@ -492,5 +589,7 @@ sub unescapeHTML { return $s; } +# END html-formatting helpers +############################################################################### 1; diff --git a/contrib/cirrus/logformatter.t b/contrib/cirrus/logformatter.t index 2075bff96..bd4179b5e 100755 --- a/contrib/cirrus/logformatter.t +++ b/contrib/cirrus/logformatter.t @@ -96,7 +96,7 @@ ok 4 blah <span class='bats-passed'><a name='t--00001'>ok 1 hi</a></span> <span class='bats-skipped'><a name='t--00002'>ok 2 bye # skip no reason</a></span> <span class='bats-failed'><a name='t--00003'>not ok 3 fail</a></span> -<span class='bats-log'># $ <span title="/path/to/podman">podman</span> foo -bar</span> +<span class='bats-log'># $ <b><span title="/path/to/podman">podman</span> foo -bar</b></span> <span class='bats-log-esm'># #| FAIL: exit code is 123; expected 321</span> <span class='bats-passed'><a name='t--00004'>ok 4 blah</a></span> <hr/><span class='bats-summary'>Summary: <span class='bats-passed'>2 Passed</span>, <span class='bats-failed'>1 Failed</span>, <span class='bats-skipped'>1 Skipped</span>. Total tests: 4</span> @@ -147,11 +147,11 @@ $SCRIPT_BASE/integration_test.sh |& ${TIMESTAMP} <pre> <span class="timestamp">[+0103s] </span>Podman pod restart <span class="timestamp"> </span><a name='t--podman-pod-restart-single-empty-pod--1'><h2> podman pod restart single empty pod</h2></a> -<span class="timestamp"> </span> /var/tmp/go/src/github.com<a class="codelink" href='https://github.com/containers/podman/blob/40f5d8b1becd381c4e8283ed3940d09193e4fe06/test/e2e/pod_restart_test.go#L41'>/containers/libpod/test/e2e/pod_restart_test.go:41</a> +<span class="timestamp"> </span> /var/tmp/go/src/github.com<a class="codelink" href='https://github.com/containers/podman/blob/40f5d8b1becd381c4e8283ed3940d09193e4fe06/test/e2e/pod_restart_test.go#L41'>/containers/podman/test/e2e/pod_restart_test.go:41</a> <span class="timestamp"> </span>[BeforeEach] Podman pod restart -<span class="timestamp"> </span> /var/tmp/go/src/github.com<a class="codelink" href='https://github.com/containers/podman/blob/40f5d8b1becd381c4e8283ed3940d09193e4fe06/test/e2e/pod_restart_test.go#L18'>/containers/libpod/test/e2e/pod_restart_test.go:18</a> +<span class="timestamp"> </span> /var/tmp/go/src/github.com<a class="codelink" href='https://github.com/containers/podman/blob/40f5d8b1becd381c4e8283ed3940d09193e4fe06/test/e2e/pod_restart_test.go#L18'>/containers/podman/test/e2e/pod_restart_test.go:18</a> <span class="timestamp"> </span>[It] podman pod restart single empty pod -<span class="timestamp"> </span> /var/tmp/go/src/github.com<a class="codelink" href='https://github.com/containers/podman/blob/40f5d8b1becd381c4e8283ed3940d09193e4fe06/test/e2e/pod_restart_test.go#L41'>/containers/libpod/test/e2e/pod_restart_test.go:41</a> +<span class="timestamp"> </span> /var/tmp/go/src/github.com<a class="codelink" href='https://github.com/containers/podman/blob/40f5d8b1becd381c4e8283ed3940d09193e4fe06/test/e2e/pod_restart_test.go#L41'>/containers/podman/test/e2e/pod_restart_test.go:41</a> <span class="timestamp"> </span>Running: <span title="/var/tmp/go/src/github.com/containers/podman/bin/podman"><b>podman</b></span> <span class="boring" title="--storage-opt vfs.imagestore=/tmp/podman/imagecachedir --root /tmp/podman_test553496330/crio --runroot /tmp/podman_test553496330/crio-run @@ -176,7 +176,7 @@ $SCRIPT_BASE/integration_test.sh |& ${TIMESTAMP} <span class="timestamp"> </span><span class='log-warn'>Error: no containers in pod 4810be0cfbd42241e349dbe7d50fbc54405cd320a6637c65fd5323f34d64af89 have no dependencies, cannot start pod: no such container</span> <span class="timestamp"> </span>output: <span class="timestamp"> </span>[AfterEach] Podman pod restart -<span class="timestamp"> </span> /var/tmp/go/src/github.com<a class="codelink" href='https://github.com/containers/podman/blob/40f5d8b1becd381c4e8283ed3940d09193e4fe06/test/e2e/pod_restart_test.go#L28'>/containers/libpod/test/e2e/pod_restart_test.go:28</a> +<span class="timestamp"> </span> /var/tmp/go/src/github.com<a class="codelink" href='https://github.com/containers/podman/blob/40f5d8b1becd381c4e8283ed3940d09193e4fe06/test/e2e/pod_restart_test.go#L28'>/containers/podman/test/e2e/pod_restart_test.go:28</a> <span class="timestamp"> </span>Running: <span title="/var/tmp/go/src/github.com/containers/podman/bin/podman"><b>podman</b></span> <span class="boring" title="--storage-opt vfs.imagestore=/tmp/podman/imagecachedir --root /tmp/podman_test553496330/crio --runroot /tmp/podman_test553496330/crio-run diff --git a/docs/source/markdown/podman-create.1.md b/docs/source/markdown/podman-create.1.md index 4a8b311f0..28c340d2f 100644 --- a/docs/source/markdown/podman-create.1.md +++ b/docs/source/markdown/podman-create.1.md @@ -215,6 +215,10 @@ Note: if the user only has access rights via a group, accessing the device from inside a rootless container will fail. The **crun**(1) runtime offers a workaround for this by adding the option **--annotation run.oci.keep_original_groups=1**. +Podman may load kernel modules required for using the specified +device. The devices that podman will load modules when necessary are: +/dev/fuse. + **--device-cgroup-rule**="type major:minor mode" Add a rule to the cgroup allowed devices list. The rule is expected to be in the format specified in the Linux kernel documentation (Documentation/cgroup-v1/devices.txt): diff --git a/docs/source/markdown/podman-run.1.md b/docs/source/markdown/podman-run.1.md index 47aa8827f..a27b1b175 100644 --- a/docs/source/markdown/podman-run.1.md +++ b/docs/source/markdown/podman-run.1.md @@ -231,6 +231,10 @@ Note: if the user only has access rights via a group, accessing the device from inside a rootless container will fail. The **crun**(1) runtime offers a workaround for this by adding the option **--annotation run.oci.keep_original_groups=1**. +Podman may load kernel modules required for using the specified +device. The devices that podman will load modules when necessary are: +/dev/fuse. + **--device-cgroup-rule**=rule Add a rule to the cgroup allowed devices list @@ -11,8 +11,8 @@ require ( github.com/containerd/containerd v1.4.1 // indirect github.com/containernetworking/cni v0.8.0 github.com/containernetworking/plugins v0.8.7 - github.com/containers/buildah v1.16.2 - github.com/containers/common v0.23.0 + github.com/containers/buildah v1.16.4 + github.com/containers/common v0.24.0 github.com/containers/conmon v2.0.20+incompatible github.com/containers/image/v5 v5.6.0 github.com/containers/psgo v1.5.1 @@ -70,11 +70,11 @@ github.com/containernetworking/cni v0.8.0 h1:BT9lpgGoH4jw3lFC7Odz2prU5ruiYKcgAjM github.com/containernetworking/cni v0.8.0/go.mod h1:LGwApLUm2FpoOfxTDEeq8T9ipbpZ61X79hmU3w8FmsY= github.com/containernetworking/plugins v0.8.7 h1:bU7QieuAp+sACI2vCzESJ3FoT860urYP+lThyZkb/2M= github.com/containernetworking/plugins v0.8.7/go.mod h1:R7lXeZaBzpfqapcAbHRW8/CYwm0dHzbz0XEjofx0uB0= -github.com/containers/buildah v1.16.2 h1:u8RA0r9sp3d5df/QRm0glG7L6ZN40UVJcYedwcZGt8w= -github.com/containers/buildah v1.16.2/go.mod h1:i1XqXgpCROnfcq4oNtfrFEk7UzNDxLJ/PZ+CnPyoIq8= +github.com/containers/buildah v1.16.4 h1:bxthp2FoGcpc2O/RyvbGUAZoefmc5hRBqWQi3BjRu7w= +github.com/containers/buildah v1.16.4/go.mod h1:i1XqXgpCROnfcq4oNtfrFEk7UzNDxLJ/PZ+CnPyoIq8= github.com/containers/common v0.21.0/go.mod h1:8w8SVwc+P2p1MOnRMbSKNWXt1Iwd2bKFu2LLZx55DTM= -github.com/containers/common v0.23.0 h1:+g4mI3wUYSzOtoWU9TNVoV4K52/aN6JEz0qs1YdPEe8= -github.com/containers/common v0.23.0/go.mod h1:E56/N0beWGf+lrrJX32atuo2hkjzHwSC8n1vCG+TAR0= +github.com/containers/common v0.24.0 h1:5C03ROzmRvZCyooNJVkZ4Q8T2d04g+VVyPMQ428XC4Y= +github.com/containers/common v0.24.0/go.mod h1:BFRo6uRh1TbkZgR2oYTILxc2BNZTBtBffa9xtu881QI= github.com/containers/conmon v2.0.20+incompatible h1:YbCVSFSCqFjjVwHTPINGdMX1F6JXHGTUje2ZYobNrkg= github.com/containers/conmon v2.0.20+incompatible/go.mod h1:hgwZ2mtuDrppv78a/cOBNiCm6O0UMWGx1mu7P00nu5I= github.com/containers/image/v5 v5.5.2/go.mod h1:4PyNYR0nwlGq/ybVJD9hWlhmIsNra4Q8uOQX2s6E2uM= diff --git a/libpod/container_log_linux.go b/libpod/container_log_linux.go index 73c2df76e..d895171cf 100644 --- a/libpod/container_log_linux.go +++ b/libpod/container_log_linux.go @@ -33,7 +33,7 @@ const ( func (c *Container) readFromJournal(ctx context.Context, options *logs.LogOptions, logChannel chan *logs.LogLine) error { var config journal.JournalReaderConfig if options.Tail < 0 { - config.NumFromTail = math.MaxUint64 + config.NumFromTail = 0 } else { config.NumFromTail = uint64(options.Tail) } diff --git a/libpod/image/prune.go b/libpod/image/prune.go index fcc65fb03..b38265a7e 100644 --- a/libpod/image/prune.go +++ b/libpod/image/prune.go @@ -125,29 +125,39 @@ func (ir *Runtime) PruneImages(ctx context.Context, all bool, filter []string) ( filterFuncs = append(filterFuncs, generatedFunc) } - pruneImages, err := ir.GetPruneImages(ctx, all, filterFuncs) - if err != nil { - return nil, errors.Wrap(err, "unable to get images to prune") - } - prunedCids := make([]string, 0, len(pruneImages)) - for _, p := range pruneImages { - repotags, err := p.RepoTags() + pruned := []string{} + prev := 0 + for { + toPrune, err := ir.GetPruneImages(ctx, all, filterFuncs) if err != nil { - return nil, err + return nil, errors.Wrap(err, "unable to get images to prune") } - if err := p.Remove(ctx, true); err != nil { - if errors.Cause(err) == storage.ErrImageUsedByContainer { - logrus.Warnf("Failed to prune image %s as it is in use: %v.\nA container associated with containers/storage i.e. Buildah, CRI-O, etc., maybe associated with this image.\nUsing the rmi command with the --force option will remove the container and image, but may cause failures for other dependent systems.", p.ID(), err) - continue - } - return nil, errors.Wrap(err, "failed to prune image") + numImages := len(toPrune) + if numImages == 0 || numImages == prev { + // If there's nothing left to do, return. + break } - defer p.newImageEvent(events.Prune) - nameOrID := p.ID() - if len(repotags) > 0 { - nameOrID = repotags[0] + prev = numImages + for _, img := range toPrune { + repotags, err := img.RepoTags() + if err != nil { + return nil, err + } + if err := img.Remove(ctx, false); err != nil { + if errors.Cause(err) == storage.ErrImageUsedByContainer { + logrus.Warnf("Failed to prune image %s as it is in use: %v.\nA container associated with containers/storage (e.g., Buildah, CRI-O, etc.) maybe associated with this image.\nUsing the rmi command with the --force option will remove the container and image, but may cause failures for other dependent systems.", img.ID(), err) + continue + } + return nil, errors.Wrap(err, "failed to prune image") + } + defer img.newImageEvent(events.Prune) + nameOrID := img.ID() + if len(repotags) > 0 { + nameOrID = repotags[0] + } + pruned = append(pruned, nameOrID) } - prunedCids = append(prunedCids, nameOrID) + } - return prunedCids, nil + return pruned, nil } diff --git a/pkg/domain/infra/abi/images.go b/pkg/domain/infra/abi/images.go index d56dc7d94..965c63bec 100644 --- a/pkg/domain/infra/abi/images.go +++ b/pkg/domain/infra/abi/images.go @@ -46,11 +46,7 @@ func (ir *ImageEngine) Exists(_ context.Context, nameOrID string) (*entities.Boo } func (ir *ImageEngine) Prune(ctx context.Context, opts entities.ImagePruneOptions) (*entities.ImagePruneReport, error) { - return ir.pruneImagesHelper(ctx, opts.All, opts.Filter) -} - -func (ir *ImageEngine) pruneImagesHelper(ctx context.Context, all bool, filters []string) (*entities.ImagePruneReport, error) { - results, err := ir.Libpod.ImageRuntime().PruneImages(ctx, all, filters) + results, err := ir.Libpod.ImageRuntime().PruneImages(ctx, opts.All, opts.Filter) if err != nil { return nil, err } diff --git a/pkg/specgen/generate/config_linux.go b/pkg/specgen/generate/config_linux.go index 1d5dcd8e7..fac02ad01 100644 --- a/pkg/specgen/generate/config_linux.go +++ b/pkg/specgen/generate/config_linux.go @@ -248,6 +248,13 @@ func addDevice(g *generate.Generator, device string) error { } g.Config.Mounts = append(g.Config.Mounts, devMnt) return nil + } else if src == "/dev/fuse" { + // if the user is asking for fuse inside the container + // make sure the module is loaded. + f, err := unix.Open(src, unix.O_RDONLY|unix.O_NONBLOCK, 0) + if err == nil { + unix.Close(f) + } } dev.Path = dst g.AddDevice(*dev) diff --git a/test/e2e/logs_test.go b/test/e2e/logs_test.go index 3aa3cf409..67ab71d20 100644 --- a/test/e2e/logs_test.go +++ b/test/e2e/logs_test.go @@ -203,6 +203,7 @@ var _ = Describe("Podman logs", func() { results.WaitWithDefaultTimeout() Expect(results).To(Exit(0)) Expect(len(results.OutputToStringArray())).To(Equal(3)) + Expect(results.OutputToString()).To(Equal("podman podman podman")) }) It("using journald tail two lines", func() { diff --git a/test/system/035-logs.bats b/test/system/035-logs.bats index cbb2091e5..130bc5243 100644 --- a/test/system/035-logs.bats +++ b/test/system/035-logs.bats @@ -50,4 +50,15 @@ ${cid[1]} c ${cid[0]} d" "Sequential output from logs" } +@test "podman logs over journald" { + msg=$(random_string 20) + + run_podman run --name myctr --log-driver journald $IMAGE echo $msg + + run_podman logs myctr + is "$output" "$msg" "check that log output equals the container output" + + run_podman rm myctr +} + # vim: filetype=sh diff --git a/test/system/500-networking.bats b/test/system/500-networking.bats index 150626ded..a923402ac 100644 --- a/test/system/500-networking.bats +++ b/test/system/500-networking.bats @@ -82,6 +82,8 @@ load helpers # "network create" now works rootless, with the help of a special container @test "podman network create" { + skip_if_remote "FIXME: pending #7808" + local mynetname=testnet-$(random_string 10) local mysubnet=$(random_rfc1918_subnet) diff --git a/vendor/github.com/containers/buildah/.golangci.yml b/vendor/github.com/containers/buildah/.golangci.yml index 888d89afa..f8247f049 100644 --- a/vendor/github.com/containers/buildah/.golangci.yml +++ b/vendor/github.com/containers/buildah/.golangci.yml @@ -7,38 +7,26 @@ run: # Don't exceed number of threads available when running under CI concurrency: 4 linters: - disable-all: true - enable: - - bodyclose + enable-all: true + disable: + # All these break for one reason or another - deadcode - depguard - dupl - errcheck - - gofmt - - goimports + - gochecknoglobals + - gochecknoinits + - goconst + - gocritic + - gocyclo - golint - # Broken? Unpredictably dies w/o any error well before deadline/timeout expires - # - gosimple - - govet - - ineffassign - - interfacer - - misspell - - nakedret - - staticcheck + - gosec + - gosimple + - lll + - maligned + - prealloc + - scopelint - structcheck - - stylecheck - typecheck - unconvert - - unparam - - unused - varcheck - # - gochecknoglobals - # - gochecknoinits - # - goconst - # - gocritic - # - gocyclo - # - gosec - # - lll - # - maligned - # - prealloc - # - scopelint diff --git a/vendor/github.com/containers/buildah/CHANGELOG.md b/vendor/github.com/containers/buildah/CHANGELOG.md index 6168dc317..ca6a98889 100644 --- a/vendor/github.com/containers/buildah/CHANGELOG.md +++ b/vendor/github.com/containers/buildah/CHANGELOG.md @@ -2,10 +2,21 @@ # Changelog +## v1.16.4 (2020-10-01) + ADD: only expand archives at the right time + +## v1.16.3 (2020-09-30) + Lint: Use same linters as podman + add: preserve ownerships and permissions on ADDed archives + chroot: fix handling of errno seccomp rules + git-validation.sh: set the base for comparison to v1.16.0 + chroot: create bind mount targets 0755 instead of 0700 + ## v1.16.2 (2020-09-21) Add(): fix handling of relative paths with no ContextDir ## v1.16.1 (2020-09-10) + CI: use release-1.16 as the basis for validation tests copier.Get(): hard link targets shouldn't be relative paths ## v1.16.0 (2020-09-03) diff --git a/vendor/github.com/containers/buildah/add.go b/vendor/github.com/containers/buildah/add.go index bbfdda9c1..a3f3c7a37 100644 --- a/vendor/github.com/containers/buildah/add.go +++ b/vendor/github.com/containers/buildah/add.go @@ -33,7 +33,8 @@ type AddAndCopyOptions struct { Chown string // PreserveOwnership, if Chown is not set, tells us to avoid setting // ownership of copied items to 0:0, instead using whatever ownership - // information is already set. Not meaningful for remote sources. + // information is already set. Not meaningful for remote sources or + // local archives that we extract. PreserveOwnership bool // All of the data being copied will pass through Hasher, if set. // If the sources are URLs or files, their contents will be passed to @@ -210,7 +211,6 @@ func (b *Builder) Add(destination string, extract bool, options AddAndCopyOption // Find out which user (and group) the destination should belong to. var chownDirs, chownFiles *idtools.IDPair - var chmodDirs, chmodFiles *os.FileMode var user specs.User if options.Chown != "" { user, _, err = b.user(mountPoint, options.Chown) @@ -319,9 +319,9 @@ func (b *Builder) Add(destination string, extract bool, options AddAndCopyOption UIDMap: destUIDMap, GIDMap: destGIDMap, ChownDirs: chownDirs, - ChmodDirs: chmodDirs, + ChmodDirs: nil, ChownFiles: chownFiles, - ChmodFiles: chmodFiles, + ChmodFiles: nil, } putErr = copier.Put(mountPoint, extractDirectory, putOptions, io.TeeReader(pipeReader, hasher)) } @@ -396,6 +396,10 @@ func (b *Builder) Add(destination string, extract bool, options AddAndCopyOption GIDMap: srcGIDMap, Excludes: options.Excludes, ExpandArchives: extract, + ChownDirs: chownDirs, + ChmodDirs: nil, + ChownFiles: chownFiles, + ChmodFiles: nil, StripSetuidBit: options.StripSetuidBit, StripSetgidBit: options.StripSetgidBit, StripStickyBit: options.StripStickyBit, @@ -423,12 +427,14 @@ func (b *Builder) Add(destination string, extract bool, options AddAndCopyOption _, putErr = io.Copy(hasher, pipeReader) } else { putOptions := copier.PutOptions{ - UIDMap: destUIDMap, - GIDMap: destGIDMap, - ChownDirs: chownDirs, - ChmodDirs: chmodDirs, - ChownFiles: chownFiles, - ChmodFiles: chmodFiles, + UIDMap: destUIDMap, + GIDMap: destGIDMap, + DefaultDirOwner: chownDirs, + DefaultDirMode: nil, + ChownDirs: nil, + ChmodDirs: nil, + ChownFiles: nil, + ChmodFiles: nil, } putErr = copier.Put(mountPoint, extractDirectory, putOptions, io.TeeReader(pipeReader, hasher)) } diff --git a/vendor/github.com/containers/buildah/buildah.go b/vendor/github.com/containers/buildah/buildah.go index e63cfff3a..2ac0210bd 100644 --- a/vendor/github.com/containers/buildah/buildah.go +++ b/vendor/github.com/containers/buildah/buildah.go @@ -28,7 +28,7 @@ const ( Package = "buildah" // Version for the Package. Bump version in contrib/rpm/buildah.spec // too. - Version = "1.16.2" + Version = "1.16.4" // The value we use to identify what type of information, currently a // serialized Builder structure, we are using as per-container state. // This should only be changed when we make incompatible changes to diff --git a/vendor/github.com/containers/buildah/changelog.txt b/vendor/github.com/containers/buildah/changelog.txt index d34ede417..048dc61c1 100644 --- a/vendor/github.com/containers/buildah/changelog.txt +++ b/vendor/github.com/containers/buildah/changelog.txt @@ -1,7 +1,18 @@ +- Changelog for v1.16.4 (2020-10-01) + * ADD: only expand archives at the right time + +- Changelog for v1.16.3 (2020-09-30) + * Lint: Use same linters as podman + * add: preserve ownerships and permissions on ADDed archives + * chroot: fix handling of errno seccomp rules + * git-validation.sh: set the base for comparison to v1.16.0 + * chroot: create bind mount targets 0755 instead of 0700 + - Changelog for v1.16.2 (2020-09-21) * Add(): fix handling of relative paths with no ContextDir - Changelog for v1.16.1 (2020-09-10) + * CI: use release-1.16 as the basis for validation tests * copier.Get(): hard link targets shouldn't be relative paths - Changelog for v1.16.0 (2020-09-03) diff --git a/vendor/github.com/containers/buildah/chroot/run.go b/vendor/github.com/containers/buildah/chroot/run.go index 7a83a73a3..e8842f7a9 100644 --- a/vendor/github.com/containers/buildah/chroot/run.go +++ b/vendor/github.com/containers/buildah/chroot/run.go @@ -1047,7 +1047,7 @@ func setupChrootBindMounts(spec *specs.Spec, bundlePath string) (undoBinds func( subDev := filepath.Join(spec.Root.Path, "/dev") if err := unix.Mount("/dev", subDev, "bind", devFlags, ""); err != nil { if os.IsNotExist(err) { - err = os.Mkdir(subDev, 0700) + err = os.Mkdir(subDev, 0755) if err == nil { err = unix.Mount("/dev", subDev, "bind", devFlags, "") } @@ -1071,7 +1071,7 @@ func setupChrootBindMounts(spec *specs.Spec, bundlePath string) (undoBinds func( subProc := filepath.Join(spec.Root.Path, "/proc") if err := unix.Mount("/proc", subProc, "bind", procFlags, ""); err != nil { if os.IsNotExist(err) { - err = os.Mkdir(subProc, 0700) + err = os.Mkdir(subProc, 0755) if err == nil { err = unix.Mount("/proc", subProc, "bind", procFlags, "") } @@ -1086,7 +1086,7 @@ func setupChrootBindMounts(spec *specs.Spec, bundlePath string) (undoBinds func( subSys := filepath.Join(spec.Root.Path, "/sys") if err := unix.Mount("/sys", subSys, "bind", sysFlags, ""); err != nil { if os.IsNotExist(err) { - err = os.Mkdir(subSys, 0700) + err = os.Mkdir(subSys, 0755) if err == nil { err = unix.Mount("/sys", subSys, "bind", sysFlags, "") } @@ -1163,15 +1163,15 @@ func setupChrootBindMounts(spec *specs.Spec, bundlePath string) (undoBinds func( } // The target isn't there yet, so create it. if srcinfo.IsDir() { - if err = os.MkdirAll(target, 0111); err != nil { + if err = os.MkdirAll(target, 0755); err != nil { return undoBinds, errors.Wrapf(err, "error creating mountpoint %q in mount namespace", target) } } else { - if err = os.MkdirAll(filepath.Dir(target), 0111); err != nil { + if err = os.MkdirAll(filepath.Dir(target), 0755); err != nil { return undoBinds, errors.Wrapf(err, "error ensuring parent of mountpoint %q (%q) is present in mount namespace", target, filepath.Dir(target)) } var file *os.File - if file, err = os.OpenFile(target, os.O_WRONLY|os.O_CREATE, 0); err != nil { + if file, err = os.OpenFile(target, os.O_WRONLY|os.O_CREATE, 0755); err != nil { return undoBinds, errors.Wrapf(err, "error creating mountpoint %q in mount namespace", target) } file.Close() diff --git a/vendor/github.com/containers/buildah/chroot/seccomp.go b/vendor/github.com/containers/buildah/chroot/seccomp.go index 12a9b0032..1ca0a159e 100644 --- a/vendor/github.com/containers/buildah/chroot/seccomp.go +++ b/vendor/github.com/containers/buildah/chroot/seccomp.go @@ -15,18 +15,28 @@ func setSeccomp(spec *specs.Spec) error { if spec.Linux.Seccomp == nil { return nil } - mapAction := func(specAction specs.LinuxSeccompAction) libseccomp.ScmpAction { + mapAction := func(specAction specs.LinuxSeccompAction, errnoRet *uint) libseccomp.ScmpAction { switch specAction { case specs.ActKill: return libseccomp.ActKill case specs.ActTrap: return libseccomp.ActTrap case specs.ActErrno: - return libseccomp.ActErrno + action := libseccomp.ActErrno + if errnoRet != nil { + action = action.SetReturnCode(int16(*errnoRet)) + } + return action case specs.ActTrace: return libseccomp.ActTrace case specs.ActAllow: return libseccomp.ActAllow + case specs.ActLog: + return libseccomp.ActLog + case specs.ActKillProcess: + return libseccomp.ActKillProcess + default: + logrus.Errorf("unmappable action %v", specAction) } return libseccomp.ActInvalid } @@ -68,6 +78,8 @@ func setSeccomp(spec *specs.Spec) error { /* fallthrough */ /* for now */ case specs.ArchPARISC64: /* fallthrough */ /* for now */ + default: + logrus.Errorf("unmappable arch %v", specArch) } return libseccomp.ArchInvalid } @@ -87,11 +99,13 @@ func setSeccomp(spec *specs.Spec) error { return libseccomp.CompareGreater case specs.OpMaskedEqual: return libseccomp.CompareMaskedEqual + default: + logrus.Errorf("unmappable op %v", op) } return libseccomp.CompareInvalid } - filter, err := libseccomp.NewFilter(mapAction(spec.Linux.Seccomp.DefaultAction)) + filter, err := libseccomp.NewFilter(mapAction(spec.Linux.Seccomp.DefaultAction, nil)) if err != nil { return errors.Wrapf(err, "error creating seccomp filter with default action %q", spec.Linux.Seccomp.DefaultAction) } @@ -112,7 +126,7 @@ func setSeccomp(spec *specs.Spec) error { } for scnum := range scnames { if len(rule.Args) == 0 { - if err = filter.AddRule(scnum, mapAction(rule.Action)); err != nil { + if err = filter.AddRule(scnum, mapAction(rule.Action, rule.ErrnoRet)); err != nil { return errors.Wrapf(err, "error adding a rule (%q:%q) to seccomp filter", scnames[scnum], rule.Action) } continue @@ -129,7 +143,7 @@ func setSeccomp(spec *specs.Spec) error { } conditions = append(conditions, condition) } - if err = filter.AddRuleConditional(scnum, mapAction(rule.Action), conditions); err != nil { + if err = filter.AddRuleConditional(scnum, mapAction(rule.Action, rule.ErrnoRet), conditions); err != nil { // Okay, if the rules specify multiple equality // checks, assume someone thought that they // were OR'd, when in fact they're ordinarily @@ -137,7 +151,7 @@ func setSeccomp(spec *specs.Spec) error { // different rules to get that OR effect. if len(rule.Args) > 1 && opsAreAllEquality && err.Error() == "two checks on same syscall argument" { for i := range conditions { - if err = filter.AddRuleConditional(scnum, mapAction(rule.Action), conditions[i:i+1]); err != nil { + if err = filter.AddRuleConditional(scnum, mapAction(rule.Action, rule.ErrnoRet), conditions[i:i+1]); err != nil { return errors.Wrapf(err, "error adding a conditional rule (%q:%q[%d]) to seccomp filter", scnames[scnum], rule.Action, i) } } diff --git a/vendor/github.com/containers/buildah/copier/copier.go b/vendor/github.com/containers/buildah/copier/copier.go index a980fe292..1021aeb6f 100644 --- a/vendor/github.com/containers/buildah/copier/copier.go +++ b/vendor/github.com/containers/buildah/copier/copier.go @@ -222,6 +222,10 @@ type GetOptions struct { UIDMap, GIDMap []idtools.IDMap // map from hostIDs to containerIDs in the output archive Excludes []string // contents to pretend don't exist, using the OS-specific path separator ExpandArchives bool // extract the contents of named items that are archives + ChownDirs *idtools.IDPair // set ownership on directories. no effect on archives being extracted + ChmodDirs *os.FileMode // set permissions on directories. no effect on archives being extracted + ChownFiles *idtools.IDPair // set ownership of files. no effect on archives being extracted + ChmodFiles *os.FileMode // set permissions on files. no effect on archives being extracted StripSetuidBit bool // strip the setuid bit off of items being copied. no effect on archives being extracted StripSetgidBit bool // strip the setgid bit off of items being copied. no effect on archives being extracted StripStickyBit bool // strip the sticky bit off of items being copied. no effect on archives being extracted @@ -265,6 +269,8 @@ func Get(root string, directory string, options GetOptions, globs []string, bulk // PutOptions controls parts of Put()'s behavior. type PutOptions struct { UIDMap, GIDMap []idtools.IDMap // map from containerIDs to hostIDs when writing contents to disk + DefaultDirOwner *idtools.IDPair // set ownership of implicitly-created directories, default is ChownDirs, or 0:0 if ChownDirs not set + DefaultDirMode *os.FileMode // set permissions on implicitly-created directories, default is ChmodDirs, or 0755 if ChmodDirs not set ChownDirs *idtools.IDPair // set ownership of newly-created directories ChmodDirs *os.FileMode // set permissions on newly-created directories ChownFiles *idtools.IDPair // set ownership of newly-created files @@ -1032,6 +1038,9 @@ func copierHandlerGet(bulkWriter io.Writer, req request, pm *fileutils.PatternMa } // evaluate excludes relative to the root directory if info.Mode().IsDir() { + // we don't expand any of the contents that are archives + options := req.GetOptions + options.ExpandArchives = false walkfn := func(path string, info os.FileInfo, err error) error { // compute the path of this item // relative to the top-level directory, @@ -1073,7 +1082,7 @@ func copierHandlerGet(bulkWriter io.Writer, req request, pm *fileutils.PatternMa symlinkTarget = target } // add the item to the outgoing tar stream - return copierHandlerGetOne(info, symlinkTarget, rel, path, req.GetOptions, tw, hardlinkChecker, idMappings) + return copierHandlerGetOne(info, symlinkTarget, rel, path, options, tw, hardlinkChecker, idMappings) } // walk the directory tree, checking/adding items individually if err := filepath.Walk(item, walkfn); err != nil { @@ -1193,6 +1202,22 @@ func copierHandlerGetOne(srcfi os.FileInfo, symlinkTarget, name, contentPath str return errors.Wrapf(err, "error mapping host filesystem owners %#v to container filesystem owners", hostPair) } } + // force ownership and/or permissions, if requested + if hdr.Typeflag == tar.TypeDir { + if options.ChownDirs != nil { + hdr.Uid, hdr.Gid = options.ChownDirs.UID, options.ChownDirs.GID + } + if options.ChmodDirs != nil { + hdr.Mode = int64(*options.ChmodDirs) + } + } else { + if options.ChownFiles != nil { + hdr.Uid, hdr.Gid = options.ChownFiles.UID, options.ChownFiles.GID + } + if options.ChmodFiles != nil { + hdr.Mode = int64(*options.ChmodFiles) + } + } // output the header if err = tw.WriteHeader(hdr); err != nil { return errors.Wrapf(err, "error writing header for %s (%s)", contentPath, hdr.Name) @@ -1220,13 +1245,20 @@ func copierHandlerPut(bulkReader io.Reader, req request, idMappings *idtools.IDM errorResponse := func(fmtspec string, args ...interface{}) (*response, func() error, error) { return &response{Error: fmt.Sprintf(fmtspec, args...), Put: putResponse{}}, nil, nil } - dirUID, dirGID := 0, 0 + dirUID, dirGID, defaultDirUID, defaultDirGID := 0, 0, 0, 0 if req.PutOptions.ChownDirs != nil { dirUID, dirGID = req.PutOptions.ChownDirs.UID, req.PutOptions.ChownDirs.GID + defaultDirUID, defaultDirGID = dirUID, dirGID } - dirMode := os.FileMode(0755) + defaultDirMode := os.FileMode(0755) if req.PutOptions.ChmodDirs != nil { - dirMode = *req.PutOptions.ChmodDirs + defaultDirMode = *req.PutOptions.ChmodDirs + } + if req.PutOptions.DefaultDirOwner != nil { + defaultDirUID, defaultDirGID = req.PutOptions.DefaultDirOwner.UID, req.PutOptions.DefaultDirOwner.GID + } + if req.PutOptions.DefaultDirMode != nil { + defaultDirMode = *req.PutOptions.DefaultDirMode } var fileUID, fileGID *int if req.PutOptions.ChownFiles != nil { @@ -1258,11 +1290,11 @@ func copierHandlerPut(bulkReader io.Reader, req request, idMappings *idtools.IDM subdir = filepath.Join(subdir, component) path := filepath.Join(req.Root, subdir) if err := os.Mkdir(path, 0700); err == nil { - if err = lchown(path, dirUID, dirGID); err != nil { - return errors.Wrapf(err, "copier: put: error setting owner of %q to %d:%d", path, dirUID, dirGID) + if err = lchown(path, defaultDirUID, defaultDirGID); err != nil { + return errors.Wrapf(err, "copier: put: error setting owner of %q to %d:%d", path, defaultDirUID, defaultDirGID) } - if err = os.Chmod(path, dirMode); err != nil { - return errors.Wrapf(err, "copier: put: error setting permissions on %q to 0%o", path, dirMode) + if err = os.Chmod(path, defaultDirMode); err != nil { + return errors.Wrapf(err, "copier: put: error setting permissions on %q to 0%o", path, defaultDirMode) } } else { if !os.IsExist(err) { diff --git a/vendor/github.com/containers/common/pkg/completion/completion.go b/vendor/github.com/containers/common/pkg/completion/completion.go index 6e7ddff30..07451e992 100644 --- a/vendor/github.com/containers/common/pkg/completion/completion.go +++ b/vendor/github.com/containers/common/pkg/completion/completion.go @@ -1,6 +1,14 @@ package completion -import "github.com/spf13/cobra" +import ( + "bufio" + "os" + "strings" + "unicode" + + "github.com/containers/common/pkg/capabilities" + "github.com/spf13/cobra" +) // FlagCompletions - hold flag completion functions to be applied later with CompleteCommandFlags() type FlagCompletions map[string]func(cmd *cobra.Command, args []string, toComplete string) ([]string, cobra.ShellCompDirective) @@ -24,3 +32,62 @@ func AutocompleteNone(cmd *cobra.Command, args []string, toComplete string) ([]s func AutocompleteDefault(cmd *cobra.Command, args []string, toComplete string) ([]string, cobra.ShellCompDirective) { return nil, cobra.ShellCompDirectiveDefault } + +// AutocompleteCapabilities - Autocomplete linux capabilities options. +// Used by --cap-add and --cap-drop. +func AutocompleteCapabilities(cmd *cobra.Command, args []string, toComplete string) ([]string, cobra.ShellCompDirective) { + caps := capabilities.AllCapabilities() + + // convertCase will convert a string to lowercase only if the user input is lowercase + convertCase := func(s string) string { return s } + if len(toComplete) > 0 && unicode.IsLower(rune(toComplete[0])) { + convertCase = strings.ToLower + } + + // offset is used to trim "CAP_" if the user doesn't type CA... or ca... + offset := 0 + if !strings.HasPrefix(toComplete, convertCase("CA")) { + // setting the offset to 4 is safe since each cap starts with CAP_ + offset = 4 + } + + var completions []string + for _, cap := range caps { + completions = append(completions, convertCase(cap)[offset:]) + } + + // add ALL here which is also a valid argument + completions = append(completions, convertCase(capabilities.All)) + return completions, cobra.ShellCompDirectiveNoFileComp +} + +// autocompleteSubIDName - autocomplete the names in /etc/subuid or /etc/subgid +func autocompleteSubIDName(filename string) ([]string, cobra.ShellCompDirective) { + file, err := os.Open(filename) + if err != nil { + return nil, cobra.ShellCompDirectiveError + } + defer file.Close() + + var names []string + scanner := bufio.NewScanner(file) + for scanner.Scan() { + name := strings.SplitN(scanner.Text(), ":", 2)[0] + names = append(names, name) + } + if err = scanner.Err(); err != nil { + return nil, cobra.ShellCompDirectiveError + } + + return names, cobra.ShellCompDirectiveNoFileComp +} + +// AutocompleteSubgidName - Autocomplete subgidname based on the names in the /etc/subgid file. +func AutocompleteSubgidName(cmd *cobra.Command, args []string, toComplete string) ([]string, cobra.ShellCompDirective) { + return autocompleteSubIDName("/etc/subgid") +} + +// AutocompleteSubuidName - Autocomplete subuidname based on the names in the /etc/subuid file. +func AutocompleteSubuidName(cmd *cobra.Command, args []string, toComplete string) ([]string, cobra.ShellCompDirective) { + return autocompleteSubIDName("/etc/subuid") +} diff --git a/vendor/github.com/containers/common/version/version.go b/vendor/github.com/containers/common/version/version.go index eaa728791..8e69c7daf 100644 --- a/vendor/github.com/containers/common/version/version.go +++ b/vendor/github.com/containers/common/version/version.go @@ -1,4 +1,4 @@ package version // Version is the version of the build. -const Version = "0.23.0" +const Version = "0.24.0" diff --git a/vendor/modules.txt b/vendor/modules.txt index 3c7749b57..e1c2b6300 100644 --- a/vendor/modules.txt +++ b/vendor/modules.txt @@ -67,7 +67,7 @@ github.com/containernetworking/plugins/pkg/utils/hwaddr github.com/containernetworking/plugins/pkg/utils/sysctl github.com/containernetworking/plugins/plugins/ipam/host-local/backend github.com/containernetworking/plugins/plugins/ipam/host-local/backend/allocator -# github.com/containers/buildah v1.16.2 +# github.com/containers/buildah v1.16.4 github.com/containers/buildah github.com/containers/buildah/bind github.com/containers/buildah/chroot @@ -87,7 +87,7 @@ github.com/containers/buildah/pkg/secrets github.com/containers/buildah/pkg/supplemented github.com/containers/buildah/pkg/umask github.com/containers/buildah/util -# github.com/containers/common v0.23.0 +# github.com/containers/common v0.24.0 github.com/containers/common/pkg/apparmor github.com/containers/common/pkg/apparmor/internal/supported github.com/containers/common/pkg/auth |