Преглед на файлове

2008-05-11 Tatsuhiro Tsujikawa <tujikawa at rednoah dot com>

	Pass std::deque<Command*> by reference to avoid unnecessary coping.
	* src/AbstractCommand.cc
	* src/BtCheckIntegrityEntry.cc
	* src/BtCheckIntegrityEntry.h
	* src/BtFileAllocationEntry.cc
	* src/BtFileAllocationEntry.h
	* src/BtSetup.cc
	* src/BtSetup.h
	* src/CheckIntegrityCommand.cc
	* src/CheckIntegrityEntry.h
	* src/ChecksumCheckIntegrityEntry.cc
	* src/ChecksumCheckIntegrityEntry.h
	* src/DHTSetup.cc
	* src/DHTSetup.h
	* src/DownloadEngine.cc
	* src/FileAllocationCommand.cc
	* src/FileAllocationEntry.h
	* src/RequestGroup.cc
	* src/RequestGroup.h
	* src/RequestGroupMan.cc
	* src/RequestGroupMan.h
	* src/StreamCheckIntegrityEntry.cc
	* src/StreamCheckIntegrityEntry.h
	* src/StreamFileAllocationEntry.cc
	* src/StreamFileAllocationEntry.h
	* src/TrackerWatcherCommand.cc
	* src/a2functional.h
Tatsuhiro Tsujikawa преди 17 години
родител
ревизия
825cfe7715

+ 30 - 0
ChangeLog

@@ -1,3 +1,33 @@
+2008-05-11  Tatsuhiro Tsujikawa  <tujikawa at rednoah dot com>
+
+	Pass std::deque<Command*> by reference to avoid unnecessary coping.
+	* src/AbstractCommand.cc
+	* src/BtCheckIntegrityEntry.cc
+	* src/BtCheckIntegrityEntry.h
+	* src/BtFileAllocationEntry.cc
+	* src/BtFileAllocationEntry.h
+	* src/BtSetup.cc
+	* src/BtSetup.h
+	* src/CheckIntegrityCommand.cc
+	* src/CheckIntegrityEntry.h
+	* src/ChecksumCheckIntegrityEntry.cc
+	* src/ChecksumCheckIntegrityEntry.h
+	* src/DHTSetup.cc
+	* src/DHTSetup.h
+	* src/DownloadEngine.cc
+	* src/FileAllocationCommand.cc
+	* src/FileAllocationEntry.h
+	* src/RequestGroup.cc
+	* src/RequestGroup.h
+	* src/RequestGroupMan.cc
+	* src/RequestGroupMan.h
+	* src/StreamCheckIntegrityEntry.cc
+	* src/StreamCheckIntegrityEntry.h
+	* src/StreamFileAllocationEntry.cc
+	* src/StreamFileAllocationEntry.h
+	* src/TrackerWatcherCommand.cc
+	* src/a2functional.h
+	
 2008-05-11  Tatsuhiro Tsujikawa  <tujikawa at rednoah dot com>
 
 	Changed method signature:

+ 7 - 2
src/AbstractCommand.cc

@@ -184,7 +184,8 @@ bool AbstractCommand::execute() {
 
 void AbstractCommand::tryReserved() {
   _requestGroup->removeServerHost(cuid);
-  Commands commands = _requestGroup->createNextCommand(e, 1);
+  Commands commands;
+  _requestGroup->createNextCommand(commands, e, 1);
   e->addCommand(commands);
 }
 
@@ -323,7 +324,11 @@ bool AbstractCommand::nameResolveFinished() const {
 void AbstractCommand::prepareForNextAction(Command* nextCommand)
 {
   CheckIntegrityEntryHandle entry(new StreamCheckIntegrityEntry(req, _requestGroup, nextCommand));
-  e->addCommand(_requestGroup->processCheckIntegrityEntry(entry, e));
+
+  std::deque<Command*> commands;
+  _requestGroup->processCheckIntegrityEntry(commands, entry, e);
+
+  e->addCommand(commands);
   e->setNoWait(true);
 }
 

+ 6 - 6
src/BtCheckIntegrityEntry.cc

@@ -47,26 +47,26 @@ BtCheckIntegrityEntry::BtCheckIntegrityEntry(RequestGroup* requestGroup):
 
 BtCheckIntegrityEntry::~BtCheckIntegrityEntry() {}
 
-Commands BtCheckIntegrityEntry::onDownloadIncomplete(DownloadEngine* e)
+void BtCheckIntegrityEntry::onDownloadIncomplete(std::deque<Command*>& commands,
+						 DownloadEngine* e)
 {
-  Commands commands;
   FileAllocationEntryHandle entry(new BtFileAllocationEntry(_requestGroup));
   if(_requestGroup->needsFileAllocation()) {
     e->_fileAllocationMan->pushFileAllocationEntry(entry);
   } else {
-    commands = entry->prepareForNextAction(e);
+    entry->prepareForNextAction(commands, e);
   }
-  return commands;
 }
 
-Commands BtCheckIntegrityEntry::onDownloadFinished(DownloadEngine* e)
+void BtCheckIntegrityEntry::onDownloadFinished(std::deque<Command*>& commands,
+					       DownloadEngine* e)
 {
   _requestGroup->getPieceStorage()->getDiskAdaptor()->onDownloadComplete();
   // TODO Currently,when all the checksums
   // are valid, then aira2 goes to seeding mode. Sometimes it is better
   // to exit rather than doing seeding. So, it would be good to toggle this
   // behavior.
-  return onDownloadIncomplete(e);
+  onDownloadIncomplete(commands, e);
 }
 
 } // namespace aria2

+ 4 - 2
src/BtCheckIntegrityEntry.h

@@ -45,9 +45,11 @@ public:
 
   virtual ~BtCheckIntegrityEntry();
 
-  virtual std::deque<Command*> onDownloadFinished(DownloadEngine* e);
+  virtual void onDownloadFinished(std::deque<Command*>& commands,
+				  DownloadEngine* e);
 
-  virtual std::deque<Command*> onDownloadIncomplete(DownloadEngine* e);
+  virtual void onDownloadIncomplete(std::deque<Command*>& commands,
+				    DownloadEngine* e);
 };
 
 typedef SharedHandle<BtCheckIntegrityEntry> BtCheckIntegrityEntryHandle;

+ 4 - 5
src/BtFileAllocationEntry.cc

@@ -46,14 +46,13 @@ BtFileAllocationEntry::BtFileAllocationEntry(RequestGroup* requestGroup):
 
 BtFileAllocationEntry::~BtFileAllocationEntry() {}
 
-Commands BtFileAllocationEntry::prepareForNextAction(DownloadEngine* e)
+void BtFileAllocationEntry::prepareForNextAction(std::deque<Command*>& commands,
+						 DownloadEngine* e)
 {
-  Commands commands = BtSetup().setup(_requestGroup, e, e->option);
+  BtSetup().setup(commands, _requestGroup, e, e->option);
   if(!_requestGroup->downloadFinished()) {
-    Commands streamCommands = _requestGroup->createNextCommandWithAdj(e, 0);
-    std::copy(streamCommands.begin(), streamCommands.end(), std::back_inserter(commands));
+    _requestGroup->createNextCommandWithAdj(commands, e, 0);
   }
-  return commands;
 }
 
 } // namespace aria2

+ 2 - 1
src/BtFileAllocationEntry.h

@@ -45,7 +45,8 @@ public:
 
   virtual ~BtFileAllocationEntry();
 
-  virtual std::deque<Command*> prepareForNextAction(DownloadEngine* e);
+  virtual void prepareForNextAction(std::deque<Command*>& commands,
+				    DownloadEngine* e);
 };
 
 typedef SharedHandle<BtFileAllocationEntry> BtFileAllocationEntryHandle;

+ 5 - 6
src/BtSetup.cc

@@ -61,14 +61,14 @@ namespace aria2 {
 
 BtSetup::BtSetup():_logger(LogFactory::getInstance()) {}
 
-Commands BtSetup::setup(RequestGroup* requestGroup,
-			DownloadEngine* e,
-			const Option* option)
+void BtSetup::setup(std::deque<Command*>& commands,
+		    RequestGroup* requestGroup,
+		    DownloadEngine* e,
+		    const Option* option)
 {
-  Commands commands;
   BtContextHandle btContext(dynamic_pointer_cast<BtContext>(requestGroup->getDownloadContext()));
   if(btContext.isNull()) {
-    return commands;
+    return;
   }
   // commands
   commands.push_back(new TrackerWatcherCommand(CUIDCounterSingletonHolder::instance()->newID(),
@@ -126,7 +126,6 @@ Commands BtSetup::setup(RequestGroup* requestGroup,
   }
 
   BT_RUNTIME(btContext)->setReady(true);
-  return commands;
 }
 
 } // namespace aria2

+ 4 - 3
src/BtSetup.h

@@ -52,9 +52,10 @@ private:
 public:
   BtSetup();
 
-  std::deque<Command*> setup(RequestGroup* requestGroup,
-			     DownloadEngine* e,
-			     const Option* option);
+  void setup(std::deque<Command*>& commands,
+	     RequestGroup* requestGroup,
+	     DownloadEngine* e,
+	     const Option* option);
 };
 
 } // namespace aria2

+ 6 - 2
src/CheckIntegrityCommand.cc

@@ -65,11 +65,15 @@ bool CheckIntegrityCommand::executeInternal()
     if(_requestGroup->downloadFinished()) {
       logger->notice(MSG_VERIFICATION_SUCCESSFUL,
 		     _requestGroup->getFilePath().c_str());
-      _e->addCommand(_entry->onDownloadFinished(_e));
+      std::deque<Command*> commands;
+      _entry->onDownloadFinished(commands, _e);
+      _e->addCommand(commands);
     } else {
       logger->error(MSG_VERIFICATION_FAILED,
 		    _requestGroup->getFilePath().c_str());
-      _e->addCommand(_entry->onDownloadIncomplete(_e));
+      std::deque<Command*> commands;
+      _entry->onDownloadIncomplete(commands,_e);
+      _e->addCommand(commands);
     }
     _e->setNoWait(true);
     return true;

+ 4 - 2
src/CheckIntegrityEntry.h

@@ -65,9 +65,11 @@ public:
 
   virtual void initValidator() = 0;
 
-  virtual std::deque<Command*> onDownloadFinished(DownloadEngine* e) = 0;
+  virtual void onDownloadFinished(std::deque<Command*>& commands,
+				  DownloadEngine* e) = 0;
 
-  virtual std::deque<Command*> onDownloadIncomplete(DownloadEngine* e) = 0;
+  virtual void onDownloadIncomplete(std::deque<Command*>& commands,
+				    DownloadEngine* e) = 0;
 };
 
 typedef SharedHandle<CheckIntegrityEntry> CheckIntegrityEntryHandle;

+ 8 - 10
src/ChecksumCheckIntegrityEntry.cc

@@ -64,16 +64,14 @@ void ChecksumCheckIntegrityEntry::initValidator()
   _validator->init();
 }
 
-std::deque<Command*>
-ChecksumCheckIntegrityEntry::onDownloadFinished(DownloadEngine* e)
-{
-  return std::deque<Command*>();
-}
+void
+ChecksumCheckIntegrityEntry::onDownloadFinished(std::deque<Command*>& commands,
+						DownloadEngine* e)
+{}
 
-std::deque<Command*>
-ChecksumCheckIntegrityEntry::onDownloadIncomplete(DownloadEngine* e)
-{
-  return std::deque<Command*>();
-}
+void
+ChecksumCheckIntegrityEntry::onDownloadIncomplete(std::deque<Command*>& commands,
+						  DownloadEngine* e)
+{}
 
 } // namespace aria2

+ 4 - 2
src/ChecksumCheckIntegrityEntry.h

@@ -50,9 +50,11 @@ public:
 
   virtual void initValidator();
 
-  virtual std::deque<Command*> onDownloadFinished(DownloadEngine* e);
+  virtual void onDownloadFinished(std::deque<Command*>& commands,
+				  DownloadEngine* e);
 
-  virtual std::deque<Command*> onDownloadIncomplete(DownloadEngine* e);
+  virtual void onDownloadIncomplete(std::deque<Command*>& commands,
+				    DownloadEngine* e);
 };
 
 } // namespace aria2

+ 14 - 12
src/DHTSetup.cc

@@ -65,7 +65,9 @@
 #include "SocketCore.h"
 #include "DlAbortEx.h"
 #include "RecoverableException.h"
+#include "a2functional.h"
 #include <fstream>
+#include <algorithm>
 
 namespace aria2 {
 
@@ -75,11 +77,13 @@ DHTSetup::DHTSetup():_logger(LogFactory::getInstance()) {}
 
 DHTSetup::~DHTSetup() {}
 
-Commands DHTSetup::setup(DownloadEngine* e, const Option* option)
+void DHTSetup::setup(std::deque<Command*>& commands,
+		     DownloadEngine* e, const Option* option)
 {
   if(_initialized) {
-    return Commands();
+    return;
   }
+  std::deque<Command*> tempCommands;
   try {
     // load routing table and localnode id here
 
@@ -182,7 +186,6 @@ Commands DHTSetup::setup(DownloadEngine* e, const Option* option)
       taskQueue->addPeriodicTask1(task);
     }
 
-    Commands commands;
     if(!option->get(PREF_DHT_ENTRY_POINT_HOST).empty()) {
       {
 	std::pair<std::string, uint16_t> addr(option->get(PREF_DHT_ENTRY_POINT_HOST),
@@ -195,7 +198,7 @@ Commands DHTSetup::setup(DownloadEngine* e, const Option* option)
 	command->setTaskFactory(taskFactory);
 	command->setRoutingTable(routingTable);
 	command->setLocalNode(localNode);
-	commands.push_back(command);
+	tempCommands.push_back(command);
       }
     } else {
       _logger->info("No DHT entry point specified.");
@@ -206,38 +209,37 @@ Commands DHTSetup::setup(DownloadEngine* e, const Option* option)
       command->setMessageReceiver(receiver);
       command->setTaskQueue(taskQueue);
       command->setReadCheckSocket(connection->getSocket());
-      commands.push_back(command);
+      tempCommands.push_back(command);
     }
     {
       DHTTokenUpdateCommand* command = new DHTTokenUpdateCommand(CUIDCounterSingletonHolder::instance()->newID(), e, DHT_TOKEN_UPDATE_INTERVAL);
       command->setTokenTracker(tokenTracker);
-      commands.push_back(command);
+      tempCommands.push_back(command);
     }
     {
       DHTBucketRefreshCommand* command = new DHTBucketRefreshCommand(CUIDCounterSingletonHolder::instance()->newID(), e, DHT_BUCKET_REFRESH_CHECK_INTERVAL);
       command->setTaskQueue(taskQueue);
       command->setRoutingTable(routingTable);
       command->setTaskFactory(taskFactory);
-      commands.push_back(command);
+      tempCommands.push_back(command);
     }
     {
       DHTPeerAnnounceCommand* command = new DHTPeerAnnounceCommand(CUIDCounterSingletonHolder::instance()->newID(), e, DHT_PEER_ANNOUNCE_CHECK_INTERVAL);
       command->setPeerAnnounceStorage(peerAnnounceStorage);
-      commands.push_back(command);
+      tempCommands.push_back(command);
     }
     {
       DHTAutoSaveCommand* command = new DHTAutoSaveCommand(CUIDCounterSingletonHolder::instance()->newID(), e, 30*60);
       command->setLocalNode(localNode);
       command->setRoutingTable(routingTable);
-      commands.push_back(command);
+      tempCommands.push_back(command);
     }
     _initialized = true;
-
-    return commands;
+    commands.insert(commands.end(), tempCommands.begin(), tempCommands.end());
   } catch(RecoverableException& e) {
     _logger->error("Exception caught while initializing DHT functionality. DHT is disabled.", e);
     DHTRegistry::clear();
-    return Commands();
+    std::for_each(tempCommands.begin(), tempCommands.end(), Deleter());
   }
 }
 

+ 2 - 1
src/DHTSetup.h

@@ -55,7 +55,8 @@ public:
 
   ~DHTSetup();
 
-  std::deque<Command*> setup(DownloadEngine* e, const Option* option);
+  void setup(std::deque<Command*>& commands,
+	     DownloadEngine* e, const Option* option);
 
   static bool initialized();
 };

+ 4 - 9
src/DownloadEngine.cc

@@ -49,6 +49,7 @@
 #include "a2time.h"
 #include "Socket.h"
 #include "Util.h"
+#include "a2functional.h"
 #include <signal.h>
 #include <cstring>
 #include <algorithm>
@@ -96,14 +97,6 @@ DownloadEngine::~DownloadEngine() {
   cleanQueue();
 }
 
-class Deleter {
-public:
-  template<class T>
-  void operator()(T* ptr) {
-    delete ptr;
-  }
-};
-
 void DownloadEngine::cleanQueue() {
   std::for_each(commands.begin(), commands.end(), Deleter());
   commands.clear();
@@ -311,7 +304,9 @@ void DownloadEngine::requestHalt()
 
 void DownloadEngine::fillCommand()
 {
-  addCommand(_requestGroupMan->getInitialCommands(this));
+  std::deque<Command*> commands;
+  _requestGroupMan->getInitialCommands(commands, this);
+  addCommand(commands);
 }
 
 void DownloadEngine::setStatCalc(const StatCalcHandle& statCalc)

+ 3 - 1
src/FileAllocationCommand.cc

@@ -62,7 +62,9 @@ bool FileAllocationCommand::executeInternal()
 		  Util::itos(_requestGroup->getTotalLength(), true).c_str());
     _e->_fileAllocationMan->markCurrentFileAllocationEntryDone();
     
-    _e->addCommand(_fileAllocationEntry->prepareForNextAction(_e));
+    std::deque<Command*> commands;
+    _fileAllocationEntry->prepareForNextAction(commands, _e);
+    _e->addCommand(commands);
     _e->setNoWait(true);
     return true;
   } else {

+ 2 - 1
src/FileAllocationEntry.h

@@ -61,7 +61,8 @@ public:
 
   void allocateChunk();
 
-  virtual std::deque<Command*> prepareForNextAction(DownloadEngine* e) = 0;
+  virtual void prepareForNextAction(std::deque<Command*>& commands,
+				    DownloadEngine* e) = 0;
 };
 
 typedef SharedHandle<FileAllocationEntry> FileAllocationEntryHandle;

+ 29 - 24
src/RequestGroup.cc

@@ -171,7 +171,8 @@ void RequestGroup::closeFile()
   }
 }
 
-Commands RequestGroup::createInitialCommand(DownloadEngine* e)
+void RequestGroup::createInitialCommand(std::deque<Command*>& commands,
+					DownloadEngine* e)
 {
 #ifdef ENABLE_BITTORRENT
   {
@@ -253,7 +254,9 @@ Commands RequestGroup::createInitialCommand(DownloadEngine* e)
       _progressInfoFile = progressInfoFile;
 
       if(!btContext->isPrivate() && _option->getAsBool(PREF_ENABLE_DHT)) {
-	e->addCommand(DHTSetup().setup(e, _option));
+	std::deque<Command*> commands;
+	DHTSetup().setup(commands, e, _option);
+	e->addCommand(commands);
 	if(btContext->getNodes().size() && DHTSetup::initialized()) {
 	  DHTEntryPointNameResolveCommand* command =
 	    new DHTEntryPointNameResolveCommand(CUIDCounterSingletonHolder::instance()->newID(), e, btContext->getNodes());
@@ -266,14 +269,15 @@ Commands RequestGroup::createInitialCommand(DownloadEngine* e)
       }
       CheckIntegrityEntryHandle entry(new BtCheckIntegrityEntry(this));
       
-      return processCheckIntegrityEntry(entry, e);
+      processCheckIntegrityEntry(commands, entry, e);
+      return;
     }
   }
 #endif // ENABLE_BITTORRENT
   // TODO I assume here when totallength is set to DownloadContext and it is
   // not 0, then filepath is also set DownloadContext correctly....
   if(_downloadContext->getTotalLength() == 0) {
-    return createNextCommand(e, 1);
+    createNextCommand(commands, e, 1);
   }else {
     if(e->_requestGroupMan->isSameFileBeingDownloaded(this)) {
       throw DownloadFailureException
@@ -281,19 +285,20 @@ Commands RequestGroup::createInitialCommand(DownloadEngine* e)
 		      getFilePath().c_str()).str());
     }
     initPieceStorage();
-    BtProgressInfoFileHandle
-      infoFile(new DefaultBtProgressInfoFile(_downloadContext, _pieceStorage, _option));
-    if(!infoFile->exists() && downloadFinishedByFileLength()) {
-      return Commands();
+    BtProgressInfoFileHandle infoFile
+      (new DefaultBtProgressInfoFile(_downloadContext, _pieceStorage, _option));
+    if(infoFile->exists() || !downloadFinishedByFileLength()) {
+      loadAndOpenFile(infoFile);
+      SharedHandle<CheckIntegrityEntry> checkIntegrityEntry
+	(new StreamCheckIntegrityEntry(SharedHandle<Request>(), this));
+      processCheckIntegrityEntry(commands, checkIntegrityEntry, e);
     }
-    loadAndOpenFile(infoFile);
-    SharedHandle<CheckIntegrityEntry>
-      checkIntegrityEntry(new StreamCheckIntegrityEntry(SharedHandle<Request>(), this));
-    return processCheckIntegrityEntry(checkIntegrityEntry, e);
   }
 }
 
-Commands RequestGroup::processCheckIntegrityEntry(const CheckIntegrityEntryHandle& entry, DownloadEngine* e)
+void RequestGroup::processCheckIntegrityEntry(std::deque<Command*>& commands,
+					      const CheckIntegrityEntryHandle& entry,
+					      DownloadEngine* e)
 {
 #ifdef ENABLE_MESSAGE_DIGEST
   if(e->option->get(PREF_CHECK_INTEGRITY) == V_TRUE &&
@@ -301,13 +306,11 @@ Commands RequestGroup::processCheckIntegrityEntry(const CheckIntegrityEntryHandl
     entry->initValidator();
     CheckIntegrityCommand* command =
       new CheckIntegrityCommand(CUIDCounterSingletonHolder::instance()->newID(), this, e, entry);
-    Commands commands;
     commands.push_back(command);
-    return commands;
   } else
 #endif // ENABLE_MESSAGE_DIGEST
     {
-      return entry->onDownloadIncomplete(e);
+      entry->onDownloadIncomplete(commands, e);
     }
 }
 
@@ -458,25 +461,28 @@ bool RequestGroup::tryAutoFileRenaming()
   return false;
 }
 
-Commands RequestGroup::createNextCommandWithAdj(DownloadEngine* e, int numAdj)
+void RequestGroup::createNextCommandWithAdj(std::deque<Command*>& commands,
+					    DownloadEngine* e, int numAdj)
 {
   unsigned int numCommand;
   if(_numConcurrentCommand == 0) {
     numCommand = _uris.size();
   } else {
     int n = _numConcurrentCommand+numAdj;
-    if(n <= 0) {
-      return Commands();
-    } else {
+    if(n > 0) {
       numCommand = n;
+    } else {
+      return;
     }
   }
-  return createNextCommand(e, numCommand, "GET");
+  createNextCommand(commands, e, numCommand, "GET");
 }
 
-Commands RequestGroup::createNextCommand(DownloadEngine* e, unsigned int numCommand, const std::string& method)
+void RequestGroup::createNextCommand(std::deque<Command*>& commands,
+				     DownloadEngine* e,
+				     unsigned int numCommand,
+				     const std::string& method)
 {
-  Commands commands;
   std::deque<std::string> pendingURIs;
   for(;!_uris.empty() && numCommand--; _uris.pop_front()) {
     std::string uri = _uris.front();
@@ -505,7 +511,6 @@ Commands RequestGroup::createNextCommand(DownloadEngine* e, unsigned int numComm
     }
   }
   std::copy(pendingURIs.begin(), pendingURIs.end(), std::front_inserter(_uris));
-  return commands;
 }
 
 std::string RequestGroup::getFilePath() const

+ 10 - 6
src/RequestGroup.h

@@ -140,11 +140,15 @@ public:
 
   SharedHandle<SegmentMan> getSegmentMan() const;
 
-  std::deque<Command*> createInitialCommand(DownloadEngine* e);
+  void createInitialCommand(std::deque<Command*>& commands,
+			    DownloadEngine* e);
 
-  std::deque<Command*> createNextCommandWithAdj(DownloadEngine* e, int numAdj);
+  void createNextCommandWithAdj(std::deque<Command*>& commands,
+				DownloadEngine* e, int numAdj);
 
-  std::deque<Command*> createNextCommand(DownloadEngine* e, unsigned int numCommand, const std::string& method = "GET");
+  void createNextCommand(std::deque<Command*>& commands,
+			 DownloadEngine* e, unsigned int numCommand,
+			 const std::string& method = "GET");
   
   void addURI(const std::string& uri)
   {
@@ -291,9 +295,9 @@ public:
 
   void clearPreDowloadHandler();
 
-  std::deque<Command*>
-  processCheckIntegrityEntry(const SharedHandle<CheckIntegrityEntry>& entry,
-			     DownloadEngine* e);
+  void processCheckIntegrityEntry(std::deque<Command*>& commands,
+				  const SharedHandle<CheckIntegrityEntry>& entry,
+				  DownloadEngine* e);
 
   void initPieceStorage();
 

+ 5 - 6
src/RequestGroupMan.cc

@@ -153,7 +153,8 @@ void RequestGroupMan::fillRequestGroupFromReserver(DownloadEngine* e)
 	temp.push_front(groupToAdd);
 	continue;
       }
-      Commands commands = groupToAdd->createInitialCommand(e);
+      Commands commands;
+      groupToAdd->createInitialCommand(commands, e);
       _requestGroups.push_back(groupToAdd);
       ++count;
       e->addCommand(commands);
@@ -169,15 +170,14 @@ void RequestGroupMan::fillRequestGroupFromReserver(DownloadEngine* e)
   }
 }
 
-Commands RequestGroupMan::getInitialCommands(DownloadEngine* e)
+void RequestGroupMan::getInitialCommands(std::deque<Command*>& commands,
+					 DownloadEngine* e)
 {
-  Commands commands;
   for(RequestGroups::iterator itr = _requestGroups.begin();
 	itr != _requestGroups.end();) {
     try {
       if((*itr)->isDependencyResolved()) {
-	Commands nextCommands = (*itr)->createInitialCommand(e);
-	std::copy(nextCommands.begin(), nextCommands.end(), std::back_inserter(commands));
+	(*itr)->createInitialCommand(commands, e);
 	++itr;
       } else {
 	_reservedGroups.push_front((*itr));
@@ -189,7 +189,6 @@ Commands RequestGroupMan::getInitialCommands(DownloadEngine* e)
       itr = _requestGroups.erase(itr);
     }  
   }
-  return commands;
 }
 
 void RequestGroupMan::save()

+ 1 - 1
src/RequestGroupMan.h

@@ -77,7 +77,7 @@ public:
 
   void forceHalt();
 
-  std::deque<Command*> getInitialCommands(DownloadEngine* e);
+  void getInitialCommands(std::deque<Command*>& commands, DownloadEngine* e);
 
   void removeStoppedGroup();
 

+ 6 - 8
src/StreamCheckIntegrityEntry.cc

@@ -50,23 +50,21 @@ StreamCheckIntegrityEntry::StreamCheckIntegrityEntry(const RequestHandle& curren
 
 StreamCheckIntegrityEntry::~StreamCheckIntegrityEntry() {}
 
-Commands StreamCheckIntegrityEntry::onDownloadIncomplete(DownloadEngine* e)
+void StreamCheckIntegrityEntry::onDownloadIncomplete(std::deque<Command*>& commands,
+						     DownloadEngine* e)
 {
-  Commands commands;
   FileAllocationEntryHandle entry
     (new StreamFileAllocationEntry(_currentRequest, _requestGroup,
 				   popNextCommand()));
   if(_requestGroup->needsFileAllocation()) {
     e->_fileAllocationMan->pushFileAllocationEntry(entry);
   } else {
-    commands = entry->prepareForNextAction(e);
+    entry->prepareForNextAction(commands, e);
   }
-  return commands;
 }
 
-Commands StreamCheckIntegrityEntry::onDownloadFinished(DownloadEngine* e)
-{
-  return Commands();
-}
+void StreamCheckIntegrityEntry::onDownloadFinished(std::deque<Command*>& commands,
+						   DownloadEngine* e)
+{}
 
 } // namespace aria2

+ 4 - 2
src/StreamCheckIntegrityEntry.h

@@ -54,9 +54,11 @@ public:
 
   virtual ~StreamCheckIntegrityEntry();
 
-  virtual std::deque<Command*> onDownloadFinished(DownloadEngine* e);
+  virtual void onDownloadFinished(std::deque<Command*>& commands,
+				  DownloadEngine* e);
 
-  virtual std::deque<Command*> onDownloadIncomplete(DownloadEngine* e);
+  virtual void onDownloadIncomplete(std::deque<Command*>& commands,
+				    DownloadEngine* e);
 };
 
 typedef SharedHandle<StreamCheckIntegrityEntry> StreamCheckIntegrityEntryHandle;

+ 11 - 11
src/StreamFileAllocationEntry.cc

@@ -53,29 +53,29 @@ StreamFileAllocationEntry::StreamFileAllocationEntry(const RequestHandle& curren
 
 StreamFileAllocationEntry::~StreamFileAllocationEntry() {}
 
-Commands StreamFileAllocationEntry::prepareForNextAction(DownloadEngine* e)
+void StreamFileAllocationEntry::prepareForNextAction(std::deque<Command*>& commands,
+						     DownloadEngine* e)
 {
-  Commands commands;
   if(_nextCommand) {
     // give _nextCommand a chance to execute in the next execution loop.
     _nextCommand->setStatus(Command::STATUS_ONESHOT_REALTIME);
     commands.push_back(popNextCommand());
     // try remaining uris
-    Commands streamCommands = _requestGroup->createNextCommandWithAdj(e, -1);
-    std::copy(streamCommands.begin(), streamCommands.end(), std::back_inserter(commands));
+    _requestGroup->createNextCommandWithAdj(commands, e, -1);
   } else {
     if(_currentRequest.isNull()) {
-      commands = _requestGroup->createNextCommandWithAdj(e, 0);
+      _requestGroup->createNextCommandWithAdj(commands, e, 0);
     } else {
-      Commands streamCommands = _requestGroup->createNextCommandWithAdj(e, -1);
-      Command* command = InitiateConnectionCommandFactory::createInitiateConnectionCommand(CUIDCounterSingletonHolder::instance()->newID(),
-											   _currentRequest, _requestGroup, e);
-      
+      Command* command =
+	InitiateConnectionCommandFactory::createInitiateConnectionCommand
+	(CUIDCounterSingletonHolder::instance()->newID(),
+	 _currentRequest, _requestGroup, e);
+
       commands.push_back(command);
-      std::copy(streamCommands.begin(), streamCommands.end(), std::back_inserter(commands));
+
+      _requestGroup->createNextCommandWithAdj(commands, e, -1);
     }
   }
-  return commands;
 }
 
 } // namespace aria2

+ 2 - 1
src/StreamFileAllocationEntry.h

@@ -53,7 +53,8 @@ public:
 
   virtual ~StreamFileAllocationEntry();
 
-  virtual std::deque<Command*> prepareForNextAction(DownloadEngine* e);
+  virtual void prepareForNextAction(std::deque<Command*>& commands,
+				    DownloadEngine* e);
 };
 
 typedef SharedHandle<StreamFileAllocationEntry> StreamFileAllocationEntryHandle;

+ 3 - 1
src/TrackerWatcherCommand.cc

@@ -88,7 +88,9 @@ bool TrackerWatcherCommand::execute() {
   if(_trackerRequestGroup.isNull()) {
     _trackerRequestGroup = createAnnounce();
     if(!_trackerRequestGroup.isNull()) {
-      e->addCommand(_trackerRequestGroup->createInitialCommand(e));
+      std::deque<Command*> commands;
+      _trackerRequestGroup->createInitialCommand(commands, e);
+      e->addCommand(commands);
       logger->debug("added tracker request command");
     }
   } else if(_trackerRequestGroup->downloadFinished()){

+ 8 - 0
src/a2functional.h

@@ -151,6 +151,14 @@ public:
   }
 };
 
+class Deleter {
+public:
+  template<class T>
+  void operator()(T* ptr) {
+    delete ptr;
+  }
+};
+
 } // namespace aria2
 
 #endif // _D_A2_FUNCTIONAL_H_