From 70b457da0192695754fb1e95f3f81a15dbb0fa78 Mon Sep 17 00:00:00 2001 From: Tatsuhiro Tsujikawa Date: Fri, 8 Aug 2008 16:44:59 +0000 Subject: [PATCH] 2008-08-09 Tatsuhiro Tsujikawa Now aria2 uses name attribute in Metalink as local filename in BitTorrent downloads. BUG#2033999 * src/BtContext.h * src/BtDependency.cc * src/DefaultBtContext.cc * src/DefaultBtContext.h * src/SingleFileDownloadContext.cc * src/SingleFileDownloadContext.h * test/BtDependencyTest.cc * test/DefaultBtContextTest.cc * test/MockBtContext.h --- ChangeLog | 14 ++++++++++++++ src/BtContext.h | 3 ++- src/BtDependency.cc | 3 ++- src/DefaultBtContext.cc | 30 ++++++++++++++++++++---------- src/DefaultBtContext.h | 17 ++++++++++++----- src/SingleFileDownloadContext.cc | 5 +++++ src/SingleFileDownloadContext.h | 5 +---- test/BtDependencyTest.cc | 17 +++++++++++------ test/DefaultBtContextTest.cc | 21 +++++++++++++++++++++ test/MockBtContext.h | 3 ++- 10 files changed, 90 insertions(+), 28 deletions(-) diff --git a/ChangeLog b/ChangeLog index 833ead63..d22c94a8 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,17 @@ +2008-08-09 Tatsuhiro Tsujikawa + + Now aria2 uses name attribute in Metalink as local filename in + BitTorrent downloads. BUG#2033999 + * src/BtContext.h + * src/BtDependency.cc + * src/DefaultBtContext.cc + * src/DefaultBtContext.h + * src/SingleFileDownloadContext.cc + * src/SingleFileDownloadContext.h + * test/BtDependencyTest.cc + * test/DefaultBtContextTest.cc + * test/MockBtContext.h + 2008-08-08 Tatsuhiro Tsujikawa Added AC_C_BIGENDIAN diff --git a/src/BtContext.h b/src/BtContext.h index 3b867e46..15b184fb 100644 --- a/src/BtContext.h +++ b/src/BtContext.h @@ -61,7 +61,8 @@ public: virtual std::deque > getAnnounceTiers() const = 0; - virtual void load(const std::string& torrentFile) = 0; + virtual void load(const std::string& torrentFile, + const std::string& overrideName = "") = 0; /** * Returns the peer id of localhost, 20 byte length diff --git a/src/BtDependency.cc b/src/BtDependency.cc index 36c30fe7..75de477e 100644 --- a/src/BtDependency.cc +++ b/src/BtDependency.cc @@ -70,7 +70,8 @@ bool BtDependency::resolve() diskAdaptor->openExistingFile(); std::string content = Util::toString(diskAdaptor); btContext->loadFromMemory(content, - File(dependee->getFilePath()).getBasename()); + File(dependee->getFilePath()).getBasename(), + _dependant->getDownloadContext()->getName()); if(_option->defined(PREF_PEER_ID_PREFIX)) { btContext->setPeerIdPrefix(_option->get(PREF_PEER_ID_PREFIX)); } diff --git a/src/DefaultBtContext.cc b/src/DefaultBtContext.cc index 8c407e04..7e5b292f 100644 --- a/src/DefaultBtContext.cc +++ b/src/DefaultBtContext.cc @@ -114,12 +114,18 @@ void DefaultBtContext::extractPieceHash(const unsigned char* hashData, void DefaultBtContext::extractFileEntries(const Dictionary* infoDic, const std::string& defaultName, + const std::string& overrideName, const std::deque& urlList) { - const Data* nameData = dynamic_cast(infoDic->get(BtContext::C_NAME)); - if(nameData) { - name = nameData->toString(); + if(overrideName.empty()) { + const Data* nameData = + dynamic_cast(infoDic->get(BtContext::C_NAME)); + if(nameData) { + name = nameData->toString(); + } else { + name = File(defaultName).getBasename()+".file"; + } } else { - name = File(defaultName).getBasename()+".file"; + name = overrideName; } const List* files = dynamic_cast(infoDic->get(BtContext::C_FILES)); if(files) { @@ -271,7 +277,8 @@ void DefaultBtContext::extractNodes(const List* nodes) void DefaultBtContext::loadFromMemory(const unsigned char* content, size_t length, - const std::string& defaultName) + const std::string& defaultName, + const std::string& overrideName) { SharedHandle rootEntry(MetaFileUtil::bdecoding(content, length)); const Dictionary* rootDic = dynamic_cast(rootEntry.get()); @@ -279,20 +286,23 @@ void DefaultBtContext::loadFromMemory(const unsigned char* content, throw DlAbortEx (StringFormat("torrent file does not contain a root dictionary .").str()); } - processRootDictionary(rootDic, defaultName); + processRootDictionary(rootDic, defaultName, overrideName); } -void DefaultBtContext::load(const std::string& torrentFile) { +void DefaultBtContext::load(const std::string& torrentFile, + const std::string& overrideName) { SharedHandle rootEntry(MetaFileUtil::parseMetaFile(torrentFile)); const Dictionary* rootDic = dynamic_cast(rootEntry.get()); if(!rootDic) { throw DlAbortEx (StringFormat("torrent file does not contain a root dictionary .").str()); } - processRootDictionary(rootDic, torrentFile); + processRootDictionary(rootDic, torrentFile, overrideName); } -void DefaultBtContext::processRootDictionary(const Dictionary* rootDic, const std::string& defaultName) +void DefaultBtContext::processRootDictionary(const Dictionary* rootDic, + const std::string& defaultName, + const std::string& overrideName) { clear(); const Dictionary* infoDic = @@ -347,7 +357,7 @@ void DefaultBtContext::processRootDictionary(const Dictionary* rootDic, const st std::deque urlList; extractUrlList(urlList, rootDic->get(BtContext::C_URL_LIST)); // retrieve file entries - extractFileEntries(infoDic, defaultName, urlList); + extractFileEntries(infoDic, defaultName, overrideName, urlList); if((totalLength+pieceLength-1)/pieceLength != numPieces) { throw DlAbortEx("Too few/many piece hash."); } diff --git a/src/DefaultBtContext.h b/src/DefaultBtContext.h index 8cc3aeba..b83f1f8f 100644 --- a/src/DefaultBtContext.h +++ b/src/DefaultBtContext.h @@ -78,6 +78,7 @@ private: size_t hashLength); void extractFileEntries(const Dictionary* infoDic, const std::string& defaultName, + const std::string& overrideName, const std::deque& urlList); void extractAnnounce(const Data* announceData); void extractAnnounceList(const List* announceListData); @@ -86,7 +87,9 @@ private: void extractNodes(const List* nodes); - void processRootDictionary(const Dictionary* rootDic, const std::string& defaultName); + void processRootDictionary(const Dictionary* rootDic, + const std::string& defaultName, + const std::string& overrideName); public: DefaultBtContext(); @@ -115,15 +118,19 @@ private: virtual std::deque > getAnnounceTiers() const; - virtual void load(const std::string& torrentFile); + virtual void load(const std::string& torrentFile, + const std::string& overrideName = ""); void loadFromMemory(const unsigned char* content, size_t length, - const std::string& defaultName); + const std::string& defaultName, + const std::string& overrideName = ""); - void loadFromMemory(const std::string& context, const std::string& defaultName) + void loadFromMemory(const std::string& context, + const std::string& defaultName, + const std::string& overrideName = "") { loadFromMemory(reinterpret_cast(context.c_str()), - context.size(), defaultName); + context.size(), defaultName, overrideName); } virtual const std::string& getName() const; diff --git a/src/SingleFileDownloadContext.cc b/src/SingleFileDownloadContext.cc index c54a35a3..c32ad208 100644 --- a/src/SingleFileDownloadContext.cc +++ b/src/SingleFileDownloadContext.cc @@ -96,4 +96,9 @@ void SingleFileDownloadContext::setTotalLength(uint64_t totalLength) _fileEntry->setLength(totalLength); } +const std::string& SingleFileDownloadContext::getName() const +{ + return _fileEntry->getPath(); +} + } // namespace aria2 diff --git a/src/SingleFileDownloadContext.h b/src/SingleFileDownloadContext.h index b15bdec5..f1944c94 100644 --- a/src/SingleFileDownloadContext.h +++ b/src/SingleFileDownloadContext.h @@ -95,10 +95,7 @@ public: virtual std::deque > getFileEntries() const; - virtual const std::string& getName() const - { - return _filename; - } + virtual const std::string& getName() const; virtual size_t getPieceLength() const { diff --git a/test/BtDependencyTest.cc b/test/BtDependencyTest.cc index 09e11dcb..be950840 100644 --- a/test/BtDependencyTest.cc +++ b/test/BtDependencyTest.cc @@ -25,7 +25,7 @@ class BtDependencyTest:public CppUnit::TestFixture { { SharedHandle dependant(new RequestGroup(option, std::deque())); SharedHandle dctx - (new SingleFileDownloadContext(0, 0, "")); + (new SingleFileDownloadContext(0, 0, "outfile.path")); dctx->setDir("/tmp"); dependant->setDownloadContext(dctx); return dependant; @@ -73,7 +73,8 @@ void BtDependencyTest::testResolve() SharedHandle btContext (dynamic_pointer_cast(dependant->getDownloadContext())); CPPUNIT_ASSERT(!btContext.isNull()); - CPPUNIT_ASSERT_EQUAL(std::string("/tmp/aria2-test"), btContext->getActualBasePath()); + CPPUNIT_ASSERT_EQUAL(std::string("/tmp/outfile.path"), + btContext->getActualBasePath()); } void BtDependencyTest::testResolve_loadError() @@ -88,9 +89,11 @@ void BtDependencyTest::testResolve_loadError() CPPUNIT_ASSERT(dep.resolve()); SharedHandle dctx - (dynamic_pointer_cast(dependant->getDownloadContext())); + (dynamic_pointer_cast + (dependant->getDownloadContext())); CPPUNIT_ASSERT(!dctx.isNull()); - CPPUNIT_ASSERT_EQUAL(std::string("/tmp/index.html"), dctx->getActualBasePath()); + CPPUNIT_ASSERT_EQUAL(std::string("/tmp/outfile.path"), + dctx->getActualBasePath()); } catch(Exception& e) { std::cerr << e.stackTrace() << std::endl; CPPUNIT_FAIL("an exception was thrown."); @@ -107,9 +110,11 @@ void BtDependencyTest::testResolve_dependeeFailure() CPPUNIT_ASSERT(dep.resolve()); SharedHandle dctx - (dynamic_pointer_cast(dependant->getDownloadContext())); + (dynamic_pointer_cast + (dependant->getDownloadContext())); CPPUNIT_ASSERT(!dctx.isNull()); - CPPUNIT_ASSERT_EQUAL(std::string("/tmp/index.html"), dctx->getActualBasePath()); + CPPUNIT_ASSERT_EQUAL(std::string("/tmp/outfile.path"), + dctx->getActualBasePath()); } void BtDependencyTest::testResolve_dependeeInProgress() diff --git a/test/DefaultBtContextTest.cc b/test/DefaultBtContextTest.cc index c73c481f..d5ec77f6 100644 --- a/test/DefaultBtContextTest.cc +++ b/test/DefaultBtContextTest.cc @@ -24,6 +24,7 @@ class DefaultBtContextTest:public CppUnit::TestFixture { CPPUNIT_TEST(testGetFileModeSingle); CPPUNIT_TEST(testGetNameMulti); CPPUNIT_TEST(testGetNameSingle); + CPPUNIT_TEST(testOverrideName); CPPUNIT_TEST(testGetAnnounceTier); CPPUNIT_TEST(testGetAnnounceTierAnnounceList); CPPUNIT_TEST(testGetPieceLength); @@ -34,6 +35,7 @@ class DefaultBtContextTest:public CppUnit::TestFixture { CPPUNIT_TEST(testGetFileEntries_singleFileUrlList); CPPUNIT_TEST(testLoadFromMemory); CPPUNIT_TEST(testLoadFromMemory_somethingMissing); + CPPUNIT_TEST(testLoadFromMemory_overrideName); CPPUNIT_TEST(testGetNodes); CPPUNIT_TEST_SUITE_END(); public: @@ -50,6 +52,7 @@ public: void testGetFileModeSingle(); void testGetNameMulti(); void testGetNameSingle(); + void testOverrideName(); void testGetAnnounceTier(); void testGetAnnounceTierAnnounceList(); void testGetPieceLength(); @@ -60,6 +63,7 @@ public: void testGetFileEntries_singleFileUrlList(); void testLoadFromMemory(); void testLoadFromMemory_somethingMissing(); + void testLoadFromMemory_overrideName(); void testGetNodes(); }; @@ -167,6 +171,13 @@ void DefaultBtContextTest::testGetNameSingle() { CPPUNIT_ASSERT_EQUAL(std::string("aria2-0.8.2.tar.bz2"), btContext.getName()); } +void DefaultBtContextTest::testOverrideName() +{ + DefaultBtContext btContext; + btContext.load("test.torrent", "aria2-override.name"); + CPPUNIT_ASSERT_EQUAL(std::string("aria2-override.name"), btContext.getName()); +} + void DefaultBtContextTest::testGetAnnounceTier() { DefaultBtContext btContext; btContext.load("single.torrent"); @@ -342,6 +353,16 @@ void DefaultBtContextTest::testLoadFromMemory_somethingMissing() } } +void DefaultBtContextTest::testLoadFromMemory_overrideName() +{ + std::string memory = "d8:announce36:http://aria.rednoah.com/announce.php13:announce-listll16:http://tracker1 el15:http://tracker2el15:http://tracker3ee7:comment17:REDNOAH.COM RULES13:creation datei1123456789e4:infod5:filesld6:lengthi284e4:pathl5:aria23:src6:aria2ceed6:lengthi100e4:pathl19:aria2-0.2.2.tar.bz2eee4:name10:aria2-test12:piece lengthi128e6:pieces60:AAAAAAAAAAAAAAAAAAAABBBBBBBBBBBBBBBBBBBBCCCCCCCCCCCCCCCCCCCCee"; + + DefaultBtContext btContext; + btContext.loadFromMemory(memory, "default", "aria2-override.name"); + + CPPUNIT_ASSERT_EQUAL(std::string("aria2-override.name"), btContext.getName()); +} + void DefaultBtContextTest::testGetNodes() { { diff --git a/test/MockBtContext.h b/test/MockBtContext.h index e8dbbba3..740a07fe 100644 --- a/test/MockBtContext.h +++ b/test/MockBtContext.h @@ -92,7 +92,8 @@ public: announceTiers.push_back(announceTier); } - virtual void load(const std::string& torrentFile) {} + virtual void load(const std::string& torrentFile, + const std::string& overrideName = "") {} virtual const std::string& getName() const { return name;