aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorVincent Richard <[email protected]>2005-03-23 08:19:23 +0000
committerVincent Richard <[email protected]>2005-03-23 08:19:23 +0000
commit29cc768d1a9c10768642992fd3ace1284688ffc0 (patch)
treef66449e64e7d05bd72634c41efd524e61feddf69
parentUpdated VMime website URL. (diff)
downloadvmime-29cc768d1a9c10768642992fd3ace1284688ffc0.tar.gz
vmime-29cc768d1a9c10768642992fd3ace1284688ffc0.zip
Fixed multiple bugs in POP3 protocol.
-rw-r--r--ChangeLog6
-rw-r--r--src/messaging/POP3Folder.cpp163
-rw-r--r--src/messaging/POP3Message.cpp11
-rw-r--r--vmime/messaging/POP3Folder.hpp2
-rw-r--r--vmime/messaging/POP3Message.hpp1
5 files changed, 138 insertions, 45 deletions
diff --git a/ChangeLog b/ChangeLog
index 8fcdf1a7..90d86856 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -2,6 +2,12 @@
VERSION 0.6.4cvs
================
+2005-03-23 Vincent Richard <[email protected]>
+
+ * messaging/POP3*: fixed incorrect message size. Fixed a bug in
+ deleteMessages() when 'to == -1' and last message not being
+ deleted (thanks to Stefan Uhrig).
+
2005-03-17 Vincent Richard <[email protected]>
* base.{cpp|hpp}: renamed 'MIME_VERSION' to 'SUPPORTED_MIME_VERSION'.
diff --git a/src/messaging/POP3Folder.cpp b/src/messaging/POP3Folder.cpp
index 096c9db6..c70005c6 100644
--- a/src/messaging/POP3Folder.cpp
+++ b/src/messaging/POP3Folder.cpp
@@ -314,11 +314,11 @@ void POP3Folder::fetchMessages(std::vector <message*>& msg, const int options,
progress->progress(++current, total);
}
- if (options & FETCH_UID)
+ if (options & FETCH_SIZE)
{
- // Send the "UIDL" command
+ // Send the "LIST" command
std::ostringstream command;
- command << "UIDL";
+ command << "LIST";
m_store->sendRequest(command.str());
@@ -330,55 +330,68 @@ void POP3Folder::fetchMessages(std::vector <message*>& msg, const int options,
{
m_store->stripFirstLine(response, response, NULL);
- // C: UIDL
+ // C: LIST
// S: +OK
- // S: 1 whqtswO00WBw418f9t5JxYwZ
- // S: 2 QhdPYR:00WBw1Ph7x7
+ // S: 1 47548
+ // S: 2 12653
// S: .
+ std::map <int, string> result;
+ parseMultiListOrUidlResponse(response, result);
- std::istringstream iss(response);
- std::map <int, string> ids;
-
- string line;
-
- while (std::getline(iss, line))
+ for (std::vector <message*>::iterator it = msg.begin() ;
+ it != msg.end() ; ++it)
{
- string::iterator it = line.begin();
+ POP3Message* m = dynamic_cast <POP3Message*>(*it);
- while (it != line.end() && (*it == ' ' || *it == '\t'))
- ++it;
+ std::map <int, string>::const_iterator x = result.find(m->m_num);
- if (it != line.end())
+ if (x != result.end())
{
- int number = 0;
-
- while (it != line.end() && (*it >= '0' && *it <= '9'))
- {
- number = (number * 10) + (*it - '0');
- ++it;
- }
-
- while (it != line.end() && !(*it == ' ' || *it == '\t')) ++it;
- while (it != line.end() && (*it == ' ' || *it == '\t')) ++it;
-
- if (it != line.end())
- {
- ids.insert(std::map <int, string>::value_type
- (number, string(it, line.end())));
- }
+ int size = 0;
+
+ std::istringstream iss((*x).second);
+ iss >> size;
+
+ m->m_size = size;
}
}
+ }
+
+ }
+
+ if (options & FETCH_UID)
+ {
+ // Send the "UIDL" command
+ std::ostringstream command;
+ command << "UIDL";
+
+ m_store->sendRequest(command.str());
+
+ // Get the response
+ string response;
+ m_store->readResponse(response, true, NULL);
+
+ if (m_store->isSuccessResponse(response))
+ {
+ m_store->stripFirstLine(response, response, NULL);
+
+ // C: UIDL
+ // S: +OK
+ // S: 1 whqtswO00WBw418f9t5JxYwZ
+ // S: 2 QhdPYR:00WBw1Ph7x7
+ // S: .
+ std::map <int, string> result;
+ parseMultiListOrUidlResponse(response, result);
for (std::vector <message*>::iterator it = msg.begin() ;
it != msg.end() ; ++it)
{
POP3Message* m = dynamic_cast <POP3Message*>(*it);
- std::map <int, string>::const_iterator id =
- ids.find(m->m_num);
+ std::map <int, string>::const_iterator x = result.find(m->m_num);
- if (id != ids.end())
- m->m_uid = (*id).second;
+ if (x != result.end())
+ m->m_uid = (*x).second;
}
}
}
@@ -397,11 +410,47 @@ void POP3Folder::fetchMessage(message* msg, const int options)
dynamic_cast <POP3Message*>(msg)->fetch(this, options);
+ if (options & FETCH_SIZE)
+ {
+ // Send the "LIST" command
+ std::ostringstream command;
+ command << "LIST " << msg->getNumber();
+
+ m_store->sendRequest(command.str());
+
+ // Get the response
+ string response;
+ m_store->readResponse(response, false, NULL);
+
+ if (m_store->isSuccessResponse(response))
+ {
+ m_store->stripResponseCode(response, response);
+
+ // C: LIST 2
+ // S: +OK 2 4242
+ string::iterator it = response.begin();
+
+ while (it != response.end() && (*it == ' ' || *it == '\t')) ++it;
+ while (it != response.end() && !(*it == ' ' || *it == '\t')) ++it;
+ while (it != response.end() && (*it == ' ' || *it == '\t')) ++it;
+
+ if (it != response.end())
+ {
+ int size = 0;
+
+ std::istringstream iss(string(it, response.end()));
+ iss >> size;
+
+ dynamic_cast <POP3Message*>(msg)->m_size = size;
+ }
+ }
+ }
+
if (options & FETCH_UID)
{
// Send the "UIDL" command
std::ostringstream command;
- command << "UIDL";
+ command << "UIDL " << msg->getNumber();
m_store->sendRequest(command.str());
@@ -504,7 +553,9 @@ void POP3Folder::deleteMessages(const int from, const int to)
else if (!isOpen())
throw exceptions::illegal_state("Folder not open");
- for (int i = from ; i < to ; ++i)
+ const int to2 = (to == -1 ? m_messageCount : to);
+
+ for (int i = from ; i <= to2 ; ++i)
{
std::ostringstream command;
command << "DELE " << i;
@@ -666,5 +717,41 @@ void POP3Folder::expunge()
}
+void POP3Folder::parseMultiListOrUidlResponse(const string& response, std::map <int, string>& result)
+{
+ std::istringstream iss(response);
+ std::map <int, string> ids;
+
+ string line;
+
+ while (std::getline(iss, line))
+ {
+ string::iterator it = line.begin();
+
+ while (it != line.end() && (*it == ' ' || *it == '\t'))
+ ++it;
+
+ if (it != line.end())
+ {
+ int number = 0;
+
+ while (it != line.end() && (*it >= '0' && *it <= '9'))
+ {
+ number = (number * 10) + (*it - '0');
+ ++it;
+ }
+
+ while (it != line.end() && !(*it == ' ' || *it == '\t')) ++it;
+ while (it != line.end() && (*it == ' ' || *it == '\t')) ++it;
+
+ if (it != line.end())
+ {
+ result.insert(std::map <int, string>::value_type(number, string(it, line.end())));
+ }
+ }
+ }
+}
+
+
} // messaging
} // vmime
diff --git a/src/messaging/POP3Message.cpp b/src/messaging/POP3Message.cpp
index 633f9491..d9ef2989 100644
--- a/src/messaging/POP3Message.cpp
+++ b/src/messaging/POP3Message.cpp
@@ -29,7 +29,7 @@ namespace messaging {
POP3Message::POP3Message(POP3Folder* folder, const int num)
- : m_folder(folder), m_num(num), m_header(NULL)
+ : m_folder(folder), m_num(num), m_size(-1), m_header(NULL)
{
m_folder->registerMessage(this);
}
@@ -64,13 +64,10 @@ const message::uid POP3Message::getUniqueId() const
const int POP3Message::getSize() const
{
- if (!m_folder)
- throw exceptions::illegal_state("Folder closed");
-
- POP3Folder::MessageMap::const_iterator it =
- m_folder->m_messages.find(const_cast <POP3Message*>(this));
+ if (m_size == -1)
+ throw exceptions::unfetched_object();
- return ((it != m_folder->m_messages.end()) ? (*it).second : 0);
+ return (m_size);
}
diff --git a/vmime/messaging/POP3Folder.hpp b/vmime/messaging/POP3Folder.hpp
index a7af9ade..2e5b88b9 100644
--- a/vmime/messaging/POP3Folder.hpp
+++ b/vmime/messaging/POP3Folder.hpp
@@ -120,6 +120,8 @@ private:
void onClose();
+ void parseMultiListOrUidlResponse(const string& response, std::map <int, string>& result);
+
POP3Store* m_store;
diff --git a/vmime/messaging/POP3Message.hpp b/vmime/messaging/POP3Message.hpp
index 5a843c1c..b7535fe9 100644
--- a/vmime/messaging/POP3Message.hpp
+++ b/vmime/messaging/POP3Message.hpp
@@ -77,6 +77,7 @@ private:
POP3Folder* m_folder;
int m_num;
uid m_uid;
+ int m_size;
header* m_header;
};