Back to index

courier  0.68.2
Classes | Defines | Functions | Variables
maildirkeywords.h File Reference
#include "config.h"
#include <stdio.h>
#include <string.h>
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Classes

struct  libmail_keywordEntry
struct  libmail_kwHashtable
struct  libmail_kwMessageEntry
struct  libmail_kwMessage
struct  maildir_kwReadInfo
struct  libmail_kwGeneric
struct  libmail_kwGenericEntry
union  libmail_keywordEntry.u
union  libmail_kwMessage.u

Defines

#define keywordName(ke)   ((char *)((ke)+1))

Functions

void libmail_kwhInit (struct libmail_kwHashtable *)
int libmail_kwhCheck (struct libmail_kwHashtable *)
int libmail_kwEnumerate (struct libmail_kwHashtable *h, int(*callback_func)(struct libmail_keywordEntry *, void *), void *callback_arg)
struct libmail_keywordEntrylibmail_kweFind (struct libmail_kwHashtable *ht, const char *name, int createIfNew)
void libmail_kweClear (struct libmail_keywordEntry *)
struct libmail_kwMessagelibmail_kwmCreate ()
void libmail_kwmDestroy (struct libmail_kwMessage *)
int libmail_kwmSet (struct libmail_kwMessage *, struct libmail_keywordEntry *)
int libmail_kwmSetName (struct libmail_kwHashtable *, struct libmail_kwMessage *, const char *)
int libmail_kwmCmp (struct libmail_kwMessage *, struct libmail_kwMessage *)
int libmail_kwmClearName (struct libmail_kwMessage *, const char *)
int libmail_kwmClear (struct libmail_kwMessage *, struct libmail_keywordEntry *)
int libmail_kwmClearEntry (struct libmail_kwMessageEntry *)
int maildir_kwRead (const char *maildir, struct maildir_kwReadInfo *rki)
int maildir_kwSave (const char *maildir, const char *filename, struct libmail_kwMessage *newKeyword, char **tmpname, char **newname, int tryAtomic)
int maildir_kwSaveArray (const char *maildir, const char *filename, const char **flags, char **tmpname, char **newname, int tryAtomic)
int maildir_kwExport (FILE *, struct maildir_kwReadInfo *)
int maildir_kwImport (FILE *, struct maildir_kwReadInfo *)
void libmail_kwgInit (struct libmail_kwGeneric *g)
int libmail_kwgDestroy (struct libmail_kwGeneric *g)
int libmail_kwgReadMaildir (struct libmail_kwGeneric *g, const char *maildir)
struct libmail_kwGenericEntrylibmail_kwgFindByName (struct libmail_kwGeneric *g, const char *filename)
struct libmail_kwGenericEntrylibmail_kwgFindByIndex (struct libmail_kwGeneric *g, size_t n)

Variables

const char * libmail_kwVerbotten
int libmail_kwCaseSensitive
int libmail_kwEnabled

Class Documentation

struct libmail_keywordEntry

Definition at line 27 of file maildirkeywords.h.

Collaboration diagram for libmail_keywordEntry:
Class Members
struct libmail_kwMessageEntry * firstMsg
struct libmail_kwMessageEntry * lastMsg
struct libmail_keywordEntry * next
struct libmail_keywordEntry * prev
union libmail_keywordEntry u
struct libmail_kwHashtable

Definition at line 45 of file maildirkeywords.h.

Class Members
int keywordAddedRemoved
struct libmail_kwMessageEntry

Definition at line 53 of file maildirkeywords.h.

Collaboration diagram for libmail_kwMessageEntry:
Class Members
struct libmail_kwMessageEntry * keywordNext
struct libmail_kwMessageEntry * keywordPrev
struct libmail_keywordEntry * libmail_keywordEntryPtr
struct libmail_kwMessage * libmail_kwMessagePtr
struct libmail_kwMessageEntry * next
struct libmail_kwMessageEntry * prev
struct libmail_kwMessage

Definition at line 64 of file maildirkeywords.h.

Collaboration diagram for libmail_kwMessage:
Class Members
struct libmail_kwMessageEntry * firstEntry
struct libmail_kwMessageEntry * lastEntry
union libmail_kwMessage u
struct libmail_kwGeneric

Definition at line 399 of file maildirkeywords.h.

Collaboration diagram for libmail_kwGeneric:
Class Members
struct libmail_kwGenericEntry * messageHashTable
struct libmail_kwGenericEntry ** messages
int messagesValid
size_t nMessages
struct libmail_kwGenericEntry

Definition at line 411 of file maildirkeywords.h.

Collaboration diagram for libmail_kwGenericEntry:
Class Members
char * filename
struct libmail_kwMessage * keywords
size_t messageNum
struct libmail_kwGenericEntry * next
union libmail_keywordEntry.u

Definition at line 33 of file maildirkeywords.h.

Class Members
unsigned long userNum
void * userPtr
union libmail_kwMessage.u

Definition at line 69 of file maildirkeywords.h.

Class Members
unsigned long userNum
void * userPtr

Define Documentation

#define keywordName (   ke)    ((char *)((ke)+1))

Definition at line 31 of file maildirkeywords.h.


Function Documentation

Definition at line 301 of file maildirkeywords.c.

{
       if (kw->firstMsg == NULL && kw->lastMsg == NULL)
       {
              struct libmail_keywordEntry *k;

              for (k=kw; k->next; k=k->next)
                     ;

              ((struct libmail_kwHashtable *)k->u.userPtr)
                     ->keywordAddedRemoved=1;

              kw->prev->next=kw->next;
              kw->next->prev=kw->prev; /* There are always dummy head/tail */

              free(kw);
       }
}

Here is the caller graph for this function:

struct libmail_keywordEntry* libmail_kweFind ( struct libmail_kwHashtable ht,
const char *  name,
int  createIfNew 
) [read]

Definition at line 56 of file maildirkeywords.c.

{
       size_t hashBucket=0;
       const char *p;
       char *fixed_p=NULL;

       struct libmail_keywordEntry *e, *eNew;

       if (libmail_kwVerbotten)
       {
              for (p=name; *p; p++)
                     if (strchr( libmail_kwVerbotten, *p))
                            break;

              if (*p) /* Verbotten char, fix it */
              {
                     char *q;

                     fixed_p=strdup(name);

                     if (!fixed_p)
                            return NULL;

                     for (q=fixed_p; *q; q++)
                            if (strchr(libmail_kwVerbotten, *q))
                                   *q='_';

                     name=fixed_p;
              }
       }

       p=name;
       while (*p)
       {
              hashBucket=(hashBucket << 1) ^ (hashBucket & 0x8000 ? 0x1301:0)

                     ^ (libmail_kwCaseSensitive ?
                        (unsigned char)*p:tolower((unsigned char)*p));
              ++p;
       }
       hashBucket=hashBucket & 0xFFFF;
       hashBucket %= sizeof(ht->heads)/sizeof(ht->heads[0]);

       for (e= ht->heads[hashBucket].next; e->next; e=e->next)
       {
              const char *kn=keywordName(e);
              int n=libmail_kwCaseSensitive ? strcmp(kn, name) :
                     strcasecmp(kn, name);

              if (n == 0)
              {
                     if (fixed_p)
                            free(fixed_p);
                     return e;
              }

              if (n > 0)
                     break;
       }

       if (!createIfNew)
       {
              if (fixed_p)
                     free(fixed_p);
              return NULL;
       }

       if ((eNew=malloc(sizeof(*e)+1+strlen(name))) == NULL)
       {
              if (fixed_p)
                     free(fixed_p);
              return NULL;
       }

       memset(eNew, 0, sizeof(*eNew));
       strcpy(keywordName(eNew), name);
       eNew->next=e;
       eNew->prev=e->prev;
       eNew->next->prev=eNew;
       eNew->prev->next=eNew;
       eNew->firstMsg=NULL;
       eNew->lastMsg=NULL;
       ht->keywordAddedRemoved=1;

       if (fixed_p)
              free(fixed_p);
       return eNew;
}

Here is the call graph for this function:

Here is the caller graph for this function:

int libmail_kwEnumerate ( struct libmail_kwHashtable h,
int(*)(struct libmail_keywordEntry *, void *)  callback_func,
void *  callback_arg 
)

Definition at line 320 of file maildirkeywords.c.

{
       size_t i;

       for (i=0; i<sizeof(h->heads)/sizeof(h->heads[0]); i++)
       {
              struct libmail_keywordEntry *ke=h->heads[i].next;

              while (ke->next)
              {
                     struct libmail_keywordEntry *ke2=ke;
                     int rc;

                     ke=ke->next;

                     if ((rc=(*callback_func)(ke2, callback_arg)) != 0)
                            return rc;
              }
       }
       return 0;
}

Here is the caller graph for this function:

Definition at line 23 of file maildirkeywords3.c.

{
       struct libmail_kwGenericEntry *p;
       size_t n;

       for (n=0; n<sizeof(g->messageHashTable)/sizeof(g->messageHashTable[0]);
            n++)
              while ((p=g->messageHashTable[n]) != NULL)
              {
                     g->messageHashTable[n]=p->next;
                     if (p->filename)
                            free(p->filename);
                     if (p->keywords)
                            libmail_kwmDestroy(p->keywords);
                     free(p);
              }

       if (g->messages)
              free(g->messages);
       g->messages=NULL;
       g->nMessages=0;
       g->messagesValid=0;
       return libmail_kwhCheck(&g->kwHashTable);
}

Here is the call graph for this function:

Here is the caller graph for this function:

struct libmail_kwGenericEntry* libmail_kwgFindByIndex ( struct libmail_kwGeneric g,
size_t  n 
) [read]

Definition at line 117 of file maildirkeywords3.c.

{
       if (!g->messagesValid || n >= g->nMessages)
              return NULL;

       return g->messages[n];
}

Here is the caller graph for this function:

struct libmail_kwGenericEntry* libmail_kwgFindByName ( struct libmail_kwGeneric g,
const char *  filename 
) [read]

Definition at line 102 of file maildirkeywords3.c.

{
       const char *p=strrchr(filename, '/');
       struct libmail_kwGenericEntry **ret;

       if (p)
              filename=p+1;

       if (srch(g, filename, &ret) == 0)
              return *ret;

       return NULL;
}

Here is the call graph for this function:

Here is the caller graph for this function:

void libmail_kwgInit ( struct libmail_kwGeneric g)

Definition at line 17 of file maildirkeywords3.c.

{
       memset(g, 0, sizeof(*g));
       libmail_kwhInit(&g->kwHashTable);
}

Here is the call graph for this function:

Here is the caller graph for this function:

int libmail_kwgReadMaildir ( struct libmail_kwGeneric g,
const char *  maildir 
)

Definition at line 146 of file maildirkeywords3.c.

{
       struct maildir_kwReadInfo ri;

       memset(&ri, 0, sizeof(ri));

       ri.findMessageByFilename= &g_findMessageByFilename;
       ri.getMessageCount= &g_getMessageCount;
       ri.findMessageByIndex= &g_findMessageByIndex;
       ri.getMessageFilename= &g_getMessageFilename;
       ri.getKeywordHashtable= &g_getKeywordHashtable;
       ri.updateKeywords=&g_updateKeywords;
       ri.voidarg=g;

       if (maildir_kwRead(maildir, &ri) < 0)
       {
              libmail_kwgDestroy(g);
              return -1;
       }

       if (ri.tryagain)
       {
              libmail_kwgDestroy(g); /* Free memory */
              return 1;
       }

       if (g_validIndex(g) < 0)
       {
              libmail_kwgDestroy(g); /* Free memory */
              return -1;
       }
       return 0;
}

Here is the call graph for this function:

Here is the caller graph for this function:

Definition at line 42 of file maildirkeywords.c.

{
       size_t i;

       for (i=0; i<sizeof(h->heads)/sizeof(h->heads[0]); i++)
              if (h->heads[i].next->next)
              {
                     errno=EIO;
                     return -1; /* Should not happen */
              }

       return 0;
}

Here is the caller graph for this function:

void libmail_kwhInit ( struct libmail_kwHashtable )

Definition at line 24 of file maildirkeywords.c.

{
       size_t i;

       memset(h, 0, sizeof(*h));

       for (i=0; i<sizeof(h->heads)/sizeof(h->heads[0]); i++)
       {
              h->heads[i].u.userPtr=h;
              h->tails[i].u.userPtr=h;

              h->heads[i].next=&h->tails[i];
              h->tails[i].prev=&h->heads[i];
       }
}

Here is the caller graph for this function:

int libmail_kwmClear ( struct libmail_kwMessage ,
struct libmail_keywordEntry  
)

Definition at line 254 of file maildirkeywords.c.

{
       return libmail_kwmClearName(km, keywordName(ke));
}

Here is the call graph for this function:

Here is the caller graph for this function:

Definition at line 273 of file maildirkeywords.c.

{
       struct libmail_keywordEntry *kw=e->libmail_keywordEntryPtr;

       if (e->next)
              e->next->prev=e->prev;
       else e->libmail_kwMessagePtr->lastEntry=e->prev;

       if (e->prev)
              e->prev->next=e->next;
       else e->libmail_kwMessagePtr->firstEntry=e->next;

       if (e->keywordNext)
              e->keywordNext->keywordPrev=e->keywordPrev;
       else
              kw->lastMsg=e->keywordPrev;

       if (e->keywordPrev)
              e->keywordPrev->keywordNext=e->keywordNext;
       else
              kw->firstMsg=e->keywordNext;

       libmail_kweClear(kw);
       free(e);
       return 0;
}

Here is the call graph for this function:

Here is the caller graph for this function:

int libmail_kwmClearName ( struct libmail_kwMessage ,
const char *   
)

Definition at line 260 of file maildirkeywords.c.

{
       struct libmail_kwMessageEntry *kEntry;

       for (kEntry=km->firstEntry; kEntry; kEntry=kEntry->next)
              if (strcmp(keywordName(kEntry->libmail_keywordEntryPtr), n) == 0)
              {
                     return libmail_kwmClearEntry(kEntry);
              }

       return 1;
}

Here is the call graph for this function:

Here is the caller graph for this function:

int libmail_kwmCmp ( struct libmail_kwMessage ,
struct libmail_kwMessage  
)

Definition at line 239 of file maildirkeywords.c.

{
       struct libmail_kwMessageEntry *e1, *e2;

       for (e1=km1->firstEntry, e2=km2->firstEntry; e1 && e2;
            e1=e1->next, e2=e2->next)
              if (strcmp(keywordName(e1->libmail_keywordEntryPtr),
                        keywordName(e2->libmail_keywordEntryPtr)))
                     break;

       return e1 || e2 ? -1:0;
}

Here is the caller graph for this function:

Definition at line 146 of file maildirkeywords.c.

{
       struct libmail_kwMessage *kw=malloc(sizeof(struct libmail_kwMessage));

       if (kw == NULL)
              return NULL;

       memset(kw, 0, sizeof(*kw));

       return kw;
}

Here is the caller graph for this function:

Definition at line 158 of file maildirkeywords.c.

{
       while (kw->firstEntry)
              libmail_kwmClearEntry(kw->firstEntry);

       free(kw);
}

Here is the call graph for this function:

Here is the caller graph for this function:

int libmail_kwmSet ( struct libmail_kwMessage ,
struct libmail_keywordEntry  
)

Definition at line 177 of file maildirkeywords.c.

{
       struct libmail_kwMessageEntry *keLast, *kePtr;

       const char *name=keywordName(ke);

       for (keLast=km->firstEntry; keLast; keLast=keLast->next)
       {
              int rc=strcmp(keywordName(keLast->libmail_keywordEntryPtr), name);

              if (rc == 0)
                     return 1; /* Keyword already set */

              if (rc > 0)
                     break;
       }

       kePtr=malloc(sizeof(*kePtr));

       if (!kePtr)
              return -1;

       if (keLast)
       {
              kePtr->next=keLast;
              kePtr->prev=keLast->prev;

              keLast->prev=kePtr;

              if (kePtr->prev)
                     kePtr->prev->next=kePtr;
              else
                     km->firstEntry=kePtr;
       }
       else
       {
              kePtr->next=NULL;

              if ((kePtr->prev=km->lastEntry) != NULL)
                     kePtr->prev->next=kePtr;
              else
                     km->firstEntry=kePtr;
              km->lastEntry=kePtr;
       }
       kePtr->libmail_kwMessagePtr=km;

       kePtr->keywordNext=NULL;
       if ((kePtr->keywordPrev=ke->lastMsg) != NULL)
              kePtr->keywordPrev->keywordNext=kePtr;
       else
              ke->firstMsg=kePtr;

       ke->lastMsg=kePtr;
       kePtr->libmail_keywordEntryPtr=ke;
       return 0;
}

Here is the caller graph for this function:

int libmail_kwmSetName ( struct libmail_kwHashtable ,
struct libmail_kwMessage ,
const char *   
)

Definition at line 166 of file maildirkeywords.c.

{
       struct libmail_keywordEntry *ke=libmail_kweFind(h, n, 1);

       if (!ke)
              return -1;

       return libmail_kwmSet(km, ke);
}

Here is the call graph for this function:

Here is the caller graph for this function:

int maildir_kwExport ( FILE *  ,
struct maildir_kwReadInfo  
)

Definition at line 679 of file maildirkeywords2.c.

{
       struct saveUpdateInfo sui;
       size_t i, n;

       sui.fp=fp;
       sui.counter=0;
       libmail_kwEnumerate((*info->getKeywordHashtable)(info->voidarg),
                      saveKeywordList, &sui);

       if (sui.counter == 0) /* No keywords set for any message */
              return 0;

       fprintf(fp, "\n");

       n= (*info->getMessageCount)(info->voidarg);

       for (i=0; i<n; i++)
       {
              const char *p;

              struct libmail_kwMessage **km=
                     (*info->findMessageByIndex)(i, 0, info->voidarg);
              struct libmail_kwMessageEntry *kme;

              if (!km || !*km || (*km)->firstEntry == NULL)
                     continue;

              for (p= (*info->getMessageFilename)(i, info->voidarg);
                   *p && *p != MDIRSEP[0]; p++)
                     putc(*p, fp);

              putc(':', fp);
              p="";

              for (kme=(*km)->firstEntry; kme; kme=kme->next)
              {
                     fprintf(fp, "%s%lu", p, kme->libmail_keywordEntryPtr
                            ->u.userNum);
                     p=" ";
              }
              fprintf(fp, "\n");
       }

       return 1;
}

Here is the call graph for this function:

Here is the caller graph for this function:

int maildir_kwImport ( FILE *  ,
struct maildir_kwReadInfo  
)

Definition at line 219 of file maildirkeywords2.c.

{
       struct keywordIndex {
              struct keywordIndex *next;
              struct libmail_keywordEntry *kw;
       } *firstKw=NULL, *lastKw=NULL, **index;
       size_t numKw=0;
       struct libmail_kwMessage *tmpMsg;
       char *p;
       int rc=0;

       struct readLine rl;

       if ((tmpMsg=libmail_kwmCreate()) == NULL)
       {
              rki->errorOccured=-1;
              return 0;
       }

       rl_init(&rl);

       while ((p=rl_read(&rl, fp)) != NULL && *p)
       {
              struct keywordIndex *ki=malloc(sizeof(*firstKw));

              if (!ki)
              {
                     rki->errorOccured=-1;
                     rl_free(&rl);
                     libmail_kwmDestroy(tmpMsg);
                     return 0;
              }

              if (lastKw)
                     lastKw->next=ki;
              else
                     firstKw=ki;

              lastKw=ki;
              ki->next=NULL;
              ++numKw;

              ki->kw=libmail_kweFind((*rki->getKeywordHashtable)
                                   (rki->voidarg), p, 1);
              if (libmail_kwmSet(tmpMsg, ki->kw) < 0)
              {
                     rki->errorOccured= -1;
                     break;
              }
       }

       if (rki->errorOccured ||
           (index=malloc(sizeof(*firstKw)*(numKw+1))) == NULL)
       {
              while ((lastKw=firstKw) != NULL)
              {
                     firstKw=firstKw->next;
                     free(lastKw);
              }
              libmail_kwmDestroy(tmpMsg);
              rki->errorOccured= -1;
              rl_free(&rl);
              return 0;
       }

       numKw=0;

       while (firstKw)
       {
              index[numKw]=firstKw;
              ++numKw;
              firstKw=firstKw->next;
       }
       index[numKw]=0;

       if (p)
              while ((p=rl_read(&rl, fp)) != NULL)
              {
                     char *q=strchr(p, ':');
                     struct libmail_kwMessage **i;
                     size_t l;
                     size_t n;

                     if (!q)
                     {
                            rc=1;
                            continue; /* Crap */
                     }

                     *q++=0;

                     i= (*rki->findMessageByFilename)(p, 0, &n,
                                                  rki->voidarg);

                     if (!i)
                     {
                            rc=1;
                            continue; /* Stale data */
                     }

                     if (*i) /* Already have it */
                            libmail_kwmDestroy(*i);
                     (*i)=NULL;

                     i=NULL;

                     while ((q=strtok(q, " ")) != NULL)
                     {
                            l=atoi(q);
                            q=NULL;

                            if (l < numKw)
                            {
                                   if (!i)
                                          i= (*rki->
                                              findMessageByFilename)
                                                 (p, 1, &n,
                                                  rki->voidarg);
                                   /* Autocreate it */

                                   if (*i == NULL) /* ENOMEM */
                                   {
                                          rc= -1;
                                          break;
                                   }

                                   if (libmail_kwmSet(*i, index[l]->kw)
                                       < 0)
                                          rki->errorOccured= -1;
                            }
                     }
              }

       rl_free(&rl);
       for (numKw=0; index[numKw]; numKw++)
              free(index[numKw]);

       free(index);
       libmail_kwmDestroy(tmpMsg);
       return rc;
}

Here is the call graph for this function:

Here is the caller graph for this function:

int maildir_kwRead ( const char *  maildir,
struct maildir_kwReadInfo rki 
)

Definition at line 126 of file maildirkeywords2.c.

{
       char *p=malloc(strlen(maildir)+sizeof("/" KEYWORDDIR));

       if (!p)
              return -1;

       strcat(strcpy(p, maildir), "/" KEYWORDDIR);

       rki->errorOccured=0;
       doReadKeywords2(maildir, p, rki);
       free(p);

       return rki->errorOccured;
}

Here is the call graph for this function:

Here is the caller graph for this function:

int maildir_kwSave ( const char *  maildir,
const char *  filename,
struct libmail_kwMessage newKeyword,
char **  tmpname,
char **  newname,
int  tryAtomic 
)

Definition at line 876 of file maildirkeywords2.c.

{
       return maildir_kwSaveCommon(maildir, filename, newKeyword, NULL,
                                tmpname, newname, tryAtomic);
}

Here is the call graph for this function:

Here is the caller graph for this function:

int maildir_kwSaveArray ( const char *  maildir,
const char *  filename,
const char **  flags,
char **  tmpname,
char **  newname,
int  tryAtomic 
)

Definition at line 887 of file maildirkeywords2.c.

{
       return maildir_kwSaveCommon(maildir, filename, NULL, flags,
                                tmpname, newname, tryAtomic);
}

Here is the call graph for this function:

Here is the caller graph for this function:


Variable Documentation

Definition at line 22 of file maildirkeywords.c.

Definition at line 43 of file maildirkeywords2.c.

const char* libmail_kwVerbotten

Definition at line 21 of file maildirkeywords.c.