4 * Copyright (c) 2012 - 2013 Samsung Electronics Co., Ltd. All rights reserved.
6 * Contact: Kyuho Jo <kyuho.jo@samsung.com>, Sunghyun Kwon <sh0701.kwon@samsung.com>
8 * Licensed under the Apache License, Version 2.0 (the "License");
9 * you may not use this file except in compliance with the License.
10 * You may obtain a copy of the License at
12 * http://www.apache.org/licenses/LICENSE-2.0
14 * Unless required by applicable law or agreed to in writing, software
15 * distributed under the License is distributed on an "AS IS" BASIS,
16 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17 * See the License for the specific language governing permissions and
18 * limitations under the License.
23 /******************************************************************************
24 * File : email-core-mailbox.c
25 * Desc : Local Mailbox Management
29 *****************************************************************************/
34 #include <sys/types.h>
35 #include "email-types.h"
36 #include "email-utilities.h"
37 #include "email-convert.h"
38 #include "email-debug-log.h"
39 #include "email-core-global.h"
40 #include "email-core-utils.h"
41 #include "email-core-mailbox.h"
42 #include "email-core-event.h"
43 #include "email-network.h"
44 #include "email-core-mail.h"
45 #include "email-core-imap-mailbox.h"
46 #include "email-storage.h"
47 #include "email-core-account.h"
49 #ifdef __FEATURE_KEEP_CONNECTION__
50 static void *g_receiving_thd_stream = NULL; /* Stores the recv thd stream for next time reuse */
51 static int prev_acc_id_recv_thd = 0; /* Stores the account id for which recv thd stream is open */
52 extern int recv_thread_run;
54 static void *g_partial_body_thd_stream = NULL; /* Stores the pb thd stream for next time reuse */
55 static int prev_acc_id_pb_thd = 0; /* Stores the account id for which pb thd stream is open */
57 __thread email_connection_info_t *g_connection_info_list = NULL;
59 static pthread_mutex_t _close_stream_lock = PTHREAD_MUTEX_INITIALIZER; /* Mutex to protect closing stream */
60 #endif /* __FEATURE_KEEP_CONNECTION__ */
63 /* Binding IMAP mailbox with its function */
64 static email_mailbox_type_item_t g_mailbox_type[MAX_MAILBOX_TYPE] = {
65 {EMAIL_MAILBOX_TYPE_INBOX, "INBOX" },
67 {EMAIL_MAILBOX_TYPE_INBOX, "Inbox" },
68 {EMAIL_MAILBOX_TYPE_SENTBOX, "Sent Messages"} ,
69 {EMAIL_MAILBOX_TYPE_SPAMBOX, "&wqTTOLpUx3zVaA-"} ,
70 {EMAIL_MAILBOX_TYPE_DRAFT, "Drafts"} ,
71 {EMAIL_MAILBOX_TYPE_TRASH, "Deleted Messages" } ,
73 {EMAIL_MAILBOX_TYPE_SENTBOX, "Sent"} ,
74 {EMAIL_MAILBOX_TYPE_SPAMBOX, "Spam" },
75 {EMAIL_MAILBOX_TYPE_DRAFT, "Drafts"} ,
76 {EMAIL_MAILBOX_TYPE_TRASH, "Trash"},
78 {EMAIL_MAILBOX_TYPE_SPAMBOX, "&wqTTONO4ycDVaA-"},
80 {EMAIL_MAILBOX_TYPE_SENTBOX, "mail/sent-mail"},
81 {EMAIL_MAILBOX_TYPE_SPAMBOX, "mail/spam-mail" },
82 {EMAIL_MAILBOX_TYPE_DRAFT, "mail/saved-drafts"} ,
83 {EMAIL_MAILBOX_TYPE_TRASH, "mail/mail-trash"},
86 #ifdef __FEATURE_KEEP_CONNECTION__
87 email_connection_info_t* emcore_get_connection_info_by_account_id(int account_id)
89 EM_DEBUG_FUNC_BEGIN("account_id [%d]", account_id);
90 email_connection_info_t *connection_info = g_connection_info_list;
92 while(connection_info) {
93 if(connection_info->account_id == account_id)
95 connection_info = connection_info->next;
98 EM_DEBUG_FUNC_END("connection_info [%p]", connection_info);
99 return connection_info;
102 int emcore_append_connection_info(email_connection_info_t *new_connection_info)
104 EM_DEBUG_FUNC_BEGIN("new_connection_info [%p]", new_connection_info);
105 email_connection_info_t *connection_info = g_connection_info_list;
107 if(!new_connection_info) {
108 EM_DEBUG_EXCEPTION("EMAIL_ERROR_INVALID_PARAM");
109 return EMAIL_ERROR_INVALID_PARAM;
112 if(emcore_get_connection_info_by_account_id(new_connection_info->account_id)) {
113 EM_DEBUG_EXCEPTION("EMAIL_ERROR_ALREADY_EXISTS");
114 return EMAIL_ERROR_ALREADY_EXISTS;
117 if(connection_info) {
118 while(connection_info) {
119 if(connection_info->next == NULL) {
120 connection_info->next = new_connection_info;
121 new_connection_info->next = NULL;
123 connection_info = connection_info->next;
127 new_connection_info->next = NULL;
128 g_connection_info_list = new_connection_info;
131 EM_DEBUG_FUNC_END("EMAIL_ERROR_NONE");
132 return EMAIL_ERROR_NONE;
135 INTERNAL_FUNC int emcore_remove_connection_info(int account_id)
137 EM_DEBUG_FUNC_BEGIN("account_id [%d]", account_id);
138 email_connection_info_t *connection_info = g_connection_info_list, *prev_connection_info = NULL;
140 while(connection_info) {
141 if(connection_info->account_id == account_id) {
142 if(prev_connection_info) {
143 prev_connection_info->next = connection_info->next;
146 g_connection_info_list = connection_info->next;
148 EM_SAFE_FREE(connection_info);
151 prev_connection_info = connection_info;
152 connection_info = connection_info->next;
155 EM_DEBUG_FUNC_END("");
156 return EMAIL_ERROR_NONE;
159 #endif /* __FEATURE_KEEP_CONNECTION__ */
163 * get local mailbox list
165 INTERNAL_FUNC int emcore_get_mailbox_list(int account_id, email_mailbox_t **mailbox_list, int *p_count, int *err_code)
167 EM_DEBUG_FUNC_BEGIN("account_id[%d], mailbox_list[%p], p_count[%p], err_code[%p]", account_id, mailbox_list, p_count, err_code);
169 if (account_id <= 0 || !mailbox_list || !p_count) {
170 EM_DEBUG_EXCEPTION("PARAM Failed account_id[%d], mailbox_list[%p], p_count[%p]", account_id, mailbox_list, p_count);
171 if (err_code != NULL)
172 *err_code = EMAIL_ERROR_INVALID_PARAM;
177 int error = EMAIL_ERROR_NONE;
178 emstorage_mailbox_tbl_t *local_mailbox_list = NULL;
179 email_account_t *ref_account = NULL;
182 /* get mailbox list from mailbox table */
184 if (!(ref_account = emcore_get_account_reference(account_id))) {
185 EM_DEBUG_EXCEPTION(" emcore_get_account_reference failed - %d", account_id);
186 error = EMAIL_ERROR_INVALID_ACCOUNT;
190 if (!emstorage_get_mailbox_list(ref_account->account_id, EMAIL_MAILBOX_ALL, EMAIL_MAILBOX_SORT_BY_NAME_ASC, &count, &local_mailbox_list, true, &error)) {
191 EM_DEBUG_EXCEPTION(" emstorage_get_mailbox failed - %d", error);
197 if (!(*mailbox_list = em_malloc(sizeof(email_mailbox_t) * count))) {
198 EM_DEBUG_EXCEPTION(" mailloc failed...");
199 error = EMAIL_ERROR_OUT_OF_MEMORY;
203 memset(*mailbox_list, 0x00, (sizeof(email_mailbox_t) * count));
205 for (i = 0; i < count; i++) {
206 em_convert_mailbox_tbl_to_mailbox(local_mailbox_list + i, (*mailbox_list) + i);
217 if (local_mailbox_list != NULL)
218 emstorage_free_mailbox(&local_mailbox_list, count, NULL);
221 emcore_free_account(ref_account);
222 EM_SAFE_FREE(ref_account);
225 if (err_code != NULL)
233 * get imap sync mailbox list
235 int emcore_get_mailbox_list_to_be_sync(int account_id, email_mailbox_t **mailbox_list, int *p_count, int *err_code)
237 EM_DEBUG_FUNC_BEGIN("account_id[%d], mailbox_list[%p], p_count[%p], err_code[%p]", account_id, mailbox_list, p_count, err_code);
239 if (account_id <= 0 || !mailbox_list || !p_count) {
240 EM_DEBUG_EXCEPTION(" account_id[%d], mailbox_list[%p], p_count[%p]", account_id, mailbox_list, p_count);
241 if (err_code != NULL)
242 *err_code = EMAIL_ERROR_INVALID_PARAM;
247 int error = EMAIL_ERROR_NONE;
248 email_mailbox_t *tmp_mailbox_list = NULL;
249 emstorage_mailbox_tbl_t *mailbox_tbl_list = NULL;
250 email_account_t *ref_account = NULL;
253 /* get mailbox list from mailbox table */
254 if (!(ref_account = emcore_get_account_reference(account_id))) {
255 EM_DEBUG_EXCEPTION("emcore_get_account_reference failed - %d", account_id);
256 error = EMAIL_ERROR_INVALID_ACCOUNT;
260 if (!emstorage_get_mailbox_list(ref_account->account_id, 0, EMAIL_MAILBOX_SORT_BY_TYPE_ASC, &count, &mailbox_tbl_list, true, &error)) {
261 EM_DEBUG_EXCEPTION("emstorage_get_mailbox failed - %d", error);
267 if (!(tmp_mailbox_list = em_malloc(sizeof(email_mailbox_t) * count))) {
268 EM_DEBUG_EXCEPTION("malloc failed...");
269 error = EMAIL_ERROR_OUT_OF_MEMORY;
273 memset(tmp_mailbox_list, 0x00, (sizeof(email_mailbox_t) * count));
275 for (i = 0; i < count; i++) {
276 em_convert_mailbox_tbl_to_mailbox(mailbox_tbl_list + i, tmp_mailbox_list + i);
280 tmp_mailbox_list = NULL;
286 *mailbox_list = tmp_mailbox_list;
289 emcore_free_account(ref_account);
290 EM_SAFE_FREE(ref_account);
293 if (mailbox_tbl_list != NULL)
294 emstorage_free_mailbox(&mailbox_tbl_list, count, NULL);
296 if (err_code != NULL)
298 EM_DEBUG_FUNC_END("error [%d]", error);
302 INTERNAL_FUNC int emcore_get_mail_count(email_mailbox_t *mailbox, int *total, int *unseen, int *err_code)
304 EM_DEBUG_FUNC_BEGIN("mailbox[%p], total[%p], unseen[%p], err_code[%p]", mailbox, total, unseen, err_code);
307 int err = EMAIL_ERROR_NONE;
310 EM_DEBUG_EXCEPTION(" mailbox[%p], total[%p], unseen[%p]", mailbox, total, unseen);
311 err = EMAIL_ERROR_INVALID_PARAM;
315 if (!emstorage_get_mail_count(mailbox->account_id, mailbox->mailbox_id, total, unseen, true, &err)) {
316 EM_DEBUG_EXCEPTION(" emstorage_get_mail_count failed - %d", err);
325 if (err_code != NULL)
331 INTERNAL_FUNC int emcore_create_mailbox(email_mailbox_t *new_mailbox, int on_server, int *err_code)
333 EM_DEBUG_FUNC_BEGIN("new_mailbox[%p], err_code[%p]", new_mailbox, err_code);
335 int err = EMAIL_ERROR_NONE;
336 emstorage_mailbox_tbl_t local_mailbox;
338 if (new_mailbox == NULL || new_mailbox->mailbox_name == NULL) {
339 err = EMAIL_ERROR_INVALID_PARAM;
344 /* Create a mailbox from Sever */
345 if (!emcore_create_imap_mailbox(new_mailbox, &err)) {
346 EM_DEBUG_EXCEPTION(">>>>> mailbox Creation in Server FAILED >>> ");
350 EM_DEBUG_LOG(">>>>> mailbox Creation in Server SUCCESS >>> ");
353 memset(&local_mailbox, 0x00, sizeof(emstorage_mailbox_tbl_t));
354 EM_DEBUG_LOG("box name[%s] local yn[%d] mailbox_type[%d]", new_mailbox->mailbox_name, local_mailbox.local_yn, new_mailbox->mailbox_type);
356 /* add local mailbox into local mailbox table */
357 local_mailbox.mailbox_id = new_mailbox->mailbox_id;
358 local_mailbox.account_id = new_mailbox->account_id;
359 local_mailbox.local_yn = new_mailbox->local;
360 local_mailbox.mailbox_name = new_mailbox->mailbox_name;
361 local_mailbox.alias = new_mailbox->alias;
362 local_mailbox.mailbox_type = new_mailbox->mailbox_type;
363 local_mailbox.unread_count = 0;
364 local_mailbox.total_mail_count_on_local = 0;
365 local_mailbox.total_mail_count_on_server = 0;
366 emcore_get_default_mail_slot_count(local_mailbox.account_id, &local_mailbox.mail_slot_size);
368 if (strncmp(new_mailbox->mailbox_name, EMAIL_INBOX_NAME, EM_SAFE_STRLEN(EMAIL_INBOX_NAME)) == 0 ||
369 strncmp(new_mailbox->mailbox_name, EMAIL_DRAFTBOX_NAME, EM_SAFE_STRLEN(EMAIL_DRAFTBOX_NAME)) == 0 ||
370 strncmp(new_mailbox->mailbox_name, EMAIL_OUTBOX_NAME, EM_SAFE_STRLEN(EMAIL_OUTBOX_NAME)) == 0 ||
371 strncmp(new_mailbox->mailbox_name, EMAIL_SENTBOX_NAME, EM_SAFE_STRLEN(EMAIL_SENTBOX_NAME)) == 0)
372 local_mailbox.modifiable_yn = 0; /* can be deleted/modified */
374 local_mailbox.modifiable_yn = 1;
377 if (!emstorage_add_mailbox(&local_mailbox, true, &err)) {
378 EM_DEBUG_EXCEPTION("emstorage_add_mailbox failed [%d]", err);
382 new_mailbox->mailbox_id = local_mailbox.mailbox_id;
392 INTERNAL_FUNC int emcore_delete_mailbox(int input_mailbox_id, int input_on_server, int input_recursive)
394 EM_DEBUG_FUNC_BEGIN("input_mailbox_id[%d] input_on_server[%d] input_recursive[%d]", input_mailbox_id, input_on_server, input_recursive);
396 int err = EMAIL_ERROR_NONE;
398 int mailbox_count = 0;
399 emstorage_mailbox_tbl_t *target_mailbox = NULL;
400 emstorage_mailbox_tbl_t *target_mailbox_array = NULL;
402 if (input_mailbox_id <= 0) {
403 EM_DEBUG_EXCEPTION("EMAIL_ERROR_INVALID_PARAM");
404 err = EMAIL_ERROR_INVALID_PARAM;
408 if ((err = emstorage_get_mailbox_by_id(input_mailbox_id, &target_mailbox)) != EMAIL_ERROR_NONE || !target_mailbox) {
409 EM_DEBUG_EXCEPTION("emstorage_get_mailbox_by_id failed. [%d]", err);
413 #ifdef __FEATURE_DELETE_MAILBOX_RECURSIVELY__
414 if(input_recursive) {
415 /* Getting children mailbox list */
416 if(!emstorage_get_child_mailbox_list(target_mailbox->account_id, target_mailbox->mailbox_name, &mailbox_count, &target_mailbox_array, false,&err)) {
417 EM_DEBUG_EXCEPTION("emstorage_get_child_mailbox_list failed. [%d]", err);
422 emstorage_free_mailbox(&target_mailbox, 1, NULL);
423 target_mailbox = NULL;
426 #endif /* __FEATURE_DELETE_MAILBOX_RECURSIVELY__ */
428 target_mailbox_array = target_mailbox;
430 target_mailbox = NULL;
433 /* Remove mailboxes */
434 for(i = 0; i < mailbox_count ; i++) {
435 EM_DEBUG_LOG("Deleting mailbox_id [%d]", target_mailbox_array[i].mailbox_id);
436 if (input_on_server) {
437 EM_DEBUG_LOG("Delete the mailbox in Sever >>> ");
438 if (!emcore_delete_imap_mailbox(target_mailbox_array[i].mailbox_id, &err))
439 EM_DEBUG_EXCEPTION("Delete the mailbox in server : failed [%d]", err);
441 EM_DEBUG_LOG("Delete the mailbox in server : success");
444 if (!emcore_delete_all_mails_of_mailbox(target_mailbox_array[i].account_id, target_mailbox_array[i].mailbox_id, false, &err)) {
445 EM_DEBUG_EXCEPTION("emcore_delete_all_mails_of_mailbox failed [%d]", err);
449 if (!emstorage_delete_mailbox(target_mailbox_array[i].account_id, -1, target_mailbox_array[i].mailbox_id, true, &err)) {
450 EM_DEBUG_EXCEPTION("emstorage_delete_mailbox failed [%d]", err);
457 emstorage_free_mailbox(&target_mailbox, 1, NULL);
459 if (target_mailbox_array)
460 emstorage_free_mailbox(&target_mailbox_array, mailbox_count, NULL);
462 EM_DEBUG_FUNC_END("err[%d]", err);
467 INTERNAL_FUNC int emcore_delete_mailbox_ex(int input_account_id, int *input_mailbox_id_array, int input_mailbox_id_count, int input_on_server, int input_recursive)
469 EM_DEBUG_FUNC_BEGIN("input_account_id [%d] input_mailbox_id_array[%p] input_mailbox_id_count[%d] input_on_server[%d] input_recursive[%d]", input_mailbox_id_array, input_mailbox_id_array, input_mailbox_id_count, input_on_server, input_recursive);
470 int err = EMAIL_ERROR_NONE;
473 if(input_account_id == 0 || input_mailbox_id_count <= 0 || input_mailbox_id_array == NULL) {
474 EM_DEBUG_EXCEPTION("EMAIL_ERROR_INVALID_PARAM");
475 err = EMAIL_ERROR_INVALID_PARAM;
479 if((err = emstorage_set_field_of_mailbox_with_integer_value(input_account_id, input_mailbox_id_array, input_mailbox_id_count, "deleted_flag", 1, true)) != EMAIL_ERROR_NONE) {
480 EM_DEBUG_EXCEPTION("emstorage_set_field_of_mailbox_with_integer_value failed[%d]", err);
484 for(i = 0; i < input_mailbox_id_count; i++) {
485 if((err = emcore_delete_mailbox(input_mailbox_id_array[i] , input_on_server, input_recursive)) != EMAIL_ERROR_NONE) {
486 EM_DEBUG_EXCEPTION("emcore_delete_mailbox failed [%d]", err);
492 EM_DEBUG_FUNC_END("err[%d]", err);
496 INTERNAL_FUNC int emcore_delete_mailbox_all(email_mailbox_t *mailbox, int *err_code)
498 EM_DEBUG_FUNC_BEGIN(" mailbox[%p], err_code[%p]", mailbox, err_code);
501 int err = EMAIL_ERROR_NONE;
503 if (mailbox == NULL) {
504 EM_DEBUG_EXCEPTION(" mailbox[%p]", mailbox);
505 err = EMAIL_ERROR_INVALID_PARAM;
509 if (!emcore_delete_all_mails_of_mailbox(mailbox->account_id, mailbox->mailbox_id, 0, /*NULL, */ &err)) {
510 EM_DEBUG_EXCEPTION(" emcore_delete_all_mails_of_mailbox failed - %d", err);
515 if (!emstorage_delete_mailbox(mailbox->account_id, -1, mailbox->mailbox_id, true, &err)) {
516 EM_DEBUG_EXCEPTION(" emstorage_delete_mailbox failed - %d", err);
525 if (err_code != NULL)
527 EM_DEBUG_FUNC_END("err[%d]", err);
531 INTERNAL_FUNC int emcore_update_mailbox(email_mailbox_t *old_mailbox, email_mailbox_t *new_mailbox, int *err_code)
533 EM_DEBUG_FUNC_BEGIN("old_mailbox[%p], new_mailbox[%p], err_code[%p]", old_mailbox, new_mailbox, err_code);
536 int err = EMAIL_ERROR_NONE;
538 if (old_mailbox == NULL || new_mailbox == NULL) {
539 EM_DEBUG_EXCEPTION("old_mailbox[%p], new_mailbox[%p]", old_mailbox, new_mailbox);
541 err = EMAIL_ERROR_INVALID_PARAM;
545 emstorage_mailbox_tbl_t new_mailbox_tbl;
546 memset(&new_mailbox_tbl, 0x00, sizeof(emstorage_mailbox_tbl_t));
548 /* Support only updating mailbox_type */
549 new_mailbox_tbl.mailbox_type = new_mailbox->mailbox_type;
551 if (old_mailbox->mailbox_type != new_mailbox_tbl.mailbox_type) {
552 if (!emstorage_update_mailbox_type(old_mailbox->account_id, -1, old_mailbox->mailbox_name, new_mailbox_tbl.mailbox_type, true, &err)) {
553 EM_DEBUG_EXCEPTION("emstorage_update_mailbox failed - %d", err);
558 new_mailbox_tbl.mailbox_id = old_mailbox->mailbox_id;
559 new_mailbox_tbl.account_id = old_mailbox->account_id;
560 new_mailbox_tbl.mailbox_name = new_mailbox->mailbox_name;
561 new_mailbox_tbl.mailbox_type = new_mailbox->mailbox_type;
562 new_mailbox_tbl.alias = new_mailbox->alias;
563 new_mailbox_tbl.mail_slot_size = new_mailbox->mail_slot_size;
564 new_mailbox_tbl.total_mail_count_on_server = new_mailbox->total_mail_count_on_server;
566 if (!emstorage_update_mailbox(old_mailbox->account_id, -1, old_mailbox->mailbox_id, &new_mailbox_tbl, true, &err)) {
567 EM_DEBUG_EXCEPTION("emstorage_update_mailbox failed - %d", err);
572 if (EM_SAFE_STRCMP(old_mailbox->mailbox_name, new_mailbox_tbl.mailbox_name) != 0) {
573 if ( (err = emstorage_rename_mailbox(old_mailbox->mailbox_id, new_mailbox_tbl.mailbox_name, new_mailbox_tbl.alias, true)) != EMAIL_ERROR_NONE) {
574 EM_DEBUG_EXCEPTION("emstorage_rename_mailbox failed [%d]", err);
589 extern int try_auth_smtp;
591 #ifdef __FEATURE_KEEP_CONNECTION__
592 extern long smtp_send(SENDSTREAM *stream, char *command, char *args);
593 #endif /* __FEATURE_KEEP_CONNECTION__ */
595 INTERNAL_FUNC int emcore_connect_to_remote_mailbox_with_account_info(email_account_t *account, int input_mailbox_id, void **result_stream, int *err_code)
597 EM_PROFILE_BEGIN(emCoreMailboxOpen);
598 EM_DEBUG_FUNC_BEGIN("account[%p], input_mailbox_id[%d], mail_stream[%p], err_code[%p]", account, input_mailbox_id, result_stream, err_code);
601 int error = EMAIL_ERROR_NONE;
602 email_session_t *session = NULL;
603 char *mbox_path = NULL;
604 void *reusable_stream = NULL;
605 int is_connection_for = _SERVICE_THREAD_TYPE_NONE;
606 emstorage_mailbox_tbl_t* mailbox = NULL;
607 char *mailbox_name = NULL;
609 if (account == NULL) {
610 EM_DEBUG_EXCEPTION("Invalid Parameter.");
611 error = EMAIL_ERROR_INVALID_PARAM;
615 if (!emcore_get_current_session(&session)) {
616 EM_DEBUG_EXCEPTION("emcore_get_current_session failed...");
617 error = EMAIL_ERROR_SESSION_NOT_FOUND;
621 if (input_mailbox_id == 0 || input_mailbox_id != EMAIL_CONNECT_FOR_SENDING)
622 is_connection_for = _SERVICE_THREAD_TYPE_RECEIVING;
624 is_connection_for = _SERVICE_THREAD_TYPE_SENDING;
626 #ifdef __FEATURE_KEEP_CONNECTION__
627 email_connection_info_t *connection_info = emcore_get_connection_info_by_account_id(account->account_id);
629 if(connection_info) {
630 if (is_connection_for == _SERVICE_THREAD_TYPE_RECEIVING) {
631 if(connection_info->receiving_server_stream_status == EMAIL_STREAM_STATUS_CONNECTED)
632 reusable_stream = connection_info->receiving_server_stream;
635 if(connection_info->sending_server_stream_status == EMAIL_STREAM_STATUS_CONNECTED)
636 reusable_stream = connection_info->sending_server_stream;
640 if (reusable_stream != NULL)
641 EM_DEBUG_LOG("Stream reuse desired");
643 reusable_stream = *result_stream;
646 session->error = EMAIL_ERROR_NONE;
647 emcore_set_network_error(EMAIL_ERROR_NONE); /* set current network error as EMAIL_ERROR_NONE before network operation */
649 if (input_mailbox_id == EMAIL_CONNECT_FOR_SENDING) {
650 mailbox_name = EM_SAFE_STRDUP(ENCODED_PATH_SMTP);
652 else if (input_mailbox_id == 0) {
655 if ( (error = emstorage_get_mailbox_by_id(input_mailbox_id, &mailbox)) != EMAIL_ERROR_NONE || !mailbox) {
656 EM_DEBUG_EXCEPTION("emstorage_get_mailbox_by_id failed [%d]", error);
659 mailbox_name = EM_SAFE_STRDUP(mailbox->mailbox_name);
662 if (is_connection_for == _SERVICE_THREAD_TYPE_RECEIVING) {
663 /* open pop3/imap server */
664 MAILSTREAM *mail_stream = NULL;
666 if (!emcore_get_long_encoded_path_with_account_info(account, mailbox_name, '/', &mbox_path, &error)) {
667 EM_DEBUG_EXCEPTION("emcore_get_long_encoded_path failed - %d", error);
668 session->error = error;
672 EM_DEBUG_LOG("open mail connection to mbox_path [%s]", mbox_path);
674 try_auth = 0; /* ref_account->receiving_auth ? 1 : 0 */
675 session->auth = 0; /* ref_account->receiving_auth ? 1 : 0 */
677 if (!(mail_stream = mail_open(reusable_stream, mbox_path, IMAP_2004_LOG))) {
678 EM_DEBUG_EXCEPTION("mail_open failed. session->error[%d], session->network[%d]", session->error, session->network);
680 if ((session->error == EMAIL_ERROR_UNKNOWN) || (session->error == EMAIL_ERROR_NONE))
681 session->error = EMAIL_ERROR_CONNECTION_FAILURE;
683 error = session->error;
685 #ifdef __FEATURE_KEEP_CONNECTION__
686 /* Since mail_open failed Reset the global stream pointer as it is a dangling pointer now */
687 #endif /* __FEATURE_KEEP_CONNECTION__ */
690 *result_stream = mail_stream;
693 /* open smtp server */
694 SENDSTREAM *send_stream = NULL;
695 char *host_list[2] = {NULL, NULL};
697 #ifdef __FEATURE_KEEP_CONNECTION__
698 if (reusable_stream != NULL) {
700 /* Check whether connection is avaiable */
701 send_stream = reusable_stream;
703 send_ret = smtp_send(send_stream, "RSET", 0);
705 if (send_ret != SMTP_RESPONSE_OK) {
706 EM_DEBUG_EXCEPTION("[SMTP] RSET --> [%s]", send_stream->reply);
713 if (!emcore_get_long_encoded_path_with_account_info(account, mailbox_name, 0, &mbox_path, &error)) {
714 EM_DEBUG_EXCEPTION(" emcore_get_long_encoded_path failed - %d", error);
715 session->error = error;
719 EM_DEBUG_LOG("open SMTP connection to mbox_path [%s]", mbox_path);
721 try_auth_smtp = account->outgoing_server_need_authentication ? 1 : 0;
722 session->auth = account->outgoing_server_need_authentication ? 1 : 0;
724 host_list[0] = mbox_path;
726 if (!(send_stream = smtp_open(host_list, 1))) {
727 EM_DEBUG_EXCEPTION("smtp_open failed... : current outgoing_server_secure_connection[%d] session->error[%d] session->network[%d]",
728 account->outgoing_server_secure_connection, session->error, session->network);
729 if (session->network != EMAIL_ERROR_NONE)
730 session->error = session->network;
731 if ((session->error == EMAIL_ERROR_UNKNOWN) || (session->error == EMAIL_ERROR_NONE))
732 session->error = EMAIL_ERROR_CONNECTION_FAILURE;
734 error = session->error;
738 *result_stream = send_stream;
745 #ifdef __FEATURE_KEEP_CONNECTION__
747 if(!connection_info) {
748 connection_info = em_malloc(sizeof(email_connection_info_t));
749 connection_info->account_id = account->account_id;
751 EM_DEBUG_EXCEPTION("em_malloc for connection_info failed.");
753 emcore_append_connection_info(connection_info);
756 if(connection_info) {
757 /* connection_info->account_id = account->account_id; */
758 if (is_connection_for == _SERVICE_THREAD_TYPE_RECEIVING) {
759 connection_info->receiving_server_stream = *result_stream;
760 connection_info->receiving_server_stream_status = EMAIL_STREAM_STATUS_CONNECTED;
763 connection_info->sending_server_stream = *result_stream;
764 connection_info->sending_server_stream_status = EMAIL_STREAM_STATUS_CONNECTED;
770 EM_SAFE_FREE(mbox_path);
772 EM_SAFE_FREE(mailbox_name);
775 emstorage_free_mailbox(&mailbox, 1, NULL);
778 if (err_code != NULL)
780 EM_PROFILE_END(emCoreMailboxOpen);
781 EM_DEBUG_FUNC_END("ret [%d]", ret);
785 #ifdef __FEATURE_KEEP_CONNECTION__
787 /*h.gahlaut@samsung.com : 20-oct-2010*/
788 /*Precaution : When Reuse Stream feature is enabled then stream should only be closed using emcore_close_mailbox from email-service code.
789 mail_close should not be used directly from anywhere in code.
790 emcore_close_mailbox uses mail_close inside it.
792 mail_close is only used in emcore_connect_to_remote_mailbox and emcore_reset_streams as an exception to above rule*/
794 INTERNAL_FUNC int emcore_connect_to_remote_mailbox(int account_id, char *mailbox, void **mail_stream, int *err_code)
796 EM_DEBUG_FUNC_BEGIN("account_id[%d], mailbox[%p], mail_stream[%p], err_code[%p]", account_id, mailbox, mail_stream, err_code);
799 int error = EMAIL_ERROR_NONE;
800 email_account_t *ref_account = NULL;
802 ref_account = emcore_get_account_reference(account_id);
805 EM_DEBUG_EXCEPTION("emcore_get_account_reference failed - account id[%d]", account_id);
806 error = EMAIL_ERROR_INVALID_ACCOUNT;
810 ret = emcore_connect_to_remote_mailbox_with_account_info(ref_account, mailbox, mail_stream, &error);
815 emcore_free_account(ref_account);
816 EM_SAFE_FREE(ref_account);
821 EM_DEBUG_FUNC_END("ret [%d]", ret);
825 INTERNAL_FUNC void emcore_close_mailbox_receiving_stream()
827 EM_DEBUG_FUNC_BEGIN("recv_thread_run [%d]", recv_thread_run);
828 if (!recv_thread_run) {
829 ENTER_CRITICAL_SECTION(_close_stream_lock);
830 mail_close(g_receiving_thd_stream);
831 g_receiving_thd_stream = NULL;
832 prev_acc_id_recv_thd = 0;
833 LEAVE_CRITICAL_SECTION(_close_stream_lock);
838 INTERNAL_FUNC void emcore_close_mailbox_partial_body_stream()
840 EM_DEBUG_FUNC_BEGIN();
841 if (false == emcore_get_pbd_thd_state()) {
842 EM_DEBUG_LOG("emcore_get_pbd_thd_state returned false");
843 mail_close(g_partial_body_thd_stream);
844 g_partial_body_thd_stream = NULL;
845 prev_acc_id_pb_thd = 0;
850 /* h.gahlaut@samsung.com : 21-10-2010 -
851 emcore_reset_stream() function is used to reset globally stored partial body thread and receiving thread streams
852 on account deletion and pdp deactivation */
854 INTERNAL_FUNC void emcore_reset_streams()
856 EM_DEBUG_FUNC_BEGIN();
858 emcore_close_mailbox_receiving_stream();
859 emcore_close_mailbox_partial_body_stream();
865 #else /* __FEATURE_KEEP_CONNECTION__ */
867 INTERNAL_FUNC int emcore_connect_to_remote_mailbox(int account_id, int input_mailbox_id, void **mail_stream, int *err_code)
869 EM_DEBUG_FUNC_BEGIN("account_id[%d], input_mailbox_id[%d], mail_stream[%p], err_code[%p]", account_id, input_mailbox_id, mail_stream, err_code);
872 int error = EMAIL_ERROR_NONE;
873 email_session_t *session = NULL;
874 email_account_t *ref_account = NULL;
876 ref_account = emcore_get_account_reference(account_id);
879 EM_DEBUG_EXCEPTION("emcore_get_account_reference failed - account id[%d]", account_id);
880 error = EMAIL_ERROR_INVALID_ACCOUNT;
884 if (!emcore_check_thread_status()) {
885 error = EMAIL_ERROR_CANCELLED;
889 if (!emnetwork_check_network_status(&error)) {
890 EM_DEBUG_EXCEPTION("emnetwork_check_network_status failed [%d]", error);
894 if (!emcore_get_empty_session(&session)) {
895 EM_DEBUG_EXCEPTION("emcore_get_empty_session failed...");
896 error = EMAIL_ERROR_SESSION_NOT_FOUND;
900 ret = emcore_connect_to_remote_mailbox_with_account_info(ref_account, input_mailbox_id, mail_stream, &error);
905 emcore_free_account(ref_account);
906 EM_SAFE_FREE(ref_account);
909 emcore_clear_session(session);
916 #endif /* __FEATURE_KEEP_CONNECTION__ */
918 INTERNAL_FUNC int emcore_close_mailbox(int account_id, void *mail_stream)
920 EM_DEBUG_FUNC_BEGIN("account_id[%d], mail_stream[%p]", account_id, mail_stream);
923 EM_DEBUG_EXCEPTION("Invalid parameter");
927 #ifdef __FEATURE_KEEP_CONNECTION__
928 thread_t thread_id = THREAD_SELF();
930 if (thread_id == (thread_t)emcore_get_receiving_thd_id()) {
931 /* Receiving thread - Dont' Free Reuse feature enabled */
933 else if (thread_id == (thread_t)emcore_get_partial_body_thd_id()) {
934 /* Partial Body Download thread - Dont' Free Reuse feature enabled */
937 /* Some other thread so free stream */
938 if (g_receiving_thd_stream != mail_stream && g_partial_body_thd_stream != mail_stream)
939 mail_close((MAILSTREAM *)mail_stream);
942 mail_close((MAILSTREAM *)mail_stream);
943 #endif /* __FEATURE_KEEP_CONNECTION__ */
948 INTERNAL_FUNC void emcore_free_mailbox_list(email_mailbox_t **mailbox_list, int count)
950 EM_DEBUG_FUNC_BEGIN("mailbox_list[%p], count[%d]", mailbox_list, count);
952 if (count <= 0 || !mailbox_list || !*mailbox_list) {
953 EM_DEBUG_EXCEPTION("INVALID_PARAM: mailbox_list[%p], count[%d]", mailbox_list, count);
957 email_mailbox_t *p = *mailbox_list;
960 for (i = 0; i < count; i++)
961 emcore_free_mailbox(p+i);
964 *mailbox_list = NULL;
970 INTERNAL_FUNC void emcore_free_mailbox(email_mailbox_t *mailbox)
972 EM_DEBUG_FUNC_BEGIN();
975 EM_DEBUG_EXCEPTION("INVALID_PARAM");
979 EM_SAFE_FREE(mailbox->mailbox_name);
980 EM_SAFE_FREE(mailbox->alias);
986 INTERNAL_FUNC int emcore_free_internal_mailbox(email_internal_mailbox_t **mailbox_list, int count, int *err_code)
988 EM_DEBUG_FUNC_BEGIN("mailbox_list[%p], count[%d], err_code[%p]", mailbox_list, count, err_code);
990 /* default variable */
992 int err = EMAIL_ERROR_NONE;
995 if (!mailbox_list || !*mailbox_list) {
996 EM_DEBUG_EXCEPTION(" mailbox_list[%p], count[%d]", mailbox_list, count);
998 err = EMAIL_ERROR_INVALID_PARAM;
1002 email_internal_mailbox_t *p = *mailbox_list;
1005 /* EM_DEBUG_LOG("before loop"); */
1006 for (i = 0; i < count; i++) {
1007 EM_SAFE_FREE(p[i].mailbox_name);
1008 EM_SAFE_FREE(p[i].alias);
1010 /* EM_DEBUG_LOG("p [%p]", p); */
1012 *mailbox_list = NULL;
1020 EM_DEBUG_FUNC_END();
1024 INTERNAL_FUNC void emcore_bind_mailbox_type(email_internal_mailbox_t *mailbox_list)
1026 EM_DEBUG_FUNC_BEGIN("mailbox_list[%p]", mailbox_list);
1029 int bIsNotUserMailbox = false;
1030 email_mailbox_type_item_t *pMailboxType1 = NULL ;
1032 for (i = 0 ; i < MAX_MAILBOX_TYPE ; i++) {
1033 pMailboxType1 = g_mailbox_type + i;
1034 if (0 == EM_SAFE_STRCMP(pMailboxType1->mailbox_name, mailbox_list->mailbox_name)) { /*prevent 24662*/
1035 mailbox_list->mailbox_type = pMailboxType1->mailbox_type;
1036 EM_DEBUG_LOG("mailbox_list->mailbox_type[%d]", mailbox_list->mailbox_type);
1037 bIsNotUserMailbox = true;
1042 if (false == bIsNotUserMailbox)
1043 mailbox_list->mailbox_type = EMAIL_MAILBOX_TYPE_USER_DEFINED;
1045 EM_DEBUG_FUNC_END();
1048 INTERNAL_FUNC int emcore_send_mail_event(email_mailbox_t *mailbox, int mail_id , int *err_code)
1050 EM_DEBUG_FUNC_BEGIN();
1053 int err = EMAIL_ERROR_NONE;
1055 email_event_t event_data;
1057 if (!mailbox || mailbox->account_id <= 0) {
1058 EM_DEBUG_LOG(" mailbox[%p]", mailbox);
1060 err = EMAIL_ERROR_INVALID_PARAM;
1063 memset(&event_data, 0x00, sizeof(email_event_t));
1065 event_data.type = EMAIL_EVENT_SEND_MAIL;
1066 event_data.account_id = mailbox->account_id;
1067 event_data.event_param_data_4 = mail_id;
1068 event_data.event_param_data_1 = NULL;
1069 event_data.event_param_data_5 = mailbox->mailbox_id;
1071 if (!emcore_insert_event_for_sending_mails(&event_data, &handle, &err)) {
1072 EM_DEBUG_LOG(" emcore_insert_event failed - %d", err);
1075 emcore_add_transaction_info(mail_id , handle , &err);
1085 INTERNAL_FUNC int emcore_partial_body_thd_local_activity_sync(int *is_event_inserted, int *err_code)
1087 EM_DEBUG_FUNC_BEGIN();
1088 int activity_count = 0;
1090 int error = EMAIL_ERROR_NONE;
1092 if (false == emstorage_get_pbd_activity_count(&activity_count, false, &error)) {
1093 EM_DEBUG_LOG("emstorage_get_pbd_activity_count failed [%d]", error);
1097 if (activity_count > 0) {
1099 email_event_partial_body_thd pbd_event;
1101 /* Carefully initialise the event */
1102 memset(&pbd_event, 0x00, sizeof(email_event_partial_body_thd));
1104 pbd_event.event_type = EMAIL_EVENT_LOCAL_ACTIVITY_SYNC_BULK_PBD;
1105 pbd_event.activity_type = EMAIL_EVENT_LOCAL_ACTIVITY_SYNC_BULK_PBD;
1107 if (false == emcore_insert_partial_body_thread_event(&pbd_event, &error)) {
1108 EM_DEBUG_LOG(" emcore_insert_partial_body_thread_event failed [%d]", error);
1112 /*Not checking for NULL here because is_event_inserted is never NULL. */
1113 *is_event_inserted = true;
1118 *is_event_inserted = false;
1125 if (NULL != err_code) {
1132 INTERNAL_FUNC int emcore_get_mailbox_by_type(int account_id, email_mailbox_type_e mailbox_type, email_mailbox_t *result_mailbox, int *err_code)
1134 EM_DEBUG_FUNC_BEGIN("account_id [%d], result_mailbox [%p], err_code [%p]", account_id, result_mailbox, err_code);
1135 int ret = false, err = EMAIL_ERROR_NONE;
1136 emstorage_mailbox_tbl_t *mail_box_tbl_spam = NULL;
1138 if (result_mailbox == NULL) {
1139 EM_DEBUG_EXCEPTION("EMAIL_ERROR_INVALID_PARAM");
1140 err = EMAIL_ERROR_INVALID_PARAM;
1144 if (!emstorage_get_mailbox_by_mailbox_type(account_id, mailbox_type, &mail_box_tbl_spam, false, &err)) {
1146 EM_DEBUG_LOG("emstorage_get_mailbox_by_mailbox_type failed - %d", err);
1149 if (mail_box_tbl_spam) {
1150 result_mailbox->mailbox_type = mail_box_tbl_spam->mailbox_type;
1151 result_mailbox->mailbox_name = EM_SAFE_STRDUP(mail_box_tbl_spam->mailbox_name);
1152 result_mailbox->account_id = mail_box_tbl_spam->account_id;
1153 result_mailbox->mail_slot_size = mail_box_tbl_spam->mail_slot_size;
1154 if (!emstorage_free_mailbox(&mail_box_tbl_spam, 1, &err))
1155 EM_DEBUG_EXCEPTION(" emstorage_free_mailbox Failed [%d]", err);
1163 EM_DEBUG_FUNC_END();
1167 #ifdef __FEATURE_LOCAL_ACTIVITY__
1168 INTERNAL_FUNC int emcore_local_activity_sync(int account_id, int *err_code)
1170 EM_DEBUG_FUNC_BEGIN();
1172 EM_DEBUG_LOG(">> account_id [%d], err_code [%p] ", account_id, err_code);
1174 int *activity_id_list = NULL;
1175 int activity_count = 0;
1179 email_event_t event_data;
1182 memset(&event_data, 0x00, sizeof(email_event_t));
1185 EM_IF_NULL_RETURN_VALUE(err_code, false);
1187 if (account_id <= 0) {
1188 EM_DEBUG_EXCEPTION(" Invalid Account ID [%d] ", account_id);
1191 EM_DEBUG_LOG(">>> emdaemon_sync_local_activity 3 ");
1193 if (!emstorage_get_activity_id_list(account_id, &activity_id_list, &activity_count, ACTIVITY_DELETEMAIL, ACTIVITY_COPYMAIL, true, &err)) {
1194 EM_DEBUG_LOG(">>> emdaemon_sync_local_activity 4 ");
1195 EM_DEBUG_EXCEPTION(" emstorage_get_activity_id_list failed [ %d] ", err);
1198 EM_DEBUG_LOG(">>> emdaemon_sync_local_activity 5 ");
1200 if (activity_count > 0) {
1201 event_data.type = EMAIL_EVENT_LOCAL_ACTIVITY;
1202 event_data.account_id = account_id;
1203 if (!emcore_insert_event(&event_data, &handle, &err)) {
1204 EM_DEBUG_LOG(" emcore_insert_event failed - %d", err);
1213 if (activity_id_list)
1214 emstorage_free_activity_id_list(activity_id_list, &err);
1216 if (err_code != NULL)
1223 INTERNAL_FUNC int emcore_save_local_activity_sync(int account_id, int *err_code)
1225 EM_DEBUG_FUNC_BEGIN();
1227 EM_DEBUG_LOG(">> account_id [%d], err_code [%p] ", account_id, err_code);
1229 emstorage_activity_tbl_t *local_activity = NULL;
1230 int *activity_id_list = NULL;
1231 int activity_count = 0;
1235 email_event_t event_data;
1237 memset(&event_data, 0x00, sizeof(email_event_t));
1239 EM_IF_NULL_RETURN_VALUE(err_code, false);
1241 if (account_id <= 0) {
1242 EM_DEBUG_EXCEPTION(" Invalid Account ID [%d] ", account_id);
1245 EM_DEBUG_LOG(">>> emdaemon_sync_local_activity 3 ");
1247 if (!emstorage_get_activity_id_list(account_id, &activity_id_list, &activity_count, ACTIVITY_SAVEMAIL, ACTIVITY_DELETEMAIL_SEND, true, &err)) {
1248 EM_DEBUG_EXCEPTION(" emstorage_get_activity_id_list [ %d] ", err);
1253 if (activity_count > 0) {
1254 event_data.type = EMAIL_EVENT_LOCAL_ACTIVITY;
1255 event_data.account_id = account_id;
1256 if (!emcore_insert_event_for_sending_mails(&event_data, &handle, &err)) {
1257 EM_DEBUG_LOG(" emcore_insert_event failed - %d", err);
1268 emstorage_free_local_activity(&local_activity, activity_count, NULL);
1270 if (activity_id_list)
1271 emstorage_free_activity_id_list(activity_id_list, &err);
1273 if (err_code != NULL)