diff options
author | David Kalnischkies <david@kalnischkies.de> | 2016-06-09 21:06:48 +0200 |
---|---|---|
committer | Julian Andres Klode <jak@debian.org> | 2016-06-10 15:25:19 +0200 |
commit | 49997ef025ee454283722a01210c169ca8910a98 (patch) | |
tree | 58f2355cc6aacdfa0b3a375e545b3ec74d853086 | |
parent | 36feef0dc51c444de1449ba26a0bf2248716591d (diff) |
don't leak an FD in lz4 (de)compression
Seen first in #826783, but as this buglog also shows leaked uncompressed
files as well we don't close it just yet.
(cherry picked from commit 6f35be91c9e86e463bca7df6eadf05412c7b732c)
-rw-r--r-- | apt-pkg/contrib/fileutl.cc | 7 | ||||
-rwxr-xr-x | test/integration/test-apt-helper-cat-file | 16 | ||||
-rw-r--r-- | test/interactive-helper/makefile | 6 | ||||
-rw-r--r-- | test/interactive-helper/test_fileutl.cc | 43 | ||||
-rw-r--r-- | test/libapt/file-helpers.cc | 2 |
5 files changed, 72 insertions, 2 deletions
diff --git a/apt-pkg/contrib/fileutl.cc b/apt-pkg/contrib/fileutl.cc index d880a725d..68298d785 100644 --- a/apt-pkg/contrib/fileutl.cc +++ b/apt-pkg/contrib/fileutl.cc @@ -1535,7 +1535,7 @@ public: return false; unsigned int flags = (Mode & (FileFd::WriteOnly|FileFd::ReadOnly)); - if (backend.OpenDescriptor(iFd, flags) == false) + if (backend.OpenDescriptor(iFd, flags, FileFd::None, true) == false) return false; // Write the file header @@ -1643,6 +1643,11 @@ public: res = LZ4F_freeDecompressionContext(dctx); dctx = nullptr; } + if (backend.IsOpen()) + { + backend.Close(); + filefd->iFd = -1; + } return LZ4F_isError(res) == false; } diff --git a/test/integration/test-apt-helper-cat-file b/test/integration/test-apt-helper-cat-file index f7c94a2b4..3f509189e 100755 --- a/test/integration/test-apt-helper-cat-file +++ b/test/integration/test-apt-helper-cat-file @@ -5,6 +5,15 @@ TESTDIR="$(readlink -f "$(dirname "$0")")" . "$TESTDIR/framework" setupenvironment +TESTTOOL="${BUILDDIRECTORY}/test_fileutl" +msgtest 'Check if we have build the test tool' "$TESTTOOL" +if [ -x "$TESTTOOL" ]; then + msgpass +else + msgskip 'not available' + exit 0 +fi + cat >rootdir/etc/apt/apt.conf.d/rev-as-compressor <<EOF APT::Compressor::rev { Name "rev"; @@ -26,5 +35,12 @@ while read compressor extension command; do else FILE="./test.txt.${extension}" fi + if [ -d /proc/self/fd ]; then + testsuccess runapt "${TESTTOOL}" "$FILE" + testequal '3' grep -c '/test.txt' rootdir/tmp/testsuccess.output + else + msgtest 'Test if /proc interface is available' + msgskip 'seems not' + fi testsuccessequal "$(cat ./test.txt)" apthelper cat-file "$FILE" done < "${TMPWORKINGDIRECTORY}/rootdir/etc/testcase-compressor.conf" diff --git a/test/interactive-helper/makefile b/test/interactive-helper/makefile index 4633b78ce..096767c41 100644 --- a/test/interactive-helper/makefile +++ b/test/interactive-helper/makefile @@ -33,6 +33,12 @@ LIB_MAKES = apt-pkg/makefile SOURCE = test_udevcdrom.cc include $(PROGRAM_H) +PROGRAM=test_fileutl +SLIBS = -lapt-pkg +LIB_MAKES = apt-pkg/makefile +SOURCE = test_fileutl.cc +include $(PROGRAM_H) + # Program for checking rpm versions #PROGRAM=rpmver #SLIBS = -lapt-pkg -lrpm diff --git a/test/interactive-helper/test_fileutl.cc b/test/interactive-helper/test_fileutl.cc new file mode 100644 index 000000000..e660c2981 --- /dev/null +++ b/test/interactive-helper/test_fileutl.cc @@ -0,0 +1,43 @@ +#include <apt-pkg/fileutl.h> +#include <apt-pkg/strutl.h> +#include <apt-pkg/error.h> + +#include <sys/types.h> +#include <sys/stat.h> +#include <unistd.h> +#include <stdlib.h> +#include <fcntl.h> + +#include <iostream> +#include <string> + +static void callsystem(std::string const &call) +{ + auto ret = system(call.c_str()); + if (WIFEXITED(ret) == false || WEXITSTATUS(ret) != 0) + _error->Error("Calling %s failed!", call.c_str()); +} + +int main(int, char ** argv) +{ + auto const pid = getpid(); + std::string ls; + strprintf(ls, "ls -l /proc/%d/fd", pid); + callsystem(ls); + FileFd t; + t.Open(argv[1], FileFd::ReadOnly, FileFd::Extension); + callsystem(ls); + char buf[1024]; + unsigned long long act; + while (t.Read(buf, sizeof(buf), &act)) + if (act == 0) + break; + callsystem(ls); + t.Seek(5); + callsystem(ls); + t.Close(); + callsystem(ls); + auto const ret = _error->PendingError(); + _error->DumpErrors(); + return ret; +} diff --git a/test/libapt/file-helpers.cc b/test/libapt/file-helpers.cc index 6811c4158..48d8a9fbb 100644 --- a/test/libapt/file-helpers.cc +++ b/test/libapt/file-helpers.cc @@ -74,7 +74,7 @@ void helperCreateTemporaryFile(std::string const &id, FileFd &fd, std::string * unlink(tempfile); free(tempfile); - EXPECT_TRUE(fd.OpenDescriptor(tempfile_fd, FileFd::ReadWrite)); + EXPECT_TRUE(fd.OpenDescriptor(tempfile_fd, FileFd::ReadWrite, true)); if (content != NULL) { ASSERT_TRUE(fd.Write(content, strlen(content))); |