diff --git a/src/CheckIntegrityCommand.cc b/src/CheckIntegrityCommand.cc index c2e225b0..bd8354a8 100644 --- a/src/CheckIntegrityCommand.cc +++ b/src/CheckIntegrityCommand.cc @@ -61,8 +61,7 @@ bool CheckIntegrityCommand::executeInternal() return true; } if(_requestGroup->needsFileAllocation()) { - FileAllocationEntryHandle entry = new FileAllocationEntry(cuid, _entry->getCurrentRequest(), _requestGroup, _requestGroup->getExistingFileLength()); - entry->setNextDownloadCommand(_entry->popNextDownloadCommand()); + FileAllocationEntryHandle entry = new FileAllocationEntry(cuid, _entry->getCurrentRequest(), _requestGroup, _entry->popNextDownloadCommand(), _requestGroup->getExistingFileLength()); _e->_fileAllocationMan->pushFileAllocationEntry(entry); } else { if(_timer.difference() <= _e->option->getAsInt(PREF_DIRECT_DOWNLOAD_TIMEOUT) && diff --git a/src/CheckIntegrityEntry.h b/src/CheckIntegrityEntry.h index 716630e5..b52b7ce6 100644 --- a/src/CheckIntegrityEntry.h +++ b/src/CheckIntegrityEntry.h @@ -44,8 +44,9 @@ private: public: CheckIntegrityEntry(int cuid, const RequestHandle& currentRequest, - RequestGroup* requestGroup): - RequestGroupEntry(cuid, currentRequest, requestGroup), + RequestGroup* requestGroup, + DownloadCommand* nextDownloadCommand = 0): + RequestGroupEntry(cuid, currentRequest, requestGroup, nextDownloadCommand), _validator(0) {} diff --git a/src/FileAllocationEntry.h b/src/FileAllocationEntry.h index 1dfe21d9..6108f41a 100644 --- a/src/FileAllocationEntry.h +++ b/src/FileAllocationEntry.h @@ -44,8 +44,9 @@ public: FileAllocationEntry(int cuid, const RequestHandle& currentRequest, RequestGroup* requestGroup, + DownloadCommand* nextDownloadCommand = 0, int64_t offset = 0): - RequestGroupEntry(cuid, currentRequest, requestGroup), + RequestGroupEntry(cuid, currentRequest, requestGroup, nextDownloadCommand), _offset(offset) {} diff --git a/src/RequestGroup.cc b/src/RequestGroup.cc index 18ca8a12..16bb8da0 100644 --- a/src/RequestGroup.cc +++ b/src/RequestGroup.cc @@ -227,16 +227,14 @@ void RequestGroup::prepareForNextAction(int cuid, const RequestHandle& req, Down // purge SegmentEntries _segmentMan->purgeSegmentEntry(); - CheckIntegrityEntryHandle entry = new CheckIntegrityEntry(cuid, req, this); - entry->setNextDownloadCommand(downloadCommand); + CheckIntegrityEntryHandle entry = new CheckIntegrityEntry(cuid, req, this, downloadCommand); entry->initValidator(); CheckIntegrityCommand* command = new CheckIntegrityCommand(cuid, this, e, entry); e->commands.push_back(command); } else #endif // ENABLE_MESSAGE_DIGEST if(needsFileAllocation()) { - FileAllocationEntryHandle entry = new FileAllocationEntry(cuid, req, this, existingFile.size()); - entry->setNextDownloadCommand(downloadCommand); + FileAllocationEntryHandle entry = new FileAllocationEntry(cuid, req, this, downloadCommand, existingFile.size()); e->_fileAllocationMan->pushFileAllocationEntry(entry); } else { if(downloadCommand) { diff --git a/src/RequestGroupEntry.cc b/src/RequestGroupEntry.cc index 0f6f85af..980d65b0 100644 --- a/src/RequestGroupEntry.cc +++ b/src/RequestGroupEntry.cc @@ -37,6 +37,8 @@ RequestGroupEntry::~RequestGroupEntry() { - --_requestGroup->numConnection; + if(_shouldAddNumConnection) { + --_requestGroup->numConnection; + } delete _nextDownloadCommand; } diff --git a/src/RequestGroupEntry.h b/src/RequestGroupEntry.h index 58689357..a294d7fc 100644 --- a/src/RequestGroupEntry.h +++ b/src/RequestGroupEntry.h @@ -47,16 +47,23 @@ protected: RequestHandle _currentRequest; RequestGroup* _requestGroup; DownloadCommand* _nextDownloadCommand; + bool _shouldAddNumConnection; public: RequestGroupEntry(int cuid, const RequestHandle& currentRequest, - RequestGroup* requestGroup): + RequestGroup* requestGroup, + DownloadCommand* nextDownloadCommand = 0): _cuid(cuid), _currentRequest(currentRequest), _requestGroup(requestGroup), - _nextDownloadCommand(0) + _nextDownloadCommand(nextDownloadCommand) { - ++_requestGroup->numConnection; + if(nextDownloadCommand) { + _shouldAddNumConnection = false; + } else { + _shouldAddNumConnection = true; + ++_requestGroup->numConnection; + } } virtual ~RequestGroupEntry(); @@ -80,12 +87,12 @@ public: { return _requestGroup; } - + /* void setNextDownloadCommand(DownloadCommand* command) { _nextDownloadCommand = command; } - + */ DownloadCommand* getNextDownloadCommand() const { return _nextDownloadCommand; diff --git a/src/UriFileListParser.cc b/src/UriFileListParser.cc index c951cc0a..bed46448 100644 --- a/src/UriFileListParser.cc +++ b/src/UriFileListParser.cc @@ -37,13 +37,13 @@ bool UriFileListParser::hasNext() const { - return _ifs; + return *_ifs; } Strings UriFileListParser::next() { string line; - while(getline(_ifs, line)) { + while(getline(*_ifs, line)) { if(Util::trim(line) != "") { Strings uris; Util::slice(uris, line, '\t', true); diff --git a/src/UriFileListParser.h b/src/UriFileListParser.h index a25a2ae0..83f720d2 100644 --- a/src/UriFileListParser.h +++ b/src/UriFileListParser.h @@ -41,9 +41,22 @@ class UriFileListParser { private: string _filename; - ifstream _ifs; + istream* _ifs; + bool _deleteOnExit; public: - UriFileListParser(const string& filename):_filename(filename), _ifs(filename.c_str()) {} + UriFileListParser(const string& filename):_filename(filename), _ifs(new ifstream(filename.c_str())), _deleteOnExit(true) {} + + UriFileListParser():_ifs(0) {} + + UriFileListParser(istream& ifs):_filename("-"), _ifs(&ifs), _deleteOnExit(false) + {} + + ~UriFileListParser() + { + if(_deleteOnExit) { + delete _ifs; + } + } bool hasNext() const; diff --git a/src/main.cc b/src/main.cc index 4f4f8667..209c149b 100644 --- a/src/main.cc +++ b/src/main.cc @@ -52,6 +52,7 @@ #include "UriFileListParser.h" #include "CookieBoxFactory.h" #include "a2algo.h" +#include "message.h" #include #include #include @@ -211,7 +212,8 @@ void showUsage() { cout << _(" -n, --no-netrc Disables netrc support.") << endl; cout << _(" -i, --input-file=FILE Downloads URIs found in FILE. You can specify\n" " multiple URIs for a single entity: deliminate\n" - " URIs by Tab in a single line.") << endl; + " URIs by Tab in a single line.\n" + " Reads input from stdin when '-' is specified.") << endl; cout << _(" -j, --max-concurrent-downloads=N Set maximum number of concurrent downloads.\n" " It should be used with -i option.\n" " Default: 5") << endl; @@ -753,10 +755,18 @@ int main(int argc, char* argv[]) { else #endif // ENABLE_METALINK if(op->defined(PREF_INPUT_FILE)) { - UriFileListParser flparser(op->get(PREF_INPUT_FILE)); + SharedHandle flparser(0); + if(op->get(PREF_INPUT_FILE) == "-") { + flparser = new UriFileListParser(cin); + } else { + if(!File(op->get(PREF_INPUT_FILE)).isFile()) { + throw new FatalException(EX_FILE_OPEN, op->get(PREF_INPUT_FILE).c_str(), "No such file"); + } + flparser = new UriFileListParser(op->get(PREF_INPUT_FILE)); + } RequestGroups groups; - while(flparser.hasNext()) { - Strings uris = flparser.next(); + while(flparser->hasNext()) { + Strings uris = flparser->next(); if(!uris.empty()) { Strings xuris; ncopy(uris.begin(), uris.end(), op->getAsInt(PREF_SPLIT),