From 27e6c17a18216e2a02de39a6d1722b83ac823d42 Mon Sep 17 00:00:00 2001 From: Michael Vogt Date: Tue, 7 Oct 2014 20:40:37 +0200 Subject: Add new Acquire::MaxReleaseFileSize=10*1000*1000 option This option controls the maximum size of Release/Release.gpg/InRelease files. The rational is that we do not know the size of these files in advance and we want to protect against a denial of service attack where someone sends us endless amounts of data until the disk is full (we do know the size all other files (Packages/Sources/debs)). --- apt-pkg/acquire-item.cc | 53 +++++++++++++------------- apt-pkg/acquire-item.h | 4 +- test/integration/test-apt-update-expected-size | 13 +++++-- 3 files changed, 39 insertions(+), 31 deletions(-) diff --git a/apt-pkg/acquire-item.cc b/apt-pkg/acquire-item.cc index 5d0a00055..1dcbde223 100644 --- a/apt-pkg/acquire-item.cc +++ b/apt-pkg/acquire-item.cc @@ -1690,14 +1690,8 @@ pkgAcqMetaSig::~pkgAcqMetaSig() /*{{{*/ // --------------------------------------------------------------------- string pkgAcqMetaSig::Custom600Headers() const { - string FinalFile = _config->FindDir("Dir::State::lists"); - FinalFile += URItoFileName(RealURI); - - struct stat Buf; - if (stat(FinalFile.c_str(),&Buf) != 0) - return "\nIndex-File: true"; - - return "\nIndex-File: true\nLast-Modified: " + TimeRFC1123(Buf.st_mtime); + std::string Header = GetCustom600Headers(RealURI); + return Header; } /*}}}*/ // pkgAcqMetaSig::Done - The signature was downloaded/verified /*{{{*/ @@ -1842,14 +1836,7 @@ void pkgAcqMetaIndex::Init(std::string URIDesc, std::string ShortDesc) // --------------------------------------------------------------------- string pkgAcqMetaIndex::Custom600Headers() const { - string Final = _config->FindDir("Dir::State::lists"); - Final += URItoFileName(RealURI); - - struct stat Buf; - if (stat(Final.c_str(),&Buf) != 0) - return "\nIndex-File: true"; - - return "\nIndex-File: true\nLast-Modified: " + TimeRFC1123(Buf.st_mtime); + return GetCustom600Headers(RealURI); } /*}}}*/ void pkgAcqMetaIndex::Done(string Message,unsigned long long Size, /*{{{*/ @@ -1910,6 +1897,26 @@ bool pkgAcqMetaBase::CheckAuthDone(string Message, const string &RealURI) /*{{{* return true; } /*}}}*/ +// pkgAcqMetaBase::GetCustom600Headers - Get header for AcqMetaBase /*{{{*/ +// --------------------------------------------------------------------- +string pkgAcqMetaBase::GetCustom600Headers(const string &RealURI) const +{ + std::string Header = "\nIndex-File: true"; + std::string MaximumSize; + strprintf(MaximumSize, "\nMaximum-Size: %i", + _config->FindI("Acquire::MaxReleaseFileSize", 10*1000*1000)); + Header += MaximumSize; + + string FinalFile = _config->FindDir("Dir::State::lists"); + FinalFile += URItoFileName(RealURI); + + struct stat Buf; + if (stat(FinalFile.c_str(),&Buf) == 0) + Header += "\nLast-Modified: " + TimeRFC1123(Buf.st_mtime); + + return Header; +} + /*}}}*/ // pkgAcqMetaBase::QueueForSignatureVerify /*{{{*/ void pkgAcqMetaBase::QueueForSignatureVerify(const std::string &MetaIndexFile, const std::string &MetaIndexFileSignature) @@ -2187,17 +2194,9 @@ pkgAcqMetaClearSig::~pkgAcqMetaClearSig() /*{{{*/ // --------------------------------------------------------------------- string pkgAcqMetaClearSig::Custom600Headers() const { - string Final = _config->FindDir("Dir::State::lists"); - Final += URItoFileName(RealURI); - - struct stat Buf; - if (stat(Final.c_str(),&Buf) != 0) - { - if (stat(Final.c_str(),&Buf) != 0) - return "\nIndex-File: true\nFail-Ignore: true\n"; - } - - return "\nIndex-File: true\nFail-Ignore: true\nLast-Modified: " + TimeRFC1123(Buf.st_mtime); + string Header = GetCustom600Headers(RealURI); + Header += "\nFail-Ignore: true"; + return Header; } /*}}}*/ // pkgAcqMetaClearSig::Done - We got a file /*{{{*/ diff --git a/apt-pkg/acquire-item.h b/apt-pkg/acquire-item.h index 0e7212fc5..68d5a01ce 100644 --- a/apt-pkg/acquire-item.h +++ b/apt-pkg/acquire-item.h @@ -390,7 +390,6 @@ class pkgAcqMetaBase : public pkgAcquire::Item */ void QueueIndexes(bool verify); - /** \brief Called when a file is finished being retrieved. * * If the file was not downloaded to DestFile, a copy process is @@ -407,6 +406,9 @@ class pkgAcqMetaBase : public pkgAcquire::Item void QueueForSignatureVerify(const std::string &MetaIndexFile, const std::string &MetaIndexFileSignature); + /** \brief get the custom600 header for all pkgAcqMeta */ + std::string GetCustom600Headers(const std::string &RealURI) const; + /** \brief Called when authentication succeeded. * * Sanity-checks the authenticated file, queues up the individual diff --git a/test/integration/test-apt-update-expected-size b/test/integration/test-apt-update-expected-size index c1eecc08a..f8ec24dcc 100755 --- a/test/integration/test-apt-update-expected-size +++ b/test/integration/test-apt-update-expected-size @@ -17,10 +17,17 @@ testsuccess aptget update # make InRelease really big mv aptarchive/dists/unstable/InRelease aptarchive/dists/unstable/InRelease.good -dd if=/dev/zero of=aptarchive/dists/unstable/InRelease bs=1M count=2 +dd if=/dev/zero of=aptarchive/dists/unstable/InRelease bs=1M count=2 2>/dev/null touch -d '+1hour' aptarchive/dists/unstable/InRelease -aptget update -o acquire::MaxReleaseFileSize=$((1*1000*1000)) - +aptget update -o acquire::MaxReleaseFileSize=$((1*1000*1000)) -o Debug::pkgAcquire::worker=0 > output.log +msgtest 'Check that the max write warning is triggered' +if grep -q "Writing more data than expected" output.log; then + msgpass +else + cat output.log + msgfail +fi +mv aptarchive/dists/unstable/InRelease.good aptarchive/dists/unstable/InRelease # append junk at the end of the Packages.gz/Packages SIZE="$(stat --printf=%s aptarchive/dists/unstable/main/binary-i386/Packages)" -- cgit v1.2.3