summaryrefslogtreecommitdiffabout
path: root/libetpan/src/driver/implementation/pop3/pop3driver.c
Unidiff
Diffstat (limited to 'libetpan/src/driver/implementation/pop3/pop3driver.c') (more/less context) (ignore whitespace changes)
-rw-r--r--libetpan/src/driver/implementation/pop3/pop3driver.c388
1 files changed, 388 insertions, 0 deletions
diff --git a/libetpan/src/driver/implementation/pop3/pop3driver.c b/libetpan/src/driver/implementation/pop3/pop3driver.c
new file mode 100644
index 0000000..ea69923
--- a/dev/null
+++ b/libetpan/src/driver/implementation/pop3/pop3driver.c
@@ -0,0 +1,388 @@
1/*
2 * libEtPan! -- a mail stuff library
3 *
4 * Copyright (C) 2001, 2005 - DINH Viet Hoa
5 * All rights reserved.
6 *
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
9 * are met:
10 * 1. Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
12 * 2. Redistributions in binary form must reproduce the above copyright
13 * notice, this list of conditions and the following disclaimer in the
14 * documentation and/or other materials provided with the distribution.
15 * 3. Neither the name of the libEtPan! project nor the names of its
16 * contributors may be used to endorse or promote products derived
17 * from this software without specific prior written permission.
18 *
19 * THIS SOFTWARE IS PROVIDED BY THE AUTHORS AND CONTRIBUTORS ``AS IS'' AND
20 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
21 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
22 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHORS OR CONTRIBUTORS BE LIABLE
23 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
24 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
25 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
26 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
27 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
28 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
29 * SUCH DAMAGE.
30 */
31
32/*
33 * $Id$
34 */
35
36#include "pop3driver.h"
37
38#include <string.h>
39#include <stdlib.h>
40
41#include "pop3driver_message.h"
42#include "maildriver_tools.h"
43#include "pop3driver_tools.h"
44#include "mailmessage.h"
45
46static int pop3driver_initialize(mailsession * session);
47
48static void pop3driver_uninitialize(mailsession * session);
49
50static int pop3driver_parameters(mailsession * session,
51 int id, void * value);
52
53static int pop3driver_connect_stream(mailsession * session, mailstream * s);
54
55static int pop3driver_starttls(mailsession * session);
56
57static int pop3driver_login(mailsession * session,
58 char * userid, char * password);
59
60static int pop3driver_logout(mailsession * session);
61
62static int pop3driver_noop(mailsession * session);
63
64static int pop3driver_status_folder(mailsession * session, char * mb,
65 uint32_t * result_messages, uint32_t * result_recent,
66 uint32_t * result_unseen);
67
68static int pop3driver_messages_number(mailsession * session, char * mb,
69 uint32_t * result);
70
71static int pop3driver_remove_message(mailsession * session, uint32_t num);
72
73static int pop3driver_get_messages_list(mailsession * session,
74 struct mailmessage_list ** result);
75
76static int pop3driver_get_message(mailsession * session,
77 uint32_t num, mailmessage ** result);
78
79static mailsession_driver local_pop3_session_driver = {
80 .sess_name = "pop3",
81
82 .sess_initialize = pop3driver_initialize,
83 .sess_uninitialize = pop3driver_uninitialize,
84
85 .sess_parameters = pop3driver_parameters,
86
87 .sess_connect_stream = pop3driver_connect_stream,
88 .sess_connect_path = NULL,
89 .sess_starttls = pop3driver_starttls,
90 .sess_login = pop3driver_login,
91 .sess_logout = pop3driver_logout,
92 .sess_noop = pop3driver_noop,
93
94 .sess_build_folder_name = NULL,
95 .sess_create_folder = NULL,
96 .sess_delete_folder = NULL,
97 .sess_rename_folder = NULL,
98 .sess_check_folder = NULL,
99 .sess_examine_folder = NULL,
100 .sess_select_folder = NULL,
101 .sess_expunge_folder = NULL,
102 .sess_status_folder = pop3driver_status_folder,
103 .sess_messages_number = pop3driver_messages_number,
104 .sess_recent_number = pop3driver_messages_number,
105 .sess_unseen_number = pop3driver_messages_number,
106 .sess_list_folders = NULL,
107 .sess_lsub_folders = NULL,
108 .sess_subscribe_folder = NULL,
109 .sess_unsubscribe_folder = NULL,
110
111 .sess_append_message = NULL,
112 .sess_append_message_flags = NULL,
113 .sess_copy_message = NULL,
114 .sess_move_message = NULL,
115
116 .sess_get_messages_list = pop3driver_get_messages_list,
117 .sess_get_envelopes_list = maildriver_generic_get_envelopes_list,
118 .sess_remove_message = pop3driver_remove_message,
119#if 0
120 .sess_search_messages = maildriver_generic_search_messages,
121#endif
122
123 .sess_get_message = pop3driver_get_message,
124 .sess_get_message_by_uid = NULL,
125};
126
127mailsession_driver * pop3_session_driver = &local_pop3_session_driver;
128
129static inline struct pop3_session_state_data *
130get_data(mailsession * session)
131{
132 return session->sess_data;
133}
134
135static mailpop3 * get_pop3_session(mailsession * session)
136{
137 return get_data(session)->pop3_session;
138}
139
140static int pop3driver_initialize(mailsession * session)
141{
142 struct pop3_session_state_data * data;
143 mailpop3 * pop3;
144
145 pop3 = mailpop3_new(0, NULL);
146 if (session == NULL)
147 goto err;
148
149 data = malloc(sizeof(* data));
150 if (data == NULL)
151 goto free;
152
153 data->pop3_session = pop3;
154 data->pop3_auth_type = POP3DRIVER_AUTH_TYPE_PLAIN;
155
156 session->sess_data = data;
157
158 return MAIL_NO_ERROR;
159
160 free:
161 mailpop3_free(pop3);
162 err:
163 return MAIL_ERROR_MEMORY;
164}
165
166static void pop3driver_uninitialize(mailsession * session)
167{
168 struct pop3_session_state_data * data;
169
170 data = get_data(session);
171
172 mailpop3_free(data->pop3_session);
173 free(data);
174
175 session->sess_data = data;
176}
177
178static int pop3driver_connect_stream(mailsession * session, mailstream * s)
179{
180 int r;
181
182 r = mailpop3_connect(get_pop3_session(session), s);
183
184 switch (r) {
185 case MAILPOP3_NO_ERROR:
186 return MAIL_NO_ERROR_NON_AUTHENTICATED;
187
188 default:
189 return pop3driver_pop3_error_to_mail_error(r);
190 }
191}
192
193static int pop3driver_starttls(mailsession * session)
194{
195 int r;
196 int fd;
197 mailstream_low * low;
198 mailstream_low * new_low;
199 mailpop3 * pop3;
200
201 pop3 = get_pop3_session(session);
202
203 r = mailpop3_stls(pop3);
204
205 switch (r) {
206 case MAILPOP3_NO_ERROR:
207 break;
208 default:
209 return pop3driver_pop3_error_to_mail_error(r);
210 }
211
212 low = mailstream_get_low(pop3->pop3_stream);
213 fd = mailstream_low_get_fd(low);
214 if (fd == -1)
215 return MAIL_ERROR_STREAM;
216
217 new_low = mailstream_low_ssl_open(fd);
218 if (new_low == NULL)
219 return MAIL_ERROR_STREAM;
220 mailstream_low_free(low);
221 mailstream_set_low(pop3->pop3_stream, new_low);
222
223 return MAIL_NO_ERROR;
224}
225
226static int pop3driver_parameters(mailsession * session,
227 int id, void * value)
228{
229 struct pop3_session_state_data * data;
230
231 data = get_data(session);
232
233 switch (id) {
234 case POP3DRIVER_SET_AUTH_TYPE:
235 {
236 int * param;
237
238 param = value;
239
240 data->pop3_auth_type = * param;
241 return MAIL_NO_ERROR;
242 }
243 }
244
245 return MAIL_ERROR_INVAL;
246}
247
248static int pop3driver_login(mailsession * session,
249 char * userid, char * password)
250{
251 int r;
252 carray * msg_tab;
253 struct pop3_session_state_data * data;
254
255 data = get_data(session);
256
257 switch (data->pop3_auth_type) {
258 case POP3DRIVER_AUTH_TYPE_TRY_APOP:
259 r = mailpop3_login_apop(get_pop3_session(session), userid, password);
260 if (r != MAILPOP3_NO_ERROR)
261 r = mailpop3_login(get_pop3_session(session), userid, password);
262 break;
263
264 case POP3DRIVER_AUTH_TYPE_APOP:
265 r = mailpop3_login_apop(get_pop3_session(session), userid, password);
266 break;
267
268 default:
269 case POP3DRIVER_AUTH_TYPE_PLAIN:
270 r = mailpop3_login(get_pop3_session(session), userid, password);
271 break;
272 }
273
274 mailpop3_list(get_pop3_session(session), &msg_tab);
275
276 return pop3driver_pop3_error_to_mail_error(r);
277}
278
279static int pop3driver_logout(mailsession * session)
280{
281 int r;
282
283 r = mailpop3_quit(get_pop3_session(session));
284
285 return pop3driver_pop3_error_to_mail_error(r);
286}
287
288static int pop3driver_noop(mailsession * session)
289{
290 int r;
291
292 r = mailpop3_noop(get_pop3_session(session));
293
294 return pop3driver_pop3_error_to_mail_error(r);
295}
296
297static int pop3driver_status_folder(mailsession * session, char * mb,
298 uint32_t * result_messages,
299 uint32_t * result_recent,
300 uint32_t * result_unseen)
301{
302 uint32_t count;
303 int r;
304
305 r = pop3driver_messages_number(session, mb, &count);
306 if (r != MAIL_NO_ERROR)
307 return r;
308
309 * result_messages = count;
310 * result_recent = count;
311 * result_unseen = count;
312
313 return MAIL_NO_ERROR;
314}
315
316static int pop3driver_messages_number(mailsession * session, char * mb,
317 uint32_t * result)
318{
319 carray * msg_tab;
320
321 mailpop3_list(get_pop3_session(session), &msg_tab);
322
323 * result = carray_count(msg_tab) -
324 get_pop3_session(session)->pop3_deleted_count;
325
326 return MAIL_NO_ERROR;
327}
328
329
330/* messages operations */
331
332static int pop3driver_remove_message(mailsession * session, uint32_t num)
333{
334 mailpop3 * pop3;
335 int r;
336
337 pop3 = get_pop3_session(session);
338
339 r = mailpop3_dele(pop3, num);
340 switch (r) {
341 case MAILPOP3_ERROR_BAD_STATE:
342 return MAIL_ERROR_BAD_STATE;
343
344 case MAILPOP3_ERROR_NO_SUCH_MESSAGE:
345 return MAIL_ERROR_MSG_NOT_FOUND;
346
347 case MAILPOP3_ERROR_STREAM:
348 return MAIL_ERROR_STREAM;
349
350 case MAILPOP3_NO_ERROR:
351 return MAIL_NO_ERROR;
352
353 default:
354 return MAIL_ERROR_REMOVE;
355 }
356}
357
358static int pop3driver_get_messages_list(mailsession * session,
359 struct mailmessage_list ** result)
360{
361 mailpop3 * pop3;
362
363 pop3 = get_pop3_session(session);
364
365 return pop3_get_messages_list(pop3, session,
366 pop3_message_driver, result);
367}
368
369static int pop3driver_get_message(mailsession * session,
370 uint32_t num, mailmessage ** result)
371{
372 mailmessage * msg_info;
373 int r;
374
375 msg_info = mailmessage_new();
376 if (msg_info == NULL)
377 return MAIL_ERROR_MEMORY;
378
379 r = mailmessage_init(msg_info, session, pop3_message_driver, num, 0);
380 if (r != MAIL_NO_ERROR) {
381 mailmessage_free(msg_info);
382 return r;
383 }
384
385 * result = msg_info;
386
387 return MAIL_NO_ERROR;
388}