[dovecot-cvs] dovecot/src/imap cmd-list.c,1.25,1.26
cras at procontrol.fi
cras at procontrol.fi
Sun Jul 27 03:53:07 EEST 2003
- Previous message: [dovecot-cvs] dovecot/src/lib-imap imap-match.c,1.6,1.7
- Next message: [dovecot-cvs] dovecot/src/lib-storage mailbox-tree.c,NONE,1.1
mailbox-tree.h,NONE,1.1 Makefile.am,1.8,1.9
mail-storage.h,1.52,1.53 proxy-mail-storage.c,1.1,1.2
- Messages sorted by:
[ date ]
[ thread ]
[ subject ]
[ author ]
Update of /home/cvs/dovecot/src/imap
In directory danu:/tmp/cvs-serv8554/imap
Modified Files:
cmd-list.c
Log Message:
API change: Mailbox list sorting must now always done by storage itself if
it's needed.
Maildir listing rewritten.
Index: cmd-list.c
===================================================================
RCS file: /home/cvs/dovecot/src/imap/cmd-list.c,v
retrieving revision 1.25
retrieving revision 1.26
diff -u -d -r1.25 -r1.26
--- cmd-list.c 23 Jun 2003 18:22:48 -0000 1.25
+++ cmd-list.c 26 Jul 2003 23:53:05 -0000 1.26
@@ -7,42 +7,15 @@
#include "imap-match.h"
#include "commands.h"
-struct list_node {
- struct list_node *next;
- struct list_node *children;
-
- char *name; /* escaped */
- enum mailbox_flags flags;
-};
-
-struct list_context {
- pool_t pool;
- struct list_node *nodes;
- struct mail_storage *storage;
-};
-
-struct list_send_context {
- struct client *client;
- const char *response_name;
- const char *sep;
- char sep_chr;
- struct imap_match_glob *glob;
- int listext, no_placeholder;
-};
-
-static const char *mailbox_flags2str(enum mailbox_flags flags,
- int listext, int no_placeholder)
+static const char *mailbox_flags2str(enum mailbox_flags flags, int listext)
{
const char *str;
if (flags & MAILBOX_PLACEHOLDER) {
- if ((flags & ~MAILBOX_CHILDREN) == MAILBOX_PLACEHOLDER) {
- if (!listext || no_placeholder)
- flags = MAILBOX_NOSELECT;
- } else {
- /* it was at one point, but then we got better specs */
- flags &= ~MAILBOX_PLACEHOLDER;
- }
+ i_assert((flags & ~MAILBOX_CHILDREN) == MAILBOX_PLACEHOLDER);
+
+ if (!listext)
+ flags = MAILBOX_NOSELECT;
flags |= MAILBOX_CHILDREN;
}
if ((flags & MAILBOX_NONEXISTENT) != 0 && !listext)
@@ -61,177 +34,33 @@
return *str == '\0' ? "" : str+1;
}
-static void list_node_update(pool_t pool, struct list_node **node,
- const char *path, char separator,
- enum mailbox_flags flags)
-{
- const char *name, *parent;
-
- parent = NULL;
-
- for (name = path;; path++) {
- if (*path != separator && *path != '\0')
- continue;
-
- t_push();
-
- name = t_strdup_until(name, path);
-
- /* find the node */
- while (*node != NULL) {
- if (strcmp((*node)->name, name) == 0)
- break;
-
- node = &(*node)->next;
- }
-
- if (*node == NULL) {
- /* not found, create it */
- *node = p_new(pool, struct list_node, 1);
- (*node)->name = p_strdup(pool, name);
- (*node)->flags = *path == '\0' ? flags :
- MAILBOX_PLACEHOLDER;
- } else {
- if (*path == '\0') {
- if (((*node)->flags & MAILBOX_NOSELECT) != 0 &&
- (flags & MAILBOX_NOSELECT) == 0) {
- /* overrides previous flag */
- (*node)->flags &= ~MAILBOX_NOSELECT;
- }
-
- (*node)->flags |= flags;
- }
- }
-
- t_pop();
-
- if (*path == '\0')
- break;
-
- name = path+1;
- parent = (*node)->name;
- node = &(*node)->children;
- }
-}
-
-static void list_send(struct list_send_context *ctx, struct list_node *node,
- const char *path)
-{
- const char *name, *send_name, *flagstr;
- enum imap_match_result match;
- string_t *str;
-
- for (; node != NULL; node = node->next) {
- t_push();
-
- /* Send INBOX always uppercased */
- if (path != NULL) {
- name = t_strdup_printf("%s%c%s", path, ctx->sep_chr,
- node->name);
- } else if (strcasecmp(node->name, "INBOX") == 0)
- name = "INBOX";
- else
- name = node->name;
- send_name = name;
-
- if ((node->flags & MAILBOX_PLACEHOLDER) == 0 &&
- (node->flags & MAILBOX_NOSELECT) == 0)
- match = IMAP_MATCH_YES;
- else {
- /* make sure the placeholder matches. */
- const char *buf;
-
- buf = str_unescape(t_strdup_noconst(name));
- match = imap_match(ctx->glob, buf);
- /* FIXME: IMAP spec says this should be done, but
- a) this is broken, we shouldn't give \NoSelect for
- this folder if it actually works.
- b) at least mozilla's subscriptions list breaks if
- this is sent
- c) cyrus and courier doesn't do this either..
-
- if (match == IMAP_MATCH_CHILDREN) {
- send_name = t_strdup_printf("%s%c", name,
- ctx->sep);
- buf = str_unescape(t_strdup_noconst(send_name));
- match = imap_match(ctx->glob, buf);
- }*/
- }
-
- if (match == IMAP_MATCH_YES) {
- /* node->name should already be escaped */
- flagstr = mailbox_flags2str(node->flags, ctx->listext,
- ctx->no_placeholder);
- t_push();
- str = t_str_new(256);
- str_printfa(str, "* %s (%s) \"%s\" ",
- ctx->response_name, flagstr, ctx->sep);
- imap_quote_append_string(str, send_name, FALSE);
- client_send_line(ctx->client, str_c(str));
- t_pop();
- }
-
- if (node->children != NULL)
- list_send(ctx, node->children, name);
-
- t_pop();
- }
-}
-
-static void list_and_sort(struct client *client,
- struct mailbox_list_context *ctx,
- const char *response_name, const char *mask,
- const char *sep, char sep_chr,
- enum mailbox_list_flags list_flags, int listext)
-{
- struct mailbox_list *list;
- struct list_node *nodes;
- struct list_send_context send_ctx;
- pool_t pool;
-
- pool = pool_alloconly_create("list_mailboxes", 10240);
- nodes = NULL;
-
- while ((list = client->storage->list_mailbox_next(ctx)) != NULL) {
- list_node_update(pool, &nodes, list->name,
- client->storage->hierarchy_sep,
- list->flags);
- }
-
- send_ctx.client = client;
- send_ctx.response_name = response_name;
- send_ctx.sep = sep;
- send_ctx.sep_chr = sep_chr;
- send_ctx.glob = imap_match_init(data_stack_pool, mask, TRUE,
- client->storage->hierarchy_sep);
- send_ctx.listext = listext;
- send_ctx.no_placeholder = (list_flags & MAILBOX_LIST_SUBSCRIBED) == 0;
-
- list_send(&send_ctx, nodes, NULL);
- imap_match_deinit(send_ctx.glob);
- pool_unref(pool);
-}
-
-static void list_unsorted(struct client *client,
- struct mailbox_list_context *ctx,
- const char *reply, const char *sep, int listext)
+static int mailbox_list(struct client *client, const char *mask,
+ const char *sep, const char *reply,
+ enum mailbox_list_flags list_flags, int listext)
{
+ struct mailbox_list_context *ctx;
struct mailbox_list *list;
string_t *str;
+ ctx = client->storage->list_mailbox_init(client->storage, mask,
+ list_flags);
+ if (ctx == NULL)
+ return FALSE;
+
+ str = t_str_new(256);
while ((list = client->storage->list_mailbox_next(ctx)) != NULL) {
- t_push();
- str = t_str_new(256);
+ str_truncate(str, 0);
str_printfa(str, "* %s (%s) \"%s\" ", reply,
- mailbox_flags2str(list->flags, listext, FALSE),
+ mailbox_flags2str(list->flags, listext),
sep);
if (strcasecmp(list->name, "INBOX") == 0)
str_append(str, "INBOX");
else
imap_quote_append_string(str, list->name, FALSE);
client_send_line(client, str_c(str));
- t_pop();
}
+
+ return client->storage->list_mailbox_deinit(ctx);
}
static int parse_list_flags(struct client *client, struct imap_arg *args,
@@ -266,10 +95,9 @@
{
struct imap_arg *args;
enum mailbox_list_flags list_flags;
- struct mailbox_list_context *ctx;
const char *ref, *mask;
char sep_chr, sep[3];
- int failed, sorted, listext;
+ int failed, listext;
sep_chr = client->storage->hierarchy_sep;
if (IS_ESCAPED_CHAR(sep_chr)) {
@@ -330,24 +158,9 @@
}
}
- ctx = client->storage->list_mailbox_init(client->storage, mask,
- list_flags, &sorted);
- if (ctx == NULL)
- failed = TRUE;
- else {
- const char *response_name = lsub ? "LSUB" : "LIST";
-
- if (sorted) {
- list_unsorted(client, ctx, response_name, sep,
- listext);
- } else {
- list_and_sort(client, ctx, response_name, mask,
- sep, sep_chr, list_flags,
- listext);
- }
-
- failed = !client->storage->list_mailbox_deinit(ctx);
- }
+ failed = !mailbox_list(client, mask, sep,
+ lsub ? "LSUB" : "LIST",
+ list_flags, listext);
}
if (failed)
- Previous message: [dovecot-cvs] dovecot/src/lib-imap imap-match.c,1.6,1.7
- Next message: [dovecot-cvs] dovecot/src/lib-storage mailbox-tree.c,NONE,1.1
mailbox-tree.h,NONE,1.1 Makefile.am,1.8,1.9
mail-storage.h,1.52,1.53 proxy-mail-storage.c,1.1,1.2
- Messages sorted by:
[ date ]
[ thread ]
[ subject ]
[ author ]
More information about the dovecot-cvs
mailing list