keep the result of driver->list() and a flag whether it is valid in the store.

This commit is contained in:
Oswald Buddenhagen 2006-03-20 19:27:38 +00:00
parent 861dd7468e
commit 47e592b603
4 changed files with 23 additions and 32 deletions

View File

@ -113,7 +113,6 @@ typedef struct imap_store {
unsigned /*currentnc:1,*/ trashnc:1;
int uidnext; /* from SELECT responses */
list_t *ns_personal, *ns_other, *ns_shared; /* NAMESPACE info */
string_list_t *boxes; /* LIST results */
message_t **msgapp; /* FETCH results */
unsigned caps, rcaps; /* CAPABILITY results */
/* command queue */
@ -898,7 +897,7 @@ parse_list_rsp( imap_store_t *ctx, char *cmd )
arg += l;
if (!memcmp( arg + strlen( arg ) - 5, ".lock", 5 )) /* workaround broken servers */
return;
add_string_list( &ctx->boxes, arg );
add_string_list( &ctx->gen.boxes, arg );
}
static int
@ -1042,6 +1041,7 @@ imap_close_store( store_t *gctx )
imap_store_t *ctx = (imap_store_t *)gctx;
free_generic_messages( gctx->msgs );
free_string_list( ctx->gen.boxes );
if (ctx->buf.sock.fd != -1) {
imap_exec( ctx, 0, "LOGOUT" );
close( ctx->buf.sock.fd );
@ -1180,6 +1180,9 @@ imap_open_store( store_conf_t *conf, store_t *oldctx )
if (ctx) {
if (((imap_store_conf_t *)(ctx->gen.conf))->server == cfg->server) {
free_string_list( ctx->gen.boxes );
ctx->gen.boxes = 0;
ctx->gen.listed = 0;
ctx->gen.conf = conf;
goto final;
}
@ -1586,16 +1589,14 @@ imap_find_msg( store_t *gctx, const char *tuid, int *uid )
}
static int
imap_list( store_t *gctx, string_list_t **retb )
imap_list( store_t *gctx )
{
imap_store_t *ctx = (imap_store_t *)gctx;
int ret;
ctx->boxes = 0;
if ((ret = imap_exec_b( ctx, 0, "LIST \"\" \"%s%%\"", ctx->prefix )) != DRV_OK)
if ((ret = imap_exec_b( ctx, 0, "LIST \"\" \"%s%%\"", ctx->prefix )) == DRV_OK)
gctx->listed = 1;
return ret;
*retb = ctx->boxes;
return DRV_OK;
}
static int

View File

@ -147,11 +147,12 @@ static void
maildir_close_store( store_t *gctx )
{
maildir_cleanup( gctx );
free_string_list( gctx->boxes );
free( gctx );
}
static int
maildir_list( store_t *gctx, string_list_t **retb )
maildir_list( store_t *gctx )
{
DIR *dir;
struct dirent *de;
@ -160,7 +161,6 @@ maildir_list( store_t *gctx, string_list_t **retb )
error( "%s: %s\n", gctx->conf->path, strerror(errno) );
return DRV_STORE_BAD;
}
*retb = 0;
while ((de = readdir( dir ))) {
struct stat st;
char buf[PATH_MAX];
@ -170,9 +170,10 @@ maildir_list( store_t *gctx, string_list_t **retb )
nfsnprintf( buf, sizeof(buf), "%s%s/cur", gctx->conf->path, de->d_name );
if (stat( buf, &st ) || !S_ISDIR(st.st_mode))
continue;
add_string_list( retb, de->d_name );
add_string_list( &gctx->boxes, de->d_name );
}
closedir (dir);
gctx->listed = 1;
return DRV_OK;
}

View File

@ -144,6 +144,8 @@ typedef struct message {
typedef struct store {
store_conf_t *conf; /* foreign */
string_list_t *boxes; /* _list results - own */
unsigned listed:1; /* was _list already run? */
/* currently open mailbox */
const char *name; /* foreign! maybe preset? */
@ -176,7 +178,7 @@ struct driver {
int (*parse_store)( conffile_t *cfg, store_conf_t **storep, int *err );
store_t *(*open_store)( store_conf_t *conf, store_t *oldctx );
void (*close_store)( store_t *ctx );
int (*list)( store_t *ctx, string_list_t **boxes );
int (*list)( store_t *ctx );
void (*prepare_paths)( store_t *ctx );
void (*prepare_opts)( store_t *ctx, int opts );
int (*select)( store_t *ctx, int minuid, int maxuid, int *excs, int nexcs );

View File

@ -194,10 +194,10 @@ main( int argc, char **argv )
group_conf_t *group;
driver_t *driver[2];
store_t *ctx[2];
string_list_t *uboxes[2], *boxes[2], *mbox, *sbox, **mboxp, **sboxp, *cboxes, *chanptr;
string_list_t *boxes[2], *mbox, *sbox, **mboxp, **sboxp, *cboxes, *chanptr;
char *config = 0, *channame, *boxlist, *opt, *ochar;
const char *names[2];
int all = 0, list = 0, cops = 0, ops[2] = { 0, 0 }, guboxes[2];
int all = 0, list = 0, cops = 0, ops[2] = { 0, 0 };
int oind, ret, op, multiple, pseudo = 0, t;
gethostname( Hostname, sizeof(Hostname) );
@ -444,8 +444,6 @@ main( int argc, char **argv )
ctx[M] = ctx[S] = 0;
conf[M] = conf[S] = 0; /* make-gcc-happy */
driver[M] = driver[S] = 0; /* make-gcc-happy */
guboxes[M] = guboxes[S] = 0;
uboxes[M] = uboxes[S] = 0;
if (all)
multiple = channels->next != 0;
else if (argv[oind + 1])
@ -493,9 +491,6 @@ main( int argc, char **argv )
if (ctx[t]) {
if (conf[t] == chan->stores[t])
continue;
free_string_list( uboxes[t] );
uboxes[t] = 0;
guboxes[t] = 0;
if (conf[t]->driver != chan->stores[t]->driver) {
driver[t]->close_store( ctx[t] );
ctx[t] = 0;
@ -525,23 +520,17 @@ main( int argc, char **argv )
}
} else if (chan->patterns) {
for (t = 0; t < 2; t++) {
if (!guboxes[t]) {
if (driver[t]->list( ctx[t], &uboxes[t] ) != DRV_OK) {
if (!ctx[t]->listed) {
if (driver[t]->list( ctx[t] ) != DRV_OK) {
screwt:
driver[t]->close_store( ctx[t] );
free_string_list( uboxes[t] );
uboxes[t] = 0;
guboxes[t] = 0;
ctx[t] = 0;
ret = 1;
goto next;
} else {
guboxes[t] = 1;
if (ctx[t]->conf->map_inbox)
add_string_list( &uboxes[t], ctx[t]->conf->map_inbox );
} else if (ctx[t]->conf->map_inbox)
add_string_list( &ctx[t]->boxes, ctx[t]->conf->map_inbox );
}
}
boxes[t] = filter_boxes( uboxes[t], chan->patterns );
boxes[t] = filter_boxes( ctx[t]->boxes, chan->patterns );
}
for (mboxp = &boxes[M]; (mbox = *mboxp); ) {
for (sboxp = &boxes[S]; (sbox = *sboxp); sboxp = &sbox->next)
@ -606,10 +595,8 @@ main( int argc, char **argv )
break;
}
}
free_string_list( uboxes[S] );
if (ctx[S])
driver[S]->close_store( ctx[S] );
free_string_list( uboxes[M] );
if (ctx[M])
driver[M]->close_store( ctx[M] );