diff --git a/ChangeLog b/ChangeLog index 17d49f90..44738b04 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,13 @@ +2007-07-18 Tatsuhiro Tsujikawa + + Fixed the bug that prevents filename in content-disposition from + being retrieved when filename is not quoted. + * src/Util.cc (getContentDispositionFilename) + + Fixed the bug that causes infinate loop and memory leak when file open + operation failed. + * src/HttpResponseCommand.cc (handleDefaultEncoding) + 2007-07-09 Tatsuhiro Tsujikawa Fixed the bug that causes segfault when all URIs specified are diff --git a/src/HttpResponseCommand.cc b/src/HttpResponseCommand.cc index 5bdf4349..821406f6 100644 --- a/src/HttpResponseCommand.cc +++ b/src/HttpResponseCommand.cc @@ -142,13 +142,18 @@ bool HttpResponseCommand::handleDefaultEncoding(const HttpResponseHandle& httpRe } DownloadCommand* command = 0; - File file(_requestGroup->getFilePath()); - if(_requestGroup->getRemainingUris().empty() && !file.exists()) { - command = createHttpDownloadCommand(httpResponse); + try { + File file(_requestGroup->getFilePath()); + if(_requestGroup->getRemainingUris().empty() && !file.exists()) { + command = createHttpDownloadCommand(httpResponse); + } + _requestGroup->loadAndOpenFile(); + _requestGroup->prepareForNextAction(cuid, req, e, command); + e->noWait = true; + } catch(Exception* e) { + delete command; + throw; } - _requestGroup->loadAndOpenFile(); - _requestGroup->prepareForNextAction(cuid, req, e, command); - e->noWait = true; return true; } diff --git a/src/Util.cc b/src/Util.cc index 9ff90376..b6cc6ad7 100644 --- a/src/Util.cc +++ b/src/Util.cc @@ -111,9 +111,9 @@ string Util::llitos(int64_t value, bool comma) return int2str(value, comma); } -string Util::trim(const string& src) { - string::size_type sp = src.find_first_not_of("\r\n\t "); - string::size_type ep = src.find_last_not_of("\r\n\t "); +string Util::trim(const string& src, const string& trimCharset) { + string::size_type sp = src.find_first_not_of(trimCharset); + string::size_type ep = src.find_last_not_of(trimCharset); if(sp == string::npos || ep == string::npos) { return ""; } else { @@ -459,16 +459,27 @@ void Util::unfoldRange(const string& src, Integers& range) { } string Util::getContentDispositionFilename(const string& header) { - string::size_type attributesp = header.find("filename=\""); + string keyName = "filename="; + string::size_type attributesp = header.find(keyName); if(attributesp == string::npos) { return ""; } - string::size_type filenamesp = attributesp+strlen("filename=\""); - string::size_type filenameep = header.find("\"", filenamesp); - if(filenameep == string::npos) { + string::size_type filenamesp = attributesp+strlen(keyName.c_str()); + string::size_type filenameep; + if(filenamesp == header.size()) { return ""; } - return trim(header.substr(filenamesp, filenameep-filenamesp)); + + if(header[filenamesp] == '\'' || header[filenamesp] == '"') { + char quoteChar = header[filenamesp]; + filenameep = header.find(quoteChar, filenamesp+1); + } else { + filenameep = header.find(';', filenamesp); + } + if(filenameep == string::npos) { + filenameep = header.size(); + } + return trim(header.substr(filenamesp, filenameep-filenamesp), "\r\n '\""); } #ifdef ENABLE_MESSAGE_DIGEST diff --git a/src/Util.h b/src/Util.h index 29b1962b..d165a589 100644 --- a/src/Util.h +++ b/src/Util.h @@ -73,7 +73,7 @@ public: */ static void slice(Strings& result, const string& src, char delim, bool trim = false); - static string trim(const string& src); + static string trim(const string& src, const string& trimCharset = "\r\n\t "); static bool startsWith(const string& target, const string& part); diff --git a/test/UtilTest.cc b/test/UtilTest.cc index 5312def9..c75332ae 100644 --- a/test/UtilTest.cc +++ b/test/UtilTest.cc @@ -203,6 +203,28 @@ void UtilTest::testGetContentDispositionFilename() { string h4 = "attachment;"; CPPUNIT_ASSERT_EQUAL(string(""), Util::getContentDispositionFilename(h4)); + + string h5 = "attachment; filename=aria2.tar.bz2"; + CPPUNIT_ASSERT_EQUAL(string("aria2.tar.bz2"), Util::getContentDispositionFilename(h5)); + + string h6 = "attachment; filename='aria2.tar.bz2'"; + CPPUNIT_ASSERT_EQUAL(string("aria2.tar.bz2"), Util::getContentDispositionFilename(h6)); + + string h7 = "attachment; filename='aria2.tar.bz2"; + CPPUNIT_ASSERT_EQUAL(string("aria2.tar.bz2"), Util::getContentDispositionFilename(h7)); + + string h8 = "attachment; filename=aria2.tar.bz2; creation-date=20 Jun 2007 00:00:00 GMT"; + CPPUNIT_ASSERT_EQUAL(string("aria2.tar.bz2"), Util::getContentDispositionFilename(h8)); + + string h9 = "attachment; filename=\"aria2.tar.bz2; creation-date=20 Jun 2007 00:00:00 GMT\""; + CPPUNIT_ASSERT_EQUAL(string("aria2.tar.bz2; creation-date=20 Jun 2007 00:00:00 GMT"), Util::getContentDispositionFilename(h9)); + + string h10 = "attachment; filename="; + CPPUNIT_ASSERT_EQUAL(string(""), Util::getContentDispositionFilename(h10)); + + string h11 = "attachment; filename=;"; + CPPUNIT_ASSERT_EQUAL(string(""), Util::getContentDispositionFilename(h11)); + } class Printer {