[haiku-commits] haiku: hrev48615 - in src: add-ons/mail_daemon/inbound_protocols/imap/imap_lib kits/mail add-ons/mail_daemon/inbound_protocols/imap servers/mail add-ons/mail_daemon/outbound_protocols/smtp

  • From: axeld@xxxxxxxxxxxxxxxx
  • To: haiku-commits@xxxxxxxxxxxxx
  • Date: Tue, 6 Jan 2015 15:31:05 +0100 (CET)

hrev48615 adds 85 changesets to branch 'master'
old head: 2ba93e7d81442ec0ec0f2fc69de582dcb8added6
new head: 46019292630b815296175cf61031f574dc15a69e
overview: http://cgit.haiku-os.org/haiku/log/?qt=range&q=4601929+%5E2ba93e7

----------------------------------------------------------------------------

37d26ae: Work in progress of rewrite; IMAP doesn't even compile at this point.

a517047: Got rid of the ConnectionReader, and implemented parsing literals.
  
  * The parser now works on a BDataIO instead. It's now even a bit simpler
    overall.
  * Implemented ParseLiteral() - the default implementation just reads the data
    into a string. Thanks to BDataIO this was now very simple to do.
  * Tested the code: imap_tester can now successfully read mails (using the raw
    command only, at the moment).

db0a4f2: More work in progress of the IMAP rework.
  
  * Implemented FetchCommand, and some more.
  * Improved and extended the imap_tester.
  * The base to implement the new InboundProtocol on is now mostly done, at 
least
    for a start.

1704480: Read some more specs, cleaned Protocol a bit.
  
  * Added some TODO comments based on the various IMAP specs and extensions.
  * Removed SelectMailbox() functionality from the Protocol class; it's not
    really useful to have it there.
  * Removed some other methods that don't belong into the Protocol class.

9192d4d: Started working on the IMAP add-on itself.
  
  * Renamed imap_config.cpp to ConfigView.cpp, IMAPFolderConfig.(h|cpp)
    to FolderConfigWindow.(h|cpp).
  * Got the latter to build.
  * Added Settings class to simplify and unify the BMessage based
    settings access.
  * Removed the InboundProtocol[Thread] implementation from the build for now.

fe26284: Added support for decoding RFC-3501 mailbox names.
  
  * Added new RFC3501Encoding class that implements modified UTF-7 as specified
    in RFC-3501; only decoding is implemented right now.
  * ListCommand now uses this new class to encode, and decode the folder names.

f1c9cc4: We need to copy the settings message.

cc3aa99: Use GETQUOTAROOT instead of GETQUOTA.
  
  * At least with my ISP, there is no "" root, so the command would fail when 
used
    as is.
  * Now we always use the GETQUOTAROOT command instead, by default for the INBOX
    mailbox. This isn't entirely correct either, but better than nothing.

3e4e5c2: Improved folder config window a bit.
  
  * Now uses the BLayoutBuilder instead of ALM layout - not only is the code 
much
    simpler now, resizing the window isn't as sluggish anymore (less 
flickering).
  * Fixed a drawing bug in the list view; the drawing state wasn't properly
    maintained, leading to rendering artefacts.
  * Moved the checkbox to the start of the line.
  * Use B_ASYNCHRONOUS_CONTROLS for all windows.
  * Fixed a few typos.

077338a: Completed literal handling.
  
  * LiteralHandler commands now receive the literal data as intended.
  * The 'fetch' command in the imap_tester now uses this to print the literal
    to stdout.

f06916d: Initial work on a class that manages an IMAP folder on disk.

6a6b7ae: Style cleanup, no functional change.

7135c4f: Renamed pop3.{cpp|h} to POP3.{cpp|h}.

20537ad: Minor coding style cleanup.

e0676bb: Fixed typo.

0f11280: Minor MailNotifier cleanup.
  
  * Renamed to BMailNotifier, as it's part of the public API.
  * Renamed Notifier.{cpp|h} to DefaultNotifier.{cpp|h} as that's the class it
    implements.
  * Made the mail counts uint32, and the byte counts uint64.

715bf3d: Work in progress of mail rework.
  
  * Not everything compiles; all protocols, and inbound filters do, though.
  * Renamed a few classes to give a better idea what they are for; prefixed
    public classes with the 'B' prefix.
  * Moved ProtocolConfigView's classes into the BPrivate namespace.
  * Moved BMailFilter into its own file.
  * Added BMailFilter::DescriptiveName(). This is now used by the RuleFilter
    in order to give a description of what it's doing (ie. no more dozens of
    "Rule filter" entries in the preferences).
  * Removed no longer used MailAddon.h.
  * Renamed Addon to AddOn where found, since that is more consistent with the
    rest of the API.
  * Merged the former MailProtocol with the former MailProtocolThread; the
    differentiation between those two was pretty messy.
  * All configuration views touched so far are now using the layout kit.
  * The RuleFilter is currently broken functionality wise; I have not yet 
decided
    how to solve the stuff it uses (TriggerFileMove() does not exist anymore,
    for example).
  * BMailAddOnSettings (formerly known as AddonSettings) now directly subclass
    BMessage; there are no Settings() and EditSettings() method anymore. The
    class uses a copy of itself to determine whether or not it has been changed.
  * Lots of cleanup.

794a013: Adapted fortune filter to the new mail API.

bebcc47: Renamed a few files to better match their class names.

383b34a: Moved ProtocolConfigView to headers/private/mail.
  
  * This is by no means meant as a public header.

146357b: Completed transition to the new mail API; ie. it compiles.
  
  * Completely untested yet. Unlikely to work yet.

4d30240: Renamed smtp.{cpp|h} to SMTP.{cpp|h}.

ae9d8c6: IMAP now compiles again with GCC 4.

daf972c: Renamed MailDaemon{App|.cpp|.h} to MailDaemonApplication[.{cpp|h}].

e1e78d4: Reset the daemon messenger after a successful Launch().

bcf60bb: Fixed Mail build.
  
  * The former kMsgBodyFetched (now B_MAIL_BODY_FETCHED, following the other
    message constant names in AppDefs.h) must be public.

9d8cf1b: E-mail now also builds, but doesn't work yet.

1f87386: Now also loads mail settings from common.
  
  * Also removed the superfluous and unused timeout argument from Save().

b448d26: Fixed mail daemon build.
  
  * Removed cvs package leftovers.

f90a3bb: Added support for letting user mail add-ons override system ones.
  
  * The path will now be relativized before storing it.
  * On load, the add-on will be tried to load from the user, then common
    and finally system add-on directory.

58b56ff: Improved mail protocol config view layout.

5faab45: Reworked the mail preferences.
  
  * Made it use the layout API.
  * Removed options that no longer apply (dial-up, for example).
  * Cleanup.
  * There are a few issues left, though, for example, the BTextView is not
    correctly sized, and it currently crashes in the protocol panels.

a6943ac: Added missing BMessage::{Get|Set}String() methods.
  
  * Forgot to add those before accidentally.

ca3341c: Major mail protocol/filter settings rework.
  
  * Instead of abusing BArchive::Archive() we now use a BMailSettingsView as
    a base view for all filter/protocol settings that works with
    BMailAddOnSettings.
  * Cleanups in E-mail which is now completely layout friendly. But also still
    crashes when changing the views.

efd1602: Fixed debugger call in E-mail.
  
  * The settings view is no longer a direct child of the protocol settings
    view.

57b3055: MailProtocolConfigView now is a BMailSettingsView.
  
  * Changed the private settings base classes to follow the new style.
  * Made BodyDownloadConfig use the layout API.
  * Adapted SMTP to these changes.

518698c: Removed commented out method in BMailSettingsView.

1da1e5a: Renamed BodyDownloadConfig to BodyDownloadConfigView.

006040d: Adapted POP3, and Fortune to the new MailSettingsView API.

792843e: Adapted IMAP to the new MailSettingsView API.

81ec973: Minor coding style fix.

4a8448c: Major coding style cleanup.

19d947e: The E-mail window's frame is no longer stored.
  
  * This is part of a clean up of BMailSettings; storing the window
    position might be implemented again later -- it just doesn't
    belong there.
  * Changed the logic when the daemon is set to auto start. It's now
    always started if at least a single account exists.

22fc80c: Align all protocol config view labels to the right.

4235da3: Improved label of the button to configure the IMAP folders.

fa587d2: The protocol config view now adds some glue at the bottom.
  
  * This makes all boxes fill the complete height of the window.
  * The SMTP add-on did that itself which makes no sense.

dcb663f: libmail: Fixed missing initialization in protocol view.
  
  * This would cause a crash when the fields were actually not being
    used.

8651ebb: Fixed stale config view pointer in E-mail.
  
  * When removing an account (all accounts would be removed when the app
    was quit), AccountItem::ConfigPanel() was used to remove views.
  * However, this member was only set when a new view was created, never when
    it was removed. This could cause a crash on quit.
  * Removed that member completely, as it was unnecessary, anyway.
  * Fixed naming of AccountItem getters to lose their Get* prefix.

acee88b: E-mail settings are now stored as they should.
  
  * ProtocolSettingsView was still using Archive() instead of SaveInto().
  * However, it looks like BMessage::Set*() does corrupt the message fields.

46851a7: BMessage::SetString() was broken.
  
  * We cannot use the macro for this, unfortunately.

93608ba: Clarified progress parameter names for the MailProtocol.

a9de7ec: pop3: Fixed maintaining fSizes list, and more.
  
  * The list was filled, but never emptied.
  * If SyncMessages() was called more than once for the same POP3 instance,
    this could garble the mails retrieved in the second run.
  * Maintain the total size of mails in fSizes to be able to report progress
    in more detail.
  * Also adapted progress reporting to the argument changes made in MailProtocol
    earlier.
  * Minor cleanup.

d6ce606: pop3: minor cleanup.

c9fb410: IMAP: fixed folder configuration.
  
  * Store the settings, don't archive the view; removed leftovers of the
    old settings API.

edf7745: IMAP: close folder config window on error, show message.

3ab3f57: IMAP: FolderList is supposed to be an interface.
  
  * Made its methods pure virtual.

186c96d: IMAP: Early work in progress of main protocol class.

f8b5e17: Minor cleanup.

c67313f: imap: added Settings::MaxConnections()/IdleMode().
  
  * Also made use of the new BMessage API for the existing methods.

4cab719: mail_daemon: auto check message was leaked, send immediately.
  
  * BMessageRunner does not take ownership of the message.
  * Instead of waiting through the complete interval, we send an auto check
    message immediately after launch (or whenever else the timer is being
    started).
  * Added constant instead of referring to 'moto' for the auto check message.

bfe83ad: imap_tester: Fixed SSL build.

adbe8fc: IMAP: The connection workers are now started.
  
  * On SyncMessages(), the main connection worker is started if it is not 
already
    running (it may only run already in idle mode).
  * This will then list the subscribed folders, and create as many more 
connection
    workers as allowed and make sense.
  * Finally, it will distribute the folders to the workers which don't do 
anything
    further yet.

a4bdd26: imap: Work in progress of connection setup.
  
  * SelectCommand now correctly encodes the mailbox name again.
  * Hierarchy separators from the LIST/LSUB commands are now properly parsed,
    and taken into account.
  * Folders in the file system are now created for mailboxes on the server,
    supporting hierarchical mailbox names.
  * A connection worker now has an IMAPFolder that handles the local side of the
    mailbox, and an IMAPMailbox that handles the server side.
  * Connection workers are now created/deleted, and setup correctly. They will
    now also wait in case they don't have a mailbox until they get some.

7993ddf: imap: Fleshed out command processing.
  
  * Still doesn't do anything useful, though.

82f27de: imap_tester: Fixed build after Protocol.GetFolders() changes.

229c777: imap: Testing for new messages is now working.
  
  * There is now a CheckSubscribedFoldersCommand that is issued on the main
    connection that triggers everything.
  * The new CheckMailboxesCommand divides the new mail check into several
    portions, and requeues itself until the next step, ie. the
    FetchHeadersCommand.
  * The headers of the new mails are downloaded, but nothing is done with
    them yet.
  * The actual check for the new mails doesn't scale that well yet, not sure
    how to properly do this without having to rely on the mail indices. Might
    be sensible to solve this via some simple heuristic.

9234fd4: imap: Implemented encoding RFC3501 strings.
  
  * Was completely missing so far.
  * Fixed bug in decoding that handled the "&-" sequence incorrectly.
  * Added small test application that should easily be convertible to
    a unit test.

3302df1: imap: WIP of getting fetching headers to work.
  
  * Changed the FetchListener mechanism quite a bit.
  * Doesn't seem to work correctly yet, although most pieces are in
    place now.

a6b84a0: BBufferedDataIO: the underlying stream might return an error.
  
  * In this case, fSize would have been set incorrectly, ignoring the error
    completely, but open the possibility to read from uninitialized or even
    unmapped memory.

c500331: BSecureSocket: prepared to do SSL error conversion.
  
  * For now, just print them to stderr; we don't really have matching error
    codes yet AFAICS.

eba458b: imap: Fetching headers is now working.
  
  * No state is stored yet, though, so that all messages will be downloaded
    over and over again.

28ee6c2: IMAP: Use useful default without destination.
  
  * We now use the account name as destination directory.
  * Turns out that an empty string is written as destination which worked
    around the GetString() solution.

47b68f5: IMAP: IMAPFolder now stores the last UID.
  
  * So mails are no longer downloaded every time.

4b2c557: IMAP: sync when requested.

aebdd0c: IMAP: call the folder's handler like the mailbox.

29e5da6: IMAP: allow only one sync at a time, divided header fetching.
  
  * CheckMailboxesCommand, and FetchHeadersCommand now inherit from SyncCommand
    which will prevent new CheckMailboxesCommand to be enqueued.
  * FetchHeadersCommand now only retrieves up to kMaxFetchEntries headers at
    once. This gets the same TODO about scaling as the limit in
    CheckMailboxesCommand when fetching the flags/UIDs. Since we already read
    all new UIDs at that point, we could easily do better there, though.

8705e1f: mail_daemon: cleanup, 30s auto check startup delay.
  
  * Refactored new message retrieval a bit, so that the notification strings
    aren't duplicated.
  * The daemon now waits 30 seconds before doing the first mail check.

e9a197f: IMAP: make the body fetch limit setting available.
  
  * This is set by the ProtocolConfigView -- there should really be
    some constant for this.

dcb85ff: IMAP: if connecting fails, try again a few times.
  
  * Also documented SyncCommand.

1052525: IMAP: work in progress of downloading the mail body.
  
  * Most things are in place now, we just try to download the body to the
    wrong file, as the final location is currently unknown.
  * Added local only kPartialMessage flag for mails, but it's not being
    used yet.

c1f779e: IMAP: FetchMessageEntriesCommand now also works without UIDs
  
  * This will be used to solve the TODO in CheckMailboxesCommand::Process()
    when the initial message sizes/flags are retrieved.
  * Also fixed imap_tester build.

549949b: Mail Kit: Changed how filter changes work.
  
  * BMailFilter::HeaderFetched() now only alters the entry_ref, and returns
    B_MOVE_MAIL_ACTION to move a mail.
  * Instead of potentially moving the file around several times, the
    BMailProtocol now takes care of carrying out the filter action just once,
    including trying to make the file name unique.
  * This also allows the IMAP add-on to know the final location of the mail,
    and thus downloading a message actually works.
  * However, with my test inbox, it currently hangs, and a current Debugger does
    not work on my older system -- I guess I need to update.
  * Replaced the duplicated space mechanism within the "HaikuMailFormatFilter"
    that is substantially faster, and handles all whitespace, not just spaces.
    It will also replace tabs with spaces.

cf14e7f: Build fixes.
  
  * Never built a complete image from the IMAP branch before.

d33e474: IMAP: downloading mails is now working.
  
  * Changed the way the attributes are written to make sure that everything
    that can be written once is in fact written just once.
  * The rename code in BMailProtocol::_ProcessFetchedHeader() was broken,
    and caused the hang of the last commit.

4601929: IMAP: let mail retrieval scale better.
  
  * We now also maintain a mail index -> UID array in IMAPMailbox.
  * Instead of fetching the message entries by a fixed range of UIDs, we use the
    message count, and get the entries by index.
  * Likewise, in FetchHeadersCommand, we now get a list of UIDs rather than a
    range. This makes it possible to only download exactly the headers we want.
  * Extended FetchCommand to be able to dynamically build a sequence list from
    a list of UIDs.
  * Besides the suboptimal body fetching (one at a time, due to holes in the
    IMAP specification), we should now be able to retrieve the messages with
    pretty much optimal performance, while retaining an acceptable 
responsiveness
    to user requests.

                                   [ Axel Dörfler <axeld@xxxxxxxxxxxxxxxx> ]

----------------------------------------------------------------------------

124 files changed, 9273 insertions(+), 8066 deletions(-)
headers/os/add-ons/mail_daemon/MailAddon.h       |  74 --
headers/os/add-ons/mail_daemon/MailFilter.h      |  51 +
headers/os/add-ons/mail_daemon/MailProtocol.h    | 260 ++----
.../os/add-ons/mail_daemon/MailSettingsView.h    |  23 +
.../os/add-ons/mail_daemon/ProtocolConfigView.h  |  69 --
headers/os/app/Message.h                         |   3 +-
headers/os/mail/MailDaemon.h                     |  60 +-
headers/os/mail/MailMessage.h                    | 215 +++--
headers/os/mail/MailSettings.h                   |  81 +-
headers/private/mail/FileConfigView.h            |  86 +-
headers/private/mail/MailPrivate.h               |  21 +-
headers/private/mail/ProtocolConfigView.h        | 106 +++
headers/private/mail/ServerConnection.h          |  48 -
.../inbound_filters/match_header/ConfigView.cpp  | 328 ++++---
.../match_header/MatchHeaderSettings.h           |  64 ++
.../inbound_filters/match_header/RuleFilter.cpp  | 161 ++--
.../inbound_filters/match_header/RuleFilter.h    |  48 +-
.../inbound_filters/notifier/ConfigView.h        |  35 -
.../mail_daemon/inbound_filters/notifier/Jamfile |  10 +-
.../{ConfigView.cpp => NotifierConfigView.cpp}   | 143 ++-
.../notifier/NotifierConfigView.h                |  40 +
.../notifier/{filter.cpp => NotifierFilter.cpp}  |  72 +-
...MailNotification.rdef => NotifierFilter.rdef} |   0
.../inbound_filters/spam_filter/SpamFilter.cpp   | 302 ++----
.../inbound_filters/spam_filter/SpamFilter.h     | 106 +--
.../spam_filter/SpamFilterConfig.cpp             | 500 +++-------
.../inbound_protocols/imap/ConfigView.cpp        | 144 +++
...APFolderConfig.cpp => FolderConfigWindow.cpp} | 190 ++--
.../{IMAPFolderConfig.h => FolderConfigWindow.h} |  20 +-
.../mail_daemon/inbound_protocols/imap/IMAP.h    | 143 +++
.../imap/IMAPConnectionWorker.cpp                | 761 +++++++++++++++
.../imap/IMAPConnectionWorker.h                  | 100 ++
.../inbound_protocols/imap/IMAPFolder.cpp        | 460 +++++++++
.../inbound_protocols/imap/IMAPFolder.h          | 111 +++
.../inbound_protocols/imap/IMAPInboundProtocol.h |   2 +-
.../inbound_protocols/imap/IMAPMailbox.cpp       | 105 +++
.../inbound_protocols/imap/IMAPMailbox.h         |  65 ++
.../inbound_protocols/imap/IMAPProtocol.cpp      | 266 ++++++
.../inbound_protocols/imap/IMAPProtocol.h        |  65 ++
.../imap/IMAPRootInboundProtocol.cpp             |   5 +-
.../mail_daemon/inbound_protocols/imap/Jamfile   |  33 +-
.../inbound_protocols/imap/Settings.cpp          | 110 +++
.../inbound_protocols/imap/Settings.h            |  41 +
.../inbound_protocols/imap/Utilities.cpp         |  21 +
.../inbound_protocols/imap/Utilities.h           |  15 +
.../inbound_protocols/imap/imap_config.cpp       | 152 ---
.../inbound_protocols/imap/imap_lib/Commands.cpp | 820 ++++++++++++++++
.../inbound_protocols/imap/imap_lib/Commands.h   | 345 +++++++
.../imap/imap_lib/IMAPFolders.cpp                | 130 ---
.../imap/imap_lib/IMAPFolders.h                  |  51 -
.../imap/imap_lib/IMAPHandler.cpp                | 936 -------------------
.../imap/imap_lib/IMAPHandler.h                  | 303 ------
.../imap/imap_lib/IMAPMailbox.cpp                |  24 +-
.../imap/imap_lib/IMAPMailbox.h                  |  15 +-
.../imap/imap_lib/IMAPParser.cpp                 | 139 ---
.../inbound_protocols/imap/imap_lib/IMAPParser.h |  35 -
.../imap/imap_lib/IMAPProtocol.cpp               | 433 ---------
.../imap/imap_lib/IMAPProtocol.h                 | 129 ---
.../imap/imap_lib/IMAPStorage.cpp                |   9 +-
.../imap/imap_lib/IMAPStorage.h                  |  13 +-
.../inbound_protocols/imap/imap_lib/Protocol.cpp | 420 +++++++++
.../inbound_protocols/imap/imap_lib/Protocol.h   | 118 +++
.../inbound_protocols/imap/imap_lib/Response.cpp | 530 +++++++++--
.../inbound_protocols/imap/imap_lib/Response.h   | 105 ++-
.../inbound_protocols/pop3/ConfigView.cpp        |  65 +-
.../mail_daemon/inbound_protocols/pop3/Jamfile   |   4 +-
.../inbound_protocols/pop3/MessageIO.h           |   5 +-
.../pop3/{pop3.cpp => POP3.cpp}                  | 391 ++++----
.../inbound_protocols/pop3/{pop3.h => POP3.h}    |  38 +-
.../outbound_filters/fortune/ConfigView.cpp      |  95 +-
.../outbound_filters/fortune/ConfigView.h        |  38 +-
.../outbound_filters/fortune/FortuneFilter.cpp   | 122 +++
.../mail_daemon/outbound_filters/fortune/Jamfile |   4 +-
.../outbound_filters/fortune/filter.cpp          | 100 --
.../outbound_protocols/smtp/ConfigView.cpp       |  89 +-
.../mail_daemon/outbound_protocols/smtp/Jamfile  |   4 +-
.../smtp/{smtp.cpp => SMTP.cpp}                  | 116 ++-
.../outbound_protocols/smtp/{smtp.h => SMTP.h}   |  28 +-
src/add-ons/tracker/mark_as/MarkAs.cpp           |   8 +-
src/add-ons/tracker/mark_as/MarkAsRead.cpp       |  14 +-
src/apps/mail/MailWindow.cpp                     |  11 +-
src/apps/people/AttributeTextControl.cpp         |   7 +-
src/kits/app/Message.cpp                         |   9 +-
src/kits/mail/FileConfigView.cpp                 | 123 +--
src/kits/mail/HaikuMailFormatFilter.cpp          | 153 +--
src/kits/mail/HaikuMailFormatFilter.h            |  30 +-
src/kits/mail/Jamfile                            |   3 +-
src/kits/mail/MailDaemon.cpp                     |  99 +-
src/kits/mail/MailFilter.cpp                     |  53 ++
src/kits/mail/MailMessage.cpp                    | 448 ++++-----
src/kits/mail/MailProtocol.cpp                   | 645 ++++---------
src/kits/mail/MailSettings.cpp                   | 353 ++++---
src/kits/mail/MailSettingsView.cpp               |  19 +
src/kits/mail/ProtocolConfigView.cpp             | 599 +++++-------
src/kits/mail/ServerConnection.cpp               | 410 --------
src/kits/mail/c_mail_api.cpp                     |  61 +-
src/kits/network/libnetapi/SecureSocket.cpp      | 115 ++-
src/kits/support/BufferedDataIO.cpp              |  11 +-
src/preferences/mail/AutoConfigView.cpp          |  49 +-
[ *** stats truncated: 25 lines dropped *** ]

############################################################################

Commit:      37d26ae5e2143d8c7f8d190cc6913880f2f5ae81
URL:         http://cgit.haiku-os.org/haiku/commit/?id=37d26ae
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Tue Nov 29 19:12:15 2011 UTC

Work in progress of rewrite; IMAP doesn't even compile at this point.

----------------------------------------------------------------------------

diff --git 
a/src/add-ons/mail_daemon/inbound_protocols/imap/IMAPFolderConfig.cpp 
b/src/add-ons/mail_daemon/inbound_protocols/imap/IMAPFolderConfig.cpp
index a5c39b0..cada937 100644
--- a/src/add-ons/mail_daemon/inbound_protocols/imap/IMAPFolderConfig.cpp
+++ b/src/add-ons/mail_daemon/inbound_protocols/imap/IMAPFolderConfig.cpp
@@ -329,9 +329,9 @@ FolderConfigWindow::_LoadFolders()
                delete[] passwd;
        }
 
-       fIMAPFolders.Connect(server, username, password, useSSL);
+       fProtocol.Connect(server, username, password, useSSL);
        fFolderList.clear();
-       fIMAPFolders.GetFolders(fFolderList);
+       fProtocol.GetFolders(fFolderList);
        for (unsigned int i = 0; i < fFolderList.size(); i++) {
                FolderInfo& info = fFolderList[i];
                CheckBoxItem* item = new CheckBoxItem(info.folder, 
info.subscribed);
@@ -340,7 +340,7 @@ FolderConfigWindow::_LoadFolders()
        }
 
        uint64 used, total;
-       if (fIMAPFolders.GetQuota(used, total) == B_OK) {
+       if (fProtocol.GetQuota(used, total) == B_OK) {
                char buffer[256];
                BString quotaString = "Server storage: ";
                quotaString += string_for_size(used, buffer, 256);
@@ -377,9 +377,9 @@ FolderConfigWindow::_ApplyChanges()
                FolderInfo& info = fFolderList[i];
                CheckBoxItem* item = (CheckBoxItem*)fFolderListView->ItemAt(i);
                if (info.subscribed && !item->Checked())
-                       fIMAPFolders.UnsubscribeFolder(info.folder);
+                       fProtocol.UnsubscribeFolder(info.folder);
                else if (!info.subscribed && item->Checked())
-                       fIMAPFolders.SubscribeFolder(info.folder);
+                       fProtocol.SubscribeFolder(info.folder);
        }
 
        status->PostMessage(B_QUIT_REQUESTED);
diff --git a/src/add-ons/mail_daemon/inbound_protocols/imap/IMAPFolderConfig.h 
b/src/add-ons/mail_daemon/inbound_protocols/imap/IMAPFolderConfig.h
index f6ae3da..f9a8fde 100644
--- a/src/add-ons/mail_daemon/inbound_protocols/imap/IMAPFolderConfig.h
+++ b/src/add-ons/mail_daemon/inbound_protocols/imap/IMAPFolderConfig.h
@@ -14,7 +14,7 @@
 
 #include <MailSettings.h>
 
-#include "IMAPFolders.h"
+#include "Protocol.h"
 
 
 class FolderConfigWindow : public BWindow {
@@ -28,11 +28,11 @@ private:
                        void                            _LoadFolders();
                        void                            _ApplyChanges();
 
-                       IMAPFolders                     fIMAPFolders;
+                       IMAP::Protocol          fProtocol;
                        BListView*                      fFolderListView;
                        BButton*                        fApplyButton;
        const   BMessage                        fSettings;
-                       FolderList                      fFolderList;
+                       IMAP::FolderList        fFolderList;
 
                        BStringView*            fQuotaView;
 };
diff --git 
a/src/add-ons/mail_daemon/inbound_protocols/imap/IMAPInboundProtocol.h 
b/src/add-ons/mail_daemon/inbound_protocols/imap/IMAPInboundProtocol.h
index 954a1fc..9b3eda7 100644
--- a/src/add-ons/mail_daemon/inbound_protocols/imap/IMAPInboundProtocol.h
+++ b/src/add-ons/mail_daemon/inbound_protocols/imap/IMAPInboundProtocol.h
@@ -15,7 +15,7 @@
 
 #include "MailSettings.h"
 
-#include "IMAPMailbox.h"
+#include "Protocol.h"
 #include "IMAPStorage.h"
 
 
diff --git 
a/src/add-ons/mail_daemon/inbound_protocols/imap/IMAPRootInboundProtocol.cpp 
b/src/add-ons/mail_daemon/inbound_protocols/imap/IMAPRootInboundProtocol.cpp
index b7e4927..544d927 100644
--- a/src/add-ons/mail_daemon/inbound_protocols/imap/IMAPRootInboundProtocol.cpp
+++ b/src/add-ons/mail_daemon/inbound_protocols/imap/IMAPRootInboundProtocol.cpp
@@ -9,8 +9,6 @@
 
 #include <Messenger.h>
 
-#include "IMAPFolders.h"
-
 
 IMAPRootInboundProtocol::IMAPRootInboundProtocol(BMailAccountSettings* 
settings)
        :
@@ -34,9 +32,8 @@ IMAPRootInboundProtocol::Connect(const char* server, const 
char* username,
        if (status != B_OK)
                return status;
 
-       IMAPFolders folder(fIMAPMailbox);
        FolderList folders;
-       folder.GetFolders(folders);
+       fIMAPMailbox.GetFolders(folders);
        for (unsigned int i = 0; i < folders.size(); i++) {
                if (!folders[i].subscribed || folders[i].folder == "INBOX")
                        continue;
diff --git a/src/add-ons/mail_daemon/inbound_protocols/imap/Jamfile 
b/src/add-ons/mail_daemon/inbound_protocols/imap/Jamfile
index d89f922..17a83c8 100644
--- a/src/add-ons/mail_daemon/inbound_protocols/imap/Jamfile
+++ b/src/add-ons/mail_daemon/inbound_protocols/imap/Jamfile
@@ -21,12 +21,10 @@ local sources =
        IMAPRootInboundProtocol.cpp
        IMAPFolderConfig.cpp
        # imap_lib
-       IMAPFolders.cpp
-       IMAPHandler.cpp
-       IMAPMailbox.cpp
-       IMAPParser.cpp
-       IMAPProtocol.cpp
+       Commands.cpp
+       Protocol.cpp
        IMAPStorage.cpp
+       Response.cpp
 ;
 
 AddResources IMAP : IMAP.rdef ;
@@ -46,8 +44,8 @@ Addon IMAP
                libshared.a [ TargetLibsupc++ ] [ TargetLibstdc++ ]
 ;
 
-SEARCH on [ FGristFiles IMAPFolders.cpp IMAPHandler.cpp IMAPMailbox.cpp
-       IMAPParser.cpp IMAPProtocol.cpp IMAPStorage.cpp ServerConnection.cpp ]
+SEARCH on [ FGristFiles Commands.cpp IMAPMailbox.cpp
+               IMAPProtocol.cpp IMAPStorage.cpp Response.cpp ]
        = [ FDirName $(HAIKU_TOP) src add-ons mail_daemon inbound_protocols imap
                imap_lib ] ;
 
diff --git 
a/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPHandler.cpp 
b/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/Commands.cpp
similarity index 69%
rename from 
src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPHandler.cpp
rename to src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/Commands.cpp
index 695f869..afcd7ed 100644
--- a/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPHandler.cpp
+++ b/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/Commands.cpp
@@ -5,16 +5,12 @@
  */
 
 
-#include "IMAPHandler.h"
+#include "Commands.h"
 
 #include <stdlib.h>
 
 #include <AutoDeleter.h>
 
-#include "IMAPMailbox.h"
-#include "IMAPParser.h"
-#include "IMAPStorage.h"
-
 
 #define DEBUG_IMAP_HANDLER
 #ifdef DEBUG_IMAP_HANDLER
@@ -28,48 +24,166 @@
 using namespace BPrivate;
 
 
-IMAPCommand::~IMAPCommand()
+namespace IMAP {
+
+
+static HandlerListener sEmptyHandler;
+
+
+Handler::Handler()
+       :
+       fListener(&sEmptyHandler)
+{
+}
+
+
+Handler::~Handler()
+{
+}
+
+
+void
+Handler::SetListener(HandlerListener& listener)
+{
+       fListener = &listener;
+}
+
+
+IMAP::LiteralHandler*
+Handler::LiteralHandler()
+{
+       return NULL;
+}
+
+
+// #pragma mark -
+
+
+Command::~Command()
+{
+}
+
+
+status_t
+Command::HandleTagged(Response& response)
+{
+       if (response.StringAt(0) == "OK")
+               return B_OK;
+       if (response.StringAt(0) == "BAD")
+               return B_BAD_VALUE;
+       if (response.StringAt(0) == "NO")
+               return B_NOT_ALLOWED;
+
+       return B_ERROR;
+}
+
+
+// #pragma mark -
+
+
+HandlerListener::~HandlerListener()
+{
+}
+
+
+void
+HandlerListener::ExpungeReceived(int32 number)
+{
+}
+
+
+void
+HandlerListener::ExistsReceived(int32 number)
+{
+}
+
+
+void
+HandlerListener::FetchBody(Command& command, int32 size)
+{
+}
+
+
+// #pragma mark -
+
+
+RawCommand::RawCommand(const BString& command)
+       :
+       fCommand(command)
 {
 }
 
 
 BString
-IMAPCommand::Command()
+RawCommand::CommandString()
 {
-       return "";
+       return fCommand;
 }
 
 
-IMAPMailboxCommand::IMAPMailboxCommand(IMAPMailbox& mailbox)
+// #pragma mark -
+
+
+LoginCommand::LoginCommand(const char* user, const char* password)
        :
-       fIMAPMailbox(mailbox),
-       fStorage(mailbox.GetStorage()),
-       fConnectionReader(mailbox.GetConnectionReader())
+       fUser(user),
+       fPassword(password)
 {
 }
 
 
-IMAPMailboxCommand::~IMAPMailboxCommand()
+BString
+LoginCommand::CommandString()
 {
+       BString command = "LOGIN ";
+       command << "\"" << fUser << "\" " << "\"" << fPassword << "\"";
+
+       return command;
+}
+
+
+bool
+LoginCommand::HandleUntagged(Response& response)
+{
+       if (!response.EqualsAt(0, "OK") || !response.IsListAt(1, '['))
+               return false;
+
+       // TODO: we only support capabilities at the moment
+       ArgumentList& list = response.ListAt(1);
+       if (!list.EqualsAt(0, "CAPABILITY"))
+               return false;
+
+       fCapabilities.MakeEmpty();
+       while (list.CountItems() > 1)
+               fCapabilities.AddItem(list.RemoveItemAt(1));
+
+       TRACE("CAPABILITY: %s\n", fCapabilities.ToString().String());
+       return true;
 }
 
 
 // #pragma mark -
 
 
-MailboxSelectHandler::MailboxSelectHandler(IMAPMailbox& mailbox)
+SelectCommand::SelectCommand()
        :
-       IMAPMailboxCommand(mailbox),
+       fNextUID(0),
+       fUIDValidity(0)
+{
+}
 
-       fMailboxName(""),
-       fNextUID(-1),
-       fUIDValidity(-1)
+
+SelectCommand::SelectCommand(const char* name)
+       :
+       fMailboxName(name),
+       fNextUID(0),
+       fUIDValidity(0)
 {
 }
 
 
 BString
-MailboxSelectHandler::Command()
+SelectCommand::CommandString()
 {
        if (fMailboxName == "")
                return "";
@@ -82,21 +196,19 @@ MailboxSelectHandler::Command()
 
 
 bool
-MailboxSelectHandler::Handle(const BString& response)
+SelectCommand::HandleUntagged(Response& response)
 {
-       BString extracted = IMAPParser::ExtractStringAfter(response,
-               "* OK [UIDVALIDITY");
-       if (extracted != "") {
-               fUIDValidity = IMAPParser::RemoveIntegerFromLeft(extracted);
-               TRACE("UIDValidity %i\n", (int)fUIDValidity);
-               return true;
-       }
-
-       extracted = IMAPParser::ExtractStringAfter(response, "* OK [UIDNEXT");
-       if (extracted != "") {
-               fNextUID = IMAPParser::RemoveIntegerFromLeft(extracted);
-               TRACE("NextUID %i\n", (int)fNextUID);
-               return true;
+       if (response.EqualsAt(0, "OK") && response.IsListAt(1, '[')) {
+               const ArgumentList& arguments = response.ListAt(1);
+               if (arguments.EqualsAt(0, "UIDVALIDITY")
+                       && arguments.IsNumberAt(1)) {
+                       fUIDValidity = arguments.NumberAt(1);
+                       return true;
+               } else if (arguments.EqualsAt(0, "UIDNEXT")
+                       && arguments.IsNumberAt(1)) {
+                       fNextUID = arguments.NumberAt(1);
+                       return true;
+               }
        }
 
        return false;
@@ -106,42 +218,94 @@ MailboxSelectHandler::Handle(const BString& response)
 // #pragma mark -
 
 
-CapabilityHandler::CapabilityHandler()
+BString
+CapabilityHandler::CommandString()
+{
+       return "CAPABILITY";
+}
+
+
+bool
+CapabilityHandler::HandleUntagged(Response& response)
+{
+       if (!response.IsCommand("CAPABILITY"))
+               return false;
+
+       fCapabilities.MakeEmpty();
+       while (response.CountItems() > 1)
+               fCapabilities.AddItem(response.RemoveItemAt(1));
+
+       TRACE("CAPABILITY: %s\n", fCapabilities.ToString().String());
+       return true;
+}
+
+
+// #pragma mark -
+
+
+FetchMessageEntriesCommand::FetchMessageEntriesCommand(
+       MessageEntryList& entries, uint32 from, uint32 to)
        :
-       fCapabilities("")
+       fEntries(entries),
+       fFrom(from),
+       fTo(to)
 {
 }
 
 
 BString
-CapabilityHandler::Command()
+FetchMessageEntriesCommand::CommandString()
 {
-       return "CAPABILITY";
+       BString command = "UID FETCH ";
+       command << fFrom << ":" << fTo << " FLAGS";
+
+       return command;
 }
 
 
 bool
-CapabilityHandler::Handle(const BString& response)
+FetchMessageEntriesCommand::HandleUntagged(Response& response)
 {
-       BString cap = IMAPParser::ExtractStringAfter(response, "* CAPABILITY");
-       if (cap == "")
+       if (!response.EqualsAt(1, "FETCH") || !response.IsListAt(2))
                return false;
-       fCapabilities = cap;
-       TRACE("CAPABILITY: %s\n", fCapabilities.String());
-       return true;
-}
 
+       MessageEntry entry;
+
+       ArgumentList& list = response.ListAt(2);
+       for (int32 i = 0; i < list.CountItems(); i += 2) {
+               if (list.EqualsAt(i, "UID") && list.IsNumberAt(i + 1))
+                       entry.uid = list.NumberAt(i + 1);
+               else if (list.EqualsAt(i, "FLAGS") && list.IsListAt(i + 1)) {
+                       // Parse flags
+                       ArgumentList& flags = list.ListAt(i + 1);
+                       printf("flags: %s\n", flags.ToString().String());
+                       for (int32 j = 0; j < flags.CountItems(); j++) {
+                               if (flags.EqualsAt(j, "\\Seen"))
+                                       entry.flags |= kSeen;
+                               else if (flags.EqualsAt(j, "\\Answered"))
+                                       entry.flags |= kAnswered;
+                               else if (flags.EqualsAt(j, "\\Flagged"))
+                                       entry.flags |= kFlagged;
+                               else if (flags.EqualsAt(j, "\\Deleted"))
+                                       entry.flags |= kDeleted;
+                               else if (flags.EqualsAt(j, "\\Draft"))
+                                       entry.flags |= kDraft;
+                       }
+               }
+       }
 
-BString&
-CapabilityHandler::Capabilities()
-{
-       return fCapabilities;
+       if (entry.uid == 0)
+               return false;
+
+       fEntries.push_back(entry);
+       return true;
 }
 
 
 // #pragma mark -
 
 
+#if 0
 FetchMinMessageCommand::FetchMinMessageCommand(IMAPMailbox& mailbox,
        int32 message, MinMessageList* list, BPositionIO** data)
        :
@@ -170,7 +334,7 @@ FetchMinMessageCommand::FetchMinMessageCommand(IMAPMailbox& 
mailbox,
 
 
 BString
-FetchMinMessageCommand::Command()
+FetchMinMessageCommand::CommandString()
 {
        if (fMessage <= 0)
                return "";
@@ -186,7 +350,7 @@ FetchMinMessageCommand::Command()
 
 
 bool
-FetchMinMessageCommand::Handle(const BString& response)
+FetchMinMessageCommand::HandleUntagged(const BString& response)
 {
        BString extracted = response;
        int32 message;
@@ -256,47 +420,6 @@ FetchMinMessageCommand::ExtractFlags(const BString& 
response)
 // #pragma mark -
 
 
-FetchMessageListCommand::FetchMessageListCommand(IMAPMailbox& mailbox,
-       MinMessageList* list, int32 nextId)
-       :
-       IMAPMailboxCommand(mailbox),
-
-       fMinMessageList(list),
-       fNextId(nextId)
-{
-}
-
-
-BString
-FetchMessageListCommand::Command()
-{
-       BString command = "UID FETCH 1:";
-       command << fNextId - 1;
-       command << " FLAGS";
-       return command;
-}
-
-
-bool
-FetchMessageListCommand::Handle(const BString& response)
-{
-       BString extracted = response;
-       int32 message;
-       if (!IMAPParser::RemoveUntagedFromLeft(extracted, "FETCH", message))
-               return false;
-
-       MinMessage minMessage;
-       if (!FetchMinMessageCommand::ParseMinMessage(extracted, minMessage))
-               return false;
-
-       fMinMessageList->push_back(minMessage);
-       return true;
-}
-
-
-// #pragma mark -
-
-
 FetchMessageCommand::FetchMessageCommand(IMAPMailbox& mailbox, int32 message,
        BPositionIO* data, int32 fetchBodyLimit)
        :
@@ -335,7 +458,7 @@ FetchMessageCommand::~FetchMessageCommand()
 
 
 BString
-FetchMessageCommand::Command()
+FetchMessageCommand::CommandString()
 {
        BString command = "FETCH ";
        command << fMessage;
@@ -349,7 +472,7 @@ FetchMessageCommand::Command()
 
 
 bool
-FetchMessageCommand::Handle(const BString& response)
+FetchMessageCommand::HandleUntagged(const BString& response)
 {
        BString extracted = response;
        int32 message;
@@ -454,7 +577,7 @@ FetchBodyCommand::~FetchBodyCommand()
 
 
 BString
-FetchBodyCommand::Command()
+FetchBodyCommand::CommandString()
 {
        BString command = "FETCH ";
        command << fMessage;
@@ -464,7 +587,7 @@ FetchBodyCommand::Command()
 
 
 bool
-FetchBodyCommand::Handle(const BString& response)
+FetchBodyCommand::HandleUntagged(const BString& response)
 {
        if (response.FindFirst("FETCH") < 0)
                return false;
@@ -521,7 +644,7 @@ SetFlagsCommand::SetFlagsCommand(IMAPMailbox& mailbox, 
int32 message,
 
 
 BString
-SetFlagsCommand::Command()
+SetFlagsCommand::CommandString()
 {
        BString command = "STORE ";
        command << fMessage;
@@ -533,7 +656,7 @@ SetFlagsCommand::Command()
 
 
 bool
-SetFlagsCommand::Handle(const BString& response)
+SetFlagsCommand::HandleUntagged(const BString& response)
 {
        return false;
 }
@@ -576,7 +699,7 @@ AppendCommand::AppendCommand(IMAPMailbox& mailbox, 
BPositionIO& message,
 
 
 BString
-AppendCommand::Command()
+AppendCommand::CommandString()
 {
        BString command = "APPEND ";
        command << fIMAPMailbox.Mailbox();
@@ -591,7 +714,7 @@ AppendCommand::Command()
 
 
 bool
-AppendCommand::Handle(const BString& response)
+AppendCommand::HandleUntagged(const BString& response)
 {
        if (response.FindFirst("+") != 0)
                return false;
@@ -614,21 +737,27 @@ AppendCommand::Handle(const BString& response)
        fIMAPMailbox.SendRawData(CRLF, strlen(CRLF));
        return true;
 }
+#endif
 
 
 // #pragma mark -
 
 
-ExistsHandler::ExistsHandler(IMAPMailbox& mailbox)
-       :
-       IMAPMailboxCommand(mailbox)
+ExistsHandler::ExistsHandler()
 {
 }
 
 
 bool
-ExistsHandler::Handle(const BString& response)
+ExistsHandler::HandleUntagged(Response& response)
 {
+       if (!response.EqualsAt(1, "EXISTS") || response.IsNumberAt(0))
+               return false;
+
+       int32 expunge = response.NumberAt(0);
+       Listener().ExistsReceived(expunge);
+
+#if 0
        if (response.FindFirst("EXISTS") < 0)
                return false;
 
@@ -654,6 +783,7 @@ ExistsHandler::Handle(const BString& response)
 
        TRACE("EXISTS %i\n", (int)exists);
        fIMAPMailbox.SendRawCommand("DONE");
+#endif
 
        return true;
 }
@@ -662,47 +792,36 @@ ExistsHandler::Handle(const BString& response)
 // #pragma mark -
 
 
-ExpungeCommmand::ExpungeCommmand(IMAPMailbox& mailbox)
-       :
-       IMAPMailboxCommand(mailbox)
+ExpungeCommand::ExpungeCommand()
 {
 }
 
 
 BString
-ExpungeCommmand::Command()
+ExpungeCommand::CommandString()
 {
        return "EXPUNGE";
 }
 
 
-bool
-ExpungeCommmand::Handle(const BString& response)
-{
-       return false;
-}
-
-
 // #pragma mark -
 
 
-ExpungeHandler::ExpungeHandler(IMAPMailbox& mailbox)
-       :
-       IMAPMailboxCommand(mailbox)
+ExpungeHandler::ExpungeHandler()
 {
 }
 
 
 bool
-ExpungeHandler::Handle(const BString& response)
+ExpungeHandler::HandleUntagged(Response& response)
 {
-       if (response.FindFirst("EXPUNGE") < 0)
+       if (!response.EqualsAt(1, "EXPUNGE") || response.IsNumberAt(0))
                return false;
 
-       int32 expunge = 0;
-       if (!IMAPParser::ExtractUntagedFromLeft(response, "EXPUNGE", expunge))
-               return false;
+       int32 expunge = response.NumberAt(0);
+       Listener().ExpungeReceived(expunge);
 
+#if 0
        // remove from storage
        IMAPStorage& storage = fIMAPMailbox.GetStorage();
        storage.DeleteMessage(fIMAPMailbox.MessageNumberToUID(expunge));
@@ -717,6 +836,7 @@ ExpungeHandler::Handle(const BString& response)
        // the watching loop restarts again, we need to watch again to because
        // some IDLE implementation stop sending notifications
        fIMAPMailbox.SendRawCommand("DONE");
+#endif
        return true;
 }
 
@@ -724,6 +844,7 @@ ExpungeHandler::Handle(const BString& response)
 // #pragma mark -
 
 
+#if 0
 FlagsHandler::FlagsHandler(IMAPMailbox& mailbox)
        :
        IMAPMailboxCommand(mailbox)
@@ -732,7 +853,7 @@ FlagsHandler::FlagsHandler(IMAPMailbox& mailbox)
 
 
 bool
-FlagsHandler::Handle(const BString& response)
+FlagsHandler::HandleUntagged(const BString& response)
 {
        if (response.FindFirst("FETCH") < 0)
                return false;
@@ -749,13 +870,14 @@ FlagsHandler::Handle(const BString& response)
 
        return true;
 }
+#endif
 
 
 // #pragma mark -
 
 
 BString
-ListCommand::Command()
+ListCommand::CommandString()
 {
        fFolders.clear();
        return "LIST \"\" \"*\"";
@@ -763,9 +885,14 @@ ListCommand::Command()
 
 
 bool
-ListCommand::Handle(const BString& response)
+ListCommand::HandleUntagged(Response& response)
 {
-       return ParseList("LIST", response, fFolders);
+       if (response.IsCommand("LIST") && response.IsStringAt(3)) {
+               fFolders.push_back(response.StringAt(3));
+               return true;
+       }
+
+       return false;
 }
 
 
@@ -776,41 +903,11 @@ ListCommand::FolderList()
 }
 
 
-bool
-ListCommand::ParseList(const char* command, const BString& response,
-       StringList& list)
-{
-       int32 textPos = response.FindFirst(command);
-       if (textPos < 0)
-               return false;
-       BString extracted = response;
-
-       extracted.Remove(0, textPos + strlen(command) + 1);
-       extracted.Trim();
-       if (extracted[0] == '(') {
-               BString flags = IMAPParser::ExtractBetweenBrackets(extracted, 
"(", ")");
-               if (flags.IFindFirst("\\Noselect") >= 0)
-                       return true;
-               textPos = extracted.FindFirst(")");
-               extracted.Remove(0, textPos + 1);
-       }
-
-       IMAPParser::RemovePrimitiveFromLeft(extracted);
-       extracted.Trim();
-       // remove quotation marks
-       extracted.Remove(0, 1);
-       extracted.Truncate(extracted.Length() - 1);
-
-       list.push_back(extracted);
-       return true;
-}
-
-
 // #pragma mark -
 
 
 BString
-ListSubscribedCommand::Command()
+ListSubscribedCommand::CommandString()
 {
        fFolders.clear();
        return "LSUB \"\" \"*\"";
@@ -818,9 +915,14 @@ ListSubscribedCommand::Command()
 
 
 bool
-ListSubscribedCommand::Handle(const BString& response)
+ListSubscribedCommand::HandleUntagged(Response& response)
 {
-       return ListCommand::ParseList("LSUB", response, fFolders);
+       if (response.IsCommand("LSUB") && response.IsStringAt(3)) {
+               fFolders.push_back(response.StringAt(3));
+               return true;
+       }
+
+       return false;
 }
 
 
@@ -842,7 +944,7 @@ SubscribeCommand::SubscribeCommand(const char* mailboxName)
 
 
 BString
-SubscribeCommand::Command()
+SubscribeCommand::CommandString()
 {
        BString command = "SUBSCRIBE \"";
        command += fMailboxName;
@@ -851,13 +953,6 @@ SubscribeCommand::Command()
 }
 
 
-bool
-SubscribeCommand::Handle(const BString& response)
-{
-       return false;
-}
-
-
 // #pragma mark -
 
 
@@ -869,7 +964,7 @@ UnsubscribeCommand::UnsubscribeCommand(const char* 
mailboxName)
 
 
 BString
-UnsubscribeCommand::Command()
+UnsubscribeCommand::CommandString()
 {
        BString command = "UNSUBSCRIBE \"";
        command += fMailboxName;
@@ -878,13 +973,6 @@ UnsubscribeCommand::Command()
 }
 
 
-bool
-UnsubscribeCommand::Handle(const BString& response)
-{
-       return false;
-}
-
-
 // #pragma mark -
 
 
@@ -898,7 +986,7 @@ GetQuotaCommand::GetQuotaCommand(const char* mailboxName)
 
 
 BString
-GetQuotaCommand::Command()
+GetQuotaCommand::CommandString()
 {
        BString command = "GETQUOTA \"";
        command += fMailboxName;
@@ -908,15 +996,14 @@ GetQuotaCommand::Command()
 
 
 bool
-GetQuotaCommand::Handle(const BString& response)
+GetQuotaCommand::HandleUntagged(Response& response)
 {
-       if (response.FindFirst("QUOTA") < 0)
+       if (!response.IsCommand("QUOTA") || response.IsListAt(1))
                return false;
 
-       BString data = IMAPParser::ExtractBetweenBrackets(response, "(", ")");
-       IMAPParser::RemovePrimitiveFromLeft(data);
-       fUsedStorage = (uint64)IMAPParser::RemoveIntegerFromLeft(data) * 1024;
-       fTotalStorage = (uint64)IMAPParser::RemoveIntegerFromLeft(data) * 1024;
+       const ArgumentList& arguments = response.ListAt(1);
+       fUsedStorage = (uint64)arguments.NumberAt(0) * 1024;
+       fTotalStorage = (uint64)arguments.NumberAt(1) * 1024;
 
        return true;
 }
@@ -934,3 +1021,6 @@ GetQuotaCommand::TotalStorage()
 {
        return fTotalStorage;
 }
+
+
+}      // namespace
diff --git a/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/Commands.h 
b/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/Commands.h
new file mode 100644
index 0000000..8a6e828
--- /dev/null
+++ b/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/Commands.h
@@ -0,0 +1,362 @@
+/*
+ * Copyright 2010-2011, Haiku Inc. All Rights Reserved.
+ * Copyright 2010 Clemens Zeidler. All rights reserved.
+ *
+ * Distributed under the terms of the MIT License.
+ */
+#ifndef COMMANDS_H
+#define COMMANDS_H
+
+
+#include <vector>
+
+#include "Response.h"
+
+
+typedef std::vector<BString> StringList;
+
+
+namespace IMAP {
+
+
+class ConnectionReader;
+class HandlerListener;
+
+
+struct MessageEntry {
+       MessageEntry()
+               :
+               uid(0),
+               flags(0)
+       {
+       }
+
+       uint32  uid;
+       uint32  flags;
+};
+typedef std::vector<MessageEntry> MessageEntryList;
+
+enum MessageFlags {
+       kSeen           = 0x01,
+       kAnswered       = 0x02,
+       kFlagged        = 0x04,
+       kDeleted        = 0x08,
+       kDraft          = 0x10
+};
+
+
+class Handler {
+public:
+                                                               Handler();
+       virtual                                         ~Handler();
+
+                       void                            
SetListener(HandlerListener& listener);
+                       HandlerListener&        Listener() { return *fListener; 
}
+
+       virtual bool                            HandleUntagged(Response& 
response) = 0;
+       virtual IMAP::LiteralHandler* LiteralHandler();
+
+protected:
+                       HandlerListener*        fListener;
+};
+
+
+class Command {
+public:
+       virtual                                         ~Command();
+
+       virtual BString                         CommandString() = 0;
+       virtual status_t                        HandleTagged(Response& 
response);
+};
+
+
+class HandlerListener {
+public:
+       virtual                                         ~HandlerListener();
+
+       virtual void                            ExpungeReceived(int32 number);
+       virtual void                            ExistsReceived(int32 number);
+       virtual void                            FetchBody(Command& command, 
int32 size);
+};
+
+
+class RawCommand : public Command {
+public:
+                                                               
RawCommand(const BString& command);
+
+       virtual BString                         CommandString();
+
+private:
+                       BString                         fCommand;
+};
+
+
+class LoginCommand : public Command, public Handler {
+public:
+                                                               
LoginCommand(const char* user,
+                                                                       const 
char* password);
+
+       virtual BString                         CommandString();
+       virtual bool                            HandleUntagged(Response& 
response);
+
+                       const ArgumentList&     Capabilities() const { return 
fCapabilities; }
+
+private:
+                       const char*                     fUser;
+                       const char*                     fPassword;
+                       ArgumentList            fCapabilities;
+};
+
+
+class SelectCommand : public Command, public Handler {
+public:
+                                                               SelectCommand();
+                                                               
SelectCommand(const char* mailboxName);
+
+                       BString                         CommandString();
+                       bool                            
HandleUntagged(Response& response);
+
+                       void                            SetTo(const char* 
mailboxName)
+                                                                       { 
fMailboxName = mailboxName; }
+                       uint32                          NextUID() { return 
fNextUID; }
+                       uint32                          UIDValidity() { return 
fUIDValidity; }
+
+private:
+                       BString                         fMailboxName;
+                       uint32                          fNextUID;
+                       uint32                          fUIDValidity;
+};
+
+
+class CapabilityHandler : public Command, public Handler {
+public:
+       virtual BString                         CommandString();
+       virtual bool                            HandleUntagged(Response& 
response);
+
+                       const ArgumentList&     Capabilities() const { return 
fCapabilities; }
+
+private:
+                       ArgumentList            fCapabilities;
+};
+
+
+class FetchMessageEntriesCommand : public Command, public Handler {
+public:
+                                                               
FetchMessageEntriesCommand(
+                                                                       
MessageEntryList& entries, uint32 from,
+                                                                       uint32 
to);
+
+                       BString                         CommandString();
+       virtual bool                            HandleUntagged(Response& 
response);
+
+private:
+                       MessageEntryList&       fEntries;
+                       uint32                          fFrom;
+                       uint32                          fTo;
+};
+
+#if 0
+
+
+class FetchMinMessageCommand : public IMAPMailboxCommand {
+public:
+                                                               
FetchMinMessageCommand(IMAPMailbox& mailbox,
+                                                                       int32 
message, MinMessageList* list,
+                                                                       
BPositionIO** data);
+                                                               
FetchMinMessageCommand(IMAPMailbox& mailbox,
+                                                                       int32 
firstMessage, int32 lastMessage,
+                                                                       
MinMessageList* list, BPositionIO** data);
+
+                       BString                         CommandString();
+                       bool                            HandleUntagged(const 
BString& response);
+
+       static  bool                            ParseMinMessage(const BString& 
response,
+                                                                       
MinMessage& minMessage);
+       static  int32                           ExtractFlags(const BString& 
response);
+
+private:
+                       int32                           fMessage;
+                       int32                           fEndMessage;
+                       MinMessageList*         fMinMessageList;
+                       BPositionIO**           fData;
+};
+
+
+class FetchMessageCommand : public IMAPMailboxCommand {
+public:
+                                                               
FetchMessageCommand(IMAPMailbox& mailbox,
+                                                                       int32 
message, BPositionIO* data,
+                                                                       int32 
fetchBodyLimit = -1);
+                       /*! Fetch multiple message within a range. */
+                                                               
FetchMessageCommand(IMAPMailbox& mailbox,
+                                                                       int32 
firstMessage, int32 lastMessage,
+                                                                       int32 
fetchBodyLimit = -1);
+                                                               
~FetchMessageCommand();
+
+                       BString                         CommandString();
+                       bool                            HandleUntagged(const 
BString& response);
+
+private:
+                       int32                           fMessage;
+                       int32                           fEndMessage;
+                       BPositionIO*            fOutData;
+                       int32                           fFetchBodyLimit;
+                       int32                           fUnhandled;
+};
+
+
+class FetchBodyCommand : public IMAPMailboxCommand {
+public:
+                                                               /*! takes 
ownership of the data */
+                                                               
FetchBodyCommand(IMAPMailbox& mailbox,
+                                                                       int32 
message, BPositionIO* data);
+                                                               
~FetchBodyCommand();
+
+                       BString                         CommandString();
+                       bool                            HandleUntagged(const 
BString& response);
+
+private:
+                       int32                           fMessage;
+                       BPositionIO*            fOutData;
+};
+
+
+class SetFlagsCommand : public IMAPMailboxCommand {
+public:
+                                                               
SetFlagsCommand(IMAPMailbox& mailbox,
+                                                                       int32 
message, int32 flags);
+
+                       BString                         CommandString();
+                       bool                            HandleUntagged(const 
BString& response);
+
+       static  BString                         GenerateFlagList(int32 flags);
+
+private:
+                       int32                           fMessage;
+                       int32                           fFlags;
+};
+
+
+class AppendCommand : public IMAPMailboxCommand {
+public:
+                                                               
AppendCommand(IMAPMailbox& mailbox,
+                                                                       
BPositionIO& message, off_t size,
+                                                                       int32 
flags, time_t time);
+
+                       BString                         CommandString();
+                       bool                            HandleUntagged(const 
BString& response);
+
+private:
+                       BPositionIO&            fMessageData;
+                       off_t                           fDataSize;
+                       int32                           fFlags;
+                       time_t                          fTime;
+};
+#endif
+
+
+class ExistsHandler : public Handler {
+public:
+                                                               ExistsHandler();
+
+                       bool                            
HandleUntagged(Response& response);
+};
+
+
+/*! Just send a expunge command to delete kDeleted flagged messages. The
+       response is handled by the unsolicited ExpungeHandler which is installed
+       all the time.
+*/
+class ExpungeCommand : public Command {
+public:
+                                                               
ExpungeCommand();
+
+                       BString                         CommandString();
+};
+
+
+class ExpungeHandler : public Handler {
+public:
+                                                               
ExpungeHandler();
+
+                       bool                            
HandleUntagged(Response& response);
+};
+
+
+#if 0
+class FlagsHandler : public Handler {
+public:
+                                                               
FlagsHandler(IMAPMailbox& mailbox);
+
+                       bool                            HandleUntagged(const 
BString& response);
+};
+#endif
+
+
+class ListCommand : public Command, public Handler {
+public:
+                       BString                         CommandString();
+                       bool                            
HandleUntagged(Response& response);
+
+       const   StringList&                     FolderList();
+
+private:
+                       StringList                      fFolders;
+};
+
+
+class ListSubscribedCommand : public Command, public Handler {
+public:
+                       BString                         CommandString();
+                       bool                            
HandleUntagged(Response& response);
+
+       const   StringList&                     FolderList();
+
+private:
+                       StringList                      fFolders;
+};
+
+
+class SubscribeCommand : public Command {
+public:
+                                                               
SubscribeCommand(const char* mailboxName);
+
+                       BString                         CommandString();
+
+private:
+                       BString                         fMailboxName;
+};
+
+
+class UnsubscribeCommand : public Command {
+public:
+                                                               
UnsubscribeCommand(const char* mailboxName);
+
+                       BString                         CommandString();
+
+private:
+                       BString                         fMailboxName;
+};
+
+
+class GetQuotaCommand : public Command, public Handler {
+public:
+                                                               
GetQuotaCommand(const char* mailboxName = "");
+
+                       BString                         CommandString();
+                       bool                            
HandleUntagged(Response& response);
+
+                       uint64                          UsedStorage();
+                       uint64                          TotalStorage();
+private:
+                       BString                         fMailboxName;
+
+                       uint64                          fUsedStorage;
+                       uint64                          fTotalStorage;
+};
+
+
+}      // namespace IMAP
+
+
+#endif // COMMANDS_H
diff --git 
a/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPFolders.cpp 
b/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPFolders.cpp
deleted file mode 100644
index 6d16ab2..0000000
--- a/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPFolders.cpp
+++ /dev/null
@@ -1,130 +0,0 @@
-/*
- * Copyright 2011, Haiku, Inc. All rights reserved.
- * Copyright 2011, Clemens Zeidler <haiku@xxxxxxxxxxxxxxxxxx>
- * Distributed under the terms of the MIT License.
- */
-
-
-#include "IMAPFolders.h"
-
-
-IMAPFolders::IMAPFolders()
-{
-       fHandlerList.AddItem(&fCapabilityHandler);
-}
-
-
-IMAPFolders::IMAPFolders(IMAPProtocol& connection)
-       :
-       IMAPProtocol(connection)
-{
-       fHandlerList.AddItem(&fCapabilityHandler);
-}
-
-
-status_t
-IMAPFolders::GetFolders(FolderList& folders)
-{
-       StringList allFolders;
-       status_t status = _GetAllFolders(allFolders);
-       if (status != B_OK)
-               return status;
-       StringList subscribedFolders;
-       status = _GetSubscribedFolders(subscribedFolders);
-       if (status != B_OK)
-               return status;
-
-       for (unsigned int i = 0; i < allFolders.size(); i++) {
-               FolderInfo info;
-               info.folder = allFolders[i];
-               for (unsigned int a = 0; a < subscribedFolders.size(); a++) {
-                       if (allFolders[i] == subscribedFolders[a]
-                               || allFolders[i].ICompare("INBOX") == 0) {
-                               info.subscribed = true;
-                               break;
-                       }
-               }
-               folders.push_back(info);
-       }
-
-       // you could be subscribed to a folder which not exist currently, add 
them:
-       for (unsigned int a = 0; a < subscribedFolders.size(); a++) {
-               bool isInlist = false;
-               for (unsigned int i = 0; i < allFolders.size(); i++) {
-                       if (subscribedFolders[a] == allFolders[i]) {
-                               isInlist = true;
-                               break;
-                       }
-               }
-               if (isInlist)
-                       continue;
-
-               FolderInfo info;
-               info.folder = subscribedFolders[a];
-               info.subscribed = true;
-               folders.push_back(info);
-       }
-
-       return B_OK;
-}
-
-
-status_t
-IMAPFolders::SubscribeFolder(const char* folder)
-{
-       SubscribeCommand command(folder);
-       return ProcessCommand(&command);
-}
-
-
-status_t
-IMAPFolders::UnsubscribeFolder(const char* folder)
-{
-       UnsubscribeCommand command(folder);
-       return ProcessCommand(&command);
-}
-
-
-status_t
-IMAPFolders::GetQuota(uint64& used, uint64& total)
-{
-       if (fCapabilityHandler.Capabilities() == "")
-               ProcessCommand(fCapabilityHandler.Command());
-       if (fCapabilityHandler.Capabilities().FindFirst("QUOTA") < 0)
-               return B_ERROR;
-
-       GetQuotaCommand quotaCommand;
-       status_t status = ProcessCommand(&quotaCommand);
-       if (status != B_OK)
-               return status;
-
-       used = quotaCommand.UsedStorage();
-       total = quotaCommand.TotalStorage();
-       return B_OK;
-}
-
-
-status_t
-IMAPFolders::_GetAllFolders(StringList& folders)
-{
-       ListCommand listCommand;
-       status_t status = ProcessCommand(&listCommand);
-       if (status != B_OK)
-               return status;
-
-       folders = listCommand.FolderList();
-       return status;
-}
-
-
-status_t
-IMAPFolders::_GetSubscribedFolders(StringList& folders)
-{
-       ListSubscribedCommand listSubscribedCommand;
-       status_t status = ProcessCommand(&listSubscribedCommand);
-       if (status != B_OK)
-               return status;
-
-       folders = listSubscribedCommand.FolderList();
-       return status;
-}
diff --git 
a/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPFolders.h 
b/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPFolders.h
deleted file mode 100644
index 8f230b0..0000000
--- a/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPFolders.h
+++ /dev/null
@@ -1,51 +0,0 @@
-/*
- * Copyright 2011, Haiku Inc. All Rights Reserved.
- * Copyright 2011 Clemens Zeidler. All rights reserved.
- *
- * Distributed under the terms of the MIT License.
- */
-#ifndef IMAP_FOLDERS_H
-#define IMAP_FOLDERS_H
-
-
-#include <vector>
-
-#include "IMAPHandler.h"
-#include "IMAPProtocol.h"
-
-
-class FolderInfo {
-public:
-       FolderInfo()
-               :
-               subscribed(false)
-       {
-       }
-
-                       BString                         folder;
-                       bool                            subscribed;
-};
-
-
-typedef std::vector<FolderInfo> FolderList;
-
-
-class IMAPFolders : public IMAPProtocol {
-public:
-                                                               IMAPFolders();
-                                                               
IMAPFolders(IMAPProtocol& connection);
-
-                       status_t                        GetFolders(FolderList& 
folders);
-                       status_t                        SubscribeFolder(const 
char* folder);
-                       status_t                        UnsubscribeFolder(const 
char* folder);
-
-                       status_t                        GetQuota(uint64& used, 
uint64& total);
-private:
-                       status_t                        
_GetAllFolders(StringList& folders);
-                       status_t                        
_GetSubscribedFolders(StringList& folders);
-
-                       CapabilityHandler       fCapabilityHandler;
-};
-
-
-#endif // IMAP_FOLDERS_H
diff --git 
a/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPHandler.h 
b/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPHandler.h
deleted file mode 100644
index ed322db..0000000
--- a/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPHandler.h
+++ /dev/null
@@ -1,303 +0,0 @@
-/*
- * Copyright 2010-2011, Haiku Inc. All Rights Reserved.
- * Copyright 2010 Clemens Zeidler. All rights reserved.
- *
- * Distributed under the terms of the MIT License.
- */
-#ifndef IMAP_HANDLER_H
-#define IMAP_HANDLER_H
-
-
-#include <vector>
-
-#include <DataIO.h>
-#include <String.h>
-
-
-class ConnectionReader;
-class IMAPMailbox;
-class IMAPStorage;
-
-
-class IMAPCommand {
-public:
-       virtual                                         ~IMAPCommand();
-
-       virtual BString                         Command();
-       virtual bool                            Handle(const BString& response) 
= 0;
-};
-
-
-class IMAPMailboxCommand  : public IMAPCommand{
-public:
-                                                               
IMAPMailboxCommand(IMAPMailbox& mailbox);
-       virtual                                         ~IMAPMailboxCommand();
-
-protected:
-                       IMAPMailbox&            fIMAPMailbox;
-                       IMAPStorage&            fStorage;
-                       ConnectionReader&       fConnectionReader;
-};
-
-
-class MailboxSelectHandler : public IMAPMailboxCommand {
-public:
-                                                               
MailboxSelectHandler(IMAPMailbox& mailbox);
-
-                       BString                         Command();
-                       bool                            Handle(const BString& 
response);
-
-                       void                            SetTo(const char* 
mailboxName)
-                                                                       { 
fMailboxName = mailboxName; }
-                       int32                           NextUID() { return 
fNextUID; }
-                       int32                           UIDValidity() { return 
fUIDValidity; }
-
-private:
-                       BString                         fMailboxName;
-                       int32                           fNextUID;
-                       int32                           fUIDValidity;
-};
-
-
-class CapabilityHandler : public IMAPCommand {
-public:
-                                                               
CapabilityHandler();
-
-                       BString                         Command();
-                       bool                            Handle(const BString& 
response);
-
-                       BString&                        Capabilities();
-
-private:
-                       BString                         fCapabilities;
-};
-
-
-struct MinMessage {
-       MinMessage();
-
-       int32   uid;
-       int32   flags;
-};
-
-
-typedef std::vector<MinMessage>        MinMessageList;
-
-
-class FetchMinMessageCommand : public IMAPMailboxCommand {
-public:
-                                                               
FetchMinMessageCommand(IMAPMailbox& mailbox,
-                                                                       int32 
message, MinMessageList* list,
-                                                                       
BPositionIO** data);
-                                                               
FetchMinMessageCommand(IMAPMailbox& mailbox,
-                                                                       int32 
firstMessage, int32 lastMessage,
-                                                                       
MinMessageList* list, BPositionIO** data);
-
-                       BString                         Command();
-                       bool                            Handle(const BString& 
response);
-
-       static  bool                            ParseMinMessage(const BString& 
response,
-                                                                       
MinMessage& minMessage);
-       static  int32                           ExtractFlags(const BString& 
response);
-
-private:
-                       int32                           fMessage;
-                       int32                           fEndMessage;
-                       MinMessageList*         fMinMessageList;
-                       BPositionIO**           fData;
-};
-
-
-class FetchMessageListCommand : public IMAPMailboxCommand {
-public:
-                                                               
FetchMessageListCommand(IMAPMailbox& mailbox,
-                                                                       
MinMessageList* list, int32 nextId);
-
-                       BString                         Command();
-                       bool                            Handle(const BString& 
response);
-
-private:
-                       MinMessageList*         fMinMessageList;
-                       int32                           fNextId;
-};
-
-
-class FetchMessageCommand : public IMAPMailboxCommand {
-public:
-                                                               
FetchMessageCommand(IMAPMailbox& mailbox,
-                                                                       int32 
message, BPositionIO* data,
-                                                                       int32 
fetchBodyLimit = -1);
-                       /*! Fetch multiple message within a range. */
-                                                               
FetchMessageCommand(IMAPMailbox& mailbox,
-                                                                       int32 
firstMessage, int32 lastMessage,
-                                                                       int32 
fetchBodyLimit = -1);
-                                                               
~FetchMessageCommand();
-
-                       BString                         Command();
-                       bool                            Handle(const BString& 
response);
-
-private:
-                       int32                           fMessage;
-                       int32                           fEndMessage;
-                       BPositionIO*            fOutData;
-                       int32                           fFetchBodyLimit;
-                       int32                           fUnhandled;
-};
-
-
-class FetchBodyCommand : public IMAPMailboxCommand {
-public:
-                                                               /*! takes 
ownership of the data */
-                                                               
FetchBodyCommand(IMAPMailbox& mailbox,
-                                                                       int32 
message, BPositionIO* data);
-                                                               
~FetchBodyCommand();
-
-                       BString                         Command();
-                       bool                            Handle(const BString& 
response);
-
-private:
-                       int32                           fMessage;
-                       BPositionIO*            fOutData;
-};
-
-
-class SetFlagsCommand : public IMAPMailboxCommand {
-public:
-                                                               
SetFlagsCommand(IMAPMailbox& mailbox,
-                                                                       int32 
message, int32 flags);
-
-                       BString                         Command();
-                       bool                            Handle(const BString& 
response);
-
-       static  BString                         GenerateFlagList(int32 flags);
-
-private:
-                       int32                           fMessage;
-                       int32                           fFlags;
-};
-
-
-class AppendCommand : public IMAPMailboxCommand {
-public:
-                                                               
AppendCommand(IMAPMailbox& mailbox,
-                                                                       
BPositionIO& message, off_t size,
-                                                                       int32 
flags, time_t time);
-
-                       BString                         Command();
-                       bool                            Handle(const BString& 
response);
-
-private:
-                       BPositionIO&            fMessageData;
-                       off_t                           fDataSize;
-                       int32                           fFlags;
-                       time_t                          fTime;
-};
-
-
-class ExistsHandler : public IMAPMailboxCommand {
-public:
-                                                               
ExistsHandler(IMAPMailbox& mailbox);
-
-                       bool                            Handle(const BString& 
response);
-};
-
-
-/*! Just send a expunge command to delete kDeleted flagged messages. The
-response is handled by the unsolicited ExpungeHandler which is installed all
-the time. */
-class ExpungeCommmand : public IMAPMailboxCommand {
-public:
-                                                               
ExpungeCommmand(IMAPMailbox& mailbox);
-
-                       BString                         Command();
-                       bool                            Handle(const BString& 
response);
-};
-
-
-class ExpungeHandler : public IMAPMailboxCommand {
-public:
-                                                               
ExpungeHandler(IMAPMailbox& mailbox);
-
-                       bool                            Handle(const BString& 
response);
-};
-
-
-class FlagsHandler : public IMAPMailboxCommand {
-public:
-                                                               
FlagsHandler(IMAPMailbox& mailbox);
-
-                       bool                            Handle(const BString& 
response);
-};
-
-
-typedef std::vector<BString> StringList;
-
-
-class ListCommand : public IMAPCommand {
-public:
-                       BString                         Command();
-                       bool                            Handle(const BString& 
response);
-
-       const   StringList&                     FolderList();
-
-       static  bool                            ParseList(const char* command,
-                                                                       const 
BString& response, StringList& list);
-private:
-                       StringList                      fFolders;
-};
-
-
-class ListSubscribedCommand : public IMAPCommand {
-public:
-                       BString                         Command();
-                       bool                            Handle(const BString& 
response);
-
-       const   StringList&                     FolderList();
-
-private:
-                       StringList                      fFolders;
-};
-
-
-class SubscribeCommand : public IMAPCommand {
-public:
-                                                               
SubscribeCommand(const char* mailboxName);
-
-                       BString                         Command();
-                       bool                            Handle(const BString& 
response);
-
-private:
-                       BString                         fMailboxName;
-};
-
-
-class UnsubscribeCommand : public IMAPCommand {
-public:
-                                                               
UnsubscribeCommand(const char* mailboxName);
-
-                       BString                         Command();
-                       bool                            Handle(const BString& 
response);
-
-private:
-                       BString                         fMailboxName;
-};
-
-
-class GetQuotaCommand : public IMAPCommand {
-public:
-                                                               
GetQuotaCommand(const char* mailboxName = "");
-
-                       BString                         Command();
-                       bool                            Handle(const BString& 
response);
-
-                       uint64                          UsedStorage();
-                       uint64                          TotalStorage();
-private:
-                       BString                         fMailboxName;
-
-                       uint64                          fUsedStorage;
-                       uint64                          fTotalStorage;
-};
-
-
-#endif // IMAP_HANDLER_H
diff --git 
a/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPMailbox.cpp 
b/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPMailbox.cpp
index 2da4cfc..96f80f4 100644
--- a/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPMailbox.cpp
+++ b/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPMailbox.cpp
@@ -43,7 +43,6 @@ IMAPMailbox::IMAPMailbox(IMAPStorage& storage)
 
        fFetchBodyLimit(0)
 {
-       fHandlerList.AddItem(&fCapabilityHandler);
        fIMAPMailboxListener = &fNULLListener;
 }
 
@@ -64,27 +63,6 @@ IMAPMailbox::SetListener(IMAPMailboxListener* listener)
 }
 
 
-status_t
-IMAPMailbox::SelectMailbox(const char* mailbox)
-{
-       TRACE("SELECT %s\n", mailbox);
-       fMailboxSelectHandler.SetTo(mailbox);
-       status_t status = ProcessCommand(&fMailboxSelectHandler);
-       if (status != B_OK)
-               return status;
-       fSelectedMailbox = mailbox;
-
-       if (fCapabilityHandler.Capabilities() != "")
-               return status;
-       //else get them
-       status = ProcessCommand(fCapabilityHandler.Command());
-       if (status != B_OK)
-               return status;
-
-       return B_OK;
-}
-
-
 BString
 IMAPMailbox::Mailbox()
 {
@@ -239,7 +217,7 @@ IMAPMailbox::FetchMessages(int32 firstMessage, int32 
lastMessage)
 status_t
 IMAPMailbox::FetchBody(int32 messageNumber)
 {
-       if (fStorage.BodyFetched(MessageNumberToUID(messageNumber)))
+       if (fStorage.IsBodyFetched(MessageNumberToUID(messageNumber)))
                return B_BAD_VALUE;
 
        BPositionIO* file;
diff --git 
a/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPMailbox.h 
b/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPMailbox.h
index b8c53dc..afb6e1c 100644
--- a/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPMailbox.h
+++ b/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPMailbox.h
@@ -30,7 +30,7 @@ public:
 class IMAPStorage;
 
 
-class IMAPMailbox : public IMAPProtocol {
+class IMAPMailbox : public IMAP::Protocol {
 public:
                                                                
IMAPMailbox(IMAPStorage& storage);
                                                                ~IMAPMailbox();
@@ -39,7 +39,6 @@ public:
                        IMAPMailboxListener&    Listener() { return 
*fIMAPMailboxListener; }
 
                        /*! Select mailbox and sync with the storage. */
-                       status_t                        SelectMailbox(const 
char* mailbox);
                        BString                         Mailbox();
                        status_t                        Sync();
 
@@ -68,7 +67,7 @@ public:
 
                        int32                           GetCurrentMessageCount()
                                                                        { 
return fMessageList.size(); }
-       const   MinMessageList&         GetMessageList() { return fMessageList; 
}
+       const   IMAP::MinMessageList& GetMessageList() { return fMessageList; }
                        IMAPStorage&            GetStorage() { return fStorage; 
}
 
                        int32                           
UIDToMessageNumber(int32 uid);
@@ -78,17 +77,15 @@ public:
 private:
                        void                            
_InstallUnsolicitedHandler(bool install);
 
-                       MinMessageList          fMessageList;
+                       IMAP::MinMessageList fMessageList;
 
                        IMAPStorage&            fStorage;
                        IMAPMailboxListener* fIMAPMailboxListener;
                        IMAPMailboxListener     fNULLListener;
 
-                       MailboxSelectHandler fMailboxSelectHandler;
-                       CapabilityHandler       fCapabilityHandler;
-                       ExistsHandler           fExistsHandler;
-                       ExpungeHandler          fExpungeHandler;
-                       FlagsHandler            fFlagsHandler;
+                       IMAP::ExistsHandler             fExistsHandler;
+                       IMAP::ExpungeHandler            fExpungeHandler;
+//                     FlagsHandler            fFlagsHandler;
 
                        int32                           fWatching;
 
diff --git 
a/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPParser.cpp 
b/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPParser.cpp
deleted file mode 100644
index 5ea9497..0000000
--- a/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPParser.cpp
+++ /dev/null
@@ -1,139 +0,0 @@
-/*
- * Copyright 2010, Haiku Inc. All Rights Reserved.
- * Copyright 2010 Clemens Zeidler. All rights reserved.
- *
- * Distributed under the terms of the MIT License.
- */
-
-
-#include "IMAPParser.h"
-
-#include <stdlib.h>
-
-
-BString
-IMAPParser::ExtractStringAfter(const BString& string, const char* after)
-{
-       int32 pos = string.FindFirst(after);
-       if (pos < 0)
-               return "";
-
-       BString extractedString = string;
-       extractedString.Remove(0, pos + strlen(after));
-
-       return extractedString.Trim();
-}
-
-
-BString
-IMAPParser::ExtractFirstPrimitive(const BString& string)
-{
-       BString extractedString = string;
-       extractedString.Trim();
-       int32 end = extractedString.FindFirst(" ");
-       if (end < 0)
-               return extractedString;
-       return extractedString.Truncate(end);
-}
-
-
-BString
-IMAPParser::ExtractBetweenBrackets(const BString& string, const char* start,
-       const char* end)
-{
-       BString outString = string;
-       int32 startPos = outString.FindFirst(start);
-       if (startPos < 0)
-               return "";
-       outString.Remove(0, startPos + 1);
-
-       int32 searchPos = 0;
-       while (true) {
-               int32 endPos = outString.FindFirst(end, searchPos);
-               if (endPos < 0)
-                       return "";
-               int32 nextStartPos =  outString.FindFirst(start, searchPos);
-               if (nextStartPos < 0 || nextStartPos > endPos)
-                       return outString.Truncate(endPos);
-               searchPos = endPos + 1;
-       }
-       return "";
-};
-
-
-BString
-IMAPParser::ExtractNextElement(const BString& string)
-{
-       if (string[0] == '(')
-               return ExtractBetweenBrackets(string, "(", ")");
-       else if (string[0] == '[')
-               return ExtractBetweenBrackets(string, "[", "]");
-       else if (string[0] == '{')
-               return ExtractBetweenBrackets(string, "{", "}");
-       else
-               return ExtractFirstPrimitive(string);
-
-       return "";
-}
-
-
-BString
-IMAPParser::ExtractElementAfter(const BString& string, const char* after)
-{
-       BString rest = ExtractStringAfter(string, after);
-       if (rest == "")
-               return rest;
-       return ExtractNextElement(rest);
-}
-
-
-BString
-IMAPParser::RemovePrimitiveFromLeft(BString& string)
-{
-       BString extracted;
-       string.Trim();
-       int32 end = string.FindFirst(" ");
-       if (end < 0) {
-               extracted = string;
-               string = "";
-       } else {
-               string.MoveInto(extracted, 0, end);
-               string.Trim();
-       }
-       return extracted;
-}
-
-
-int
-IMAPParser::RemoveIntegerFromLeft(BString& string)
-{
-       BString extracted = RemovePrimitiveFromLeft(string);
-       return atoi(extracted);
-}
-
-
-bool
-IMAPParser::RemoveUntagedFromLeft(BString& string, const char* keyword,
-       int32& number)
-{
-       BString result = RemovePrimitiveFromLeft(string);
-       if (result != "*")
-               return false;
-       number = RemoveIntegerFromLeft(string);
-       if (number == 0)
-               return false;
-       result = RemovePrimitiveFromLeft(string);
-       if (result != keyword)
-               return false;
-       return true;
-}
-
-
-bool
-IMAPParser::ExtractUntagedFromLeft(const BString& string, const char* keyword,
-       int32& number)
-{
-       //TODO: could be more efficient without copy the string
-       BString copy = string;
-       return RemoveUntagedFromLeft(copy, keyword, number);
-}
diff --git 
a/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPParser.h 
b/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPParser.h
deleted file mode 100644
index 91590f1..0000000
--- a/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPParser.h
+++ /dev/null
@@ -1,35 +0,0 @@
-/*
- * Copyright 2010, Haiku Inc. All Rights Reserved.
- * Copyright 2010 Clemens Zeidler. All rights reserved.
- *
- * Distributed under the terms of the MIT License.
- */
-#ifndef IMAP_PARSER_H
-#define IMAP_PARSER_H
-
-
-#include <String.h>
-
-
-namespace IMAPParser {
-
-BString                ExtractStringAfter(const BString& string, const char* 
after);
-BString                ExtractFirstPrimitive(const BString& string);
-BString                ExtractBetweenBrackets(const BString& string, const 
char* start,
-                               const char* end);
-BString                ExtractNextElement(const BString& string);
-BString                ExtractElementAfter(const BString& string, const char* 
after);
-
-BString                RemovePrimitiveFromLeft(BString& string);
-int                    RemoveIntegerFromLeft(BString& string);
-
-// remove the part like "* 234 FETCH " where FETCH is the keyword
-bool           RemoveUntagedFromLeft(BString& string, const char* keyword,
-                               int32& number);
-bool           ExtractUntagedFromLeft(const BString& string, const char* 
keyword,
-                               int32& number);
-
-}
-
-
-#endif // IMAP_PARSER_H
diff --git 
a/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPProtocol.cpp 
b/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPProtocol.cpp
deleted file mode 100644
index 8297b9d..0000000
--- a/src/add-ons/mail_daemon/inbound_protocols/imap/imap_lib/IMAPProtocol.cpp
+++ /dev/null
@@ -1,433 +0,0 @@
-/*
- * Copyright 2010-2011, Haiku Inc. All Rights Reserved.
- * Copyright 2010 Clemens Zeidler. All rights reserved.
- *
- * Distributed under the terms of the MIT License.
- */
-
-
-#include "IMAPProtocol.h"
-
-#include "IMAPHandler.h"
-#include "IMAPParser.h"
-
-
-#define DEBUG_IMAP_PROTOCOL
-#ifdef DEBUG_IMAP_PROTOCOL
-#      include <stdio.h>
-#      define TRACE(x...) printf(x)
-#else
-#      define TRACE(x...) ;
-#endif
-
-
-ConnectionReader::ConnectionReader(ServerConnection* connection)
-       :
-       fServerConnection(connection)
-{
-}
-
-
-status_t
-ConnectionReader::GetNextLine(BString& line, bigtime_t timeout,
-       int32 maxUnfinishedLine)
-{
-       line.SetTo((const char*)NULL, 0);
-
-       while (true) {
-               status_t status = _GetNextDataBunch(line, timeout);
-               if (status == B_OK)
-                       return status;
-               if (status == B_NAME_NOT_FOUND) {
-                       if (maxUnfinishedLine < 0 || line.Length() < 
maxUnfinishedLine)
-                               continue;
-                       else
-                               return status;
-               }
-               return status;
-       }
-       return B_ERROR;
-}
-
-
-status_t
-ConnectionReader::FinishLine(BString& line)
-{
-       while (true) {
-               status_t status = _GetNextDataBunch(line, B_INFINITE_TIMEOUT);
-               if (status == B_OK)
-                       return status;
-               if (status == B_NAME_NOT_FOUND)
-                       continue;
-               return status;
-       }
-       return B_ERROR;
-}
-
-
-status_t
-ConnectionReader::ReadToFile(int32 size, BPositionIO* out)
-{
-       const int32 kBunchSize = 1024; // 1Kb
-       char buffer[kBunchSize];
-
-       int32 readSize = size - fStringBuffer.Length();
-       int32 readed = fStringBuffer.Length();
-       if (readSize < 0) {
-               readed = size;
-       }
-       out->Write(fStringBuffer.String(), readed);
-       fStringBuffer.Remove(0, readed);
-
-       while (readSize > 0) {
-               int32 bunchSize = readSize < kBunchSize ? readSize : kBunchSize;
-               int nReaded = fServerConnection->Read(buffer, bunchSize);
-               if (nReaded < 0)
-                       return B_ERROR;
-               readSize -= nReaded;
-               out->Write(buffer, nReaded);
-       }
-       return B_OK;
-}
-
-
-status_t
-ConnectionReader::_GetNextDataBunch(BString& line, bigtime_t timeout,
-       uint32 maxNewLength)
-{
-       if (_ExtractTillEndOfLine(line))
-               return B_OK;
-
-       char buffer[maxNewLength];
-
-       if (timeout != B_INFINITE_TIMEOUT) {
-               status_t status = fServerConnection->WaitForData(timeout);
-               if (status != B_OK)
-                       return status;
-       }
-
-       int nReaded = fServerConnection->Read(buffer, maxNewLength);
-       if (nReaded <= 0)
-               return B_ERROR;
-
-       fStringBuffer.SetTo(buffer, nReaded);
-       if (_ExtractTillEndOfLine(line))
-               return B_OK;
-       return B_NAME_NOT_FOUND;
-}
-
-
-bool
-ConnectionReader::_ExtractTillEndOfLine(BString& out)
-{
-       int32 endPos = fStringBuffer.FindFirst('\n');
-       if (endPos == B_ERROR) {
-               endPos = fStringBuffer.FindFirst(xEOF);
-               if (endPos == B_ERROR) {
-                       out += fStringBuffer;
-                       fStringBuffer.SetTo((const char*)NULL, 0);
-                       return false;
-               }
-       }
-       out.Append(fStringBuffer, endPos + 1);
-       fStringBuffer.Remove(0, endPos + 1);
-
-       return true;
-}
-
-
-// #pragma mark -
-
-
-IMAPProtocol::IMAPProtocol()
-       :
-       fServerConnection(&fOwnServerConnection),
-       fConnectionReader(fServerConnection),
-       fCommandID(0),
-       fStopNow(0),
-       fIsConnected(false)
-{
-}
-
-
-IMAPProtocol::IMAPProtocol(IMAPProtocol& connection)
-       :
-       fServerConnection(connection.fServerConnection),
-       fConnectionReader(fServerConnection),
-       fCommandID(0),
-       fStopNow(0),
-       fIsConnected(false)
-{
-}
-
-
-IMAPProtocol::~IMAPProtocol()
-{
-       for (int32 i = 0; i < fAfterQuackCommands.CountItems(); i++)
-               delete fAfterQuackCommands.ItemAt(i);
-}
-
-
-
-void
-IMAPProtocol::SetStopNow()
-{
-       atomic_set(&fStopNow, 1);
-}
-
-
-bool
-IMAPProtocol::StopNow()
-{
-       return (atomic_get(&fStopNow) != 0);
-}
-
-
-status_t
-IMAPProtocol::Connect(const char* server, const char* username,
-       const char* password, bool useSSL, int32 port)
-{
-       TRACE("Connect\n");
-       status_t status = B_ERROR;
-       if (useSSL) {
-               if (port >= 0)
-                       status = fServerConnection->ConnectSSL(server, port);
-               else
-                       status = fServerConnection->ConnectSSL(server);
-       } else {
-               if (port >= 0)
-                       status = fServerConnection->ConnectSocket(server, port);
-               else
-                       status = fServerConnection->ConnectSocket(server);
-       }
-       if (status != B_OK)
-               return status;
-
-       TRACE("Login\n");
-
-       fIsConnected = true;
-
-       BString command = "LOGIN ";
-       command << "\"" << username << "\" ";
-       command << "\"" << password << "\"";
-       status = ProcessCommand(command);
-       if (status != B_OK) {
-               _Disconnect();
-               return status;
-       }
-
-       return B_OK;
-}
-
-
-status_t
-IMAPProtocol::Disconnect()
-{
-       ProcessCommand("LOGOUT");
-       return _Disconnect();
-}
-
-
-bool
-IMAPProtocol::IsConnected()
-{
-       return fIsConnected;
-}
-
-
-ConnectionReader&
-IMAPProtocol::GetConnectionReader()
-{
-       return fConnectionReader;
-}
-
-
-status_t
-IMAPProtocol::SendRawCommand(const char* command)
-{
-       static char cmd[256];
-       ::sprintf(cmd, "%s"CRLF, command);
-       int32 commandLength = strlen(cmd);
-
-       if (fServerConnection->Write(cmd, commandLength) != commandLength)
-               return B_ERROR;
-       return B_OK;
-}
-
-
-int32
-IMAPProtocol::SendRawData(const char* buffer, uint32 nBytes)
-{
-       return fServerConnection->Write(buffer, nBytes);
-}
-
-
-status_t
-IMAPProtocol::AddAfterQuakeCommand(IMAPCommand* command)
-{
-       return fAfterQuackCommands.AddItem(command);
-}
-
-
-status_t
-IMAPProtocol::ProcessCommand(IMAPCommand* command, bigtime_t timeout)
-{
-       status_t status = _ProcessCommandWithoutAfterQuake(command, timeout);
-
-       ProcessAfterQuacks(timeout);
-
-       return status;
-}
-
-
-status_t
-IMAPProtocol::ProcessCommand(const char* command, bigtime_t timeout)
-{
-       status_t status = _ProcessCommandWithoutAfterQuake(command, timeout);
-
-       ProcessAfterQuacks(timeout);
-       return status;
-}
-
-
-status_t
-IMAPProtocol::SendCommand(const char* command, int32 commandID)
-{
-       if (strlen(command) + 10 > 256)
-               return B_NO_MEMORY;
-
-       static char cmd[256];
-       ::sprintf(cmd, "A%.7" B_PRId32 " %s"CRLF, commandID, command);
-
-       TRACE("_SendCommand: %s\n", cmd);
-       int commandLength = strlen(cmd);
-       if (fServerConnection->Write(cmd, commandLength) != commandLength) {
-               // we might lost the connection, clear the connection state
-               _Disconnect();
-               return B_ERROR;
-       }
-
-       fOngoingCommands.push_back(commandID);
-       return B_OK;
-}
-
-
-status_t
-IMAPProtocol::HandleResponse(int32 commandID, bigtime_t timeout,
-       bool disconnectOnTimeout)
-{
-       status_t commandStatus = B_ERROR;
-
-       bool done = false;
-       while (done != true) {
-               BString line;
-               status_t status = fConnectionReader.GetNextLine(line, timeout);
-               if (status != B_OK) {
-                       // we might lost the connection, clear the connection 
state
-                       if (status != B_TIMED_OUT) {
-                               TRACE("S:read error %s", line.String());
-                               _Disconnect();
-                       } else if (disconnectOnTimeout) {
-                               _Disconnect();
-                       }
-                       return status;
-               }
-               //TRACE("S: %s", line.String());
-
-               bool handled = false;
-               for (int i = 0; i < fHandlerList.CountItems(); i++) {
-                       if (fHandlerList.ItemAt(i)->Handle(line) == true) {
-                               handled = true;
-                               break;
-                       }
-               }
-               if (handled == true)
-                       continue;
-
-               for (std::vector<int32>::iterator it = fOngoingCommands.begin();
-                       it != fOngoingCommands.end(); it++) {
-                       static char idString[8];
-                       ::sprintf(idString, "A%.7" B_PRId32, *it);
-                       if (line.FindFirst(idString) >= 0) {
-                               if (*it == commandID) {
-                                       BString result = 
IMAPParser::ExtractElementAfter(line,
-                                               idString);
-                                       if (result == "OK")
-                                               commandStatus = B_OK;
-                                       else {
-                                               fCommandError = 
IMAPParser::ExtractStringAfter(line,
-                                                       idString);
-                                               TRACE("Command Error %s\n", 
fCommandError.String());
-                                       }
-                               }
-                               fOngoingCommands.erase(it);
-                               break;
-                       }
-               }
-               if (fOngoingCommands.size() == 0)
-                       done = true;
-
-               TRACE("Unhandled S: %s", line.String());
-       }
-
-       return commandStatus;
-}
-
-
-void
-IMAPProtocol::ProcessAfterQuacks(bigtime_t timeout)
-{
-       while (fAfterQuackCommands.CountItems() != 0) {
-               IMAPCommand* currentCommand = 
fAfterQuackCommands.RemoveItemAt(0);
-               _ProcessCommandWithoutAfterQuake(currentCommand, timeout);
-               delete currentCommand;
-       }
-}
-
-
-int32
-IMAPProtocol::NextCommandID()
-{
-       fCommandID++;
-       return fCommandID;
-}
-
-
-status_t
-IMAPProtocol::_ProcessCommandWithoutAfterQuake(IMAPCommand* command,
-       bigtime_t timeout)
-{
-       BString cmd = command->Command();
-       if (cmd == "")
-               return B_BAD_VALUE;
-       if (!fHandlerList.AddItem(command, 0))
-               return B_NO_MEMORY;
-
-       status_t status = _ProcessCommandWithoutAfterQuake(cmd, timeout);
-
-       fHandlerList.RemoveItem(command);
-
-       return status;
-}
-
-
-status_t
-IMAPProtocol::_ProcessCommandWithoutAfterQuake(const char* command,
-       bigtime_t timeout)
-{
-       int32 commandID = NextCommandID();
-       status_t status = SendCommand(command, commandID);
-       if (status != B_OK)

[ *** diff truncated: 1427 lines dropped *** ]


############################################################################

Commit:      a5170470701b5d51ede5a4ec9ef60b28aff62a3f
URL:         http://cgit.haiku-os.org/haiku/commit/?id=a517047
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Wed Nov 30 21:17:23 2011 UTC

Got rid of the ConnectionReader, and implemented parsing literals.

* The parser now works on a BDataIO instead. It's now even a bit simpler
  overall.
* Implemented ParseLiteral() - the default implementation just reads the data
  into a string. Thanks to BDataIO this was now very simple to do.
* Tested the code: imap_tester can now successfully read mails (using the raw
  command only, at the moment).

----------------------------------------------------------------------------

############################################################################

Commit:      db0a4f2c001485adccd9b344987ec8a6055626c8
URL:         http://cgit.haiku-os.org/haiku/commit/?id=db0a4f2
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Thu Dec  1 23:15:53 2011 UTC

More work in progress of the IMAP rework.

* Implemented FetchCommand, and some more.
* Improved and extended the imap_tester.
* The base to implement the new InboundProtocol on is now mostly done, at least
  for a start.

----------------------------------------------------------------------------

############################################################################

Commit:      1704480100a35875a8742f3c7a11426d92bb1b46
URL:         http://cgit.haiku-os.org/haiku/commit/?id=1704480
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Sat Dec  3 00:05:11 2011 UTC

Read some more specs, cleaned Protocol a bit.

* Added some TODO comments based on the various IMAP specs and extensions.
* Removed SelectMailbox() functionality from the Protocol class; it's not
  really useful to have it there.
* Removed some other methods that don't belong into the Protocol class.

----------------------------------------------------------------------------

############################################################################

Commit:      9192d4dcf36ca64087e0702be1ef464c1e49d208
URL:         http://cgit.haiku-os.org/haiku/commit/?id=9192d4d
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Wed Dec 14 23:36:07 2011 UTC

Started working on the IMAP add-on itself.

* Renamed imap_config.cpp to ConfigView.cpp, IMAPFolderConfig.(h|cpp)
  to FolderConfigWindow.(h|cpp).
* Got the latter to build.
* Added Settings class to simplify and unify the BMessage based
  settings access.
* Removed the InboundProtocol[Thread] implementation from the build for now.

----------------------------------------------------------------------------

############################################################################

Commit:      fe26284795c623afb2448bf19b116d5ce4c70b94
URL:         http://cgit.haiku-os.org/haiku/commit/?id=fe26284
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Sun Dec 18 22:49:53 2011 UTC

Added support for decoding RFC-3501 mailbox names.

* Added new RFC3501Encoding class that implements modified UTF-7 as specified
  in RFC-3501; only decoding is implemented right now.
* ListCommand now uses this new class to encode, and decode the folder names.

----------------------------------------------------------------------------

############################################################################

Commit:      f1c9cc4292df9264a1230336d114c7dc164f4cfb
URL:         http://cgit.haiku-os.org/haiku/commit/?id=f1c9cc4
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Thu Jan  5 22:02:19 2012 UTC

We need to copy the settings message.

----------------------------------------------------------------------------

############################################################################

Commit:      cc3aa99cb3ca7796ae4a199e445608fc478d4f45
URL:         http://cgit.haiku-os.org/haiku/commit/?id=cc3aa99
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Thu Jan  5 22:03:20 2012 UTC

Use GETQUOTAROOT instead of GETQUOTA.

* At least with my ISP, there is no "" root, so the command would fail when used
  as is.
* Now we always use the GETQUOTAROOT command instead, by default for the INBOX
  mailbox. This isn't entirely correct either, but better than nothing.

----------------------------------------------------------------------------

############################################################################

Commit:      3e4e5c2cf62f2393d3aaa0dfd2ed44e0b7e6125d
URL:         http://cgit.haiku-os.org/haiku/commit/?id=3e4e5c2
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Thu Jan  5 22:06:25 2012 UTC

Improved folder config window a bit.

* Now uses the BLayoutBuilder instead of ALM layout - not only is the code much
  simpler now, resizing the window isn't as sluggish anymore (less flickering).
* Fixed a drawing bug in the list view; the drawing state wasn't properly
  maintained, leading to rendering artefacts.
* Moved the checkbox to the start of the line.
* Use B_ASYNCHRONOUS_CONTROLS for all windows.
* Fixed a few typos.

----------------------------------------------------------------------------

############################################################################

Commit:      077338a9b8c22b209c28e996fb952eb60fe56886
URL:         http://cgit.haiku-os.org/haiku/commit/?id=077338a
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Thu Aug  9 11:03:37 2012 UTC

Completed literal handling.

* LiteralHandler commands now receive the literal data as intended.
* The 'fetch' command in the imap_tester now uses this to print the literal
  to stdout.

----------------------------------------------------------------------------

############################################################################

Commit:      f06916d5726232b9e535ef50a5b7e860b793be6b
URL:         http://cgit.haiku-os.org/haiku/commit/?id=f06916d
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Thu Aug  9 11:33:24 2012 UTC

Initial work on a class that manages an IMAP folder on disk.

----------------------------------------------------------------------------

############################################################################

Commit:      6a6b7ae7a0d29b844fbab698f41f5df584554676
URL:         http://cgit.haiku-os.org/haiku/commit/?id=6a6b7ae
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Mon Oct 15 21:03:34 2012 UTC

Style cleanup, no functional change.

----------------------------------------------------------------------------

############################################################################

Commit:      7135c4f8feab2985af8e202cdd378986706ed22a
URL:         http://cgit.haiku-os.org/haiku/commit/?id=7135c4f
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Mon Oct 15 21:07:16 2012 UTC

Renamed pop3.{cpp|h} to POP3.{cpp|h}.

----------------------------------------------------------------------------

############################################################################

Commit:      20537ad06737ba1ba9baf1acd9f1914eeb813b07
URL:         http://cgit.haiku-os.org/haiku/commit/?id=20537ad
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Fri Oct 26 09:43:14 2012 UTC

Minor coding style cleanup.

----------------------------------------------------------------------------

############################################################################

Commit:      e0676bb9820e7bec77a18608ac7c4911886222e4
URL:         http://cgit.haiku-os.org/haiku/commit/?id=e0676bb
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Fri Oct 26 09:47:35 2012 UTC

Fixed typo.

----------------------------------------------------------------------------

############################################################################

Commit:      0f11280e6d43c1d497b20d76759ae8b653876654
URL:         http://cgit.haiku-os.org/haiku/commit/?id=0f11280
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Fri Oct 26 12:44:44 2012 UTC

Minor MailNotifier cleanup.

* Renamed to BMailNotifier, as it's part of the public API.
* Renamed Notifier.{cpp|h} to DefaultNotifier.{cpp|h} as that's the class it
  implements.
* Made the mail counts uint32, and the byte counts uint64.

----------------------------------------------------------------------------

############################################################################

Commit:      715bf3d17a81353ae5d1fa6867587cc0f5c32ce1
URL:         http://cgit.haiku-os.org/haiku/commit/?id=715bf3d
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Fri Oct 26 23:25:39 2012 UTC

Work in progress of mail rework.

* Not everything compiles; all protocols, and inbound filters do, though.
* Renamed a few classes to give a better idea what they are for; prefixed
  public classes with the 'B' prefix.
* Moved ProtocolConfigView's classes into the BPrivate namespace.
* Moved BMailFilter into its own file.
* Added BMailFilter::DescriptiveName(). This is now used by the RuleFilter
  in order to give a description of what it's doing (ie. no more dozens of
  "Rule filter" entries in the preferences).
* Removed no longer used MailAddon.h.
* Renamed Addon to AddOn where found, since that is more consistent with the
  rest of the API.
* Merged the former MailProtocol with the former MailProtocolThread; the
  differentiation between those two was pretty messy.
* All configuration views touched so far are now using the layout kit.
* The RuleFilter is currently broken functionality wise; I have not yet decided
  how to solve the stuff it uses (TriggerFileMove() does not exist anymore,
  for example).
* BMailAddOnSettings (formerly known as AddonSettings) now directly subclass
  BMessage; there are no Settings() and EditSettings() method anymore. The
  class uses a copy of itself to determine whether or not it has been changed.
* Lots of cleanup.

----------------------------------------------------------------------------

############################################################################

Commit:      794a013e9beece2ee9d01a9f1f745b10e360b601
URL:         http://cgit.haiku-os.org/haiku/commit/?id=794a013
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Tue Oct 30 19:30:50 2012 UTC

Adapted fortune filter to the new mail API.

----------------------------------------------------------------------------

############################################################################

Commit:      bebcc474f865f05ed524f43fe27df98a5d1696dc
URL:         http://cgit.haiku-os.org/haiku/commit/?id=bebcc47
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Tue Oct 30 19:37:51 2012 UTC

Renamed a few files to better match their class names.

----------------------------------------------------------------------------

############################################################################

Commit:      383b34adacaff87d0b4fd459b1a53de58ba4df6a
URL:         http://cgit.haiku-os.org/haiku/commit/?id=383b34a
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Tue Oct 30 19:42:13 2012 UTC

Moved ProtocolConfigView to headers/private/mail.

* This is by no means meant as a public header.

----------------------------------------------------------------------------

############################################################################

Commit:      146357b547221dd608cdb63feadd8b6bbc5988da
URL:         http://cgit.haiku-os.org/haiku/commit/?id=146357b
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Tue Oct 30 21:45:54 2012 UTC

Completed transition to the new mail API; ie. it compiles.

* Completely untested yet. Unlikely to work yet.

----------------------------------------------------------------------------

############################################################################

Commit:      4d30240166270ab3ec93ef0e367daea249d06dea
URL:         http://cgit.haiku-os.org/haiku/commit/?id=4d30240
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Tue Oct 30 21:47:57 2012 UTC

Renamed smtp.{cpp|h} to SMTP.{cpp|h}.

----------------------------------------------------------------------------

############################################################################

Commit:      ae9d8c6addb7494fdcf79fc802763e97ad412b71
URL:         http://cgit.haiku-os.org/haiku/commit/?id=ae9d8c6
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Tue Oct 30 21:50:18 2012 UTC

IMAP now compiles again with GCC 4.

----------------------------------------------------------------------------

############################################################################

Commit:      daf972c99c4a66baa0bc4df698334eda8f224a7d
URL:         http://cgit.haiku-os.org/haiku/commit/?id=daf972c
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Tue Oct 30 23:08:20 2012 UTC

Renamed MailDaemon{App|.cpp|.h} to MailDaemonApplication[.{cpp|h}].

----------------------------------------------------------------------------

############################################################################

Commit:      e1e78d4debcf718826f5f726cb9fc17ebeca2542
URL:         http://cgit.haiku-os.org/haiku/commit/?id=e1e78d4
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Tue Oct 30 23:21:01 2012 UTC

Reset the daemon messenger after a successful Launch().

----------------------------------------------------------------------------

############################################################################

Commit:      bcf60bbb83484e8a2715daae55bce55d60457853
URL:         http://cgit.haiku-os.org/haiku/commit/?id=bcf60bb
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Tue Oct 30 23:21:55 2012 UTC

Fixed Mail build.

* The former kMsgBodyFetched (now B_MAIL_BODY_FETCHED, following the other
  message constant names in AppDefs.h) must be public.

----------------------------------------------------------------------------

############################################################################

Commit:      9d8cf1b6f77ed091893a65798c6d8ac88a510cd6
URL:         http://cgit.haiku-os.org/haiku/commit/?id=9d8cf1b
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Wed Oct 31 00:13:02 2012 UTC

E-mail now also builds, but doesn't work yet.

----------------------------------------------------------------------------

############################################################################

Commit:      1f87386b0ae4ba1a154db7f7a6b00cc54adbd654
URL:         http://cgit.haiku-os.org/haiku/commit/?id=1f87386
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Sun Nov  4 14:28:50 2012 UTC

Now also loads mail settings from common.

* Also removed the superfluous and unused timeout argument from Save().

----------------------------------------------------------------------------

############################################################################

Commit:      b448d260c372640992cb6757dc0bb84ff97ba4e4
URL:         http://cgit.haiku-os.org/haiku/commit/?id=b448d26
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Sun Nov  4 14:30:04 2012 UTC

Fixed mail daemon build.

* Removed cvs package leftovers.

----------------------------------------------------------------------------

############################################################################

Commit:      f90a3bbd67be2e5f3aa32afcbbeff7ce36dfe531
URL:         http://cgit.haiku-os.org/haiku/commit/?id=f90a3bb
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Sun Nov  4 16:27:11 2012 UTC

Added support for letting user mail add-ons override system ones.

* The path will now be relativized before storing it.
* On load, the add-on will be tried to load from the user, then common
  and finally system add-on directory.

----------------------------------------------------------------------------

############################################################################

Commit:      58b56ffc807cbf601af80f1a5092be957f846fe5
URL:         http://cgit.haiku-os.org/haiku/commit/?id=58b56ff
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Sun Nov  4 16:29:23 2012 UTC

Improved mail protocol config view layout.

----------------------------------------------------------------------------

############################################################################

Commit:      5faab458af8f58100399701f9cf27ccbbf242c07
URL:         http://cgit.haiku-os.org/haiku/commit/?id=5faab45
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Mon Nov  5 10:49:46 2012 UTC

Reworked the mail preferences.

* Made it use the layout API.
* Removed options that no longer apply (dial-up, for example).
* Cleanup.
* There are a few issues left, though, for example, the BTextView is not
  correctly sized, and it currently crashes in the protocol panels.

----------------------------------------------------------------------------

############################################################################

Commit:      a6943acbe043e34f97b5f26f72ba194a5533fbd4
URL:         http://cgit.haiku-os.org/haiku/commit/?id=a6943ac
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Mon Nov 12 22:48:45 2012 UTC

Added missing BMessage::{Get|Set}String() methods.

* Forgot to add those before accidentally.

----------------------------------------------------------------------------

############################################################################

Commit:      ca3341c7b430ae9c6a1e7ec22f9aa83d46910814
URL:         http://cgit.haiku-os.org/haiku/commit/?id=ca3341c
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Mon Nov 12 22:51:51 2012 UTC

Major mail protocol/filter settings rework.

* Instead of abusing BArchive::Archive() we now use a BMailSettingsView as
  a base view for all filter/protocol settings that works with
  BMailAddOnSettings.
* Cleanups in E-mail which is now completely layout friendly. But also still
  crashes when changing the views.

----------------------------------------------------------------------------

############################################################################

Commit:      efd1602a79101b5734e88ac43a752b7732a56979
URL:         http://cgit.haiku-os.org/haiku/commit/?id=efd1602
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Tue Nov 20 23:43:01 2012 UTC

Fixed debugger call in E-mail.

* The settings view is no longer a direct child of the protocol settings
  view.

----------------------------------------------------------------------------

############################################################################

Commit:      57b305558b1c3eb23ef00d616a3458a479361732
URL:         http://cgit.haiku-os.org/haiku/commit/?id=57b3055
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Thu Nov 22 22:51:48 2012 UTC

MailProtocolConfigView now is a BMailSettingsView.

* Changed the private settings base classes to follow the new style.
* Made BodyDownloadConfig use the layout API.
* Adapted SMTP to these changes.

----------------------------------------------------------------------------

############################################################################

Commit:      518698c7e70dcdfe42d1b87a2d8701047532ff58
URL:         http://cgit.haiku-os.org/haiku/commit/?id=518698c
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Thu Nov 22 22:53:56 2012 UTC

Removed commented out method in BMailSettingsView.

----------------------------------------------------------------------------

############################################################################

Commit:      1da1e5a16627889c8ed0abf8d64f1214afce7992
URL:         http://cgit.haiku-os.org/haiku/commit/?id=1da1e5a
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Thu Nov 22 22:55:30 2012 UTC

Renamed BodyDownloadConfig to BodyDownloadConfigView.

----------------------------------------------------------------------------

############################################################################

Commit:      006040d06e9c2bae884d2c706496af38c610eaaf
URL:         http://cgit.haiku-os.org/haiku/commit/?id=006040d
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Mon Nov 26 20:13:05 2012 UTC

Adapted POP3, and Fortune to the new MailSettingsView API.

----------------------------------------------------------------------------

############################################################################

Commit:      792843e8aff42e1bc7fe49c7a9b50c68eeac46d2
URL:         http://cgit.haiku-os.org/haiku/commit/?id=792843e
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Mon Nov 26 20:17:13 2012 UTC

Adapted IMAP to the new MailSettingsView API.

----------------------------------------------------------------------------

############################################################################

Commit:      81ec973846ea4816c53ed8901822e43c8b06878d
URL:         http://cgit.haiku-os.org/haiku/commit/?id=81ec973
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Mon Nov 26 21:36:34 2012 UTC

Minor coding style fix.

----------------------------------------------------------------------------

############################################################################

Commit:      4a8448ce3494eb8f753bf02aee67f0aa09a058f3
URL:         http://cgit.haiku-os.org/haiku/commit/?id=4a8448c
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Mon Nov 26 23:05:52 2012 UTC

Major coding style cleanup.

----------------------------------------------------------------------------

############################################################################

Commit:      19d947eb7fa93cb144528b3e7ce4168736e7328e
URL:         http://cgit.haiku-os.org/haiku/commit/?id=19d947e
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Mon Nov 26 23:09:15 2012 UTC

The E-mail window's frame is no longer stored.

* This is part of a clean up of BMailSettings; storing the window
  position might be implemented again later -- it just doesn't
  belong there.
* Changed the logic when the daemon is set to auto start. It's now
  always started if at least a single account exists.

----------------------------------------------------------------------------

############################################################################

Commit:      22fc80c6e38747760efc86f1d6c371cdd5bf5e7d
URL:         http://cgit.haiku-os.org/haiku/commit/?id=22fc80c
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Mon Nov 26 23:13:31 2012 UTC

Align all protocol config view labels to the right.

----------------------------------------------------------------------------

############################################################################

Commit:      4235da3061f958e97f85bc046163278c15d0dab8
URL:         http://cgit.haiku-os.org/haiku/commit/?id=4235da3
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Mon Nov 26 23:14:15 2012 UTC

Improved label of the button to configure the IMAP folders.

----------------------------------------------------------------------------

############################################################################

Commit:      fa587d2956d870ef4ae055403ee5ee980d52b138
URL:         http://cgit.haiku-os.org/haiku/commit/?id=fa587d2
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Mon Nov 26 23:15:02 2012 UTC

The protocol config view now adds some glue at the bottom.

* This makes all boxes fill the complete height of the window.
* The SMTP add-on did that itself which makes no sense.

----------------------------------------------------------------------------

############################################################################

Commit:      dcb663f33983a7872304f205759b4262b961d0ec
URL:         http://cgit.haiku-os.org/haiku/commit/?id=dcb663f
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Thu Dec 13 21:19:15 2012 UTC

libmail: Fixed missing initialization in protocol view.

* This would cause a crash when the fields were actually not being
  used.

----------------------------------------------------------------------------

############################################################################

Commit:      8651ebbe7aa59e7c3be42749ec742dea7c6c3ac1
URL:         http://cgit.haiku-os.org/haiku/commit/?id=8651ebb
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Thu Dec 13 21:20:33 2012 UTC

Fixed stale config view pointer in E-mail.

* When removing an account (all accounts would be removed when the app
  was quit), AccountItem::ConfigPanel() was used to remove views.
* However, this member was only set when a new view was created, never when
  it was removed. This could cause a crash on quit.
* Removed that member completely, as it was unnecessary, anyway.
* Fixed naming of AccountItem getters to lose their Get* prefix.

----------------------------------------------------------------------------

############################################################################

Commit:      acee88be992fbf79ba85e83a2657785f36dbb767
URL:         http://cgit.haiku-os.org/haiku/commit/?id=acee88b
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Thu Dec 13 21:36:09 2012 UTC

E-mail settings are now stored as they should.

* ProtocolSettingsView was still using Archive() instead of SaveInto().
* However, it looks like BMessage::Set*() does corrupt the message fields.

----------------------------------------------------------------------------

############################################################################

Commit:      46851a74af0277d0fe96325969c83ed7270f5875
URL:         http://cgit.haiku-os.org/haiku/commit/?id=46851a7
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Thu Dec 13 21:43:26 2012 UTC

BMessage::SetString() was broken.

* We cannot use the macro for this, unfortunately.

----------------------------------------------------------------------------

############################################################################

Commit:      93608baf608dbdd875a33083cfba23261a3f547e
URL:         http://cgit.haiku-os.org/haiku/commit/?id=93608ba
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Wed Jan 16 12:52:15 2013 UTC

Clarified progress parameter names for the MailProtocol.

----------------------------------------------------------------------------

############################################################################

Commit:      a9de7ece6bcbcee28f93f8d48a91aef36d5aceff
URL:         http://cgit.haiku-os.org/haiku/commit/?id=a9de7ec
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Wed Jan 16 13:01:32 2013 UTC

pop3: Fixed maintaining fSizes list, and more.

* The list was filled, but never emptied.
* If SyncMessages() was called more than once for the same POP3 instance,
  this could garble the mails retrieved in the second run.
* Maintain the total size of mails in fSizes to be able to report progress
  in more detail.
* Also adapted progress reporting to the argument changes made in MailProtocol
  earlier.
* Minor cleanup.

----------------------------------------------------------------------------

############################################################################

Commit:      d6ce6060b9b00192036ae31b349fc70ff738de09
URL:         http://cgit.haiku-os.org/haiku/commit/?id=d6ce606
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Wed Jan 16 13:11:14 2013 UTC

pop3: minor cleanup.

----------------------------------------------------------------------------

############################################################################

Commit:      c9fb410e4237e8e778d54f27f009f4f4cb60397d
URL:         http://cgit.haiku-os.org/haiku/commit/?id=c9fb410
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Fri Jan 18 10:00:12 2013 UTC

IMAP: fixed folder configuration.

* Store the settings, don't archive the view; removed leftovers of the
  old settings API.

----------------------------------------------------------------------------

############################################################################

Commit:      edf77456f2f1f35b4fbfcd7b63f48ab14d0c8399
URL:         http://cgit.haiku-os.org/haiku/commit/?id=edf7745
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Fri Jan 18 10:02:11 2013 UTC

IMAP: close folder config window on error, show message.

----------------------------------------------------------------------------

############################################################################

Commit:      3ab3f57ad2a7e7bd4314b5791fde5dc0b99066f4
URL:         http://cgit.haiku-os.org/haiku/commit/?id=3ab3f57
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Fri Jan 18 17:17:46 2013 UTC

IMAP: FolderList is supposed to be an interface.

* Made its methods pure virtual.

----------------------------------------------------------------------------

############################################################################

Commit:      186c96d50c1df03eb711dce3d1d22ebae88c18ae
URL:         http://cgit.haiku-os.org/haiku/commit/?id=186c96d
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Fri Jan 18 17:19:24 2013 UTC

IMAP: Early work in progress of main protocol class.

----------------------------------------------------------------------------

############################################################################

Commit:      f8b5e17a239b094593e4049827571bb9d20a8399
URL:         http://cgit.haiku-os.org/haiku/commit/?id=f8b5e17
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Fri Jan 18 17:20:01 2013 UTC

Minor cleanup.

----------------------------------------------------------------------------

############################################################################

Commit:      c67313f3c37605d888e1be78880db418f9866a5c
URL:         http://cgit.haiku-os.org/haiku/commit/?id=c67313f
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Wed Jan 23 19:27:45 2013 UTC

imap: added Settings::MaxConnections()/IdleMode().

* Also made use of the new BMessage API for the existing methods.

----------------------------------------------------------------------------

############################################################################

Commit:      4cab719ff29893ac868af8a6fa910e009b42322a
URL:         http://cgit.haiku-os.org/haiku/commit/?id=4cab719
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Sun Mar 24 23:00:18 2013 UTC

mail_daemon: auto check message was leaked, send immediately.

* BMessageRunner does not take ownership of the message.
* Instead of waiting through the complete interval, we send an auto check
  message immediately after launch (or whenever else the timer is being
  started).
* Added constant instead of referring to 'moto' for the auto check message.

----------------------------------------------------------------------------

############################################################################

Commit:      bfe83adcb28b0f6d8d8f911e0a8aac3a79932360
URL:         http://cgit.haiku-os.org/haiku/commit/?id=bfe83ad
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Sun Mar 24 23:02:14 2013 UTC

imap_tester: Fixed SSL build.

----------------------------------------------------------------------------

############################################################################

Commit:      adbe8fc944d2568ba87d7603e921115830ef1416
URL:         http://cgit.haiku-os.org/haiku/commit/?id=adbe8fc
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Mon Mar 25 00:09:37 2013 UTC

IMAP: The connection workers are now started.

* On SyncMessages(), the main connection worker is started if it is not already
  running (it may only run already in idle mode).
* This will then list the subscribed folders, and create as many more connection
  workers as allowed and make sense.
* Finally, it will distribute the folders to the workers which don't do anything
  further yet.

----------------------------------------------------------------------------

############################################################################

Commit:      a4bdd26d61967231469220573c4b5ee09e29dd49
URL:         http://cgit.haiku-os.org/haiku/commit/?id=a4bdd26
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Fri Apr  5 23:32:39 2013 UTC

imap: Work in progress of connection setup.

* SelectCommand now correctly encodes the mailbox name again.
* Hierarchy separators from the LIST/LSUB commands are now properly parsed,
  and taken into account.
* Folders in the file system are now created for mailboxes on the server,
  supporting hierarchical mailbox names.
* A connection worker now has an IMAPFolder that handles the local side of the
  mailbox, and an IMAPMailbox that handles the server side.
* Connection workers are now created/deleted, and setup correctly. They will
  now also wait in case they don't have a mailbox until they get some.

----------------------------------------------------------------------------

############################################################################

Commit:      7993ddfabaa0069192062289b4fb18c0034cdf76
URL:         http://cgit.haiku-os.org/haiku/commit/?id=7993ddf
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Wed Apr 10 20:47:47 2013 UTC

imap: Fleshed out command processing.

* Still doesn't do anything useful, though.

----------------------------------------------------------------------------

############################################################################

Commit:      82f27de2389ec7d30d77e924341de43ab763e449
URL:         http://cgit.haiku-os.org/haiku/commit/?id=82f27de
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Sun Apr 14 21:15:10 2013 UTC

imap_tester: Fixed build after Protocol.GetFolders() changes.

----------------------------------------------------------------------------

############################################################################

Commit:      229c7773234389164b47efc09f348b248b8caf47
URL:         http://cgit.haiku-os.org/haiku/commit/?id=229c777
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Sun Apr 14 22:53:34 2013 UTC

imap: Testing for new messages is now working.

* There is now a CheckSubscribedFoldersCommand that is issued on the main
  connection that triggers everything.
* The new CheckMailboxesCommand divides the new mail check into several
  portions, and requeues itself until the next step, ie. the
  FetchHeadersCommand.
* The headers of the new mails are downloaded, but nothing is done with
  them yet.
* The actual check for the new mails doesn't scale that well yet, not sure
  how to properly do this without having to rely on the mail indices. Might
  be sensible to solve this via some simple heuristic.

----------------------------------------------------------------------------

############################################################################

Commit:      9234fd439edf8e9047e7eceb9ad34ee39b192edb
URL:         http://cgit.haiku-os.org/haiku/commit/?id=9234fd4
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Wed Apr 17 20:25:33 2013 UTC

imap: Implemented encoding RFC3501 strings.

* Was completely missing so far.
* Fixed bug in decoding that handled the "&-" sequence incorrectly.
* Added small test application that should easily be convertible to
  a unit test.

----------------------------------------------------------------------------

############################################################################

Commit:      3302df142ef8f47c0c0a7d6020b38a63c7cb7403
URL:         http://cgit.haiku-os.org/haiku/commit/?id=3302df1
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Fri Apr 19 21:29:34 2013 UTC

imap: WIP of getting fetching headers to work.

* Changed the FetchListener mechanism quite a bit.
* Doesn't seem to work correctly yet, although most pieces are in
  place now.

----------------------------------------------------------------------------

############################################################################

Commit:      a6b84a0c57bcbdc9ce22bbd789d56ab4a0d41929
URL:         http://cgit.haiku-os.org/haiku/commit/?id=a6b84a0
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Wed Apr 24 22:13:39 2013 UTC

BBufferedDataIO: the underlying stream might return an error.

* In this case, fSize would have been set incorrectly, ignoring the error
  completely, but open the possibility to read from uninitialized or even
  unmapped memory.

----------------------------------------------------------------------------

############################################################################

Commit:      c500331f6684588cd41b52dc438f9ab480b7d0ef
URL:         http://cgit.haiku-os.org/haiku/commit/?id=c500331
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Wed Apr 24 23:31:20 2013 UTC

BSecureSocket: prepared to do SSL error conversion.

* For now, just print them to stderr; we don't really have matching error
  codes yet AFAICS.

----------------------------------------------------------------------------

############################################################################

Commit:      eba458b9407056235aeb184a038e202b2d7bfe5e
URL:         http://cgit.haiku-os.org/haiku/commit/?id=eba458b
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Wed Apr 24 23:35:38 2013 UTC

imap: Fetching headers is now working.

* No state is stored yet, though, so that all messages will be downloaded
  over and over again.

----------------------------------------------------------------------------

############################################################################

Commit:      28ee6c28394b54048a391dfd1b398aad22b47a38
URL:         http://cgit.haiku-os.org/haiku/commit/?id=28ee6c2
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Thu Apr 25 18:56:11 2013 UTC

IMAP: Use useful default without destination.

* We now use the account name as destination directory.
* Turns out that an empty string is written as destination which worked
  around the GetString() solution.

----------------------------------------------------------------------------

############################################################################

Commit:      47b68f5806099ae651be808e3b119c2a6ee06be9
URL:         http://cgit.haiku-os.org/haiku/commit/?id=47b68f5
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Thu Apr 25 18:56:49 2013 UTC

IMAP: IMAPFolder now stores the last UID.

* So mails are no longer downloaded every time.

----------------------------------------------------------------------------

############################################################################

Commit:      4b2c5571c05d4f7edb62cb093ce8374d57778498
URL:         http://cgit.haiku-os.org/haiku/commit/?id=4b2c557
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Mon May 13 21:22:02 2013 UTC

IMAP: sync when requested.

----------------------------------------------------------------------------

############################################################################

Commit:      aebdd0c14bb3c216f000f5ffa99912383c1e9dba
URL:         http://cgit.haiku-os.org/haiku/commit/?id=aebdd0c
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Mon May 13 22:54:31 2013 UTC

IMAP: call the folder's handler like the mailbox.

----------------------------------------------------------------------------

############################################################################

Commit:      29e5da6f2070ba3c177a8383e9ad3e1c4cdcbd0d
URL:         http://cgit.haiku-os.org/haiku/commit/?id=29e5da6
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Mon May 13 23:25:59 2013 UTC

IMAP: allow only one sync at a time, divided header fetching.

* CheckMailboxesCommand, and FetchHeadersCommand now inherit from SyncCommand
  which will prevent new CheckMailboxesCommand to be enqueued.
* FetchHeadersCommand now only retrieves up to kMaxFetchEntries headers at
  once. This gets the same TODO about scaling as the limit in
  CheckMailboxesCommand when fetching the flags/UIDs. Since we already read
  all new UIDs at that point, we could easily do better there, though.

----------------------------------------------------------------------------

############################################################################

Commit:      8705e1f6e7fcc9892785d1406b2d0c0e530d0e11
URL:         http://cgit.haiku-os.org/haiku/commit/?id=8705e1f
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Wed May 22 21:15:29 2013 UTC

mail_daemon: cleanup, 30s auto check startup delay.

* Refactored new message retrieval a bit, so that the notification strings
  aren't duplicated.
* The daemon now waits 30 seconds before doing the first mail check.

----------------------------------------------------------------------------

############################################################################

Commit:      e9a197ffff095d52b175baf265cd42b2b82db7f2
URL:         http://cgit.haiku-os.org/haiku/commit/?id=e9a197f
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Wed May 22 22:40:27 2013 UTC

IMAP: make the body fetch limit setting available.

* This is set by the ProtocolConfigView -- there should really be
  some constant for this.

----------------------------------------------------------------------------

############################################################################

Commit:      dcb85ffa51a542a7c1164346fe17fc1ec2168ad2
URL:         http://cgit.haiku-os.org/haiku/commit/?id=dcb85ff
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Wed May 22 22:43:16 2013 UTC

IMAP: if connecting fails, try again a few times.

* Also documented SyncCommand.

----------------------------------------------------------------------------

############################################################################

Commit:      1052525dc5cfda3563a36ad82b4a900d7beb5221
URL:         http://cgit.haiku-os.org/haiku/commit/?id=1052525
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Wed May 22 22:50:26 2013 UTC

IMAP: work in progress of downloading the mail body.

* Most things are in place now, we just try to download the body to the
  wrong file, as the final location is currently unknown.
* Added local only kPartialMessage flag for mails, but it's not being
  used yet.

----------------------------------------------------------------------------

############################################################################

Commit:      c1f779e3500b6157de46ccdf7ddccd70850beab9
URL:         http://cgit.haiku-os.org/haiku/commit/?id=c1f779e
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Wed May 29 16:01:07 2013 UTC

IMAP: FetchMessageEntriesCommand now also works without UIDs

* This will be used to solve the TODO in CheckMailboxesCommand::Process()
  when the initial message sizes/flags are retrieved.
* Also fixed imap_tester build.

----------------------------------------------------------------------------

############################################################################

Commit:      549949b26f4df07ba280792c18a515553f489388
URL:         http://cgit.haiku-os.org/haiku/commit/?id=549949b
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Wed Jun 26 22:30:14 2013 UTC

Mail Kit: Changed how filter changes work.

* BMailFilter::HeaderFetched() now only alters the entry_ref, and returns
  B_MOVE_MAIL_ACTION to move a mail.
* Instead of potentially moving the file around several times, the
  BMailProtocol now takes care of carrying out the filter action just once,
  including trying to make the file name unique.
* This also allows the IMAP add-on to know the final location of the mail,
  and thus downloading a message actually works.
* However, with my test inbox, it currently hangs, and a current Debugger does
  not work on my older system -- I guess I need to update.
* Replaced the duplicated space mechanism within the "HaikuMailFormatFilter"
  that is substantially faster, and handles all whitespace, not just spaces.
  It will also replace tabs with spaces.

----------------------------------------------------------------------------

############################################################################

Commit:      cf14e7f21f0c663f4ec7a10d475e01279f0f45a0
URL:         http://cgit.haiku-os.org/haiku/commit/?id=cf14e7f
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Wed Jun 26 23:51:07 2013 UTC

Build fixes.

* Never built a complete image from the IMAP branch before.

----------------------------------------------------------------------------

############################################################################

Commit:      d33e4744df1542a1350f55c25ce7b691560d7345
URL:         http://cgit.haiku-os.org/haiku/commit/?id=d33e474
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Wed Jul  3 20:52:22 2013 UTC

IMAP: downloading mails is now working.

* Changed the way the attributes are written to make sure that everything
  that can be written once is in fact written just once.
* The rename code in BMailProtocol::_ProcessFetchedHeader() was broken,
  and caused the hang of the last commit.

----------------------------------------------------------------------------

############################################################################

Revision:    hrev48615
Commit:      46019292630b815296175cf61031f574dc15a69e
URL:         http://cgit.haiku-os.org/haiku/commit/?id=4601929
Author:      Axel Dörfler <axeld@xxxxxxxxxxxxxxxx>
Date:        Thu Jul 18 21:53:17 2013 UTC

IMAP: let mail retrieval scale better.

* We now also maintain a mail index -> UID array in IMAPMailbox.
* Instead of fetching the message entries by a fixed range of UIDs, we use the
  message count, and get the entries by index.
* Likewise, in FetchHeadersCommand, we now get a list of UIDs rather than a
  range. This makes it possible to only download exactly the headers we want.
* Extended FetchCommand to be able to dynamically build a sequence list from
  a list of UIDs.
* Besides the suboptimal body fetching (one at a time, due to holes in the
  IMAP specification), we should now be able to retrieve the messages with
  pretty much optimal performance, while retaining an acceptable responsiveness
  to user requests.

----------------------------------------------------------------------------


Other related posts: