##################################################################### */
/*}}}*/
// Include Files /*{{{*/
+#include <config.h>
+
#include <apt-pkg/acquire-worker.h>
#include <apt-pkg/acquire-item.h>
#include <apt-pkg/configuration.h>
#include <apt-pkg/fileutl.h>
#include <apt-pkg/strutl.h>
-#include <apti18n.h>
-
#include <iostream>
#include <sstream>
#include <fstream>
-
+
#include <sys/stat.h>
#include <unistd.h>
#include <fcntl.h>
#include <signal.h>
#include <stdio.h>
#include <errno.h>
+
+#include <apti18n.h>
/*}}}*/
using namespace std;
pkgAcquire::Queue::QItem *Itm = 0;
if (URI.empty() == false)
Itm = OwnerQ->FindItem(URI,this);
+
+ // update used mirror
+ string UsedMirror = LookupTag(Message,"UsedMirror", "");
+ if (!UsedMirror.empty() &&
+ Itm &&
+ Itm->Description.find(" ") != string::npos)
+ {
+ Itm->Description.replace(0, Itm->Description.find(" "), UsedMirror);
+ // FIXME: will we need this as well?
+ //Itm->ShortDesc = UsedMirror;
+ }
// Determine the message number and dispatch
switch (Number)
Status = LookupTag(Message,"Message");
break;
+ // 103 Redirect
+ case 103:
+ {
+ if (Itm == 0)
+ {
+ _error->Error("Method gave invalid 103 Redirect message");
+ break;
+ }
+
+ string NewURI = LookupTag(Message,"New-URI",URI.c_str());
+ Itm->URI = NewURI;
+
+ ItemDone();
+
+ pkgAcquire::Item *Owner = Itm->Owner;
+ pkgAcquire::ItemDesc Desc = *Itm;
+
+ // Change the status so that it can be dequeued
+ Owner->Status = pkgAcquire::Item::StatIdle;
+ // Mark the item as done (taking care of all queues)
+ // and then put it in the main queue again
+ OwnerQ->ItemDone(Itm);
+ OwnerQ->Owner->Enqueue(Desc);
+
+ if (Log != 0)
+ Log->Done(Desc);
+ break;
+ }
+
// 200 URI Start
case 200:
{
CurrentItem = Itm;
CurrentSize = 0;
- TotalSize = atoi(LookupTag(Message,"Size","0").c_str());
- ResumePoint = atoi(LookupTag(Message,"Resume-Point","0").c_str());
- Itm->Owner->Start(Message,atoi(LookupTag(Message,"Size","0").c_str()));
+ TotalSize = strtoull(LookupTag(Message,"Size","0").c_str(), NULL, 10);
+ ResumePoint = strtoull(LookupTag(Message,"Resume-Point","0").c_str(), NULL, 10);
+ Itm->Owner->Start(Message,strtoull(LookupTag(Message,"Size","0").c_str(), NULL, 10));
// Display update before completion
if (Log != 0 && Log->MorePulses == true)
Log->Pulse(Owner->GetOwner());
OwnerQ->ItemDone(Itm);
- if (TotalSize != 0 &&
- (unsigned)atoi(LookupTag(Message,"Size","0").c_str()) != TotalSize)
- _error->Warning("Bizarre Error - File size is not what the server reported %s %lu",
- LookupTag(Message,"Size","0").c_str(),TotalSize);
+ unsigned long long const ServerSize = strtoull(LookupTag(Message,"Size","0").c_str(), NULL, 10);
+ if (TotalSize != 0 && ServerSize != TotalSize)
+ _error->Warning("Size of file %s is not what the server reported %s %llu",
+ Owner->DestFile.c_str(), LookupTag(Message,"Size","0").c_str(),TotalSize);
// see if there is a hash to verify
string RecivedHash;
if(!expectedHash.empty())
{
string hashTag = expectedHash.HashType()+"-Hash";
- RecivedHash = expectedHash.HashType() + ":" + LookupTag(Message, hashTag.c_str());
+ string hashSum = LookupTag(Message, hashTag.c_str());
+ if(!hashSum.empty())
+ RecivedHash = expectedHash.HashType() + ":" + hashSum;
if(_config->FindB("Debug::pkgAcquire::Auth", false) == true)
{
clog << "201 URI Done: " << Owner->DescURI() << endl
<< endl << endl;
}
}
- Owner->Done(Message,atoi(LookupTag(Message,"Size","0").c_str()),
- RecivedHash.c_str(), Config);
+ Owner->Done(Message, ServerSize, RecivedHash.c_str(), Config);
ItemDone();
// Log that we are done
// set some status
if(LookupTag(Message,"FailReason") == "Timeout" ||
LookupTag(Message,"FailReason") == "TmpResolveFailure" ||
+ LookupTag(Message,"FailReason") == "ResolveFailure" ||
LookupTag(Message,"FailReason") == "ConnectionRefused")
Owner->Status = pkgAcquire::Item::StatTransientNetworkError;
<< Drive << ":" // drive
<< msg.str() // l10n message
<< endl;
- write(status_fd, status.str().c_str(), status.str().size());
+
+ std::string const dlstatus = status.str();
+ FileFd::Write(status_fd, dlstatus.c_str(), dlstatus.size());
}
if (Log == 0 || Log->MediaChange(LookupTag(Message,"Media"),
if (OutFd == -1)
return false;
-
- string Message = "601 Configuration\n";
- Message.reserve(2000);
- /* Write out all of the configuration directives by walking the
+ /* Write out all of the configuration directives by walking the
configuration tree */
- const Configuration::Item *Top = _config->Tree(0);
- for (; Top != 0;)
- {
- if (Top->Value.empty() == false)
- {
- string Line = "Config-Item: " + QuoteString(Top->FullTag(),"=\"\n") + "=";
- Line += QuoteString(Top->Value,"\n") + '\n';
- Message += Line;
- }
-
- if (Top->Child != 0)
- {
- Top = Top->Child;
- continue;
- }
-
- while (Top != 0 && Top->Next == 0)
- Top = Top->Parent;
- if (Top != 0)
- Top = Top->Next;
- }
- Message += '\n';
+ std::ostringstream Message;
+ Message << "601 Configuration\n";
+ _config->Dump(Message, NULL, "Config-Item: %F=%V\n", false);
+ Message << '\n';
if (Debug == true)
- clog << " -> " << Access << ':' << QuoteString(Message,"\n") << endl;
- OutQueue += Message;
- OutReady = true;
-
+ clog << " -> " << Access << ':' << QuoteString(Message.str(),"\n") << endl;
+ OutQueue += Message.str();
+ OutReady = true;
+
return true;
}
/*}}}*/
Res = write(OutFd,OutQueue.c_str(),OutQueue.length());
}
while (Res < 0 && errno == EINTR);
-
+
if (Res <= 0)
return MethodFailure();
- // Hmm.. this should never happen.
- if (Res < 0)
- return true;
-
OutQueue.erase(0,Res);
if (OutQueue.empty() == true)
OutReady = false;
{
_error->Error("Method %s has died unexpectedly!",Access.c_str());
- ExecWait(Process,Access.c_str(),true);
+ // do not reap the child here to show meaningfull error to the user
+ ExecWait(Process,Access.c_str(),false);
Process = -1;
close(InFd);
close(OutFd);