summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDavid Kalnischkies <kalnischkies@gmail.com>2010-01-02 00:22:31 +0100
committerDavid Kalnischkies <kalnischkies@gmail.com>2010-01-02 00:22:31 +0100
commit02dceb31f77f0812c76334a1758631c7cf9544a3 (patch)
treec3a10a2dd01c78eb6ff4c08e60d546ecea7b420c
parent806969420fa6a12471b237eccd21edaff4a33767 (diff)
add configuration PDiffs::Limit-options (FileLimit and SizeLimit) to
not download too many or too big patches (Closes: #554349)
-rw-r--r--apt-pkg/acquire-item.cc62
-rw-r--r--debian/changelog3
-rw-r--r--doc/apt.conf.5.xml9
-rw-r--r--doc/examples/configure-index5
4 files changed, 64 insertions, 15 deletions
diff --git a/apt-pkg/acquire-item.cc b/apt-pkg/acquire-item.cc
index 10e80eb56..4f0abbb91 100644
--- a/apt-pkg/acquire-item.cc
+++ b/apt-pkg/acquire-item.cc
@@ -219,19 +219,19 @@ bool pkgAcqDiffIndex::ParseDiffIndex(string IndexDiffFile) /*{{{*/
if(TF.Step(Tags) == true)
{
- string local_sha1;
bool found = false;
DiffInfo d;
string size;
- string tmp = Tags.FindS("SHA1-Current");
+ string const tmp = Tags.FindS("SHA1-Current");
std::stringstream ss(tmp);
- ss >> ServerSha1;
+ ss >> ServerSha1 >> size;
+ unsigned long const ServerSize = atol(size.c_str());
FileFd fd(CurrentPackagesFile, FileFd::ReadOnly);
SHA1Summation SHA1;
SHA1.AddFD(fd.Fd(), fd.Size());
- local_sha1 = string(SHA1.Result());
+ string const local_sha1 = SHA1.Result();
if(local_sha1 == ServerSha1)
{
@@ -248,20 +248,56 @@ bool pkgAcqDiffIndex::ParseDiffIndex(string IndexDiffFile) /*{{{*/
std::clog << "SHA1-Current: " << ServerSha1 << std::endl;
// check the historie and see what patches we need
- string history = Tags.FindS("SHA1-History");
+ string const history = Tags.FindS("SHA1-History");
std::stringstream hist(history);
- while(hist >> d.sha1 >> size >> d.file)
+ while(hist >> d.sha1 >> size >> d.file)
{
- d.size = atoi(size.c_str());
// read until the first match is found
+ // from that point on, we probably need all diffs
if(d.sha1 == local_sha1)
found=true;
- // from that point on, we probably need all diffs
- if(found)
+ else if (found == false)
+ continue;
+
+ if(Debug)
+ std::clog << "Need to get diff: " << d.file << std::endl;
+ available_patches.push_back(d);
+ }
+
+ if (available_patches.empty() == false)
+ {
+ // patching with too many files is rather slow compared to a fast download
+ unsigned long const fileLimit = _config->FindI("Acquire::PDiffs::FileLimit", 0);
+ if (fileLimit != 0 && fileLimit < available_patches.size())
+ {
+ if (Debug)
+ std::clog << "Need " << available_patches.size() << " diffs (Limit is " << fileLimit
+ << ") so fallback to complete download" << std::endl;
+ return false;
+ }
+
+ // see if the patches are too big
+ found = false; // it was true and it will be true again at the end
+ d = *available_patches.begin();
+ string const firstPatch = d.file;
+ unsigned long patchesSize = 0;
+ std::stringstream patches(Tags.FindS("SHA1-Patches"));
+ while(patches >> d.sha1 >> size >> d.file)
+ {
+ if (firstPatch == d.file)
+ found = true;
+ else if (found == false)
+ continue;
+
+ patchesSize += atol(size.c_str());
+ }
+ unsigned long const sizeLimit = ServerSize * _config->FindI("Acquire::PDiffs::SizeLimit", 100);
+ if (sizeLimit > 0 && (sizeLimit/100) < patchesSize)
{
- if(Debug)
- std::clog << "Need to get diff: " << d.file << std::endl;
- available_patches.push_back(d);
+ if (Debug)
+ std::clog << "Need " << patchesSize << " bytes (Limit is " << sizeLimit/100
+ << ") so fallback to complete download" << std::endl;
+ return false;
}
}
}
@@ -270,7 +306,7 @@ bool pkgAcqDiffIndex::ParseDiffIndex(string IndexDiffFile) /*{{{*/
if(found)
{
// queue the diffs
- string::size_type last_space = Description.rfind(" ");
+ string::size_type const last_space = Description.rfind(" ");
if(last_space != string::npos)
Description.erase(last_space, Description.size()-last_space);
new pkgAcqIndexDiffs(Owner, RealURI, Description, Desc.ShortDesc,
diff --git a/debian/changelog b/debian/changelog
index e36813148..1454eed3c 100644
--- a/debian/changelog
+++ b/debian/changelog
@@ -31,6 +31,9 @@ apt (0.7.26) UNRELEASED; urgency=low
- instruct debiandoc to build files with utf-8 encoding
* buildlib/tools.m4:
- fix some warning from the buildtools
+ * apt-pkg/acquire-item.cc:
+ - add configuration PDiffs::Limit-options to not download
+ too many or too big patches (Closes: #554349)
-- Michael Vogt <mvo@debian.org> Thu, 10 Dec 2009 22:02:38 +0100
diff --git a/doc/apt.conf.5.xml b/doc/apt.conf.5.xml
index 734ae1fe7..fd50e377f 100644
--- a/doc/apt.conf.5.xml
+++ b/doc/apt.conf.5.xml
@@ -221,7 +221,14 @@ DPkg::Pre-Install-Pkgs {"/usr/sbin/dpkg-preconfigure --apt";};
<varlistentry><term>PDiffs</term>
<listitem><para>Try to download deltas called <literal>PDiffs</literal> for
Packages or Sources files instead of downloading whole ones. True
- by default.</para></listitem>
+ by default.</para>
+ <para>Two sub-options to limit the use of PDiffs are also available:
+ With <literal>FileLimit</literal> can be specified how many PDiff files
+ are downloaded at most to patch a file. <literal>SizeLimit</literal>
+ on the other hand is the maximum precentage of the size of all patches
+ compared to the size of the targeted file. If one of these limits is
+ exceeded the complete file is downloaded instead of the patches.
+ </para></listitem>
</varlistentry>
<varlistentry><term>Queue-Mode</term>
diff --git a/doc/examples/configure-index b/doc/examples/configure-index
index 0a20e8f2b..be461aaad 100644
--- a/doc/examples/configure-index
+++ b/doc/examples/configure-index
@@ -176,7 +176,10 @@ Acquire
Source-Symlinks "true";
PDiffs "true"; // try to get the IndexFile diffs
-
+ PDiffs::FileLimit "4"; // don't use diffs if we would need more than 4 diffs
+ PDiffs::SizeLimit "50"; // don't use diffs if size of all patches excess
+ // 50% of the size of the original file
+
// HTTP method configuration
http
{