mail-custom-flags.c revision 02b32cf39a098edf60981fc228e4b034f11f3b90
/* Copyright (C) 2002 Timo Sirainen */
#include "lib.h"
#include "file-lock.h"
#include "mmap-util.h"
#include "write-full.h"
#include "imap-util.h"
#include "mail-index.h"
#include "mail-index-util.h"
#include "mail-custom-flags.h"
#include <unistd.h>
#include <fcntl.h>
#include <ctype.h>
/* Header is simply a counter which is increased every time the file is
updated. This allows other processes to easily notice if there's been
any changes. */
#define COUNTER_SIZE 4
struct _MailCustomFlags {
char *filepath;
int fd;
int lock_type;
char sync_counter[COUNTER_SIZE];
char *custom_flags[MAIL_CUSTOM_FLAGS_COUNT];
void *mmap_base;
unsigned int syncing:1;
};
const char *function)
{
}
{
return FALSE;
}
return TRUE;
}
{
return FALSE;
/* make sure it's still empty after locking */
if (pos == -1) {
return FALSE;
}
/* write the header - it's a 4 byte counter as hex */
return FALSE;
}
return FALSE;
return TRUE;
}
{
unsigned int num;
int i;
for (i = 0; i < MAIL_CUSTOM_FLAGS_COUNT; i++) {
}
}
/* this loop skips the first line, which is the header */
if (*data != '\n') {
data++;
continue;
}
/* beginning of line, get the index */
break;
data++;
continue;
num = 0;
data++;
}
if (num < MAIL_CUSTOM_FLAGS_COUNT) {
/* get the name */
continue;
data++;
i_warning("Error in custom flags file %s: "
num);
}
}
}
}
{
if (mcf->custom_flags_refcount > 0) {
/* we've been locked from updates for now.. */
return TRUE;
}
if (mcf->mmap_length != 0 &&
return TRUE;
/* file modified, resync */
if (!update_mmap(mcf))
return FALSE;
/* it's broken, rewrite header */
if (!custom_flags_init(mcf))
return FALSE;
if (!update_mmap(mcf))
return FALSE;
}
return TRUE;
}
{
return TRUE;
return FALSE;
}
if (!custom_flags_check_sync(mcf)) {
return FALSE;
}
/* syncing may have changed locking, do it again */
return FALSE;
}
}
return TRUE;
}
{
const char *path;
int fd;
if (fd == -1) {
path);
return FALSE;
}
if (!update_mmap(mcf)) {
return FALSE;
}
/* we just created it, write the header */
return FALSE;
}
}
return TRUE;
}
{
int i;
for (i = 0; i < MAIL_CUSTOM_FLAGS_COUNT; i++)
}
{
int i;
return FALSE;
}
for (i = COUNTER_SIZE-1; i >= 0; i--) {
break;
}
/* digit wrapped, update next one */
} else {
mcf->sync_counter[i]++;
break;
}
}
return FALSE;
}
return TRUE;
}
{
const char *buf;
/* first update the sync counter */
if (!custom_flags_update_counter(mcf))
return FALSE;
/* add the flag */
if (pos < 0) {
return FALSE;
}
"changed by someone while we were"
return FALSE;
}
/* don't add the \n prefix */
buf++;
len--;
}
return FALSE;
}
if (!update_mmap(mcf))
return FALSE;
return TRUE;
}
{
unsigned int num;
if (*data != '\n') {
data++;
continue;
}
/* beginning of line, get the index */
break;
num = 0;
data++;
}
/* remove this line */
data++;
return FALSE;
}
return TRUE;
}
}
return FALSE;
}
{
int i;
for (i = 0; i < MAIL_CUSTOM_FLAGS_COUNT; i++) {
return i;
}
return -1;
}
{
unsigned int i;
for (i = 0; i < MAIL_CUSTOM_FLAGS_COUNT; i++) {
custom_flags_remove(mcf, i);
}
}
}
{
used_flags = 0;
}
return used_flags;
}
int index_hint)
{
int i, first_empty;
return index_hint;
}
/* check existing flags */
for (i = 0; i < MAIL_CUSTOM_FLAGS_COUNT; i++) {
continue;
return i;
}
/* unlock + write lock, don't directly change from read -> write lock
to prevent deadlocking */
return -1;
}
/* new flag, add it. first find the first free flag, note that
unlock+lock might have just changed it. */
if (first_empty == -1) {
/* all custom flags are used, see if some of them are unused */
if (first_empty == -1) {
/* everything is in use */
return -1;
}
}
return -1;
return first_empty;
}
const char *custom_flags[], unsigned int count)
{
unsigned int i;
int idx;
if ((*flags & MAIL_CUSTOM_FLAGS_MASK) == 0)
return 1;
return -1;
if (idx == -1) {
return 0;
}
}
}
return -1;
return 1;
}
{
return (const char **) mcf->custom_flags;
}
{
}