diff options
Diffstat (limited to 'test')
-rw-r--r-- | test/apiv2/20-containers.at | 56 | ||||
-rw-r--r-- | test/apiv2/containers.no_hosts.conf | 2 | ||||
-rw-r--r-- | test/e2e/container_clone_test.go | 14 | ||||
-rw-r--r-- | test/e2e/run_passwd_test.go | 12 | ||||
-rw-r--r-- | test/e2e/run_volume_test.go | 13 | ||||
-rw-r--r-- | test/system/010-images.bats | 11 | ||||
-rw-r--r-- | test/system/015-help.bats | 15 | ||||
-rw-r--r-- | test/system/030-run.bats | 24 | ||||
-rw-r--r-- | test/system/035-logs.bats | 28 | ||||
-rw-r--r-- | test/system/045-start.bats | 13 | ||||
-rw-r--r-- | test/system/090-events.bats | 65 | ||||
-rw-r--r-- | test/system/190-run-ipcns.bats | 70 |
12 files changed, 289 insertions, 34 deletions
diff --git a/test/apiv2/20-containers.at b/test/apiv2/20-containers.at index 94de2cf24..2d5754077 100644 --- a/test/apiv2/20-containers.at +++ b/test/apiv2/20-containers.at @@ -239,16 +239,11 @@ t GET containers/$cid/json 200 \ t POST containers/create Image=$IMAGE Entrypoint='["top"]' 201 \ .Id~[0-9a-f]\\{64\\} cid_top=$(jq -r '.Id' <<<"$output") -# .Network is N/A when rootless -network_expect= -if root; then - network_expect='.NetworkSettings.Networks.podman.NetworkID=podman' -fi t GET containers/${cid_top}/json 200 \ .Config.Entrypoint[0]="top" \ .Config.Cmd='[]' \ .Path="top" \ - $network_expect + .NetworkSettings.Networks.podman.NetworkID=podman t POST containers/${cid_top}/start 204 # make sure the container is running t GET containers/${cid_top}/json 200 \ @@ -372,15 +367,11 @@ t GET containers/$cid/json 200 \ t DELETE containers/$cid?v=true 204 # Test Compat Create with default network mode (#10569) -networkmode=slirp4netns -if root; then - networkmode=bridge -fi t POST containers/create Image=$IMAGE HostConfig='{"NetworkMode":"default"}' 201 \ .Id~[0-9a-f]\\{64\\} cid=$(jq -r '.Id' <<<"$output") t GET containers/$cid/json 200 \ - .HostConfig.NetworkMode="$networkmode" + .HostConfig.NetworkMode="bridge" t DELETE containers/$cid?v=true 204 @@ -447,3 +438,46 @@ t GET images/$iid/json 200 \ t DELETE containers/$cid 204 t DELETE images/docker.io/library/newrepo:v3?force=false 200 + +# test create without default no_hosts +t POST containers/create \ + Image=$IMAGE \ + 201 \ + .Id~[0-9a-f]\\{64\\} +cid=$(jq -r '.Id' <<<"$output") + +t POST libpod/containers/$cid/init 204 + +t GET libpod/containers/$cid/json 200 + +cpid_file=$(jq -r '.ConmonPidFile' <<<"$output") +userdata_path=$(dirname $cpid_file) + +t GET libpod/containers/$cid/json 200 \ + .HostsPath=$userdata_path/hosts + +t DELETE containers/$cid 204 + +# test create with default no_hosts=true +stop_service + +CONTAINERS_CONF=$TESTS_DIR/containers.no_hosts.conf start_service + +# check docker and libpod endpoint +for endpoint in containers/create libpod/containers/create; do + t POST $endpoint \ + Image=$IMAGE \ + 201 \ + .Id~[0-9a-f]\\{64\\} + cid=$(jq -r '.Id' <<<"$output") + + t POST libpod/containers/$cid/init 204 + + t GET libpod/containers/$cid/json 200 \ + .HostsPath="" + + t DELETE containers/$cid 204 +done + +stop_service +start_service diff --git a/test/apiv2/containers.no_hosts.conf b/test/apiv2/containers.no_hosts.conf new file mode 100644 index 000000000..b4c78bedb --- /dev/null +++ b/test/apiv2/containers.no_hosts.conf @@ -0,0 +1,2 @@ +[containers] +no_hosts=true diff --git a/test/e2e/container_clone_test.go b/test/e2e/container_clone_test.go index a327bb8ed..1d5944d1a 100644 --- a/test/e2e/container_clone_test.go +++ b/test/e2e/container_clone_test.go @@ -146,6 +146,20 @@ var _ = Describe("Podman container clone", func() { cloneData = cloneInspect.InspectContainerToJSON() Expect(createData[0].HostConfig.NanoCpus).ToNot(Equal(cloneData[0].HostConfig.NanoCpus)) Expect(cloneData[0].HostConfig.NanoCpus).To(Equal(nanoCPUs)) + + create = podmanTest.Podman([]string{"create", ALPINE}) + create.WaitWithDefaultTimeout() + Expect(create).To(Exit(0)) + clone = podmanTest.Podman([]string{"container", "clone", "--cpus=4", create.OutputToString()}) + clone.WaitWithDefaultTimeout() + Expect(clone).To(Exit(0)) + + cloneInspect = podmanTest.Podman([]string{"inspect", clone.OutputToString()}) + cloneInspect.WaitWithDefaultTimeout() + Expect(cloneInspect).To(Exit(0)) + cloneData = cloneInspect.InspectContainerToJSON() + Expect(cloneData[0].HostConfig.MemorySwappiness).To(Equal(int64(0))) + }) It("podman container clone in a pod", func() { diff --git a/test/e2e/run_passwd_test.go b/test/e2e/run_passwd_test.go index 4c97e665a..ce6c6ffda 100644 --- a/test/e2e/run_passwd_test.go +++ b/test/e2e/run_passwd_test.go @@ -137,4 +137,16 @@ USER 1000`, ALPINE) Expect(run).Should(Exit(0)) Expect(run.OutputToString()).NotTo((ContainSubstring("1234:1234"))) }) + + It("podman run --passwd-entry flag", func() { + // Test that the line we add doesn't contain anything else than what is specified + run := podmanTest.Podman([]string{"run", "--user", "1234:1234", "--passwd-entry=FOO", ALPINE, "grep", "^FOO$", "/etc/passwd"}) + run.WaitWithDefaultTimeout() + Expect(run).Should(Exit(0)) + + run = podmanTest.Podman([]string{"run", "--user", "12345:12346", "-w", "/etc", "--passwd-entry=$UID-$GID-$NAME-$HOME-$USERNAME", ALPINE, "cat", "/etc/passwd"}) + run.WaitWithDefaultTimeout() + Expect(run).Should(Exit(0)) + Expect(run.OutputToString()).To(ContainSubstring("12345-12346-container user-/etc-12345")) + }) }) diff --git a/test/e2e/run_volume_test.go b/test/e2e/run_volume_test.go index 471b3a342..4887197f6 100644 --- a/test/e2e/run_volume_test.go +++ b/test/e2e/run_volume_test.go @@ -797,6 +797,19 @@ VOLUME /test/`, ALPINE) Expect(session.OutputToString()).Should(Equal("888:888")) }) + It("podman run with --mount and named volume with driver-opts", func() { + // anonymous volume mount with driver opts + vol := "type=volume,source=test_vol,dst=/test,volume-opt=type=tmpfs,volume-opt=device=tmpfs,volume-opt=o=nodev" + session := podmanTest.Podman([]string{"run", "--rm", "--mount", vol, ALPINE, "echo", "hello"}) + session.WaitWithDefaultTimeout() + Expect(session).Should(Exit(0)) + + inspectVol := podmanTest.Podman([]string{"volume", "inspect", "test_vol"}) + inspectVol.WaitWithDefaultTimeout() + Expect(inspectVol).Should(Exit(0)) + Expect(inspectVol.OutputToString()).To(ContainSubstring("nodev")) + }) + It("volume permissions after run", func() { imgName := "testimg" dockerfile := fmt.Sprintf(`FROM %s diff --git a/test/system/010-images.bats b/test/system/010-images.bats index 352c3aa95..257508418 100644 --- a/test/system/010-images.bats +++ b/test/system/010-images.bats @@ -312,15 +312,4 @@ Deleted: $pauseID" is "$output" "" } -@test "podman images --size" { - run_podman images - is "${lines[0]}" "REPOSITORY.*TAG.*IMAGE ID.*CREATED.*SIZE" - run_podman images --noheading --format "{{.Size}}" - is "$output" ".* MB" - run_podman images --size=false - is "${lines[0]}" "REPOSITORY.*TAG.*IMAGE ID.*CREATED" - run_podman images --noheading --format "{{.Size}}" --size=false - is "$output" "0 B" -} - # vim: filetype=sh diff --git a/test/system/015-help.bats b/test/system/015-help.bats index a87081687..4eeea85bf 100644 --- a/test/system/015-help.bats +++ b/test/system/015-help.bats @@ -68,9 +68,10 @@ function check_help() { if [ "$cmd" != "help" ]; then dprint "$command_string invalid-arg" run_podman '?' "$@" $cmd invalid-arg - is "$status" 125 "'$command_string invalid-arg' - exit status" + is "$status" 125 \ + "'$usage' indicates that the command takes no arguments. I invoked it with 'invalid-arg' and expected an error status" is "$output" "Error: .* takes no arguments" \ - "'$command_string' with extra (invalid) arguments" + "'$usage' indicates that the command takes no arguments. I invoked it with 'invalid-arg' and expected the following error message" fi found[takes_no_args]=1 fi @@ -115,9 +116,10 @@ function check_help() { # try to read username/password from stdin. dprint "$command_string (without required args)" run_podman '?' "$@" $cmd </dev/null - is "$status" 125 "'$command_string' with no arguments - exit status" + is "$status" 125 \ + "'$usage' indicates at least one required arg. I invoked it with no args and expected an error exit code" is "$output" "Error:.* \(require\|specif\|must\|provide\|need\|choose\|accepts\)" \ - "'$command_string' without required arg" + "'$usage' indicates at least one required arg. I invoked it with no args and expected one of these error messages" found[required_args]=1 fi @@ -138,9 +140,10 @@ function check_help() { local n_args=$(wc -w <<<"$rhs") run_podman '?' "$@" $cmd $(seq --format='x%g' 0 $n_args) - is "$status" 125 "'$command_string' with >$n_args arguments - exit status" + is "$status" 125 \ + "'$usage' indicates a maximum of $n_args args. I invoked it with more, and expected this exit status" is "$output" "Error:.* \(takes no arguments\|requires exactly $n_args arg\|accepts at most\|too many arguments\|accepts $n_args arg(s), received\|accepts between .* and .* arg(s), received \)" \ - "'$command_string' with >$n_args arguments" + "'$usage' indicates a maximum of $n_args args. I invoked it with more, and expected one of these error messages" found[fixed_args]=1 fi diff --git a/test/system/030-run.bats b/test/system/030-run.bats index 72e4a2bc8..aba18badb 100644 --- a/test/system/030-run.bats +++ b/test/system/030-run.bats @@ -821,4 +821,28 @@ EOF run_podman run --rm $IMAGE cat /proc/self/oom_score_adj is "$output" "$current_oom_score_adj" "different oom_score_adj in the container" } + +# CVE-2022-1227 : podman top joins container mount NS and uses nsenter from image +@test "podman top does not use nsenter from image" { + tmpdir=$PODMAN_TMPDIR/build-test + mkdir -p $tmpdir + tmpbuilddir=$tmpdir/build + mkdir -p $tmpbuilddir + dockerfile=$tmpbuilddir/Dockerfile + cat >$dockerfile <<EOF +FROM $IMAGE +RUN rm /usr/bin/nsenter; \ +echo -e "#!/bin/sh\nfalse" >> /usr/bin/nsenter; \ +chmod +x /usr/bin/nsenter +EOF + + test_image="cve_2022_1227_test" + run_podman build -t $test_image $tmpbuilddir + run_podman run -d --userns=keep-id $test_image top + ctr="$output" + run_podman top $ctr huser,user + run_podman rm -f -t0 $ctr + run_podman rmi $test_image +} + # vim: filetype=sh diff --git a/test/system/035-logs.bats b/test/system/035-logs.bats index db50c8f8c..e38cdb383 100644 --- a/test/system/035-logs.bats +++ b/test/system/035-logs.bats @@ -30,6 +30,34 @@ load helpers run_podman rm $cid } +function _log_test_tail() { + local driver=$1 + + run_podman run -d --log-driver=$driver $IMAGE sh -c "echo test1; echo test2" + cid="$output" + + run_podman logs --tail 1 $cid + is "$output" "test2" "logs should only show last line" + + run_podman restart $cid + + run_podman logs --tail 1 $cid + is "$output" "test2" "logs should only show last line after restart" + + run_podman rm $cid +} + +@test "podman logs - tail test, k8s-file" { + _log_test_tail k8s-file +} + +@test "podman logs - tail test, journald" { + # We can't use journald on RHEL as rootless: rhbz#1895105 + skip_if_journald_unavailable + + _log_test_tail journald +} + function _additional_events_backend() { local driver=$1 # Since PR#10431, 'logs -f' with journald driver is only supported with journald events backend. diff --git a/test/system/045-start.bats b/test/system/045-start.bats index 2ea057cd3..31e924ca5 100644 --- a/test/system/045-start.bats +++ b/test/system/045-start.bats @@ -41,18 +41,19 @@ load helpers @test "podman start --filter - start only containers that match the filter" { run_podman run -d $IMAGE /bin/true cid="$output" - run_podman start --filter restart-policy=always $cid "CID of restart-policy=always container" - is "$output" "" + run_podman start --filter restart-policy=always $cid + is "$output" "" "CID of restart-policy=always container" - run_podman start --filter restart-policy=none $cid "CID of restart-policy=none container" - is "$output" "$cid" + run_podman start --filter restart-policy=none $cid + is "$output" "$cid" "CID of restart-policy=none container" } @test "podman start --filter invalid-restart-policy - return error" { run_podman run -d $IMAGE /bin/true cid="$output" - run_podman 125 start --filter restart-policy=fakepolicy $cid "CID of restart-policy=<not-exists> container" - is "$output" "Error: fakepolicy invalid restart policy" + run_podman 125 start --filter restart-policy=fakepolicy $cid + is "$output" "Error: fakepolicy invalid restart policy" \ + "CID of restart-policy=<not-exists> container" } @test "podman start --all --filter" { diff --git a/test/system/090-events.bats b/test/system/090-events.bats index a0b0380a2..cac0a177c 100644 --- a/test/system/090-events.bats +++ b/test/system/090-events.bats @@ -129,3 +129,68 @@ EOF run cat $events_file is "$output" ".*\"Name\":\"$IMAGE" "test" } + +function _populate_events_file() { + # Create 100 duplicate entries to populate the events log file. + local events_file=$1 + truncate --size=0 $events_file + for i in {0..99}; do + printf '{"Name":"busybox","Status":"pull","Time":"2022-04-06T11:26:42.7236679%02d+02:00","Type":"image","Attributes":null}\n' $i >> $events_file + done +} + +@test "events log-file rotation" { + skip_if_remote "setting CONTAINERS_CONF logger options does not affect remote client" + + # Make sure that the events log file is (not) rotated depending on the + # settings in containers.conf. + + # Config without a limit + eventsFile=$PODMAN_TMPDIR/events.txt + _populate_events_file $eventsFile + containersConf=$PODMAN_TMPDIR/containers.conf + cat >$containersConf <<EOF +[engine] +events_logger="file" +events_logfile_path="$eventsFile" +EOF + + # Create events *without* a limit and make sure that it has not been + # rotated/truncated. + contentBefore=$(head -n100 $eventsFile) + CONTAINERS_CONF=$containersConf run_podman run --rm $IMAGE true + contentAfter=$(head -n100 $eventsFile) + is "$contentBefore" "$contentAfter" "events file has not been rotated" + + # Repopulate events file + rm $eventsFile + _populate_events_file $eventsFile + + # Config with a limit + rm $containersConf + cat >$containersConf <<EOF +[engine] +events_logger="file" +events_logfile_path="$eventsFile" +# The limit of 4750 is the *exact* half of the inital events file. +events_logfile_max_size=4750 +EOF + + # Create events *with* a limit and make sure that it has been + # rotated/truncated. Once rotated, the events file should only contain the + # second half of its previous events plus the new ones. + expectedContentAfterTruncation=$PODMAN_TMPDIR/truncated.txt + + run_podman create $IMAGE + CONTAINERS_CONF=$containersConf run_podman rm $output + tail -n52 $eventsFile >> $expectedContentAfterTruncation + + # Make sure the events file looks as expected. + is "$(cat $eventsFile)" "$(cat $expectedContentAfterTruncation)" "events file has been rotated" + + # Make sure that `podman events` can read the file, and that it returns the + # same amount of events. We checked the contents before. + CONTAINERS_CONF=$containersConf run_podman events --stream=false --since="2022-03-06T11:26:42.723667984+02:00" + is "$(wc -l <$eventsFile)" "$(wc -l <<<$output)" "all events are returned" + is "${lines[-2]}" ".* log-rotation $eventsFile" +} diff --git a/test/system/190-run-ipcns.bats b/test/system/190-run-ipcns.bats new file mode 100644 index 000000000..9327d8ec7 --- /dev/null +++ b/test/system/190-run-ipcns.bats @@ -0,0 +1,70 @@ +#!/usr/bin/env bats -*- bats -*- +# shellcheck disable=SC2096 +# +# Tests for podman build +# + +load helpers + +@test "podman --ipc=host" { + run readlink /proc/self/ns/ipc + hostipc=$output + run_podman run --rm --ipc=host $IMAGE readlink /proc/self/ns/ipc + is "$output" "$hostipc" "HostIPC and container IPC should be same" +} + +@test "podman --ipc=none" { + run readlink /proc/self/ns/ipc + hostipc=$output + run_podman run --rm --ipc=none $IMAGE readlink /proc/self/ns/ipc + if [[ $output == "$hostipc" ]]; then + die "hostipc and containeripc should be different" + fi + run_podman 1 run --rm --ipc=none $IMAGE ls /dev/shm + is "$output" "ls: /dev/shm: No such file or directory" "Should fail with missing /dev/shm" +} + +@test "podman --ipc=private" { + run readlink /proc/self/ns/ipc + hostipc=$output + run_podman run -d --ipc=private --name test $IMAGE sleep 100 + if [[ $output == "$hostipc" ]]; then + die "hostipc and containeripc should be different" + fi + run_podman 125 run --ipc=container:test --rm $IMAGE readlink /proc/self/ns/ipc + is "$output" ".*is not allowed: non-shareable IPC (hint: use IpcMode:shareable for the donor container)" "Containers should not share private ipc namespace" + run_podman stop -t 0 test + run_podman rm test +} + +@test "podman --ipc=shareable" { + run readlink /proc/self/ns/ipc + hostipc=$output + run_podman run -d --ipc=shareable --name test $IMAGE sleep 100 + if [[ $output == "$hostipc" ]]; then + die "hostipc and containeripc should be different" + fi + run_podman run --ipc=container:test --rm $IMAGE readlink /proc/self/ns/ipc + if [[ $output == "$hostipc" ]]; then + die "hostipc and containeripc should be different" + fi + run_podman stop -t 0 test + run_podman rm test +} + +@test "podman --ipc=container@test" { + run readlink /proc/self/ns/ipc + hostipc=$output + run_podman run -d --name test $IMAGE sleep 100 + run_podman exec test readlink /proc/self/ns/ipc + if [[ $output == "$hostipc" ]]; then + die "hostipc and containeripc should be different" + fi + testipc=$output + run_podman run --ipc=container:test --rm $IMAGE readlink /proc/self/ns/ipc + is "$output" "$testipc" "Containers should share ipc namespace" + run_podman stop -t 0 test + run_podman rm test +} + +# vim: filetype=sh |