Back to index

courier  0.68.2
maildirkeywords4.cpp
Go to the documentation of this file.
00001 /*
00002 ** Copyright 2003 Double Precision, Inc.
00003 ** See COPYING for distribution information.
00004 */
00005 
00006 #if    HAVE_CONFIG_H
00007 #include      "config.h"
00008 #endif
00009 #include      "maildirkeywords.h"
00010 #include      <iostream>
00011 #include      <stdlib.h>
00012 #include      <errno.h>
00013 #include      <stdio.h>
00014 
00015 #include      <vector>
00016 
00017 using namespace std;
00018 
00019 mail::keywords::Hashtable::Hashtable()
00020 {
00021        libmail_kwhInit(&kwh);
00022 }
00023 
00024 mail::keywords::Hashtable::~Hashtable()
00025 {
00026        if (libmail_kwhCheck(&kwh))
00027        {
00028               cerr << "INTERNAL ERROR: "
00029                      "mail::keywords::Hashtable::~Hashtable: "
00030                      "dangling references remain." << endl;
00031 
00032               abort();
00033        }
00034 }
00035 
00036 mail::keywords::MessageBase::MessageBase()
00037        : km(NULL), refCnt(0)
00038 {
00039 }
00040 
00041 mail::keywords::MessageBase::~MessageBase()
00042 {
00043        if (km)
00044               libmail_kwmDestroy(km);
00045 }
00046 
00047 mail::keywords::Message::Message()
00048        : b(new MessageBase)
00049 {
00050        if (!b)
00051               throw strerror(errno);
00052 
00053        ++b->refCnt;
00054 }
00055 
00056 mail::keywords::Message::~Message()
00057 {
00058        if (b && --b->refCnt == 0)
00059               delete b;
00060 }
00061 
00062 mail::keywords::Message::Message(const mail::keywords::Message &m)
00063        : b(m.b)
00064 {
00065        ++b->refCnt;
00066 }
00067 
00068 mail::keywords::Message &
00069 mail::keywords::Message::operator=(const mail::keywords::Message &m)
00070 {
00071        ++m.b->refCnt;
00072 
00073        if (--b->refCnt == 0)
00074               delete b;
00075 
00076        b=m.b;
00077        return *this;
00078 }
00079 
00080 void mail::keywords::Message::getFlags(std::set<std::string> &kwSet) const
00081 {
00082        kwSet.clear();
00083        if (!b->km)
00084               return;
00085 
00086        struct libmail_kwMessageEntry *e;
00087 
00088        for (e= b->km->firstEntry; e; e=e->next)
00089               kwSet.insert(keywordName(e->libmail_keywordEntryPtr));
00090 }
00091 
00092 bool mail::keywords::Message::copyOnWrite()
00093 {
00094        if (b->refCnt > 1) // Sharing a copy? We want our own.
00095        {
00096               MessageBase *nb=new MessageBase;
00097 
00098               if (!nb)
00099                      return false;
00100 
00101               --b->refCnt;
00102               b=nb;
00103               ++b->refCnt;
00104        }
00105        return true;
00106 }
00107 
00108 bool mail::keywords::Message::setFlags(mail::keywords::Hashtable &h,
00109                                    const std::set<std::string> &kwSet)
00110 {
00111        if (!copyOnWrite())
00112               return false;
00113 
00114        if (b->km)
00115               libmail_kwmDestroy(b->km);
00116        b->km=NULL;
00117 
00118        if (kwSet.empty())
00119        {
00120               return true;
00121        }
00122 
00123        if ((b->km=libmail_kwmCreate()) == NULL)
00124               return false;
00125 
00126        set<string>::const_iterator kb=kwSet.begin(), ke=kwSet.end();
00127 
00128        while (kb != ke)
00129        {
00130               if (libmail_kwmSetName(&h.kwh, b->km, kb->c_str()))
00131                      return false;
00132 
00133               ++kb;
00134        }
00135        return true;
00136 }
00137 
00138 bool mail::keywords::Message::addFlag(Hashtable &h, string flagName)
00139 {
00140        if (!copyOnWrite())
00141               return false;
00142 
00143        if (!b->km)
00144               if ((b->km=libmail_kwmCreate()) == NULL)
00145                      return false;
00146 
00147        if (libmail_kwmSetName(&h.kwh, b->km, flagName.c_str()))
00148               return false;
00149        return true;
00150 }
00151 
00152 bool mail::keywords::Message::remFlag(std::string s)
00153 {
00154        if (!copyOnWrite())
00155               return false;
00156        if (b->km)
00157               libmail_kwmClearName(b->km, s.c_str());
00158        return true;
00159 }
00160 
00161 int maildir_kwSave(const char *maildir,
00162                  const char *filename,
00163                  set<string> keywords,
00164 
00165                  char **tmpname,
00166                  char **newname,
00167 
00168                  int tryAtomic)
00169 {
00170        vector<const char *> keywordArray;
00171        set<string>::iterator b, e;
00172 
00173        keywordArray.reserve(keywords.size()+1);
00174 
00175        for (b=keywords.begin(), e=keywords.end(); b != e; ++b)
00176               keywordArray.push_back(b->c_str());
00177 
00178        keywordArray.push_back((const char *)NULL);
00179        return maildir_kwSaveArray(maildir, filename, &keywordArray[0],
00180                                tmpname, newname, tryAtomic);
00181 }