summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--.cirrus.yml15
-rw-r--r--cmd/podman/images/build.go2
-rw-r--r--contrib/cirrus/required_host_ports.txt1
-rwxr-xr-xcontrib/cirrus/runner.sh17
-rw-r--r--libpod/oci_conmon_exec_linux.go48
-rw-r--r--libpod/util.go17
-rw-r--r--nix/nixpkgs.json8
-rw-r--r--test/system/070-build.bats23
-rw-r--r--test/system/075-exec.bats2
9 files changed, 93 insertions, 40 deletions
diff --git a/.cirrus.yml b/.cirrus.yml
index 5a4815e1c..5b0d9ee6c 100644
--- a/.cirrus.yml
+++ b/.cirrus.yml
@@ -351,14 +351,13 @@ static_alt_build_task:
ALT_NAME: 'Static build'
# Do not use 'latest', fixed-version tag for runtime stability.
CTR_FQIN: "docker.io/nixos/nix:2.3.6"
- # This is critical, it helps to avoid a very lengthy process of
- # statically building every dependency needed to build podman.
- # Assuming the dependency and build description hasn't changed,
- # this cache ensures only the static podman binary is built.
- nix_cache:
- folder: '/var/cache/nix'
- # Cirrus will calculate/use sha of this output as the cache key
- fingerprint_script: echo "${IMAGE_SUFFIX}" && cat nix/*
+ # Authentication token for pushing the build cache to cachix.
+ # This is critical, it helps to avoid a very lengthy process of
+ # statically building every dependency needed to build podman.
+ # Assuming the pinned nix dependencies in nix/nixpkgs.json have not
+ # changed, this cache will ensure that only the static podman binary is
+ # built.
+ CACHIX_AUTH_TOKEN: ENCRYPTED[df0d4d0a67474e8ea49cc503221dcb912b7e2ba45c8ec4bf2e5fd9c49a18ac21c24bacee59b5393355ed9e4358d2baef]
setup_script: *setup
main_script: *main
always: *binary_artifacts
diff --git a/cmd/podman/images/build.go b/cmd/podman/images/build.go
index 4219e325b..957c0ac2d 100644
--- a/cmd/podman/images/build.go
+++ b/cmd/podman/images/build.go
@@ -266,7 +266,7 @@ func buildFlagsWrapperToOptions(c *cobra.Command, contextDir string, flags *buil
pullPolicy := imagebuildah.PullIfMissing
if c.Flags().Changed("pull") && flags.Pull {
- pullPolicy = imagebuildah.PullAlways
+ pullPolicy = imagebuildah.PullIfNewer
}
if flags.PullAlways {
pullPolicy = imagebuildah.PullAlways
diff --git a/contrib/cirrus/required_host_ports.txt b/contrib/cirrus/required_host_ports.txt
index 9248e497a..5f066e059 100644
--- a/contrib/cirrus/required_host_ports.txt
+++ b/contrib/cirrus/required_host_ports.txt
@@ -2,3 +2,4 @@ github.com 22
docker.io 443
quay.io 443
registry.fedoraproject.org 443
+podman.cachix.org 443
diff --git a/contrib/cirrus/runner.sh b/contrib/cirrus/runner.sh
index 50bc1102f..3292cea84 100755
--- a/contrib/cirrus/runner.sh
+++ b/contrib/cirrus/runner.sh
@@ -241,15 +241,14 @@ function _run_altbuild() {
req_env_vars CTR_FQIN
[[ "$UID" -eq 0 ]] || \
die "Static build must execute nixos container as root on host"
- mkdir -p /var/cache/nix
- podman run -i --rm -v /var/cache/nix:/mnt/nix:Z \
- $CTR_FQIN cp -rfT /nix /mnt/nix
- podman run -i --rm -v /var/cache/nix:/nix:Z \
- -v $PWD:$PWD:Z -w $PWD $CTR_FQIN \
- nix --print-build-logs --option cores 4 --option max-jobs 4 \
- build --file ./nix/
- # result symlink is absolute from container perspective :(
- cp /var/cache/$(readlink result)/bin/podman ./ # for cirrus-ci artifact
+ podman run -i --rm \
+ -e CACHIX_AUTH_TOKEN \
+ -v $PWD:$PWD:Z -w $PWD $CTR_FQIN sh -c \
+ "nix-env -iA cachix -f https://cachix.org/api/v1/install && \
+ cachix use podman && \
+ nix-build nix && \
+ nix-store -qR --include-outputs \$(nix-instantiate nix/default.nix) | grep -v podman | cachix push podman && \
+ cp -R result/bin ."
rm result # makes cirrus puke
;;
*)
diff --git a/libpod/oci_conmon_exec_linux.go b/libpod/oci_conmon_exec_linux.go
index dc5dd03df..faf86ea5b 100644
--- a/libpod/oci_conmon_exec_linux.go
+++ b/libpod/oci_conmon_exec_linux.go
@@ -126,20 +126,25 @@ func (r *ConmonOCIRuntime) ExecContainerHTTP(ctr *Container, sessionID string, o
}()
attachChan := make(chan error)
+ conmonPipeDataChan := make(chan conmonPipeData)
go func() {
// attachToExec is responsible for closing pipes
- attachChan <- attachExecHTTP(ctr, sessionID, req, w, streams, pipes, detachKeys, options.Terminal, cancel, hijackDone, holdConnOpen)
+ attachChan <- attachExecHTTP(ctr, sessionID, req, w, streams, pipes, detachKeys, options.Terminal, cancel, hijackDone, holdConnOpen, execCmd, conmonPipeDataChan, ociLog)
close(attachChan)
}()
- // Wait for conmon to succeed, when return.
- if err := execCmd.Wait(); err != nil {
- return -1, nil, errors.Wrapf(err, "cannot run conmon")
- }
+ // NOTE: the channel is needed to communicate conmon's data. In case
+ // of an error, the error will be written on the hijacked http
+ // connection such that remote clients will receive the error.
+ pipeData := <-conmonPipeDataChan
- pid, err := readConmonPipeData(pipes.syncPipe, ociLog)
+ return pipeData.pid, attachChan, pipeData.err
+}
- return pid, attachChan, err
+// conmonPipeData contains the data when reading from conmon's pipe.
+type conmonPipeData struct {
+ pid int
+ err error
}
// ExecContainerDetached executes a command in a running container, but does
@@ -488,9 +493,16 @@ func (r *ConmonOCIRuntime) startExec(c *Container, sessionID string, options *Ex
}
// Attach to a container over HTTP
-func attachExecHTTP(c *Container, sessionID string, r *http.Request, w http.ResponseWriter, streams *HTTPAttachStreams, pipes *execPipes, detachKeys []byte, isTerminal bool, cancel <-chan bool, hijackDone chan<- bool, holdConnOpen <-chan bool) (deferredErr error) {
+func attachExecHTTP(c *Container, sessionID string, r *http.Request, w http.ResponseWriter, streams *HTTPAttachStreams, pipes *execPipes, detachKeys []byte, isTerminal bool, cancel <-chan bool, hijackDone chan<- bool, holdConnOpen <-chan bool, execCmd *exec.Cmd, conmonPipeDataChan chan<- conmonPipeData, ociLog string) (deferredErr error) {
+ // NOTE: As you may notice, the attach code is quite complex.
+ // Many things happen concurrently and yet are interdependent.
+ // If you ever change this function, make sure to write to the
+ // conmonPipeDataChan in case of an error.
+
if pipes == nil || pipes.startPipe == nil || pipes.attachPipe == nil {
- return errors.Wrapf(define.ErrInvalidArg, "must provide a start and attach pipe to finish an exec attach")
+ err := errors.Wrapf(define.ErrInvalidArg, "must provide a start and attach pipe to finish an exec attach")
+ conmonPipeDataChan <- conmonPipeData{-1, err}
+ return err
}
defer func() {
@@ -509,17 +521,20 @@ func attachExecHTTP(c *Container, sessionID string, r *http.Request, w http.Resp
// set up the socket path, such that it is the correct length and location for exec
sockPath, err := c.execAttachSocketPath(sessionID)
if err != nil {
+ conmonPipeDataChan <- conmonPipeData{-1, err}
return err
}
// 2: read from attachFd that the parent process has set up the console socket
if _, err := readConmonPipeData(pipes.attachPipe, ""); err != nil {
+ conmonPipeDataChan <- conmonPipeData{-1, err}
return err
}
// 2: then attach
conn, err := openUnixSocket(sockPath)
if err != nil {
+ conmonPipeDataChan <- conmonPipeData{-1, err}
return errors.Wrapf(err, "failed to connect to container's attach socket: %v", sockPath)
}
defer func() {
@@ -540,11 +555,13 @@ func attachExecHTTP(c *Container, sessionID string, r *http.Request, w http.Resp
// Perform hijack
hijacker, ok := w.(http.Hijacker)
if !ok {
+ conmonPipeDataChan <- conmonPipeData{-1, err}
return errors.Errorf("unable to hijack connection")
}
httpCon, httpBuf, err := hijacker.Hijack()
if err != nil {
+ conmonPipeDataChan <- conmonPipeData{-1, err}
return errors.Wrapf(err, "error hijacking connection")
}
@@ -555,10 +572,23 @@ func attachExecHTTP(c *Container, sessionID string, r *http.Request, w http.Resp
// Force a flush after the header is written.
if err := httpBuf.Flush(); err != nil {
+ conmonPipeDataChan <- conmonPipeData{-1, err}
return errors.Wrapf(err, "error flushing HTTP hijack header")
}
go func() {
+ // Wait for conmon to succeed, when return.
+ if err := execCmd.Wait(); err != nil {
+ conmonPipeDataChan <- conmonPipeData{-1, err}
+ } else {
+ pid, err := readConmonPipeData(pipes.syncPipe, ociLog)
+ if err != nil {
+ hijackWriteError(err, c.ID(), isTerminal, httpBuf)
+ conmonPipeDataChan <- conmonPipeData{pid, err}
+ } else {
+ conmonPipeDataChan <- conmonPipeData{pid, err}
+ }
+ }
// We need to hold the connection open until the complete exec
// function has finished. This channel will be closed in a defer
// in that function, so we can wait for it here.
diff --git a/libpod/util.go b/libpod/util.go
index bf9bf2542..391208fb9 100644
--- a/libpod/util.go
+++ b/libpod/util.go
@@ -235,20 +235,16 @@ func checkDependencyContainer(depCtr, ctr *Container) error {
return nil
}
-// hijackWriteErrorAndClose writes an error to a hijacked HTTP session and
-// closes it. Intended to HTTPAttach function.
-// If error is nil, it will not be written; we'll only close the connection.
-func hijackWriteErrorAndClose(toWrite error, cid string, terminal bool, httpCon io.Closer, httpBuf *bufio.ReadWriter) {
+// hijackWriteError writes an error to a hijacked HTTP session.
+func hijackWriteError(toWrite error, cid string, terminal bool, httpBuf *bufio.ReadWriter) {
if toWrite != nil {
- errString := []byte(fmt.Sprintf("%v\n", toWrite))
+ errString := []byte(fmt.Sprintf("Error: %v\n", toWrite))
if !terminal {
// We need a header.
header := makeHTTPAttachHeader(2, uint32(len(errString)))
if _, err := httpBuf.Write(header); err != nil {
logrus.Errorf("Error writing header for container %s attach connection error: %v", cid, err)
}
- // TODO: May want to return immediately here to avoid
- // writing garbage to the socket?
}
if _, err := httpBuf.Write(errString); err != nil {
logrus.Errorf("Error writing error to container %s HTTP attach connection: %v", cid, err)
@@ -257,6 +253,13 @@ func hijackWriteErrorAndClose(toWrite error, cid string, terminal bool, httpCon
logrus.Errorf("Error flushing HTTP buffer for container %s HTTP attach connection: %v", cid, err)
}
}
+}
+
+// hijackWriteErrorAndClose writes an error to a hijacked HTTP session and
+// closes it. Intended to HTTPAttach function.
+// If error is nil, it will not be written; we'll only close the connection.
+func hijackWriteErrorAndClose(toWrite error, cid string, terminal bool, httpCon io.Closer, httpBuf *bufio.ReadWriter) {
+ hijackWriteError(toWrite, cid, terminal, httpBuf)
if err := httpCon.Close(); err != nil {
logrus.Errorf("Error closing container %s HTTP attach connection: %v", cid, err)
diff --git a/nix/nixpkgs.json b/nix/nixpkgs.json
index d304de536..0cfb251f2 100644
--- a/nix/nixpkgs.json
+++ b/nix/nixpkgs.json
@@ -1,9 +1,9 @@
{
"url": "https://github.com/nixos/nixpkgs",
- "rev": "4a75203f0270f96cbc87f5dfa5d5185690237d87",
- "date": "2020-12-29T03:18:48+01:00",
- "path": "/nix/store/scswsm6r4jnhp9ki0f6s81kpj5x6jkn7-nixpkgs",
- "sha256": "0h70fm9aa7s06wkalbadw70z5rscbs3p6nblb47z523nhlzgjxk9",
+ "rev": "ce7b327a52d1b82f82ae061754545b1c54b06c66",
+ "date": "2021-01-25T11:28:05+01:00",
+ "path": "/nix/store/dpsa6a1sy8hwhwjkklc52brs9z1k5fx9-nixpkgs",
+ "sha256": "1rc4if8nmy9lrig0ddihdwpzg2s8y36vf20hfywb8hph5hpsg4vj",
"fetchSubmodules": false,
"deepClone": false,
"leaveDotGit": false
diff --git a/test/system/070-build.bats b/test/system/070-build.bats
index 7a42a4c18..6b5bc68fb 100644
--- a/test/system/070-build.bats
+++ b/test/system/070-build.bats
@@ -29,6 +29,29 @@ EOF
run_podman rmi -f build_test
}
+@test "podman build - basic test with --pull" {
+ rand_filename=$(random_string 20)
+ rand_content=$(random_string 50)
+
+ run_podman tag $IMAGE localhost/localonly
+
+ tmpdir=$PODMAN_TMPDIR/build-test
+ mkdir -p $tmpdir
+ dockerfile=$tmpdir/Dockerfile
+ cat >$dockerfile <<EOF
+FROM localhost/localonly
+RUN echo $rand_content > /$rand_filename
+EOF
+ # With --pull, Podman would try to pull a newer image but use the local one
+ # if present. See #9111.
+ run_podman build --pull -t build_test $tmpdir
+
+ run_podman run --rm build_test cat /$rand_filename
+ is "$output" "$rand_content" "reading generated file in image"
+
+ run_podman rmi -f build_test localhost/localonly
+}
+
@test "podman build - global runtime flags test" {
skip_if_remote "--runtime-flag flag not supported for remote"
diff --git a/test/system/075-exec.bats b/test/system/075-exec.bats
index c028e16c9..badf44c49 100644
--- a/test/system/075-exec.bats
+++ b/test/system/075-exec.bats
@@ -6,8 +6,6 @@
load helpers
@test "podman exec - basic test" {
- skip_if_remote "FIXME: pending #7241"
-
rand_filename=$(random_string 20)
rand_content=$(random_string 50)