annotate src/plugins/virtual/virtual-search.c @ 8483:b12705704329 HEAD

Optimized searching with virtual mailboxes. Instead of going through the messages in the virtual mailbox order, go them through one mailbox at a time and in ascending message order within that mailbox.
author Timo Sirainen <tss@iki.fi>
date Sun, 23 Nov 2008 02:40:09 +0200
parents
children f323bf2465bd
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
8483
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
1 /* Copyright (c) 2008 Dovecot authors, see the included COPYING file */
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
2
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
3 #include "lib.h"
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
4 #include "array.h"
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
5 #include "mail-search.h"
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
6 #include "index-storage.h"
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
7 #include "virtual-storage.h"
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
8
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
9 #include <stdlib.h>
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
10
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
11 enum virtual_search_state {
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
12 VIRTUAL_SEARCH_STATE_FAILED = -1,
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
13 VIRTUAL_SEARCH_STATE_BUILD,
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
14 VIRTUAL_SEARCH_STATE_RETURN,
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
15 VIRTUAL_SEARCH_STATE_SORT,
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
16 VIRTUAL_SEARCH_STATE_SORT_DONE
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
17 };
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
18
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
19 struct virtual_search_record {
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
20 uint32_t mailbox_id;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
21 uint32_t real_uid;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
22 uint32_t virtual_seq;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
23 };
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
24
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
25 struct virtual_search_context {
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
26 union mail_search_module_context module_ctx;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
27
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
28 ARRAY_TYPE(seq_range) result;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
29 struct seq_range_iter result_iter;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
30 ARRAY_DEFINE(records, struct virtual_search_record);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
31
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
32 enum virtual_search_state search_state;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
33 unsigned int next_result_n;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
34 unsigned int next_record_idx;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
35 };
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
36
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
37 static int virtual_search_record_cmp(const void *p1, const void *p2)
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
38 {
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
39 const struct virtual_search_record *r1 = p1, *r2 = p2;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
40
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
41 if (r1->mailbox_id < r2->mailbox_id)
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
42 return -1;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
43 if (r1->mailbox_id > r2->mailbox_id)
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
44 return 1;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
45
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
46 if (r1->real_uid < r2->real_uid)
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
47 return -1;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
48 if (r1->real_uid > r2->real_uid)
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
49 return 1;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
50 return 0;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
51 }
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
52
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
53 static int mail_search_get_result(struct mail_search_context *ctx)
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
54 {
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
55 const struct mail_search_arg *arg;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
56 int ret = 1;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
57
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
58 for (arg = ctx->args->args; arg != NULL; arg = arg->next) {
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
59 if (arg->result < 0)
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
60 return -1;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
61 if (arg->result == 0)
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
62 ret = 0;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
63 }
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
64 return ret;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
65 }
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
66
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
67 static int virtual_search_get_records(struct mail_search_context *ctx,
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
68 struct virtual_search_context *vctx)
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
69 {
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
70 struct virtual_mailbox *mbox =
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
71 (struct virtual_mailbox *)ctx->transaction->box;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
72 const struct virtual_mail_index_record *vrec;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
73 struct virtual_search_record srec, *srecs;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
74 unsigned int count;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
75 const void *data;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
76 bool expunged;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
77 int ret, result;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
78
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
79 memset(&srec, 0, sizeof(srec));
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
80 while ((ret = index_storage_search_next_update_seq(ctx)) > 0) {
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
81 result = mail_search_get_result(ctx);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
82 i_assert(result != 0);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
83 if (result > 0) {
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
84 /* full match, no need to check this any further */
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
85 seq_range_array_add(&vctx->result, 0, ctx->seq);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
86 } else {
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
87 /* possible match, save and check later */
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
88 mail_index_lookup_ext(mbox->ibox.view, ctx->seq,
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
89 mbox->virtual_ext_id,
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
90 &data, &expunged);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
91 vrec = data;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
92
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
93 srec.mailbox_id = vrec->mailbox_id;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
94 srec.real_uid = vrec->real_uid;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
95 srec.virtual_seq = ctx->seq;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
96 array_append(&vctx->records, &srec, 1);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
97 }
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
98 mail_search_args_reset(ctx->args->args, FALSE);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
99 }
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
100 srecs = array_get_modifiable(&vctx->records, &count);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
101 qsort(srecs, count, sizeof(*srecs), virtual_search_record_cmp);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
102 return ret;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
103 }
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
104
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
105 struct mail_search_context *
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
106 virtual_search_init(struct mailbox_transaction_context *t,
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
107 struct mail_search_args *args,
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
108 const enum mail_sort_type *sort_program)
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
109 {
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
110 struct mail_search_context *ctx;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
111 struct virtual_search_context *vctx;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
112
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
113 ctx = index_storage_search_init(t, args, sort_program);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
114
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
115 vctx = i_new(struct virtual_search_context, 1);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
116 vctx->search_state = VIRTUAL_SEARCH_STATE_BUILD;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
117 i_array_init(&vctx->result, 64);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
118 i_array_init(&vctx->records, 64);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
119 MODULE_CONTEXT_SET(ctx, virtual_storage_module, vctx);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
120
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
121 if (virtual_search_get_records(ctx, vctx) < 0)
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
122 vctx->search_state = VIRTUAL_SEARCH_STATE_FAILED;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
123
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
124 seq_range_array_iter_init(&vctx->result_iter, &vctx->result);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
125 return ctx;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
126 }
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
127
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
128 int virtual_search_deinit(struct mail_search_context *ctx)
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
129 {
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
130 struct virtual_search_context *vctx = VIRTUAL_CONTEXT(ctx);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
131
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
132 array_free(&vctx->result);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
133 array_free(&vctx->records);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
134 i_free(vctx);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
135 return index_storage_search_deinit(ctx);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
136 }
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
137
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
138 int virtual_search_next_nonblock(struct mail_search_context *ctx,
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
139 struct mail *mail, bool *tryagain_r)
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
140 {
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
141 struct virtual_search_context *vctx = VIRTUAL_CONTEXT(ctx);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
142 uint32_t seq;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
143 int ret;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
144
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
145 switch (vctx->search_state) {
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
146 case VIRTUAL_SEARCH_STATE_FAILED:
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
147 return -1;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
148 case VIRTUAL_SEARCH_STATE_BUILD:
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
149 if (ctx->sort_program == NULL)
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
150 vctx->search_state = VIRTUAL_SEARCH_STATE_SORT;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
151 else
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
152 vctx->search_state = VIRTUAL_SEARCH_STATE_RETURN;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
153 return virtual_search_next_nonblock(ctx, mail, tryagain_r);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
154 case VIRTUAL_SEARCH_STATE_RETURN:
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
155 return index_storage_search_next_nonblock(ctx, mail, tryagain_r);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
156 case VIRTUAL_SEARCH_STATE_SORT:
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
157 /* the messages won't be returned sorted, so we'll have to
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
158 do it ourself */
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
159 while ((ret = index_storage_search_next_nonblock(ctx, mail,
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
160 tryagain_r)) > 0)
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
161 seq_range_array_add(&vctx->result, 0, mail->seq);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
162 if (ret < 0 || *tryagain_r)
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
163 return ret;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
164
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
165 vctx->next_result_n = 0;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
166 vctx->search_state = VIRTUAL_SEARCH_STATE_SORT_DONE;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
167 /* fall through */
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
168 case VIRTUAL_SEARCH_STATE_SORT_DONE:
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
169 *tryagain_r = FALSE;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
170 if (!seq_range_array_iter_nth(&vctx->result_iter,
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
171 vctx->next_result_n, &seq))
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
172 return 0;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
173 vctx->next_result_n++;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
174 mail_set_seq(mail, seq);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
175 return 1;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
176 }
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
177 i_unreached();
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
178 }
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
179
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
180 static void search_args_set_full_match(struct mail_search_arg *args)
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
181 {
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
182 for (; args != NULL; args = args->next)
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
183 args->result = 1;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
184 }
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
185
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
186 bool virtual_search_next_update_seq(struct mail_search_context *ctx)
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
187 {
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
188 struct virtual_search_context *vctx = VIRTUAL_CONTEXT(ctx);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
189 const struct virtual_search_record *recs;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
190 unsigned int count;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
191
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
192 recs = array_get(&vctx->records, &count);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
193 if (vctx->next_record_idx < count) {
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
194 ctx->seq = recs[vctx->next_record_idx++].virtual_seq - 1;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
195 if (!index_storage_search_next_update_seq(ctx))
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
196 i_unreached();
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
197 return TRUE;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
198 }
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
199
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
200 if (ctx->sort_program != NULL &&
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
201 seq_range_array_iter_nth(&vctx->result_iter,
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
202 vctx->next_result_n, &ctx->seq)) {
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
203 search_args_set_full_match(ctx->args->args);
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
204 vctx->next_result_n++;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
205 return TRUE;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
206 }
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
207 return FALSE;
b12705704329 Optimized searching with virtual mailboxes.
Timo Sirainen <tss@iki.fi>
parents:
diff changeset
208 }