2.0_alpha release commit
[framework/messaging/email-service.git] / email-core / email-core-mailbox-sync.c
1 /*
2 *  email-service
3 *
4 * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved.
5 *
6 * Contact: Kyuho Jo <kyuho.jo@samsung.com>, Sunghyun Kwon <sh0701.kwon@samsung.com>
7
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
11 *
12 * http://www.apache.org/licenses/LICENSE-2.0
13 *
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.
19 *
20 */
21
22
23 /******************************************************************************
24  * File :  email-core-mailbox-sync.c
25  * Desc :  Mail Header Sync
26  *
27  * Auth : 
28  *****************************************************************************/
29 #include <stdio.h>
30 #include <stdlib.h>
31 #include <string.h>
32 #include <ctype.h>
33
34 #include "email-internal-types.h"
35
36 #include "c-client.h"
37 #include "lnx_inc.h"
38
39 #include "email-utilities.h"
40 #include "email-convert.h" 
41 #include "email-core-mailbox-sync.h"
42 #include "email-core-global.h"
43 #include "email-core-imap-mailbox.h"
44 #include "email-core-event.h"
45 #include "email-core-mailbox.h"
46 #include "email-core-mail.h"
47 #include "email-core-mime.h"
48 #include "email-core-utils.h"
49 #include "email-core-smtp.h"
50 #include "email-core-account.h" 
51 #include "email-storage.h"
52 #include "flstring.h"
53 #include "email-debug-log.h"
54
55 #define MAX_CHARSET_VALUE 256
56
57 static char g_append_uid_rsp[129]; /* added for getting server response  */
58
59 extern void imap_parse_body_structure (MAILSTREAM *stream, BODY *body, unsigned char **txtptr, IMAPPARSEDREPLY *reply);
60
61 #ifdef __FEATURE_PARTIAL_BODY_DOWNLOAD__
62 static email_partial_buffer *emcore_get_response_from_server (NETSTREAM *nstream, char *tag, IMAPPARSEDREPLY **reply, int input_download_size);
63 static int emcore_initiate_pbd(MAILSTREAM *stream, int account_id, int mail_id, char *uid, int mailbox_id, int *err_code);
64 #endif
65
66 #ifdef __FEATURE_SYNC_CLIENT_TO_SERVER__
67 static char g_append_uid_rsp[129]; /* added for getting server response  */
68 #endif
69
70
71 int pop3_mail_calc_rfc822_size(MAILSTREAM *stream, int msgno, int *size, int *err_code)
72 {
73         EM_DEBUG_FUNC_BEGIN();
74         
75         int ret = false;
76         int err = EMAIL_ERROR_NONE;
77         
78         POP3LOCAL *pop3local = NULL;
79         char command[16];
80         char *response = NULL;
81
82         if (!stream || !size) {
83                 EM_DEBUG_EXCEPTION(" stream[%p], msgno[%d], size[%p]\n", stream, msgno, size);
84                 
85                 err = EMAIL_ERROR_INVALID_PARAM;
86                 goto FINISH_OFF;
87         }
88         
89         if (!(pop3local = stream->local) || !pop3local->netstream) {
90                 err = EMAIL_ERROR_INVALID_STREAM;
91                 goto FINISH_OFF;
92         }
93
94         memset(command, 0x00, sizeof(command));
95         
96         SNPRINTF(command, sizeof(command), "LIST %d\015\012", msgno);
97
98         /* EM_DEBUG_LOG(" [POP3] >>> %s", command); */
99         
100         /*  send command  :  get rfc822 size by msgno */
101         if (!net_sout(pop3local->netstream, command, (int)strlen(command))) {
102                 EM_DEBUG_EXCEPTION(" net_sout failed...");
103                 
104                 err = EMAIL_ERROR_INVALID_RESPONSE;
105                 goto FINISH_OFF;
106         }
107         
108         /*  receive response */
109         if (!(response = net_getline(pop3local->netstream))) {
110                 err = EMAIL_ERROR_CONNECTION_BROKEN;            /* EMAIL_ERROR_UNKNOWN; */
111                 goto FINISH_OFF;
112         }
113         
114         /* EM_DEBUG_LOG(" [POP3] <<< %s", response); */
115         
116         if (*response == '+') {         /*  "+ OK" */
117                 char *p = NULL;
118                 
119                 if (!(p = strchr(response + strlen("+OK "), ' '))) {
120                         err = EMAIL_ERROR_INVALID_RESPONSE;
121                         goto FINISH_OFF;
122                 }
123                 
124                 *size = atoi(p + 1);
125         }
126         else if (*response == '-') {            /*  "- ERR" */
127                 err = EMAIL_ERROR_POP3_LIST_FAILURE;
128                 goto FINISH_OFF;
129         }
130         else {
131                 err = EMAIL_ERROR_INVALID_RESPONSE;
132                 goto FINISH_OFF;
133         }
134         
135         ret = true;
136         
137 FINISH_OFF: 
138         EM_SAFE_FREE(response);
139         
140         if (err_code  != NULL)
141                 *err_code = err;
142         
143         EM_DEBUG_FUNC_END("ret [%d]", ret);     
144         return ret;
145 }
146
147 int imap4_mail_calc_rfc822_size(MAILSTREAM *stream, int msgno, int *size, int *err_code)
148 {
149         EM_DEBUG_FUNC_BEGIN();
150         
151         int ret = false;
152         int err = EMAIL_ERROR_NONE;
153         
154         IMAPLOCAL *imaplocal = NULL;
155         char tag[32], command[128];
156         char *response = NULL;
157
158         if (!stream || !size) {
159                 EM_DEBUG_EXCEPTION("stream[%p], msgno[%d], size[%p]", stream, msgno, size);
160                 
161                 err = EMAIL_ERROR_INVALID_PARAM;
162                 goto FINISH_OFF;
163         }
164         
165         if (!(imaplocal = stream->local) || !imaplocal->netstream) {
166                 err = EMAIL_ERROR_INVALID_STREAM;
167                 goto FINISH_OFF;
168         }
169
170         memset(tag, 0x00, sizeof(tag));
171         memset(command, 0x00, sizeof(command));
172
173         SNPRINTF(tag, sizeof(tag), "%08lx", 0xffffffff & (stream->gensym++));
174         SNPRINTF(command, sizeof(command), "%s FETCH %d RFC822.SIZE\015\012", tag, msgno);
175
176         /* EM_DEBUG_LOG(" [IMAP4] >>> %s", command); */
177         
178         /*  send command  :  get rfc822 size by msgno */
179         if (!net_sout(imaplocal->netstream, command, (int)strlen(command))) {
180                 EM_DEBUG_EXCEPTION(" net_sout failed...");
181                 
182                 err = EMAIL_ERROR_INVALID_RESPONSE;
183                 goto FINISH_OFF;
184         }
185         
186         while (imaplocal->netstream) {
187                 char *s = NULL;
188                 char *t = NULL;
189                 
190                 /*  receive response */
191                 if (!(response = net_getline(imaplocal->netstream)))
192                         break;
193                 
194                 /* EM_DEBUG_LOG(" [IMAP4] <<< %s", response); */
195                 
196                 if (!strncmp(response, tag, strlen(tag))) {
197                         if (!strncmp(response + strlen(tag) + 1, "OK", 2)) {
198                                 EM_SAFE_FREE(response);
199                                 break;
200                         }
201                         else {          /*  'NO' or 'BAD' */
202                                 err = EMAIL_ERROR_IMAP4_FETCH_SIZE_FAILURE;             /* EMAIL_ERROR_INVALID_RESPONSE; */
203                                 goto FINISH_OFF;
204                         }
205                 }
206                 else {          /*  untagged response */
207                         if (*response == '*') {
208                                 if (!(t = strstr(response, "FETCH (RFC822.SIZE "))) {
209                                         EM_SAFE_FREE(response);
210                                         continue;
211                                 }
212                                 
213                                 s = t + strlen("FETCH (RFC822.SIZE ");
214                                 
215                                 if (!(t = strchr(s, ' '))) {
216                                         err = EMAIL_ERROR_INVALID_RESPONSE;
217                                         goto FINISH_OFF;
218                                 }
219                                 
220                                 *t = '\0';
221                                 
222                                 *size = atoi(s);
223                         }
224                 }
225                 
226                 EM_SAFE_FREE(response);
227         }
228         
229         ret = true;
230         
231 FINISH_OFF: 
232         EM_SAFE_FREE(response);
233         
234         if (err_code  != NULL)
235                 *err_code = err;
236         
237         EM_DEBUG_FUNC_END("ret [%d]", ret);     
238         return ret;
239 }
240
241 int pop3_mailbox_get_uids(MAILSTREAM *stream, emcore_uid_list** uid_list, int *err_code)
242 {
243         EM_PROFILE_BEGIN(pop3MailboxGetuid);
244         EM_DEBUG_FUNC_BEGIN("stream[%p], uid_list[%p], err_code[%p]", stream, uid_list, err_code);
245
246         int ret = false;
247         int err = EMAIL_ERROR_NONE;
248         
249         POP3LOCAL *pop3local = NULL;
250         char command[64];
251         char *response = NULL;
252         emcore_uid_list *uid_elem = NULL;
253         
254         if (!stream || !uid_list) {
255                 EM_DEBUG_EXCEPTION("stream[%p], uid_list[%p]n", stream, uid_list);
256                 err = EMAIL_ERROR_INVALID_PARAM;
257                 goto FINISH_OFF;
258         }
259         
260         if (!(pop3local = stream->local) || !pop3local->netstream) {
261                 EM_DEBUG_EXCEPTION("invalid POP3 stream detected...");
262                 err = EMAIL_ERROR_INVALID_STREAM;
263                 goto FINISH_OFF;
264         }
265         
266         memset(command, 0x00, sizeof(command));
267         
268         SNPRINTF(command, sizeof(command), "UIDL\015\012");
269         
270 #ifdef FEATURE_CORE_DEBUG
271         EM_DEBUG_LOG(" [POP3] >>> [%s]", command);
272 #endif
273         
274         /*  send command  :  get msgno/uid for all message */
275         if (!net_sout(pop3local->netstream, command, (int)strlen(command))) {
276                 EM_DEBUG_EXCEPTION("net_sout failed...");
277                 err = EMAIL_ERROR_CONNECTION_BROKEN;            /* EMAIL_ERROR_UNKNOWN; */
278                 goto FINISH_OFF;
279         }
280         
281         *uid_list = NULL;
282         
283         while (pop3local->netstream) {
284                 char *p = NULL;
285                 
286                 /*  receive response */
287                 if (!(response = net_getline(pop3local->netstream))) {
288                         EM_DEBUG_EXCEPTION("net_getline failed...");
289                         err = EMAIL_ERROR_INVALID_RESPONSE;
290                         goto FINISH_OFF;
291                 }
292                 
293 #ifdef FEATURE_CORE_DEBUG
294                 EM_DEBUG_LOG(" [POP3] <<< [%s]", response);
295 #endif
296                 
297                 if (*response == '-') {         /*  "-ERR" */
298                         err = EMAIL_ERROR_POP3_UIDL_FAILURE;            /* EMAIL_ERROR_INVALID_RESPONSE; */
299                         goto FINISH_OFF;
300                 }
301                 
302                 if (*response == '+') {         /*  "+OK" */
303                         free(response); response = NULL;
304                         continue;
305                 }
306                 
307                 if (*response == '.') {
308                         free(response); response = NULL;
309                         break;
310                 }
311                 
312                 if ((p = strchr(response, ' '))) { 
313                         *p = '\0';
314                         
315                         if (!(uid_elem = em_malloc(sizeof(emcore_uid_list)))) {
316                                 EM_DEBUG_EXCEPTION("malloc failed...");
317                                 err = EMAIL_ERROR_OUT_OF_MEMORY;
318                                 goto FINISH_OFF;
319                         }
320                         
321                         uid_elem->msgno = atoi(response);
322                         uid_elem->uid = EM_SAFE_STRDUP(p + 1);
323                         
324                         if (*uid_list  != NULL)
325                                 uid_elem->next = *uid_list;             /*  prepend new data to table */
326                         
327                         *uid_list = uid_elem;
328                 }
329                 else {
330                         err = EMAIL_ERROR_INVALID_RESPONSE;
331                         goto FINISH_OFF;
332                 }
333                 
334                 free(response); response = NULL;
335         }
336         
337         ret = true;
338
339 FINISH_OFF: 
340         if (response  != NULL)
341                 free(response);
342         
343         if (err_code  != NULL)
344                 *err_code = err;
345         
346         EM_PROFILE_END(pop3MailboxGetuid);
347         EM_DEBUG_FUNC_END("ret [%d]", ret);     
348         return ret;
349 }
350
351 int imap4_mailbox_get_uids(MAILSTREAM *stream, emcore_uid_list** uid_list, int *err_code)
352 {
353         EM_PROFILE_BEGIN(ImapMailboxGetUids);
354         EM_DEBUG_FUNC_BEGIN("stream[%p], uid_list[%p], err_code[%p]", stream, uid_list, err_code);
355
356         int ret = false;
357         int err = EMAIL_ERROR_NONE;
358         
359         IMAPLOCAL *imaplocal = NULL;
360         char tag[16], command[64];
361         char *response = NULL;
362         emcore_uid_list *uid_elem = NULL;
363         
364         if (!stream || !uid_list) {
365                 EM_DEBUG_EXCEPTION("stream[%p], uid_list[%p]", stream, uid_list);
366                 err = EMAIL_ERROR_INVALID_PARAM;
367                 goto FINISH_OFF;
368         }
369         
370         if (!(imaplocal = stream->local) || !imaplocal->netstream) {
371                 EM_DEBUG_EXCEPTION("invalid IMAP4 stream detected...");
372                 err = EMAIL_ERROR_INVALID_PARAM;                /* EMAIL_ERROR_UNKNOWN */
373                 goto FINISH_OFF;
374         }
375         
376         if (stream->nmsgs == 0){
377                 err = EMAIL_ERROR_MAIL_NOT_FOUND_ON_SERVER;
378                 goto FINISH_OFF;
379         }
380         memset(tag, 0x00, sizeof(tag));
381         memset(command, 0x00, sizeof(command));
382         
383         SNPRINTF(tag, sizeof(tag), "%08lx", 0xffffffff & (stream->gensym++));
384         SNPRINTF(command, sizeof(command), "%s FETCH 1:* (FLAGS UID)\015\012", tag);
385         EM_DEBUG_LOG("COMMAND [%s] \n", command);
386 #ifdef FEATURE_CORE_DEBUG
387         EM_DEBUG_LOG(" [IMAP4] >>> [%s]", command);
388 #endif
389         
390         /*  send command  :  get msgno/uid for all message */
391         if (!net_sout(imaplocal->netstream, command, (int)strlen(command))) {
392                 EM_DEBUG_EXCEPTION(" net_sout failed...\n");
393                 err = EMAIL_ERROR_CONNECTION_BROKEN;    
394                 goto FINISH_OFF;
395         }
396         
397         *uid_list = NULL;
398         
399         while (imaplocal->netstream) {
400                 char *p = NULL;
401                 char *s = NULL;
402                 int seen = 0;
403                 int forwarded = 0;      
404                 int draft = 0;
405                 /*  receive response */
406                 if (!(response = net_getline(imaplocal->netstream))) {
407                         EM_DEBUG_EXCEPTION("net_getline failed...");
408                         err = EMAIL_ERROR_INVALID_RESPONSE;             
409                         goto FINISH_OFF;
410                 }
411                 
412 #ifdef FEATURE_CORE_DEBUG
413                 EM_DEBUG_LOG(" [IMAP4] <<< [%s]", response);
414 #endif
415                 
416                 if (!strncmp(response, tag, strlen(tag))) {
417                         if (!strncmp(response + strlen(tag) + 1, "OK", 2)) {
418                                 free(response); response = NULL;
419                                 break;
420                         }
421                         else {          /*  'NO' or 'BAD' */
422                                 err = EMAIL_ERROR_IMAP4_FETCH_UID_FAILURE;              /* EMAIL_ERROR_INVALID_RESPONSE; */
423                                 goto FINISH_OFF;
424                         }
425                 }
426                 
427                 if ((p = strstr(response, " FETCH ("))) { 
428                         if (!strstr(p, "\\Deleted")) {  /*  undeleted only */
429                                 *p = '\0'; p  += strlen(" FETCH ");
430                                 
431                                 seen = strstr(p, "\\Seen") ? 1  :  0;
432                                 draft = strstr(p, "\\Draft") ? 1  :  0;
433                                 forwarded = strstr(p, "$Forwarded") ? 1  :  0;
434                                 
435                                 if ((p = strstr(p, "UID "))) {
436                                         s = p + strlen("UID ");
437                                         
438                                         while (isdigit(*s))
439                                                 s++;
440                                         
441                                         *s = '\0';
442                                         
443                                         if (!(uid_elem = em_malloc(sizeof(emcore_uid_list)))) {
444                                                 EM_DEBUG_EXCEPTION("em_malloc failed...");
445                                                 err = EMAIL_ERROR_OUT_OF_MEMORY;
446                                                 goto FINISH_OFF;
447                                         }
448                                         
449                                         uid_elem->msgno = atoi(response + strlen("* "));
450                                         uid_elem->uid = EM_SAFE_STRDUP(p + strlen("UID "));
451                                         uid_elem->flag.seen = seen;
452                                         uid_elem->flag.draft = draft;
453                                         uid_elem->flag.forwarded = forwarded;
454                                         if (*uid_list  != NULL)
455                                                 uid_elem->next = *uid_list;             /*  prepend new data to list */
456                                         
457                                         *uid_list = uid_elem;
458                                 }
459                                 else {
460                                         err = EMAIL_ERROR_INVALID_RESPONSE;
461                                         goto FINISH_OFF;
462                                 }
463                         }
464                 }
465                 else {
466                         err = EMAIL_ERROR_INVALID_RESPONSE;
467                         goto FINISH_OFF;
468                 }
469                 
470                 EM_SAFE_FREE(response);;
471         }
472         
473         ret = true;
474
475 FINISH_OFF: 
476         EM_SAFE_FREE(response);
477
478         if (err_code  != NULL)
479                 *err_code = err;
480         
481         EM_PROFILE_END(ImapMailboxGetUids);
482         EM_DEBUG_FUNC_END("ret [%d]", ret);     
483         return ret;
484 }
485
486 static char *__em_get_month_in_string(int month)
487 {
488         EM_DEBUG_FUNC_BEGIN("month [%d]", month);
489
490         char *mon = NULL;
491
492         switch (month){
493             case 0:
494                         mon = EM_SAFE_STRDUP("jan");
495                 break;
496             case 1:
497                         mon = EM_SAFE_STRDUP("feb");
498                 break;
499             case 2:
500                         mon = EM_SAFE_STRDUP("mar");
501                 break;
502             case 3:
503                         mon = EM_SAFE_STRDUP("apr");
504                 break;
505             case 4:
506                         mon = EM_SAFE_STRDUP("may");
507                 break;
508             case 5:
509                         mon = EM_SAFE_STRDUP("jun");
510                 break;
511             case 6:
512                         mon = EM_SAFE_STRDUP("jul");
513                 break;
514             case 7:
515                         mon = EM_SAFE_STRDUP("aug");
516                 break;
517             case 8:
518                         mon = EM_SAFE_STRDUP("sep");
519                 break;
520             case 9:
521                         mon = EM_SAFE_STRDUP("oct");
522                 break;
523             case 10:
524                         mon = EM_SAFE_STRDUP("nov");
525                 break;
526             case 11:
527                         mon = EM_SAFE_STRDUP("dec");
528                 break;
529         }
530         return mon;
531 }
532         
533 int imap4_mailbox_get_uids_by_timestamp(MAILSTREAM *stream, emcore_uid_list** uid_list,  int *err_code)
534 {
535         EM_PROFILE_BEGIN(emCoreMailboxuidsbystamp);
536         EM_DEBUG_FUNC_BEGIN("stream[%p], uid_list[%p],  err_code[%p]", stream, uid_list, err_code);
537
538         int ret = false;
539         int err = EMAIL_ERROR_NONE;
540         
541         IMAPLOCAL *imaplocal = NULL;
542         char tag[16], command[64];
543         char *response = NULL;
544         emcore_uid_list *uid_elem = NULL;
545         char delims[] = " ";
546         char *result = NULL;
547
548         struct tm   *timeinfo = NULL;
549         time_t         RawTime = 0;
550         time_t         week_before_RawTime = 0; 
551         char  date_string[16];
552         char *mon = NULL;
553         
554         if (!stream || !uid_list) {
555                 EM_DEBUG_EXCEPTION(" stream[%p], uid_list[%p]", stream, uid_list);
556                 err = EMAIL_ERROR_INVALID_PARAM;
557                 goto FINISH_OFF;
558         }
559         
560         if (!(imaplocal = stream->local) || !imaplocal->netstream) {
561                 EM_DEBUG_EXCEPTION(" invalid IMAP4 stream detected...");
562                 err = EMAIL_ERROR_INVALID_PARAM;                /* EMAIL_ERROR_UNKNOWN */
563                 goto FINISH_OFF;
564         }
565
566         /* Fetch the System time and Retrieve the a Week before time */
567         /*      tzset(); */
568         time(&RawTime);
569
570         EM_DEBUG_LOG("RawTime Info [%lu]", RawTime);
571
572         timeinfo = localtime (&RawTime);
573
574         EM_DEBUG_LOG(">>>>>Current TIme %d %d %d %d %d %d", 1900+timeinfo->tm_year, timeinfo->tm_mon+1, timeinfo->tm_mday);
575
576         week_before_RawTime = RawTime - 604800;
577
578         /* Reading the current timeinfo */
579         timeinfo = localtime (&week_before_RawTime);
580
581         EM_DEBUG_LOG(">>>>>Mobile Date a Week before %d %d %d %d %d %d", 1900 + timeinfo->tm_year, timeinfo->tm_mon+1, timeinfo->tm_mday);
582
583         memset(&date_string, 0x00, 16);
584
585         mon = __em_get_month_in_string(timeinfo->tm_mon);
586
587         if (mon){
588                 snprintf(date_string, 16, "%d-%s-%04d", timeinfo->tm_mday, mon, 1900 + timeinfo->tm_year);
589                 EM_DEBUG_LOG("DATE IS [ %s ] ", date_string);
590                 EM_SAFE_FREE(mon);
591         }
592         
593         memset(tag, 0x00, sizeof(tag));
594         memset(command, 0x00, sizeof(command));
595         
596         SNPRINTF(tag, sizeof(tag), "%08lx", 0xffffffff & (stream->gensym++));
597         SNPRINTF(command, sizeof(command), "%s UID SEARCH 1:* SINCE %s\015\012", tag, date_string);
598         EM_DEBUG_LOG("COMMAND [%s] ", command);
599         
600 #ifdef FEATURE_CORE_DEBUG
601         EM_DEBUG_LOG(" [IMAP4] >>> [%s]", command);
602 #endif
603
604         /*  send command  :  get msgno/uid for all message */
605         if (!net_sout(imaplocal->netstream, command, (int)strlen(command))) {
606                 EM_DEBUG_EXCEPTION(" net_sout failed...");
607                 err = EMAIL_ERROR_CONNECTION_BROKEN;            /* EMAIL_ERROR_UNKNOWN */
608                 goto FINISH_OFF;
609         }
610
611         *uid_list = NULL;
612
613         while (imaplocal->netstream) {
614                 char *p = NULL;
615                 /*  receive response */
616                 if (!(response = net_getline(imaplocal->netstream))) {
617                         EM_DEBUG_EXCEPTION(" net_getline failed...");
618                         err = EMAIL_ERROR_INVALID_RESPONSE;             /* EMAIL_ERROR_UNKNOWN; */
619                         goto FINISH_OFF;
620                 }
621 #ifdef FEATURE_CORE_DEBUG
622                 EM_DEBUG_LOG(" [IMAP4] <<< [%s]", response);
623 #endif
624
625                 if (!strncmp(response, tag, strlen(tag))) {
626                         if (!strncmp(response + strlen(tag) + 1, "OK", 2)) {
627                                 free(response); response = NULL;
628                                 break;
629                         }
630                         else {  /*  'NO' or 'BAD' */
631                                 err = EMAIL_ERROR_IMAP4_FETCH_UID_FAILURE;              /* EMAIL_ERROR_INVALID_RESPONSE; */
632                                 goto FINISH_OFF;
633                         }
634                 }
635
636                 if ((p = strstr(response, " SEARCH "))){
637                     *p = '\0'; p  += strlen(" SEARCH ");
638
639                     result = strtok(p, delims);
640
641                     while (result  != NULL)
642                     {
643                                 EM_DEBUG_LOG("UID VALUE DEEP is [%s]", result);
644
645                                 if (!(uid_elem = em_malloc(sizeof(emcore_uid_list)))) {
646                                         EM_DEBUG_EXCEPTION(" malloc failed...");
647                                         err = EMAIL_ERROR_OUT_OF_MEMORY;
648                                         goto FINISH_OFF;
649                                 }
650
651                                 uid_elem->uid = EM_SAFE_STRDUP(result);
652
653                                 if (*uid_list  != NULL)
654                                         uid_elem->next = *uid_list;
655                                 *uid_list = uid_elem;
656                                 result = strtok(NULL, delims);
657                     }
658
659                         EM_SAFE_FREE(response);
660                     return 1;
661                 }
662                 else {
663                         err = EMAIL_ERROR_INVALID_RESPONSE;
664                         goto FINISH_OFF;
665                 }
666                 
667                 free(response); response = NULL;
668         }
669
670         ret = true;
671
672 FINISH_OFF: 
673         if (response  != NULL)
674                 free(response);
675
676         if (err_code  != NULL)
677                 *err_code = err;
678         EM_PROFILE_END(emCoreMailboxuidsbystamp);
679         EM_DEBUG_FUNC_END("ret [%d]", ret);     
680         return ret;
681 }
682
683 #define PARSE_BUFFER_LENGTH 4096
684 static int emcore_parse_header(char *rfc822_header, int *req_read_receipt, int *priority, int *err_code)
685 {
686         EM_DEBUG_FUNC_BEGIN("rfc822_header[%p], req_read_receipt[%p], priority[%p], err_code[%p]", rfc822_header, req_read_receipt, priority,  err_code);
687
688         if (!rfc822_header || !priority) 
689                 return false;
690
691         if (err_code)
692                 *err_code = EMAIL_ERROR_NONE;
693
694         EM_PROFILE_BEGIN(emCoreMailboxParseHeader);
695         
696         char buf[PARSE_BUFFER_LENGTH];
697         int len, i, j;
698         
699         EM_DEBUG_LOG("Buffer length [%d]", PARSE_BUFFER_LENGTH);
700
701         *priority = 3;
702                 
703         memset(buf, 0x00, PARSE_BUFFER_LENGTH);
704         
705         for (len = strlen(rfc822_header), i = 0, j = 0; i < len; i++) {
706                 if (rfc822_header[i] == CR && rfc822_header[i+1] == LF){
707                         if (j + 3 < PARSE_BUFFER_LENGTH) /* '3' include CR LF NULL */
708                                 strncpy(buf + j, CRLF_STRING, PARSE_BUFFER_LENGTH - (j + 2)); /* '3' include CR LF */ 
709                         else
710                                 EM_DEBUG_EXCEPTION("buf is too small.");
711
712                         i++;
713                         j = 0;
714                         
715                         /*  parsing data */
716                         em_upper_string(buf);
717                         
718                         /*  disposition_notification_to */
719                         if (buf[0] == 'D' && buf[11] == '-' && buf[12] == 'N' && buf[24] == '-' && buf[25] == 'T') {
720                                 if (req_read_receipt) 
721                                         *req_read_receipt = 1;
722                                 memset(buf, 0x00, PARSE_BUFFER_LENGTH);
723                                 continue;
724                         }
725                         
726                         /*  x-priority */
727                         if (buf[0] == 'X' && buf[2] == 'P' && buf[9] == 'Y'){
728                                 size_t len_2 = strlen(buf);
729                                 if (len_2 >= 12){       
730                                         buf[len_2 - 2] = '\0';
731                                         *priority = atoi(buf + 11);
732                                         memset(buf, 0x00, PARSE_BUFFER_LENGTH);
733                                         continue;
734                                 }
735                         }
736                         
737                         /*  x-msmail-priority */
738                         if (buf[0] == 'X' && buf[2] == 'M' && buf[9] == 'P' && buf[16] == 'Y'){
739                                 if (strstr(buf, "HIGH")) 
740                                         *priority = 1;
741                                 if (strstr(buf, "NORMAL")) 
742                                         *priority = 3;
743                                 if (strstr(buf, "LOW")) 
744                                         *priority = 5;
745                                 memset(buf, 0x00, PARSE_BUFFER_LENGTH);
746                                 continue;
747                         }
748                         
749                         memset(buf, 0x00, PARSE_BUFFER_LENGTH);
750                         continue;
751                 }
752                 
753                 if (j + 1 < PARSE_BUFFER_LENGTH)
754                         buf[j++] = rfc822_header[i];
755                 else
756                         EM_DEBUG_EXCEPTION("buf is too small.");
757         }
758         
759         EM_PROFILE_END(emCoreMailboxParseHeader);
760
761         if (err_code)
762                 *err_code = EMAIL_ERROR_NONE;
763
764         return true;
765 }
766
767
768 static int emcore_get_mail_extra_info(MAILSTREAM *stream, int msgno, int *req_read_receipt, int *priority, int *err_code)
769 {
770         EM_PROFILE_BEGIN(emCoreMailGetExtraInfo);
771         EM_DEBUG_FUNC_BEGIN("stream[%p], msgno[%d], req_read_receipt[%p], priority[%p], err_code[%p]", stream, msgno, req_read_receipt, priority, err_code);
772         
773         int ret = false;
774         int err = EMAIL_ERROR_NONE;
775         char *rfc822_header = NULL;
776         unsigned long len = 0;
777         
778         EM_PROFILE_BEGIN(MaiFetchHeader);
779 #ifdef __FEATURE_HEADER_OPTIMIZATION__
780         /* Check if header already available in cache */
781         if (stream && stream->cache && stream->cache[msgno-1]->private.msg.header.text.data){
782                 EM_DEBUG_LOG("I found the header in stream->cache!!");
783                 rfc822_header = (char *) stream->cache[msgno-1]->private.msg.header.text.data;
784         }
785         else{
786                 EM_DEBUG_LOG("I couldn't find the header. I'll fetch the header from server again.");
787                 if (stream)
788                         rfc822_header = mail_fetch_header(stream, msgno, NULL, NULL, &len, FT_PEEK);
789         }
790
791 #else
792         rfc822_header = mail_fetch_header(stream, msgno, NULL, NULL, &len, FT_PEEK);
793 #endif
794         EM_PROFILE_END(MaiFetchHeader);
795
796         if (!rfc822_header || !*rfc822_header) {
797                 EM_DEBUG_EXCEPTION("mail_fetch_header failed...");
798                 err = EMAIL_ERROR_IMAP4_FETCH_UID_FAILURE;              /* EMAIL_ERROR_UNKNOWN; */
799                 goto FINISH_OFF;
800         }
801         
802         if (!emcore_parse_header(rfc822_header, req_read_receipt, priority, &err)) {
803                 EM_DEBUG_EXCEPTION("emcore_parse_header falied - %d", err);
804                 goto FINISH_OFF;
805         }
806         ret = true;
807         
808 FINISH_OFF: 
809         
810         if (err_code  != NULL)
811                 *err_code = err;
812
813         EM_PROFILE_END(emCoreMailGetExtraInfo);
814         EM_DEBUG_FUNC_END("ret [%d]", ret);     
815         return ret;
816 }
817
818 static int emcore_get_uids_to_download(MAILSTREAM *stream, email_account_t *account, emstorage_mailbox_tbl_t *input_mailbox_tbl, int limit_count, emcore_uid_list** uid_list, int *uids, int retrieve_mode ,  int *err_code)
819 {
820         EM_PROFILE_BEGIN(emCoreGetUidsDownload);
821         EM_DEBUG_FUNC_BEGIN("account[%p], input_mailbox_tbl[%p], limit_count[%d], uid_list[%p], err_code[%p]", account, input_mailbox_tbl, limit_count, uid_list, err_code);
822
823         int ret = false;
824         int err = EMAIL_ERROR_NONE;
825         
826         emstorage_read_mail_uid_tbl_t *downloaded_uids = NULL;
827         int i = 0, j = 0, uid_count = 0, uid_to_be_downloaded_count = 0;                
828         emcore_uid_list *uid_elem = NULL;
829         emcore_uid_list *head_uid_elem = NULL, *end =  NULL;
830         emcore_uid_list *next_uid_elem = NULL;
831         emstorage_mail_tbl_t *mail = NULL;
832
833         if (!account || !input_mailbox_tbl || !uid_list) {
834                 EM_DEBUG_EXCEPTION("account[%p], input_mailbox_tbl[%p], uid_list[%p]", account, input_mailbox_tbl, uid_list);
835                 err = EMAIL_ERROR_INVALID_PARAM;
836                 goto FINISH_OFF;
837         }
838         
839         *uid_list = NULL;
840   
841         if (account->incoming_server_type == EMAIL_SERVER_TYPE_POP3) {
842                 if (!pop3_mailbox_get_uids(stream, uid_list, &err)) {
843                         EM_DEBUG_EXCEPTION("pop3_mailbox_get_uids failed - %d", err);
844                         goto FINISH_OFF;
845                 }
846         }
847         else {  /*  EMAIL_SERVER_TYPE_IMAP4 */
848                 /*  sowmya.kr commented , since imap4_mailbox_get_uids_by_timestamp will fetch mails since last week and not all mails  */
849                                 
850                 EM_DEBUG_LOG("calling imap4_mailbox_get_uids");
851                 if (!imap4_mailbox_get_uids(stream, uid_list, &err)) {
852                         EM_DEBUG_EXCEPTION("imap4_mailbox_get_uids failed [%d]", err);
853                         if (err  != EMAIL_ERROR_MAIL_NOT_FOUND_ON_SERVER)
854                                 goto FINISH_OFF;
855             }
856         }
857         
858         if (!emstorage_get_downloaded_list(input_mailbox_tbl->account_id,
859         (account->incoming_server_type == EMAIL_SERVER_TYPE_POP3) ? 0 : input_mailbox_tbl->mailbox_id,
860         &downloaded_uids, &j, true, &err)) {
861                 EM_DEBUG_EXCEPTION("emstorage_get_downloaded_list failed [%d]", err);
862
863                 goto FINISH_OFF;
864         }
865         EM_DEBUG_LOG("Number of Mails in Downloaded Table [%d]", j);
866
867         uid_elem = *uid_list;
868         uid_count = 0;
869
870         if(!uid_elem) { /* If there is no mail in the input_mailbox_tbl, remove all mails in the input_mailbox_tbl */
871                 for (i = 0; i < j; i++) {
872                         downloaded_uids[i].reserved = 0;
873                 }
874         }
875         
876         EM_PROFILE_BEGIN(emCoreGetUidsDownloadWhilwLoop);       
877         
878         while (uid_elem) {
879                 next_uid_elem = uid_elem->next;
880
881                 if ((account->retrieval_mode == EMAIL_IMAP4_RETRIEVAL_MODE_NEW) && (uid_elem->flag.seen != 0)){         /*  already seen */
882                         if (uid_elem->uid)
883                                 free(uid_elem->uid);
884                         
885                         free(uid_elem);
886                 }
887                 else {
888                         int to_be_downloaded = 1;
889                         
890                         if (limit_count > 0 && uid_count >= limit_count){
891                                 /*  EM_DEBUG_LOG("hit the limit[%d] for [%s]", limit_count, uid_elem->uid);              */
892                                 to_be_downloaded = 0;   
893                         }
894                         else{
895                                 for (i = j; i > 0; i--) {
896                                         if (downloaded_uids[i - 1].reserved == 0 && !strcmp(uid_elem->uid, downloaded_uids[i - 1].s_uid)) {
897                                                 downloaded_uids[i - 1].reserved = uid_elem->flag.seen ? 2 : 1;
898                                                 to_be_downloaded = 0;
899                                                 break;
900                                         }
901                                 }
902                         }
903
904                         /*  EM_DEBUG_LOG("Is uid[%s] going to be downloded ? [%d]", uid_elem->uid, to_be_downloaded); */
905                         
906                         if (to_be_downloaded) {         
907                                 if (retrieve_mode == EMAIL_SYNC_OLDEST_MAILS_FIRST){
908                                         uid_elem->next = head_uid_elem;
909                                         head_uid_elem = uid_elem;
910                                 }
911                                 else{   /* if retrieve_mode is EMAIL_SYNC_LATEST_MAILS_FIRST, add uid elem to end so that latest mails are in front of list */
912                                         if (head_uid_elem == NULL){
913                                                 uid_elem->next = head_uid_elem;
914                                                 head_uid_elem = uid_elem;                                               
915                                                 end = head_uid_elem;
916                                         }
917                                         else{
918                                                 end->next = uid_elem;
919                                                 uid_elem->next = NULL;
920                                                 end = uid_elem;                                 
921                                         }
922                                 }
923                                 uid_to_be_downloaded_count++;
924                                 
925                         }
926                         else {
927                                 if (uid_elem->uid)
928                                         free(uid_elem->uid);
929                                 free(uid_elem);
930                         }
931                         
932                         uid_count++;
933                 }
934
935                 uid_elem = next_uid_elem;
936         }
937
938         EM_PROFILE_END(emCoreGetUidsDownloadWhilwLoop); 
939         EM_PROFILE_BEGIN(emCoreGetUidsDownloadForLoop); 
940         
941         for (i = 0; i < j; i++) {
942                 /*  EM_DEBUG_LOG("input_mailbox_tbl[%s] reserved[%d]", input_mailbox_tbl->name, downloaded_uids[i].reserved); */
943                 if (downloaded_uids[i].reserved == 0) {         /*  deleted on server */
944                         if (!emstorage_get_maildata_by_servermailid(input_mailbox_tbl->account_id, downloaded_uids[i].s_uid, &mail, true, &err)){
945                                 EM_DEBUG_EXCEPTION("emstorage_get_maildata_by_servermailid for uid[%s] Failed [%d] \n ", downloaded_uids[i].s_uid, err);
946                                 if (err == EMAIL_ERROR_MAIL_NOT_FOUND){
947                                         continue;
948                                 }
949                         }
950                                                 
951                         if (account->incoming_server_type == EMAIL_SERVER_TYPE_IMAP4) {
952                                 if (!emcore_delete_mails_from_local_storage(input_mailbox_tbl->account_id, &(mail->mail_id), 1, EMAIL_DELETED_FROM_SERVER, false, &err)) {
953                                         EM_DEBUG_EXCEPTION("emcore_delete_mails_from_local_storage falied - %d", err);
954                                         goto FINISH_OFF;
955                                 }
956                                 /* emcore_delete_notification_for_read_mail(mail->mail_id); */
957                                 emcore_check_unread_mail(); 
958                         }
959                         
960                         if (!emstorage_remove_downloaded_mail(input_mailbox_tbl->account_id, input_mailbox_tbl->mailbox_name, downloaded_uids[i].s_uid, true, &err)) {   /*  remove uid from uid list */
961                                 EM_DEBUG_EXCEPTION("emstorage_remove_downloaded_mail failed - %d", err);
962                 
963                                 /* goto FINISH_OFF; */
964                         }
965                         
966                 }
967                 else if (account->incoming_server_type == EMAIL_SERVER_TYPE_IMAP4 && downloaded_uids[i].reserved == 1) {        
968                         /*  unseen on server */
969                         if  (!emstorage_get_mail_by_id(downloaded_uids[i].local_uid, &mail, true, &err)){
970                                 EM_DEBUG_EXCEPTION("emstorage_get_mail_by_id failed for [%d] - [%d]", downloaded_uids[i].local_uid, err);
971                                 continue;
972                         }
973                         
974                         if (mail) {
975                                 if (mail->body_download_status && mail->flags_seen_field){
976                                         EM_DEBUG_LOG("Set flag as seen on server");
977                                         mail_setflag_full(stream, downloaded_uids[i].s_uid, "\\Seen", ST_UID);
978                                 }
979                         }
980                 }
981                 if (mail != NULL)
982                         emstorage_free_mail(&mail, 1, NULL);
983                 mail = NULL;
984         }
985         EM_PROFILE_END(emCoreGetUidsDownloadForLoop);   
986         
987         *uid_list = head_uid_elem;
988         *uids = uid_to_be_downloaded_count;
989         
990         ret = true;
991         
992 FINISH_OFF: 
993         if (ret == false){
994                 if (head_uid_elem)
995                         emcore_free_uids(head_uid_elem, NULL);
996         }
997         
998         if (downloaded_uids != NULL)
999                 emstorage_free_read_mail_uid(&downloaded_uids, j, NULL);
1000
1001         if (mail != NULL)
1002                 emstorage_free_mail(&mail, 1, NULL);
1003         
1004         if (err_code  != NULL)
1005                 *err_code = err;
1006         
1007         EM_PROFILE_END(emCoreGetUidsDownload);
1008         EM_DEBUG_FUNC_END("ret [%d]", ret);     
1009         return ret;
1010 }
1011
1012 /* insert received mail UID to read mail uid table */
1013 static int emcore_add_read_mail_uid(emstorage_mailbox_tbl_t *input_maibox_data, char *server_mailbox_name, int mail_id, char *uid, int rfc822_size, int rule_id, int *err_code)
1014 {
1015         EM_DEBUG_FUNC_BEGIN("input_maibox_data[%p], server_mailbox_name[%s], uid[%s], rfc822_size[%d], rule_id[%d], err_code[%p]", input_maibox_data, server_mailbox_name, uid, rfc822_size, rule_id, err_code);
1016         
1017         int ret = false;
1018         int err = EMAIL_ERROR_NONE;
1019         
1020         emstorage_read_mail_uid_tbl_t  read_mail_uid = { 0 };
1021         emstorage_mailbox_tbl_t       *mailbox_tbl = NULL;
1022         
1023         if (!input_maibox_data || !uid) {
1024                 EM_DEBUG_EXCEPTION("EMAIL_ERROR_INVALID_PARAM");
1025                 err = EMAIL_ERROR_INVALID_PARAM;
1026                 goto FINISH_OFF;
1027         }
1028         
1029         read_mail_uid.account_id = input_maibox_data->account_id;
1030         
1031         if (!(input_maibox_data->mailbox_name) || !(server_mailbox_name)){
1032                 if (!emstorage_get_mailbox_by_mailbox_type(input_maibox_data->account_id, EMAIL_MAILBOX_TYPE_INBOX, &mailbox_tbl, false, &err)) {
1033                         EM_DEBUG_EXCEPTION("emstorage_get_mailbox_by_mailbox_type failed [%d]", err);
1034                         goto FINISH_OFF;
1035                 }
1036         }
1037         
1038         if (input_maibox_data->mailbox_id)
1039                 read_mail_uid.mailbox_id = input_maibox_data->mailbox_id;
1040         else
1041                 read_mail_uid.mailbox_id = mailbox_tbl->mailbox_id;
1042         
1043         read_mail_uid.local_uid = mail_id;
1044         EM_DEBUG_LOG("MAIL ID [%d] LOCAL_UID [%d]", mail_id, read_mail_uid.local_uid); 
1045         
1046         if (server_mailbox_name)
1047                 read_mail_uid.mailbox_name = server_mailbox_name;
1048         else
1049                 read_mail_uid.mailbox_name = mailbox_tbl->mailbox_name;
1050         
1051         read_mail_uid.s_uid = uid;
1052         read_mail_uid.data1 = rfc822_size;
1053         read_mail_uid.flag = rule_id;
1054         
1055         if (!emstorage_add_downloaded_mail(&read_mail_uid, false, &err)) {
1056                 EM_DEBUG_EXCEPTION("emstorage_add_downloaded_mail failed [%d]", err);
1057
1058                 goto FINISH_OFF;
1059         }
1060         
1061         ret = true;
1062         
1063 FINISH_OFF: 
1064         if (mailbox_tbl)
1065                 emstorage_free_mailbox(&mailbox_tbl, 1, NULL);
1066
1067         if (err_code)
1068                 *err_code = err;
1069         
1070         EM_DEBUG_FUNC_END("ret [%d]", ret);     
1071         return ret;
1072 }
1073
1074 int emcore_add_mail_to_mailbox(emstorage_mailbox_tbl_t *input_maibox_data, emstorage_mail_tbl_t *input_new_mail_tbl_data, int *output_mail_id, int *output_thread_id)
1075 {
1076         EM_DEBUG_FUNC_BEGIN("input_maibox_data[%p], input_new_mail_tbl_data[%p], uid_elem[%p], output_mail_id[%p], output_thread_id[%p]", mail_stream, input_maibox_data, input_new_mail_tbl_data, output_mail_id, output_thread_id);
1077         
1078         int                   err = EMAIL_ERROR_NONE;
1079         int                   thread_id = -1;
1080         int                   thread_item_count = 0;
1081         int                   latest_mail_id_in_thread = -1;
1082
1083         if (!input_maibox_data || !input_new_mail_tbl_data) {
1084                 EM_DEBUG_EXCEPTION("Invalid Parameter");
1085                 err = EMAIL_ERROR_INVALID_PARAM;
1086                 goto FINISH_OFF;
1087         }       
1088
1089         input_new_mail_tbl_data->account_id            = input_maibox_data->account_id;
1090         input_new_mail_tbl_data->mailbox_id            = input_maibox_data->mailbox_id;
1091         input_new_mail_tbl_data->mailbox_name          = EM_SAFE_STRDUP(input_maibox_data->mailbox_name);
1092         input_new_mail_tbl_data->mailbox_type          = input_maibox_data->mailbox_type;
1093
1094         emstorage_begin_transaction(NULL, NULL, NULL);
1095
1096         /* Get the Mail_id */
1097         if (!emstorage_increase_mail_id(&(input_new_mail_tbl_data->mail_id), false, &err)) {
1098                 EM_DEBUG_EXCEPTION("emstorage_increase_mail_id failed [%d]", err);
1099                 goto FINISH_OFF;
1100         }
1101
1102         if (emstorage_get_thread_id_of_thread_mails(input_new_mail_tbl_data, &thread_id, &latest_mail_id_in_thread, &thread_item_count)  != EMAIL_ERROR_NONE)
1103                 EM_DEBUG_LOG(" emstorage_get_thread_id_of_thread_mails is failed.");
1104
1105         if (thread_id == -1){
1106                 input_new_mail_tbl_data->thread_id = input_new_mail_tbl_data->mail_id;
1107                 input_new_mail_tbl_data->thread_item_count = thread_item_count = 1;
1108         }
1109         else {
1110                 input_new_mail_tbl_data->thread_id = thread_id;
1111                 thread_item_count++;
1112         }
1113         
1114         if (!emstorage_add_mail(input_new_mail_tbl_data, 0, false, &err)) {
1115                 EM_DEBUG_EXCEPTION("emstorage_add_mail failed [%d]", err);
1116                 emstorage_rollback_transaction(NULL, NULL, NULL);
1117                 goto FINISH_OFF;
1118         }
1119                 
1120         if (thread_item_count > 1){
1121                 if (!emstorage_update_latest_thread_mail(input_new_mail_tbl_data->account_id, input_new_mail_tbl_data->thread_id, 0, 0, false, &err)) {
1122                         EM_DEBUG_EXCEPTION("emstorage_update_latest_thread_mail failed [%d]", err);
1123                         emstorage_rollback_transaction(NULL, NULL, NULL);
1124                         goto FINISH_OFF;
1125                 }
1126         }
1127         if (output_thread_id)
1128                 *output_thread_id = input_new_mail_tbl_data->thread_id;
1129         
1130         if (output_mail_id != NULL)
1131                 *output_mail_id = input_new_mail_tbl_data->mail_id;
1132         
1133         EM_DEBUG_LOG("mail_table_data.mail_id [%d]", input_new_mail_tbl_data->mail_id);
1134         EM_DEBUG_LOG("mail_table_data.thread_id [%d]", input_new_mail_tbl_data->thread_id);
1135
1136         if (!emcore_add_read_mail_uid(input_maibox_data, input_maibox_data->mailbox_name, input_new_mail_tbl_data->mail_id, input_new_mail_tbl_data->server_mail_id, input_new_mail_tbl_data->mail_size, 0, &err)) {
1137                 EM_DEBUG_EXCEPTION("emcore_add_read_mail_uid failed [%d]", err);
1138                 emstorage_rollback_transaction(NULL, NULL, NULL);
1139                 goto FINISH_OFF;
1140         }
1141         
1142         emstorage_commit_transaction(NULL, NULL, NULL);
1143         
1144 FINISH_OFF: 
1145
1146         EM_DEBUG_FUNC_END("err [%d]", err);
1147         return err;
1148 }
1149
1150 int emcore_check_rule(const char *input_full_address_from, const char *input_subject, emstorage_rule_tbl_t *rule, int rule_len, int *matched, int *err_code)
1151 {
1152         EM_DEBUG_FUNC_BEGIN("input_full_address_from [%p], input_subject [%p], rule [%p], rule_len [%d], matched [%p], err_code [%p]", input_full_address_from, input_subject, rule, rule_len, matched, err_code);
1153         
1154         int ret = false, err = EMAIL_ERROR_NONE, i;
1155         size_t len = 0;
1156         char *src = NULL;       /*  string which will be compared with rules */
1157         char *from_address = NULL;
1158         ADDRESS *addr = NULL;
1159         
1160         if (!matched || !input_full_address_from || !input_subject) {
1161                 EM_DEBUG_EXCEPTION("EMAIL_ERROR_INVALID_PARAM");
1162                 err = EMAIL_ERROR_INVALID_PARAM;
1163                 goto FINISH_OFF;
1164         }
1165         
1166         *matched = -1;
1167         
1168         rfc822_parse_adrlist(&addr, (char*)input_full_address_from, NULL);
1169
1170         if(addr) {
1171                 EM_DEBUG_LOG("rule : full_address_from[%s], addr->mailbox[%s], addr->host[%s]", input_full_address_from, addr->mailbox, addr->host);
1172
1173                 if (addr->mailbox)
1174                         len = strlen(addr->mailbox);
1175                 if (addr->host)
1176                         len  += strlen(addr->host);
1177                         len  += 2;
1178
1179                 if (!(from_address = em_malloc(len))) {
1180                         EM_DEBUG_EXCEPTION("em_malloc failed...");
1181                         err = EMAIL_ERROR_OUT_OF_MEMORY;
1182                         goto FINISH_OFF;
1183                 }
1184
1185                 SNPRINTF(from_address, len, "%s@%s", addr->mailbox, addr->host);
1186         }
1187         else  {
1188                 EM_DEBUG_EXCEPTION("rfc822_parse_adrlist failed.");
1189                 err = EMAIL_ERROR_INVALID_ADDRESS;
1190                 goto FINISH_OFF;
1191         }
1192
1193         for (i = 0; i < rule_len; i++) {
1194                 if (!(rule + i)) {
1195                         EM_DEBUG_EXCEPTION("EMAIL_ERROR_INVALID_PARAM");
1196                         err = EMAIL_ERROR_INVALID_PARAM;
1197                         goto FINISH_OFF;
1198                 }
1199
1200                 EM_DEBUG_LOG("rule[%d].flag1(rule id[%d]) is %d", i, rule[i].rule_id, rule[i].flag1);
1201
1202                 if (rule[i].flag1){     
1203                         /*  'ON' */
1204                         EM_DEBUG_LOG("rule[%d].flag2(rule id[%d]) is %d", i, rule[i].rule_id, rule[i].flag2);
1205                         switch (rule[i].type) {
1206                                 case EMAIL_FILTER_FROM:
1207                                         src = from_address;
1208                                         break;
1209                                 case EMAIL_FILTER_SUBJECT:
1210                                         src = (char*)input_subject;
1211                                         break;
1212                                 case EMAIL_FILTER_BODY: 
1213                                         err = EMAIL_ERROR_NOT_SUPPORTED;
1214                                         goto FINISH_OFF;
1215                                         break;
1216                         }
1217                         EM_DEBUG_LOG("rule src[%s], value[%s]\n", src, rule[i].value);
1218
1219                         if (src && rule[i].value) {
1220                             if (RULE_TYPE_INCLUDES == rule[i].flag2) {
1221                                         if (strstr(src, rule[i].value)) {
1222                                                 *matched = i; 
1223                                                 break;
1224                                         }
1225                                 }
1226                                 else if (RULE_TYPE_EXACTLY == rule[i].flag2) {
1227                                         if (!strcmp(src, rule[i].value)) {
1228                                                 *matched = i; 
1229                                                 break;
1230                                         }
1231                                 }
1232                         }
1233                 }
1234                 else
1235                         EM_DEBUG_LOG("Invald src or rule[i].value");
1236         }
1237         ret = true;
1238
1239         EM_DEBUG_LOG("i [%d], matched [%d]", i, *matched);
1240 FINISH_OFF: 
1241
1242         EM_SAFE_FREE(from_address);
1243         
1244         if (addr  != NULL)
1245                 mail_free_address(&addr);       
1246         
1247         if (err_code  != NULL)
1248                 *err_code = err;
1249         
1250         EM_DEBUG_FUNC_END("ret [%d]", ret);     
1251         return ret;
1252 }
1253
1254 static int emcore_get_utf8_address(char **dest, ADDRESS *address, int *err_code)
1255 {
1256         EM_DEBUG_FUNC_BEGIN("dest[%p], address[%p], err_code[%p]", dest, address, err_code);
1257         
1258         if (!dest || !address)  {
1259                 EM_DEBUG_EXCEPTION("dest[%p], address[%p]", dest, address);
1260                 if (err_code != NULL)
1261                         *err_code = EMAIL_ERROR_INVALID_PARAM;
1262                 return false;
1263         }
1264         
1265         int ret = false;
1266         int err = EMAIL_ERROR_NONE;
1267         
1268         gchar *concatenated = NULL;
1269         gchar *utf8_address = NULL;
1270         gchar *temp = NULL;
1271         char *nickname = NULL;
1272         
1273         while (address)  {
1274                 EM_DEBUG_LOG("address->mailbox[%s], address->host[%s]", address->mailbox, address->host);
1275                 if (!address->mailbox || !address->host) {
1276                         address = address->next;
1277                         continue;
1278                 }
1279                 EM_DEBUG_LOG("address->mailbox[%p]", address->personal);
1280                 if (address->personal)  {
1281                         if (!(nickname = emcore_decode_rfc2047_text(address->personal, &err)))  {
1282                                 EM_DEBUG_EXCEPTION("emcore_decode_rfc2047_text failed - %d", err);
1283                                 goto FINISH_OFF;
1284                         }
1285                         EM_DEBUG_LOG("nickname[%s]", nickname);
1286                         if (*nickname != '\0') 
1287                                 utf8_address = g_strdup_printf("\"%s\" <%s@%s>", nickname, address->mailbox ? address->mailbox : "", address->host ? address->host : "");
1288                         else
1289                                 utf8_address = g_strdup_printf("<%s@%s>", address->mailbox ? address->mailbox : "", address->host ? address->host : "");
1290                         
1291                         EM_SAFE_FREE(nickname);
1292                 }
1293                 else
1294                         utf8_address = g_strdup_printf("<%s@%s>", address->mailbox ? address->mailbox : "", address->host ? address->host : "");
1295                 
1296                 EM_DEBUG_LOG("utf8_address[%s]", utf8_address);
1297                 
1298                 if (concatenated != NULL)  {
1299                         temp = concatenated;
1300                         concatenated = g_strdup_printf("%s; %s", temp, utf8_address);
1301                         g_free(temp);
1302                 }
1303                 else
1304                         concatenated = g_strdup(utf8_address);
1305                 
1306                 g_free(utf8_address); 
1307                 utf8_address = NULL;
1308                 
1309                 address = address->next;
1310         }
1311         
1312         *dest = concatenated;
1313         
1314         ret = true;
1315         
1316 FINISH_OFF:
1317         EM_SAFE_FREE(nickname);
1318         EM_DEBUG_FUNC_END("ret[%d]", ret);
1319         return ret;
1320 }
1321
1322
1323 int emcore_make_mail_tbl_data_from_envelope(MAILSTREAM *mail_stream, ENVELOPE *input_envelope, emcore_uid_list *input_uid_elem, emstorage_mail_tbl_t **output_mail_tbl_data,  int *err_code)
1324 {
1325         EM_PROFILE_BEGIN(emCoreParseEnvelope);
1326         EM_DEBUG_FUNC_BEGIN("input_envelope[%p], input_uid_elem [%p], output_mail_tbl_data[%p],  err_code[%p]", input_envelope, input_uid_elem, output_mail_tbl_data, err_code);
1327
1328         int ret = false;
1329         int err = EMAIL_ERROR_NONE;
1330         int priority = 3;
1331         int req_read_receipt = 0;
1332         struct tm             temp_time_info;
1333         MESSAGECACHE         *mail_cache_element = NULL;
1334         emstorage_mail_tbl_t *temp_mail_tbl_data = NULL;
1335
1336         if (!output_mail_tbl_data) {
1337                 EM_DEBUG_EXCEPTION("EMAIL_ERROR_INVALID_PARAM");
1338                 err = EMAIL_ERROR_INVALID_PARAM;
1339                 goto FINISH_OFF;
1340         }
1341         
1342         if (!(temp_mail_tbl_data = em_malloc(sizeof(emstorage_mail_tbl_t)))) {
1343                 EM_DEBUG_EXCEPTION("em_malloc failed...");
1344                 err = EMAIL_ERROR_OUT_OF_MEMORY;
1345                 goto FINISH_OFF;
1346         }
1347         
1348         if (!(mail_cache_element = mail_elt(mail_stream, input_uid_elem->msgno))) {
1349                 EM_DEBUG_EXCEPTION("mail_elt failed...");
1350                 err = EMAIL_ERROR_UNKNOWN;
1351                 goto FINISH_OFF;
1352         }
1353
1354         if (!emcore_get_mail_extra_info(mail_stream, input_uid_elem->msgno, &req_read_receipt, &priority, &err)) {
1355                 EM_DEBUG_EXCEPTION("emcore_get_mail_extra_info failed [%d]", err);
1356                 goto FINISH_OFF;
1357         }
1358
1359         if (input_envelope->subject) {
1360                 temp_mail_tbl_data->subject = emcore_decode_rfc2047_text(input_envelope->subject, &err);
1361                 EM_DEBUG_LOG("subject[%s]", temp_mail_tbl_data->subject);
1362         }
1363         
1364         if (input_envelope->from) {
1365                 if (!emcore_get_utf8_address(&temp_mail_tbl_data->full_address_from, input_envelope->from, &err)) {
1366                         EM_DEBUG_EXCEPTION("emcore_get_utf8_address failed [%d]", err);
1367                         goto FINISH_OFF;
1368                 }
1369                 
1370                 EM_DEBUG_LOG("full_address_from[%s]", temp_mail_tbl_data->full_address_from);
1371         }
1372         
1373         if (input_envelope->to) {
1374                 EM_DEBUG_LOG("input_envelope->to");
1375                 if (!emcore_get_utf8_address(&temp_mail_tbl_data->full_address_to, input_envelope->to, &err)) {
1376                         EM_DEBUG_EXCEPTION("emcore_get_utf8_address failed [%d]", err);
1377                         goto FINISH_OFF;
1378                 }
1379                 
1380                 EM_DEBUG_LOG("full_address_to[%s]", temp_mail_tbl_data->full_address_to);
1381         }
1382         
1383         if (input_envelope->cc) {
1384                 EM_DEBUG_LOG("input_envelope->cc");
1385                 if (!emcore_get_utf8_address(&temp_mail_tbl_data->full_address_cc, input_envelope->cc, &err)) {
1386                         EM_DEBUG_EXCEPTION("emcore_get_utf8_address failed [%d]", err);
1387                         goto FINISH_OFF;
1388                 }
1389                 
1390                 EM_DEBUG_LOG("full_address_cc [%s]", temp_mail_tbl_data->full_address_cc);
1391         }
1392         
1393         if (input_envelope->bcc) {
1394                 if (!emcore_get_utf8_address(&temp_mail_tbl_data->full_address_bcc, input_envelope->bcc, &err)) {
1395                         EM_DEBUG_EXCEPTION("emcore_get_utf8_address failed [%d]", err);
1396                         goto FINISH_OFF;
1397                 }
1398                 
1399                 EM_DEBUG_LOG("full_address_bcc [%s]", temp_mail_tbl_data->full_address_bcc);
1400         }
1401         
1402         if (input_envelope->reply_to) {
1403                 if (!emcore_get_utf8_address(&temp_mail_tbl_data->full_address_reply, input_envelope->reply_to, &err)) {
1404                         EM_DEBUG_EXCEPTION("emcore_get_utf8_address failed [%d]", err);
1405                         goto FINISH_OFF;
1406                 }
1407                 
1408                 EM_DEBUG_LOG("full_address_reply [%s]\n", temp_mail_tbl_data->full_address_reply);
1409         }
1410         
1411         if (input_envelope->return_path) {
1412                 if (!emcore_get_utf8_address(&temp_mail_tbl_data->full_address_return , input_envelope->return_path, &err)) {
1413                         EM_DEBUG_EXCEPTION("emcore_get_utf8_address failed [%d]", err);
1414                         goto FINISH_OFF;
1415                 }
1416                 EM_DEBUG_LOG("full_address_return[%s]", temp_mail_tbl_data->full_address_return);
1417         }
1418         
1419         temp_mail_tbl_data->message_id            = EM_SAFE_STRDUP(input_envelope->message_id);
1420         
1421         memset((void*)&temp_time_info, 0,  sizeof(struct tm));
1422
1423         temp_time_info.tm_sec  = mail_cache_element->seconds;
1424         temp_time_info.tm_min  = mail_cache_element->minutes - mail_cache_element->zminutes;
1425         temp_time_info.tm_hour = mail_cache_element->hours - mail_cache_element->zhours;
1426
1427         if(mail_cache_element->hours - mail_cache_element->zhours < 0) {
1428                 temp_time_info.tm_mday = mail_cache_element->day - 1;
1429                 temp_time_info.tm_hour += 24;
1430         }
1431         else
1432                 temp_time_info.tm_mday = mail_cache_element->day;
1433
1434         temp_time_info.tm_mon  = mail_cache_element->month - 1;
1435         temp_time_info.tm_year = mail_cache_element->year + 70;
1436
1437         temp_mail_tbl_data->date_time             = timegm(&temp_time_info);
1438
1439         temp_mail_tbl_data->server_mail_status    = 1;
1440         temp_mail_tbl_data->server_mail_id        = EM_SAFE_STRDUP(input_uid_elem->uid);
1441         temp_mail_tbl_data->mail_size             = mail_cache_element->rfc822_size;
1442         temp_mail_tbl_data->flags_seen_field      = input_uid_elem->flag.seen;
1443         temp_mail_tbl_data->flags_deleted_field   = mail_cache_element->deleted;
1444         temp_mail_tbl_data->flags_flagged_field   = mail_cache_element->flagged;
1445         temp_mail_tbl_data->flags_answered_field  = mail_cache_element->answered;
1446         temp_mail_tbl_data->flags_recent_field    = mail_cache_element->recent;
1447         temp_mail_tbl_data->flags_draft_field     = mail_cache_element->draft;
1448         temp_mail_tbl_data->flags_forwarded_field = input_uid_elem->flag.forwarded;
1449         temp_mail_tbl_data->priority              = priority;
1450         temp_mail_tbl_data->report_status         = (req_read_receipt ? 3  :  0);
1451         temp_mail_tbl_data->attachment_count      = 0;
1452
1453         emcore_fill_address_information_of_mail_tbl(temp_mail_tbl_data);
1454
1455         *output_mail_tbl_data = temp_mail_tbl_data;
1456         temp_mail_tbl_data = NULL;
1457         
1458         ret = true;
1459         
1460 FINISH_OFF: 
1461
1462         if (ret != true)
1463                 EM_SAFE_FREE(temp_mail_tbl_data);
1464         
1465         if (err_code  != NULL)
1466                 *err_code = err;
1467         
1468         EM_PROFILE_END(emCoreParseEnvelope);
1469         EM_DEBUG_FUNC_END("ret [%d]", ret);     
1470         return ret;
1471 }
1472
1473 INTERNAL_FUNC int emcore_sync_header(emstorage_mailbox_tbl_t *input_mailbox_tbl, emstorage_mailbox_tbl_t *input_mailbox_tbl_spam, void *stream_recycle, emcore_uid_list **input_uid_list, int *unread_mail, int *err_code)
1474 {
1475         EM_PROFILE_BEGIN(emCoreSyncHeader);
1476         EM_DEBUG_FUNC_BEGIN("input_mailbox_tbl[%p], input_mailbox_tbl_spam[%p], input_uid_list [%p], err_code[%p]", input_mailbox_tbl, input_mailbox_tbl_spam, input_uid_list, err_code);
1477
1478         int ret = false;
1479         int err = EMAIL_ERROR_NONE, err_2 = EMAIL_ERROR_NONE;
1480         int status = EMAIL_LIST_FAIL;
1481         int download_limit_count;
1482         email_account_t        *account_ref = NULL;
1483         emstorage_rule_tbl_t *rule = NULL;
1484         emcore_uid_list      *uid_list = NULL;
1485         emcore_uid_list      *uid_elem = NULL;
1486         emstorage_mail_tbl_t *new_mail_tbl_data = NULL;
1487         ENVELOPE *env = NULL;
1488         int account_id = 0, mail_id = 0, rule_len = 1000, total = 0, unread = 0, i = 0, percentage  = 0, thread_id = -1;
1489         void *stream = NULL;
1490         char *uid_range = NULL;
1491         char mailbox_id_param_string[10] = {0,};
1492         
1493         if (!input_mailbox_tbl) {
1494                 EM_DEBUG_EXCEPTION("EMAIL_ERROR_INVALID_PARAM:input_mailbox_tbl[%p]", input_mailbox_tbl);
1495                 err = EMAIL_ERROR_INVALID_PARAM;
1496                 goto FINISH_OFF;
1497         }
1498
1499         account_id = input_mailbox_tbl->account_id;
1500         account_ref = emcore_get_account_reference(account_id);
1501         if (!account_ref) {             
1502                 EM_DEBUG_EXCEPTION("emcore_get_account_reference failed - %d", account_id);
1503                 err = EMAIL_ERROR_INVALID_ACCOUNT;
1504                 goto FINISH_OFF;
1505         }
1506         
1507         if(account_ref->incoming_server_type == EMAIL_SERVER_TYPE_IMAP4 && input_mailbox_tbl->local_yn == 1) {
1508                 EM_DEBUG_EXCEPTION("local_yn flag is false for this mailbox");
1509                 err = EMAIL_ERROR_INVALID_MAILBOX;
1510                 goto FINISH_OFF;
1511         }
1512
1513         FINISH_OFF_IF_CANCELED;
1514         
1515 #ifndef         __FEATURE_KEEP_CONNECTION__
1516         /*  h.gahlaut :  Recycling of stream is taken care internally in emcore_connect_to_remote_mailbox so no need of this code here */
1517         if (stream_recycle)
1518                 stream = stream_recycle; /*  set stream for recycling connection. */
1519 #endif
1520         
1521         if (!emcore_connect_to_remote_mailbox(account_id, input_mailbox_tbl->mailbox_id, (void **)&stream, &err) || !stream){
1522                 EM_DEBUG_EXCEPTION("emcore_connect_to_remote_mailbox failed - %d", err);
1523                 status = EMAIL_LIST_CONNECTION_FAIL;
1524                 goto FINISH_OFF;
1525         }
1526         
1527         FINISH_OFF_IF_CANCELED;
1528         
1529         /*  save total mail count on server to DB */
1530         if (!emstorage_update_mailbox_total_count(account_id, input_mailbox_tbl->mailbox_id, ((MAILSTREAM *)stream)->nmsgs, 1, &err)){
1531                 EM_DEBUG_EXCEPTION("emstorage_update_mailbox_total_count failed [%d]", err);
1532
1533                 goto FINISH_OFF;
1534         }
1535         
1536         /* if (((MAILSTREAM *)stream)->nmsgs > 0) */
1537         {               
1538                 email_option_t *opt_ref = &account_ref->options;
1539                 EM_DEBUG_LOG("block_address = %d, block_subject = %d", opt_ref->block_address, opt_ref->block_subject);
1540                 
1541                 if (opt_ref->block_address || opt_ref->block_subject) {
1542                         int is_completed = false;
1543                         int type = 0;
1544                         
1545                         if (!opt_ref->block_address)
1546                                 type = EMAIL_FILTER_SUBJECT;
1547                         else if (!opt_ref->block_subject)
1548                                 type = EMAIL_FILTER_FROM;
1549                         
1550                         if (!emstorage_get_rule(ALL_ACCOUNT, type, 0, &rule_len, &is_completed, &rule, true, &err) || !rule) 
1551                                 EM_DEBUG_EXCEPTION("emstorage_get_rule failed - %d", err);
1552                 }
1553                 download_limit_count = input_mailbox_tbl->mail_slot_size;
1554                 if (!emcore_get_uids_to_download(stream, account_ref, input_mailbox_tbl, download_limit_count,  &uid_list, &total, EMAIL_SYNC_LATEST_MAILS_FIRST, &err)){
1555                         EM_DEBUG_EXCEPTION("emcore_get_uids_to_download failed [%d]", err);
1556                         uid_list = NULL; 
1557                         goto FINISH_OFF;
1558                 }
1559                 
1560                 FINISH_OFF_IF_CANCELED;
1561                 
1562                 if (input_uid_list && *input_uid_list){
1563                         emcore_free_uids(*input_uid_list, NULL);                
1564                         *input_uid_list = uid_list;
1565                 }
1566                 uid_elem = uid_list;
1567                 i = 0;
1568                 EM_PROFILE_BEGIN(emCoreSyncHeaderwhileloop);
1569
1570 #ifdef  __FEATURE_HEADER_OPTIMIZATION__
1571                 /* g.shyamakshi@samsung.com : Bulk fetch of headers only if the recieving server type is IMAP */
1572
1573                 EM_DEBUG_LOG("((MAILSTREAM *)stream)->nmsgs [%d]", ((MAILSTREAM *)stream)->nmsgs);
1574                 EM_DEBUG_LOG("uid_list [%p]", uid_list);
1575                 if (account_ref->incoming_server_type == EMAIL_SERVER_TYPE_IMAP4 && uid_list  != NULL){
1576                         emcore_uid_list *uid_list_prev = NULL;
1577                         emcore_uid_list *uid_list_fast = uid_list;  
1578                         int index = 0;
1579                         int msg_count = total;
1580                         int uid_range_size = msg_count * 8 + 1000;
1581
1582                         EM_DEBUG_LOG("memory allocation for uid_range [%d, %d]", msg_count, uid_range_size);
1583                         uid_range = malloc(sizeof(char) * uid_range_size);
1584
1585                         if (uid_range == NULL){
1586                                 EM_DEBUG_EXCEPTION("memory allocation for uid_range failed");
1587                                 err  = EMAIL_ERROR_OUT_OF_MEMORY;
1588                                 goto FINISH_OFF;
1589                         }
1590                         
1591                         uid_list_prev = uid_list_fast;
1592
1593                         if (uid_list_fast->next == NULL){
1594                                 /* Single list entry */
1595                                 snprintf(uid_range, uid_range_size, "%d", atoi(uid_list_fast->uid));
1596                         }
1597                         else{
1598                                 /* forming range of uids to be passed */
1599                                 while (uid_list_fast  != NULL){
1600                                         /* uid_list_fast = uid_list_fast->next; */
1601
1602                                         if ((uid_list_fast->next != NULL) && (((atoi(uid_list_prev->uid)) - (atoi(uid_list_fast->next->uid))) == 1)){
1603                                                 index += snprintf(uid_range+index, uid_range_size, "%d", atoi(uid_list_prev->uid));
1604
1605                                                 uid_list_fast = uid_list_fast->next;
1606                                                 uid_list_prev = uid_list_fast;
1607                                                 
1608                                                 /* to make UID range string "abc, XX : YY" */
1609                                                 while (uid_list_fast  != NULL){
1610                                                         if (uid_list_fast->next == NULL)
1611                                                                 break;
1612                                                         if (((atoi(uid_list_prev->uid)) - (atoi(uid_list_fast->next->uid))) == 1){
1613                                                                 uid_list_fast = uid_list_fast->next;
1614                                                                 uid_list_prev = uid_list_fast;
1615                                                         }
1616                                                         else
1617                                                                 break;
1618                                                 }
1619                                                 if ((uid_list_fast  != NULL) && (uid_list_fast->next  != NULL))
1620                                                         index  += snprintf(uid_range+index, uid_range_size, ":%d,", atoi(uid_list_prev->uid));
1621                                                 else
1622                                                         index  += snprintf(uid_range+index, uid_range_size, ":%d", atoi(uid_list_prev->uid));
1623                                                 
1624                                                 uid_list_fast = uid_list_fast->next;
1625                                                 uid_list_prev = uid_list_fast;
1626                                         }
1627                                         else{
1628                                                 if (uid_list_fast->next  != NULL)
1629                                                         index  += snprintf(uid_range+index, uid_range_size, "%d,", atoi(uid_list_prev->uid));
1630                                                 else
1631                                                         index  += snprintf(uid_range+index, uid_range_size, "%d", atoi(uid_list_prev->uid));
1632                                                 uid_list_fast = uid_list_fast->next;
1633                                                 uid_list_prev = uid_list_fast;
1634                                         }
1635                                 }
1636                         }
1637                         
1638                         /* h.gahlaut :  [Start] */
1639                         /* Adding this check here to check if application has called cancel job. */
1640                         /* This checking should be done because fetching 50 headers will take time  */
1641                         FINISH_OFF_IF_CANCELED;
1642
1643                         EM_DEBUG_LOG("index [%d]", index);
1644
1645                         /*  h.gahlaut :  [End] */
1646                         uid_elem = uid_list;
1647                         if (stream && uid_elem){
1648                                 EM_DEBUG_LOG("msgno : %d", uid_elem->msgno);
1649                                 ((MAILSTREAM *)stream)->nmsgs = uid_elem->msgno;
1650                         }
1651                         else{
1652                                 EM_DEBUG_LOG("Uid List Null");
1653                         }
1654                         EM_DEBUG_LOG("Calling ... mail_fetch_fast. uid_range [%s]", uid_range);
1655                         mail_fetch_fast(stream, uid_range, FT_UID | FT_PEEK | FT_NEEDENV); 
1656                         EM_SAFE_FREE(uid_range);
1657                 }
1658 #endif
1659                 
1660                 /*  h.gahlaut@samsung.com :  Clear the event queue of partial body download thread before starting fetching new headers  */
1661 #ifndef __PARTIAL_BODY_FOR_POP3__
1662                 if (account_ref->incoming_server_type == EMAIL_SERVER_TYPE_IMAP4){
1663 #endif /*  __PARTIAL_BODY_FOR_POP3__ */
1664                         /*  Partial body download feature is only for IMAP accounts  */
1665                         if (false == emcore_clear_partial_body_thd_event_que(&err))
1666                                 EM_DEBUG_LOG("emcore_clear_partial_body_thd_event_que failed [%d]", err);
1667 #ifndef __PARTIAL_BODY_FOR_POP3__
1668                 }
1669 #endif /*  __PARTIAL_BODY_FOR_POP3__ */
1670                 while (uid_elem) {
1671                         EM_PROFILE_BEGIN(emCoreSyncHeaderEachMail);
1672                         EM_DEBUG_LOG("mail_fetchstructure_full  :  uid_elem->msgno[%d]", uid_elem->msgno);
1673
1674                         env = NULL;
1675
1676                         if (uid_elem->msgno > ((MAILSTREAM *)stream)->nmsgs)
1677                                 EM_DEBUG_EXCEPTION("Warnings! msgno[%d] can't be greater than nmsgs[%d]. It might cause crash.", uid_elem->msgno, ((MAILSTREAM *)stream)->nmsgs);       
1678                         else{
1679                         
1680 #ifdef __FEATURE_HEADER_OPTIMIZATION__
1681                                 if (account_ref->incoming_server_type == EMAIL_SERVER_TYPE_IMAP4) /* Fetch env from cache in case of IMAP */
1682                                         env = mail_fetchstructure_full(stream, uid_elem->msgno, NULL, FT_PEEK, 0);
1683                                 else /* Fetch header from network in case of POP */
1684                                         env = mail_fetchstructure_full(stream, uid_elem->msgno, NULL, FT_PEEK, 1);
1685 #else
1686                                 env = mail_fetchstructure_full(stream, uid_elem->msgno, NULL, FT_PEEK);
1687 #endif                  
1688                         }
1689                         FINISH_OFF_IF_CANCELED;
1690                         
1691                         if (env != NULL){
1692                                 int matched = -1;
1693                                 
1694                                 if (!emcore_make_mail_tbl_data_from_envelope(stream, env, uid_elem, &new_mail_tbl_data, &err) || !new_mail_tbl_data) {
1695                                         EM_DEBUG_EXCEPTION("emcore_make_mail_tbl_data_from_envelope failed [%d]", err);
1696                                         goto FINISH_OFF;
1697                                 }
1698
1699                                 if (rule && input_mailbox_tbl_spam && !emcore_check_rule(new_mail_tbl_data->full_address_from, new_mail_tbl_data->subject, rule, rule_len, &matched, &err)) {
1700                                         EM_DEBUG_EXCEPTION("emcore_check_rule failed [%d]", err);
1701                                         goto FINISH_OFF;
1702                                 }
1703                                 
1704                                 if (matched >= 0 && input_mailbox_tbl_spam){    /*  add filtered mails to SPAMBOX */
1705                                         EM_DEBUG_LOG("mail[%d] added to spambox", mail_id);
1706                                         
1707                                         if ( (err = emcore_add_mail_to_mailbox(input_mailbox_tbl_spam, new_mail_tbl_data, &mail_id, &thread_id)) != EMAIL_ERROR_NONE) {
1708                                                 EM_DEBUG_EXCEPTION("emcore_add_mail_to_mailbox falied [%d]", err);
1709                                                 goto FINISH_OFF;
1710                                         }
1711                                         
1712                                         if (account_ref->incoming_server_type == EMAIL_SERVER_TYPE_IMAP4){
1713                                                 if (!emcore_move_mail_on_server(account_id, input_mailbox_tbl->mailbox_id,  &mail_id, 1, input_mailbox_tbl_spam->mailbox_name, &err)){
1714                                                         EM_DEBUG_EXCEPTION("emcore_move_mail_on_server falied [%d]", err);
1715                                                         goto FINISH_OFF;
1716                                                 }
1717                                         }
1718                                 } else {        
1719                                         /*  add mails to specified mail box */
1720                                         EM_DEBUG_LOG("mail[%d] moved to input_mailbox_tbl [%s]", mail_id, input_mailbox_tbl->mailbox_name);
1721                                         if ( (err = emcore_add_mail_to_mailbox(input_mailbox_tbl, new_mail_tbl_data, &mail_id, &thread_id)) != EMAIL_ERROR_NONE) {
1722                                                 EM_DEBUG_EXCEPTION("emcore_add_mail_to_mailbox falied [%d]", err);
1723                                                 goto FINISH_OFF;
1724                                         }
1725                                         
1726                                         /*h.gahlaut :  Start partial body dowload using partial body thread only for IMAP accounts*/
1727 #ifndef __PARTIAL_BODY_FOR_POP3__
1728                                         if (account_ref->incoming_server_type == EMAIL_SERVER_TYPE_IMAP4) {
1729 #endif /*  __PARTIAL_BODY_FOR_POP3__ */
1730                                                 if (account_ref->auto_download_size != 0) {
1731                                                         if (false == emcore_initiate_pbd(stream, account_id, mail_id, uid_elem->uid, input_mailbox_tbl->mailbox_id, &err))
1732                                                                 EM_DEBUG_LOG("Partial body download initiation failed [%d]", err);
1733                                                 }
1734 #ifndef __PARTIAL_BODY_FOR_POP3__
1735                                         }
1736 #endif /*  __PARTIAL_BODY_FOR_POP3__ */
1737
1738                                         if (!uid_elem->flag.seen && input_mailbox_tbl->mailbox_type != EMAIL_MAILBOX_TYPE_SPAMBOX)
1739                                                 emcore_add_notification_for_unread_mail(new_mail_tbl_data);
1740                                         
1741                                         FINISH_OFF_IF_CANCELED;
1742                                         
1743                                         if (!uid_elem->flag.seen)
1744                                                 unread++;
1745
1746                                         percentage = ((i+1) * 100) / total ;
1747                                         EM_DEBUG_LOG("Header Percentage Completed [%d] : [%d/%d]  mail_id [%d]", percentage, i+1, total, mail_id);
1748                                         SNPRINTF(mailbox_id_param_string, 10, "%d", input_mailbox_tbl->mailbox_id);
1749
1750                                         if (!emstorage_notify_storage_event(NOTI_MAIL_ADD, account_id, mail_id, mailbox_id_param_string, thread_id))
1751                                                 EM_DEBUG_EXCEPTION("emstorage_notify_storage_event [NOTI_MAIL_ADD] failed");
1752                                 }
1753                                 
1754                                 /*  Release for envelope is not required and it may cause crash. Don't free the memory for envelope here. */
1755                                 /*  Envelope data will be freed by garbage collector in mail_close_full */
1756                                 if (new_mail_tbl_data){
1757                                         emstorage_free_mail(&new_mail_tbl_data, 1, NULL);
1758                                         new_mail_tbl_data = NULL;
1759                                 }
1760
1761                                 FINISH_OFF_IF_CANCELED;
1762                         }
1763                         
1764                         uid_elem = uid_elem->next;
1765                         i++;
1766                         EM_PROFILE_END(emCoreSyncHeaderEachMail);
1767                 }
1768                 EM_PROFILE_END(emCoreSyncHeaderwhileloop);
1769         }
1770         
1771         ret = true;
1772 FINISH_OFF: 
1773
1774         *unread_mail = unread;
1775
1776         if (!emcore_remove_overflowed_mails(input_mailbox_tbl, &err_2))
1777                 EM_DEBUG_EXCEPTION("emcore_remove_overflowed_mails failed - %d", err_2);
1778
1779         emstorage_stamp_last_sync_time_of_mailbox(input_mailbox_tbl->mailbox_id, 1);
1780
1781         if (new_mail_tbl_data)
1782                 emstorage_free_mail(&new_mail_tbl_data, 1, NULL);
1783         
1784         if (uid_list != NULL){
1785                 emcore_free_uids(uid_list, NULL);
1786                 /*  uid_list point to the same memory with input_mailbox_tbl->user_data.  */
1787                 /*  input_mailbox_tbl->user_data should be set NULL if uid_list is freed */
1788                 *input_uid_list = NULL;
1789         }
1790
1791         EM_SAFE_FREE(uid_range);
1792
1793         if (rule  != NULL)
1794                 emstorage_free_rule(&rule, rule_len, NULL); 
1795
1796 #ifdef __FEATURE_KEEP_CONNECTION__      
1797         if (stream  != NULL) {
1798 #else /*  __FEATURE_KEEP_CONNECTION__    */
1799         if (stream  != NULL && stream_recycle == NULL)  {
1800 #endif /*  __FEATURE_KEEP_CONNECTION__   */
1801                 emcore_close_mailbox(0, stream);                                
1802                 stream = NULL;
1803         }
1804
1805         if (err_code  != NULL)
1806                 *err_code = err;
1807         
1808         EM_PROFILE_END(emCoreSyncHeader);
1809         EM_DEBUG_FUNC_END("ret [%d]", ret);     
1810         return ret;
1811 }
1812
1813
1814 emcore_uid_list *__ReverseList(emcore_uid_list *uid_list)
1815 {
1816         emcore_uid_list *temp, *current, *result;
1817
1818         temp = NULL;
1819         result = NULL;
1820         current = uid_list;
1821
1822         while (current != NULL){
1823                 temp = current->next;
1824                 current->next = result;
1825                 result = current;
1826                 current = temp;
1827         }
1828         uid_list = result;
1829         return uid_list;
1830 }
1831
1832                         
1833
1834 int emcore_download_uid_all(email_internal_mailbox_t *mailbox, emcore_uid_list** uid_list, int *total, emstorage_read_mail_uid_tbl_t *downloaded_uids, int count, emcore_get_uids_for_delete_t for_delete, int *err_code)
1835 {
1836         EM_DEBUG_FUNC_BEGIN("mailbox[%p], uid_list[%p], total[%p], downloaded_uids[%p], count[%d], for_delete[%d], err_code[%p]", mailbox, uid_list, total, downloaded_uids, count, for_delete, err_code);
1837
1838         int ret = false;
1839         int err = EMAIL_ERROR_NONE;
1840         
1841         MAILSTREAM *stream = NULL;
1842         email_account_t *ref_account = NULL;
1843         emcore_uid_list *uid_elem = NULL;
1844         emcore_uid_list *fetch_data_p = NULL;
1845         void *tmp_stream = NULL;
1846         char cmd[64] = {0x00, };
1847         char *p = NULL;
1848
1849         if (!mailbox || !uid_list) {
1850                 EM_DEBUG_EXCEPTION("mailbox[%p], uid_list[%p], total[%p], downloaded_uids[%p], count[%d], for_delete[%d]", mailbox, uid_list, total, downloaded_uids, count, for_delete);
1851                 
1852                 err = EMAIL_ERROR_INVALID_PARAM;
1853                 goto FINISH_OFF;
1854         }
1855
1856         if (!(ref_account = emcore_get_account_reference(mailbox->account_id))) {
1857                 EM_DEBUG_EXCEPTION("emcore_get_account_reference failed - %d", mailbox->account_id);
1858                 
1859                 err = EMAIL_ERROR_INVALID_ACCOUNT;
1860                 goto FINISH_OFF;
1861         }
1862
1863         if (!mailbox->mail_stream) {
1864                 if (!emcore_connect_to_remote_mailbox(mailbox->account_id, mailbox->mailbox_id, (void **)&tmp_stream, &err)){
1865                         EM_DEBUG_EXCEPTION("emcore_connect_to_remote_mailbox failed...");
1866                         
1867                         goto FINISH_OFF;
1868                 }
1869                 
1870                 stream = (MAILSTREAM *)tmp_stream;
1871         } 
1872         else 
1873                 stream = mailbox->mail_stream;
1874         
1875         if (ref_account->incoming_server_type == EMAIL_SERVER_TYPE_POP3) {              /*  POP3 */
1876                 POP3LOCAL *pop3local = NULL;
1877                 
1878                 if (!stream || !(pop3local = stream->local) || !pop3local->netstream) {
1879                         err = EMAIL_ERROR_INVALID_PARAM;                /* EMAIL_ERROR_UNKNOWN; */
1880                         goto FINISH_OFF;
1881                 }
1882                 
1883                 /*  send UIDL */
1884                 memset(cmd, 0x00, sizeof(cmd));
1885                 
1886                 SNPRINTF(cmd, sizeof(cmd), "UIDL\015\012");
1887                 
1888 #ifdef FEATURE_CORE_DEBUG
1889                 EM_DEBUG_LOG("[POP3] >>> [%s]", cmd);
1890 #endif
1891
1892                 if (!net_sout(pop3local->netstream, cmd, (int)strlen(cmd))) {
1893                         EM_DEBUG_EXCEPTION("net_sout failed...");
1894                         
1895                         err = EMAIL_ERROR_CONNECTION_BROKEN;
1896                         goto FINISH_OFF;
1897                 }
1898                 
1899                 /*  get uid from replied data */
1900                 while (pop3local->netstream) {
1901                         char *s = NULL;
1902                         
1903                         if (!(p = net_getline(pop3local->netstream)))
1904                                 break;
1905                         
1906 #ifdef FEATURE_CORE_DEBUG
1907                         EM_DEBUG_LOG(" [POP3] <<< [%s]", p);
1908 #endif
1909                         
1910                         /*  replied error "-ERR" */
1911                         if (*p == '-') {
1912                                 err = EMAIL_ERROR_MAIL_NOT_FOUND;               
1913                                 goto FINISH_OFF;
1914                         }
1915                         
1916                         /*  replied success "+OK" */
1917                         if (*p == '+') {
1918                                 free(p); p = NULL;
1919                                 continue;
1920                         }
1921                         
1922                         /*  end of command */
1923                         if (*p == '.')
1924                                 break;
1925                         
1926                         /* EM_DEBUG_LOG("UID list [%s]", p); */
1927                         
1928                         uid_elem = (emcore_uid_list *)malloc(sizeof(emcore_uid_list));
1929                         if (!uid_elem) {
1930                                 EM_DEBUG_EXCEPTION("malloc falied...");
1931                                 
1932                                 err = EMAIL_ERROR_OUT_OF_MEMORY;
1933                                 goto FINISH_OFF;
1934                         }
1935                         
1936                         memset(uid_elem, 0x00, sizeof(emcore_uid_list));
1937                         
1938                         /*  format  :  "1 AAA6FHEAAAQrB6c1ymXxty04yks7hcQ7" */
1939                         
1940                         /*  save uid                     */
1941                         s = strstr(p, " ");
1942                         if (s) {
1943                                 *s = '\0';
1944                                 uid_elem->msgno = atoi(p);
1945                                 uid_elem->uid = EM_SAFE_STRDUP(s+1);
1946                         }
1947                         
1948                         /*  check downloaded_uids */
1949                         if (downloaded_uids) {
1950                                 int i;
1951                                 for (i = 0; i < count; ++i) {
1952                                         if (!strcmp(uid_elem->uid, downloaded_uids[i].s_uid)) {
1953                                                 downloaded_uids[i].flag = 1;
1954                                                 break;
1955                                         }
1956                                 }
1957                         }
1958                         
1959                         if (*uid_list) {
1960                                 fetch_data_p = *uid_list;
1961                                 
1962                                 while (fetch_data_p->next)
1963                                         fetch_data_p = fetch_data_p->next;
1964                                 
1965                                 fetch_data_p->next = uid_elem;
1966                         }
1967                         else
1968                                 *uid_list = uid_elem;
1969                         
1970                         if (total)
1971                                 ++(*total);
1972                         
1973                         free(p); p = NULL;
1974                 }
1975         }
1976         else {          /*  IMAP */
1977                 IMAPLOCAL *imaplocal = NULL;
1978                 char tag[16];
1979                 char *s = NULL;
1980                 char *t = NULL;
1981                 
1982                 if (!stream || !(imaplocal = stream->local) || !imaplocal->netstream) {
1983                         err = EMAIL_ERROR_INVALID_PARAM;                /* EMAIL_ERROR_UNKNOWN; */
1984                         goto FINISH_OFF;
1985                 }
1986                 
1987                 /*  send FETCH UID */
1988                 memset(tag, 0x00, sizeof(tag));
1989                 memset(cmd, 0x00, sizeof(cmd));
1990                 
1991                 SNPRINTF(tag, sizeof(tag), "%08lx", 0xffffffff & (stream->gensym++));
1992                 SNPRINTF(cmd, sizeof(cmd), "%s UID FETCH %d:* (FLAGS)\015\012", tag, 1);
1993 #ifdef FEATURE_CORE_DEBUG
1994                 EM_DEBUG_LOG("[IMAP] >>> %s", cmd);             
1995 #endif
1996                 if (!net_sout(imaplocal->netstream, cmd, (int)strlen(cmd))) {
1997                         EM_DEBUG_EXCEPTION("net_sout failed...");
1998                         
1999                         err = EMAIL_ERROR_CONNECTION_BROKEN;
2000                         goto FINISH_OFF;
2001                 }
2002                 
2003                 /*  get uid from replied data */
2004                 while (imaplocal->netstream) {
2005                         if (!(p = net_getline(imaplocal->netstream)))
2006                                 break;
2007                         
2008                         /* EM_DEBUG_LOG(" [IMAP] <<< %s", p); */
2009                         
2010                         /*  tagged line - end of command */
2011                         if (!strncmp(p, tag, strlen(tag)))
2012                                 break;
2013                         
2014                         /*  check that reply is reply to our command */
2015                         /*  format  :  "* 9 FETCH (UID 68)" */
2016                         if (!strstr(p, "FETCH (FLAGS")) {
2017                                 free(p); p = NULL;
2018                                 continue;
2019                         }
2020                         
2021                         if (for_delete == EM_CORE_GET_UIDS_FOR_NO_DELETE) {
2022                                 if ((ref_account->retrieval_mode == EMAIL_IMAP4_RETRIEVAL_MODE_NEW) && (strstr(p, "\\Seen"))) {
2023                                         free(p); p = NULL;
2024                                         continue;
2025                                 }
2026                         }
2027                         
2028                         uid_elem = (emcore_uid_list *)malloc(sizeof(emcore_uid_list));
2029                         if (!uid_elem) {
2030                                 EM_DEBUG_EXCEPTION("malloc failed...");
2031                                 
2032                                 err = EMAIL_ERROR_OUT_OF_MEMORY;
2033                                 goto FINISH_OFF;
2034                         }
2035                         
2036                         memset(uid_elem, 0x00, sizeof(emcore_uid_list));
2037                         /*  parse uid, sequence, flags from replied data */
2038                         
2039                         /*  parse uid from replied data */
2040                         s = p+2;
2041                         t = strchr(s, ' ');
2042                         
2043                         if (!t) {
2044                                 err = EMAIL_ERROR_INVALID_RESPONSE;             
2045                                 goto FINISH_OFF;
2046                         }
2047                         
2048                         *t = '\0';
2049                         
2050                         /*  save sequence */
2051                         uid_elem->msgno = atoi(s);
2052                         
2053                         if (strstr(++t, "\\Deleted"))           
2054                                 uid_elem->flag.deleted = 1;
2055                         
2056                         /*  parse uid */
2057                         s  = strstr(++t, "UID ");
2058                         if (s) {
2059                                 s  += strlen("UID ");
2060                                 t  = strchr(s, ')');
2061                                 
2062                                 if (!t) {
2063                                         err = EMAIL_ERROR_INVALID_RESPONSE;             
2064                                         goto FINISH_OFF;
2065                                 }
2066                                 
2067                                 *t = '\0';
2068                         }
2069                         else {          
2070                                 err = EMAIL_ERROR_INVALID_RESPONSE;             
2071                                 goto FINISH_OFF;
2072                         }
2073                         
2074                         /*  save uid */
2075                         uid_elem->uid = EM_SAFE_STRDUP(s);
2076                         
2077                         /*  check downloaded_uids */
2078                         if (downloaded_uids) {
2079                                 int i;
2080                                 for (i = 0; i < count; ++i) {
2081                                         if (uid_elem->uid && !strcmp(uid_elem->uid, downloaded_uids[i].s_uid)) {
2082                                                 downloaded_uids[i].flag = 1;
2083                                                 free(uid_elem->uid);
2084                                                 free(uid_elem); uid_elem = NULL;
2085                                                 break;
2086                                         }
2087                                 }
2088                         }
2089                         
2090                         if (uid_elem) {
2091                                 if (*uid_list) {
2092                                         fetch_data_p = *uid_list;
2093                                         
2094                                         while (fetch_data_p->next)
2095                                                 fetch_data_p = fetch_data_p->next;
2096                                         
2097                                         fetch_data_p->next = uid_elem;
2098                                 }
2099                                 else {
2100                                         *uid_list = uid_elem;
2101                                 }
2102                                 
2103                                 if (total)
2104                                         ++(*total);
2105                         }
2106                         
2107                         free(p); p = NULL;
2108                 }
2109         }
2110
2111         ret = true;
2112
2113 FINISH_OFF: 
2114         if (uid_elem && ret == false)           
2115                 free(uid_elem);
2116         
2117         if (p)
2118                 free(p);
2119         
2120         if (mailbox && !mailbox->mail_stream) {
2121                 emcore_close_mailbox(0, stream);
2122                 stream = NULL;
2123         }
2124         
2125         if (err_code)
2126                 *err_code = err;
2127
2128         EM_DEBUG_FUNC_END("ret [%d]", ret);     
2129         return ret;
2130 }
2131
2132 int emcore_download_imap_msgno(email_internal_mailbox_t *mailbox, char *uid, int *msgno, int *err_code)
2133 {
2134         EM_DEBUG_FUNC_BEGIN("mailbox[%p], uid[%p], msgno[%p], err_code[%p]", mailbox, uid, msgno, err_code);
2135
2136         int ret = false;
2137         int err = EMAIL_ERROR_NONE;
2138         MAILSTREAM *stream = NULL;
2139         IMAPLOCAL *imaplocal = NULL;
2140         email_account_t *ref_account = NULL;
2141         void *tmp_stream = NULL;
2142         char tag[32], cmd[64];
2143         char *p = NULL;
2144
2145         if (!mailbox || !uid) {
2146                 EM_DEBUG_EXCEPTION("mailbox[%p], uid[%p], msgno[%p]", mailbox, uid, msgno);
2147                 
2148                 err = EMAIL_ERROR_INVALID_PARAM;
2149                 goto FINISH_OFF;
2150         }
2151
2152         if (!(ref_account = emcore_get_account_reference(mailbox->account_id))) {
2153                 EM_DEBUG_EXCEPTION("emcore_get_account_reference failed [%d]", mailbox->account_id);
2154                 
2155                 err = EMAIL_ERROR_INVALID_ACCOUNT;
2156                 goto FINISH_OFF;
2157         }
2158
2159         if (ref_account->incoming_server_type  != EMAIL_SERVER_TYPE_IMAP4) {
2160                 err = EMAIL_ERROR_INVALID_ACCOUNT;              /* EMAIL_ERROR_INVALID_PARAM; */
2161                 goto FINISH_OFF;
2162         }
2163
2164         if (!mailbox->mail_stream) {
2165                 if (!emcore_connect_to_remote_mailbox(mailbox->account_id, mailbox->mailbox_id, (void **)&tmp_stream, &err)) {
2166                         EM_DEBUG_EXCEPTION("emcore_connect_to_remote_mailbox failed - %d", err);
2167                         
2168                         goto FINISH_OFF;
2169                 }
2170                 
2171                 stream = (MAILSTREAM *)tmp_stream;
2172         } 
2173         else
2174                 stream = mailbox->mail_stream;
2175
2176         if (!stream || !(imaplocal = stream->local) || !imaplocal->netstream) {
2177                 err = EMAIL_ERROR_INVALID_PARAM;                /* EMAIL_ERROR_UNKNOWN; */
2178                 goto FINISH_OFF;
2179         }
2180
2181         /*  send SEARCH UID */
2182         memset(tag, 0x00, sizeof(tag));
2183         memset(cmd, 0x00, sizeof(cmd));
2184
2185         SNPRINTF(tag, sizeof(tag), "%08lx", 0xffffffff & (stream->gensym++));
2186         SNPRINTF(cmd, sizeof(cmd), "%s SEARCH UID %s\015\012", tag, uid);
2187
2188         if (!net_sout(imaplocal->netstream, cmd, (int)strlen(cmd))) {
2189                 EM_DEBUG_EXCEPTION("net_sout failed...");
2190                 
2191                 err = EMAIL_ERROR_CONNECTION_BROKEN;
2192                 goto FINISH_OFF;
2193         }
2194
2195         /*  get message number from replied data */
2196         while (imaplocal->netstream) {
2197                 if (!(p = net_getline(imaplocal->netstream)))
2198                         break;
2199                 
2200                 /*  tagged line - end of command */
2201                 if (!strncmp(p, tag, strlen(tag)))
2202                         break;
2203                 
2204                 /*  check that reply is reply to our command */
2205                 /*  format :  "* SEARCH 68", if not found, "* SEARCH" */
2206                 if (!strstr(p, "SEARCH ") || (p[9] < '0' || p[9] > '9')) {
2207                         free(p); p = NULL;
2208                         continue;
2209                 }
2210                 
2211                 if (msgno)
2212                         *msgno = atoi(p+9);
2213                 
2214                 free(p); p = NULL;
2215                 
2216                 ret = true;
2217         }
2218         
2219         if (ret  != true)
2220                 err = EMAIL_ERROR_MAIL_NOT_FOUND;
2221         
2222 FINISH_OFF: 
2223         if (p)
2224                 free(p);
2225         
2226         if (mailbox && !mailbox->mail_stream){
2227                 emcore_close_mailbox(0, stream);                                
2228                 stream = NULL;
2229         }
2230         
2231         if (err_code)
2232                 *err_code = err;
2233         
2234         EM_DEBUG_FUNC_END("ret [%d]", ret);     
2235         return ret;
2236 }
2237
2238 int emcore_get_msgno(emcore_uid_list *uid_list, char *uid, int *msgno, int *err_code)
2239 {
2240         EM_DEBUG_FUNC_BEGIN("uid_list[%p], uid[%s], msgno[%p], err_code[%p]", uid_list, uid, msgno, err_code);
2241         
2242         int ret = false;
2243         int err = EMAIL_ERROR_MAIL_NOT_FOUND;           /* EMAIL_ERROR_NONE; */
2244         
2245         if (!uid || !msgno || !uid_list) {
2246                 EM_DEBUG_EXCEPTION("uid_list[%p], uid[%p], msgno[%p]", uid_list, uid, msgno);
2247                 
2248                 err = EMAIL_ERROR_INVALID_PARAM;
2249                 goto FINISH_OFF;
2250         }
2251         
2252         EM_DEBUG_LOG(" >> uid[%s]", uid);
2253         
2254         while (uid_list) {
2255                 if (!strcmp(uid_list->uid, uid)) {
2256                         *msgno = uid_list->msgno;
2257                         
2258                         EM_DEBUG_LOG("*msgno[%d]", *msgno);
2259                         
2260                         err = EMAIL_ERROR_NONE;
2261                         
2262                         ret = true;
2263                         break;
2264                 }
2265                 
2266                 uid_list = uid_list->next;
2267         }
2268         
2269 FINISH_OFF: 
2270         if (err_code  != NULL)
2271                 *err_code = err;
2272         
2273         EM_DEBUG_FUNC_END("ret [%d]", ret);     
2274         return ret;
2275 }
2276
2277 int emcore_get_uid(emcore_uid_list *uid_list, int msgno, char **uid, int *err_code)
2278 {
2279         EM_DEBUG_FUNC_BEGIN();
2280         
2281         int ret = false, err = EMAIL_ERROR_NONE;
2282         
2283         if (!uid || msgno <= 0 || !uid_list){
2284                 err = EMAIL_ERROR_INVALID_PARAM;
2285                 goto FINISH_OFF;
2286         }
2287
2288         while (uid_list) {
2289                 if (uid_list->msgno == msgno) {
2290                         if (uid) {
2291                                 if (!(*uid = EM_SAFE_STRDUP(uid_list->uid))) {
2292                                         EM_DEBUG_EXCEPTION("strdup failed...");
2293                                         err = EMAIL_ERROR_OUT_OF_MEMORY;
2294                                         goto FINISH_OFF;
2295                                 }
2296                                 
2297                                 ret = true;
2298                                 break;
2299                         }
2300                 }
2301                 
2302                 uid_list = uid_list->next;
2303         }
2304         
2305         if (ret  != true)
2306                 err = EMAIL_ERROR_MAIL_NOT_FOUND;
2307
2308 FINISH_OFF: 
2309         if (err_code)
2310                 *err_code = err;
2311         
2312         EM_DEBUG_FUNC_END("ret [%d]", ret);     
2313         return ret;
2314 }
2315
2316 int emcore_free_uids(emcore_uid_list *uid_list, int *err_code)
2317 {
2318         EM_DEBUG_FUNC_BEGIN("uid_list[%p], err_code[%p]", uid_list, err_code);
2319         
2320         int ret = false;
2321         int err = EMAIL_ERROR_NONE;
2322         emcore_uid_list *p = NULL;
2323         
2324         if (!uid_list) {
2325                 EM_DEBUG_EXCEPTION(" uid_list[%p]\n", uid_list);
2326                 
2327                 err = EMAIL_ERROR_INVALID_PARAM;
2328                 goto FINISH_OFF;
2329         }
2330
2331         while (uid_list) {
2332                 p = uid_list;
2333                 uid_list = uid_list->next;
2334                 EM_SAFE_FREE(p->uid);
2335                 free(p);
2336                 p = NULL;
2337         }
2338         
2339         ret = true;
2340
2341 FINISH_OFF: 
2342         if (err_code)
2343                 *err_code = err;
2344
2345         EM_DEBUG_FUNC_END("ret [%d]", ret);     
2346         return ret;
2347 }
2348
2349
2350 #ifdef __FEATURE_SYNC_CLIENT_TO_SERVER__
2351 /* callback for GET_APPENDUID - shasikala.p */
2352 void mail_appenduid(char *mailbox, unsigned long uidvalidity, SEARCHSET *set)
2353 {
2354         EM_DEBUG_FUNC_BEGIN("mailbox - %s", mailbox);
2355     EM_DEBUG_LOG("UID - %ld", set->first);
2356
2357     memset(g_append_uid_rsp, 0x00, 129);
2358
2359     sprintf(g_append_uid_rsp, "%ld", set->first);
2360     EM_DEBUG_LOG("append uid - %s", g_append_uid_rsp);
2361 }
2362
2363 INTERNAL_FUNC int emcore_sync_mail_from_client_to_server(int account_id, int mail_id, int *err_code)
2364 {
2365         EM_DEBUG_FUNC_BEGIN("account_id [%d], mail_id [%d], err_code [%p]", account_id, mail_id, *err_code);
2366
2367         int                             err                  = EMAIL_ERROR_NONE;
2368         int                             ret                  = false;
2369         int                             len                  = 0;
2370         int                             read_size            = 0;
2371         int                             attachment_tbl_count = 0;
2372         char                           *fname                = NULL;
2373         char                           *long_enc_path        = NULL;
2374         char                           *data                 = NULL;
2375         char                            set_flags[100]       = { 0, };
2376         ENVELOPE                       *envelope             = NULL;
2377         FILE                           *fp                   = NULL;
2378         STRING                          str;
2379         MAILSTREAM                     *stream               = NULL;
2380         emstorage_mail_tbl_t           *mail_table_data      = NULL;
2381         emstorage_attachment_tbl_t     *attachment_tbl_data  = NULL;
2382         emstorage_mailbox_tbl_t        *mailbox_tbl          = NULL;
2383
2384         if (mail_id < 1){
2385         EM_DEBUG_EXCEPTION("EMAIL_ERROR_INVALID_PARAM");
2386                 err = EMAIL_ERROR_INVALID_PARAM;
2387         goto FINISH_OFF;
2388         }
2389
2390         /*  get a mail from mail table */
2391         if (!emstorage_get_mail_by_id(mail_id, &mail_table_data, true, &err)) {
2392                 EM_DEBUG_EXCEPTION("emstorage_get_mail_by_id failed [%d]", err);
2393                 goto FINISH_OFF;
2394         }
2395
2396         if ( (err = emstorage_get_attachment_list(mail_id, false, &attachment_tbl_data, &attachment_tbl_count)) != EMAIL_ERROR_NONE) {
2397                 EM_DEBUG_EXCEPTION("emstorage_get_attachment_list failed [%d]", err);
2398                 goto FINISH_OFF;
2399         }
2400
2401         EM_DEBUG_LOG("mailbox_name [%s]", mail_table_data->mailbox_name);
2402         if (!emstorage_get_mailbox_by_name(mail_table_data->account_id, 0, mail_table_data->mailbox_name, &mailbox_tbl, false, &err) || !mailbox_tbl){
2403                 EM_DEBUG_EXCEPTION("emstorage_get_mailbox_by_name failed [%d]", err);
2404                 goto FINISH_OFF;
2405         }
2406
2407         if (mailbox_tbl->sync_with_server_yn == 0) {
2408                 EM_DEBUG_EXCEPTION("The mailbox [%s] is not on server.", mail_table_data->mailbox_name);
2409                 err = EMAIL_ERROR_INVALID_MAILBOX;
2410                 goto FINISH_OFF;
2411         }
2412
2413         if (!emcore_get_long_encoded_path(mail_table_data->account_id, mail_table_data->mailbox_name, '/', &long_enc_path, &err)) {
2414                 EM_DEBUG_EXCEPTION(">>emcore_get_long_encoded_path  :  Failed [%d] ", err);
2415                 goto FINISH_OFF;
2416         }
2417
2418         if (!long_enc_path) {
2419             EM_DEBUG_EXCEPTION(">>long_enc_path  :  NULL ");
2420             goto FINISH_OFF;
2421         }
2422
2423         if (!emcore_make_rfc822_file_from_mail(mail_table_data, attachment_tbl_data, attachment_tbl_count, &envelope, &fname, NULL, &err)){
2424             EM_DEBUG_EXCEPTION(" emcore_make_rfc822_file_from_mail failed [%d]", err);
2425             goto FINISH_OFF;                        
2426         }
2427
2428         if (fname){
2429             if (!(fp = fopen(fname, "a+"))) {
2430                 EM_DEBUG_EXCEPTION("fopen failed - %s", fname);
2431                         err = EMAIL_ERROR_SYSTEM_FAILURE;
2432                 goto FINISH_OFF;
2433             }
2434         }
2435
2436         if (!fp) {
2437             EM_DEBUG_EXCEPTION("fp is NULL..!");
2438                 err = EMAIL_ERROR_SYSTEM_FAILURE;
2439             goto FINISH_OFF;
2440         }
2441
2442         rewind(fp);
2443
2444         ret = fseek(fp, 0, SEEK_END) == 0 && (len = ftell(fp)) != -1;
2445
2446         if (fname)
2447                 EM_DEBUG_LOG("Composed file name [%s] and file size [%d]", fname, len);
2448
2449         rewind(fp);
2450
2451         ret = 0;
2452         stream = NULL;
2453         if (!emcore_connect_to_remote_mailbox(mail_table_data->account_id, 0, (void **)&stream, &err)){
2454             EM_DEBUG_EXCEPTION("emcore_move_mail_on_server failed :  Mailbox open[%d]", err);
2455             goto FINISH_OFF;
2456         }
2457
2458         /* added for copying server UID to DB */
2459         mail_parameters(stream, SET_APPENDUID, mail_appenduid);
2460
2461         data = (char *)malloc(len + 1);
2462         /* copy data from file to data */
2463         read_size = fread(data, sizeof (char), len, fp);
2464         if (read_size  != len){
2465             /* read faiil. */
2466             EM_DEBUG_EXCEPTION("Read from file failed");
2467         }
2468
2469         INIT(&str, mail_string, data, len);
2470
2471         sprintf(set_flags, "\\Seen");
2472
2473         if (mail_table_data->flags_seen_field){
2474                 if (!mail_append_full(stream, long_enc_path, set_flags, NULL, &str)) {
2475                     EM_DEBUG_EXCEPTION("mail_append  failed -");
2476                     goto FINISH_OFF;
2477                 }
2478         }
2479         else{
2480                 if (!mail_append_full(stream, long_enc_path, NULL, NULL, &str)) {
2481                         EM_DEBUG_EXCEPTION("mail_append  failed -");
2482                         goto FINISH_OFF;
2483                 }
2484         }
2485
2486         /* Update read_mail_uid tbl */
2487         if (!emcore_add_read_mail_uid(mailbox_tbl, mail_table_data->mailbox_name, mail_table_data->mail_id, g_append_uid_rsp, mail_table_data->mail_size, 0, &err)) {
2488                 EM_DEBUG_EXCEPTION(" emcore_add_read_mail_uid failed [%d]", err);
2489                 emstorage_rollback_transaction(NULL, NULL, NULL);
2490                 goto FINISH_OFF;
2491         }
2492
2493         ret = true;
2494
2495 FINISH_OFF: 
2496
2497 #ifdef __FEATURE_LOCAL_ACTIVITY__
2498         if (ret){
2499                 emstorage_activity_tbl_t new_activity;
2500                 memset(&new_activity, 0x00, sizeof(emstorage_activity_tbl_t));
2501                 new_activity.activity_type = ACTIVITY_SAVEMAIL;
2502                 new_activity.account_id    = account_id;
2503                 new_activity.mail_id       = mail_id;
2504                 new_activity.dest_mbox     = NULL;
2505                 new_activity.server_mailid = NULL;
2506                 new_activity.src_mbox      = NULL;
2507
2508                 if (!emcore_delete_activity(&new_activity, &err)){
2509                         EM_DEBUG_EXCEPTION(">>>>>>Local Activity [ACTIVITY_SAVEMAIL] [%d] ", err);
2510                 }
2511         }
2512 #endif /* __FEATURE_LOCAL_ACTIVITY__ */ 
2513
2514         EM_SAFE_FREE(data);
2515         EM_SAFE_FREE(long_enc_path);
2516
2517         if (fp)
2518                 fclose(fp);
2519
2520         if (envelope)
2521                 mail_free_envelope(&envelope);
2522
2523         if (mail_table_data)
2524                 emstorage_free_mail(&mail_table_data, 1, NULL);
2525
2526         if (attachment_tbl_data)
2527                 emstorage_free_attachment(&attachment_tbl_data, attachment_tbl_count, NULL);
2528
2529         if (mailbox_tbl)
2530                 emstorage_free_mailbox(&mailbox_tbl, 1, NULL);
2531
2532         if (fname) {
2533                 remove(fname);
2534                 EM_SAFE_FREE(fname);
2535         }
2536
2537         if (stream){
2538                 emcore_close_mailbox(0, stream);                                
2539                 stream = NULL;  
2540         }
2541
2542         if (err_code  != NULL)
2543                 *err_code = err;
2544         EM_DEBUG_FUNC_END("ret [%d]", ret);     
2545         return ret;
2546 }
2547
2548 #endif
2549
2550 #ifdef __FEATURE_PARTIAL_BODY_DOWNLOAD__
2551
2552 static int emcore_initiate_pbd(MAILSTREAM *stream, int account_id, int mail_id, char *uid, int input_maibox_id, int *err_code)
2553 {
2554         EM_DEBUG_FUNC_BEGIN("account_id [%d], mail_id[%d], uid[%p], input_maibox_id[%d]", account_id, mail_id, uid, input_maibox_id);
2555
2556         int ret = false;
2557         int err = EMAIL_ERROR_NONE;
2558         email_account_t *account_ref;
2559         emstorage_mailbox_tbl_t* mailbox = NULL;
2560
2561         if (account_id < FIRST_ACCOUNT_ID || mail_id < 0 || NULL == uid || 0 == input_maibox_id){
2562                 EM_DEBUG_EXCEPTION("EMAIL_ERROR_INVALID_PARAM");
2563                 err = EMAIL_ERROR_INVALID_PARAM;
2564                 goto FINISH_OFF;
2565         }
2566
2567         account_ref = emcore_get_account_reference(account_id);
2568
2569         email_event_partial_body_thd pbd_event;
2570
2571         memset(&pbd_event, 0x00, sizeof(email_event_partial_body_thd));
2572
2573         pbd_event.account_id = account_id;
2574         if (account_ref && account_ref->incoming_server_type == EMAIL_SERVER_TYPE_POP3)
2575                 pbd_event.activity_type = ACTIVITY_PARTIAL_BODY_DOWNLOAD_POP3_WAIT;
2576         else
2577                 pbd_event.activity_type = ACTIVITY_PARTIAL_BODY_DOWNLOAD_IMAP4;
2578
2579         if ( (err = emstorage_get_mailbox_by_id(input_maibox_id, &mailbox)) != EMAIL_ERROR_NONE || !mailbox) {
2580                 EM_DEBUG_EXCEPTION("emstorage_get_mailbox_by_id failed [%d]", err);
2581                 goto FINISH_OFF;
2582         }
2583                 
2584         pbd_event.mailbox_id     = input_maibox_id;
2585         pbd_event.mail_id        = mail_id;
2586         pbd_event.server_mail_id = strtoul(uid, NULL, 0);
2587         pbd_event.mailbox_name   = EM_SAFE_STRDUP(mailbox->mailbox_name);
2588
2589         EM_DEBUG_LOG("input_mailbox_name name [%d]", pbd_event.mailbox_id);
2590         EM_DEBUG_LOG("uid [%s]", uid);
2591         EM_DEBUG_LOG("pbd_event.account_id[%d], pbd_event.mail_id[%d], pbd_event.server_mail_id [%d]", pbd_event.account_id, pbd_event.mail_id , pbd_event.server_mail_id);
2592         
2593         if (!emcore_insert_pbd_activity(&pbd_event, &pbd_event.activity_id, &err)){
2594                 EM_DEBUG_EXCEPTION("Inserting Partial Body Download activity failed with error[%d]", err);
2595                 goto FINISH_OFF;
2596         }
2597         else{
2598                 if (false == emcore_is_partial_body_thd_que_full()){
2599                         /* h.gahaut :  Before inserting the event into event queue activity_type should be made 0
2600                         Because partial body thread differentiates events coming from DB and event queue 
2601                         on the basis of activity_type and event_type fields */
2602
2603                         pbd_event.activity_type = 0;
2604                         pbd_event.event_type = EMAIL_EVENT_BULK_PARTIAL_BODY_DOWNLOAD;
2605                         
2606                         if (!emcore_insert_partial_body_thread_event(&pbd_event, &err)){
2607                                 EM_DEBUG_EXCEPTION("Inserting Partial body thread event failed with error[%d]", err);
2608                                 goto FINISH_OFF;
2609                         }
2610
2611                         /*h.gahlaut :  Partial body thread has created a copy of event for itself so this local event should be freed here*/
2612                         if (!emcore_free_partial_body_thd_event(&pbd_event, &err))
2613                                 EM_DEBUG_EXCEPTION("Freeing Partial body thread event failed with error[%d]", err);
2614                 }
2615                 else{
2616                         EM_DEBUG_LOG(" Activity inserted only in DB .. Queue is Full");
2617                 }
2618         }
2619
2620         ret = true;
2621         
2622         FINISH_OFF: 
2623
2624         if (mailbox) {
2625                 emstorage_free_mailbox(&mailbox, 1, &err);
2626         }
2627
2628         if (NULL  != err_code)
2629                 *err_code = err;
2630
2631         EM_DEBUG_FUNC_END("ret [%d]", ret);     
2632         return ret;
2633 }
2634
2635 #define UID_RANGE_STRING_LENGTH 3000
2636 #define TEMP_STRING_LENGTH              50
2637
2638 static int emcore_parse_html_part_for_partial_body(char *start_header, char *boundary_string, char *bufsendforparse, char *text_html, int body_size)
2639 {
2640         EM_DEBUG_FUNC_BEGIN("start_header [%s], boundary_string [%s], bufsendforparse [%s], text_html [%s], body_size [%d]", start_header, boundary_string, bufsendforparse, text_html, body_size);
2641
2642         int   err = EMAIL_ERROR_NONE;
2643         int   html_uidno = 0;
2644         int   iEncodingHeader = 0;
2645         int   enc_type = ENCOTHER, dec_len = 0, html_length = 0;
2646         char  EncodingHeader[40] = {0};
2647         char  Encoding[30] = {0};
2648         char *pEncodingHeaderEnd = NULL;
2649         char *txt_html = NULL;
2650         char *pHeaderStart = NULL;
2651         char *start = NULL, *end = NULL;
2652         char *temp_enc1 = NULL;
2653
2654         EM_DEBUG_LOG("Content-Type : text/html or message/rfc822 or text/rfc822-headers");
2655
2656         pHeaderStart = start_header;
2657         pHeaderStart = pHeaderStart-2;
2658         do{
2659                 pHeaderStart--;
2660         } while (*pHeaderStart != LF && bufsendforparse < pHeaderStart);
2661         
2662         pHeaderStart++;
2663         
2664         memcpy(EncodingHeader, pHeaderStart, 25);
2665
2666         if (strcasecmp(EncodingHeader, "Content-Transfer-Encoding") == 0){
2667                 pEncodingHeaderEnd = strstr(pHeaderStart, CRLF_STRING);
2668                 memcpy(Encoding, pHeaderStart + 27, pEncodingHeaderEnd - (pHeaderStart+27));
2669                 iEncodingHeader = 1;
2670         }
2671
2672         /* HTML Content found */
2673         
2674         txt_html = start_header;
2675         txt_html = strstr(txt_html, CRLF_STRING CRLF_STRING);
2676
2677         if (txt_html != NULL){
2678                 txt_html += 4; /*  txt_html points at html content */
2679                 start = txt_html;
2680                 char multipart_boundary[100] = {0};
2681                 char *multipart_related_boundry = NULL;
2682                 char *multipart_related_boundry_end = NULL;
2683                 if (iEncodingHeader == 1)
2684                         multipart_related_boundry = pHeaderStart;
2685                 else
2686                         multipart_related_boundry = start_header;
2687                 
2688                 multipart_related_boundry = multipart_related_boundry - 3;
2689                 multipart_related_boundry_end = multipart_related_boundry;
2690                 
2691                 while (bufsendforparse < multipart_related_boundry && *multipart_related_boundry != LF && *multipart_related_boundry != NULL_CHAR)
2692                         multipart_related_boundry -= 1;
2693                 
2694                 multipart_related_boundry  += 1;
2695                 memcpy(multipart_boundary, multipart_related_boundry, multipart_related_boundry_end - multipart_related_boundry);
2696                 
2697                 EM_DEBUG_LOG("multipart_boundary [%s], boundary_string [%s]", multipart_boundary, boundary_string);
2698
2699                 if (strcmp(multipart_boundary, boundary_string) == 0)
2700                         end = strstr(txt_html, boundary_string);
2701                 else
2702                         end = strstr(txt_html, multipart_boundary);
2703
2704                 memset(multipart_boundary, 0, strlen(multipart_boundary));
2705
2706                 EM_DEBUG_LOG("end [%p], txt_html [%p]", end, txt_html);
2707
2708                 if (end == NULL) {
2709                         EM_DEBUG_LOG("HTML body contents exceeds limited Bytes");
2710                         
2711                         end = txt_html + body_size - (txt_html - bufsendforparse);
2712                         html_uidno = 1;
2713                 }
2714                 else if(end == txt_html) { /* empty multipart */
2715                         EM_DEBUG_LOG("Emtpy HTML multipart");
2716                         return false;
2717                 }                                               
2718                 else {
2719                         if ((*(end-2) == CR) && (*(end-1) == LF))
2720                                 end -= 2;
2721                         else if ((*(end-2) == CR) && (*(end-1) == LF) 
2722                                     && (*(end-4) == CR) && (*(end-3) == LF))
2723                                 end -= 4;
2724                         else
2725                                 EM_DEBUG_EXCEPTION(" Content not per as grammar.");
2726                 }
2727
2728                 EM_DEBUG_LOG("end [%p], txt_html [%p]", end, txt_html);
2729
2730                 EM_DEBUG_LOG("iEncodingHeader [%d]", iEncodingHeader);
2731
2732                 if (iEncodingHeader == 1){
2733                         enc_type = ENCOTHER;
2734                         if (strncasecmp(Encoding, "base64", strlen("base64")) == 0)
2735                                 enc_type = ENCBASE64;
2736                         else if (strncasecmp(Encoding, "quoted-printable", strlen("quoted-printable")) == 0)
2737                                 enc_type = ENCQUOTEDPRINTABLE;
2738         
2739                         EM_DEBUG_LOG("enc_type [%d]", enc_type);
2740
2741                         memcpy(text_html, start, end - txt_html);
2742                         
2743                         if (emcore_decode_body_text(text_html, end - txt_html, enc_type , &dec_len, &err) < 0) 
2744                                 EM_DEBUG_EXCEPTION("emcore_decode_body_text failed [%d]", err);
2745                 }
2746                 else if (start_header && ((temp_enc1 = (char *)strcasestr(start_header, "Content-transfer-encoding:"))  != NULL) && !(temp_enc1 && temp_enc1 >= end)){
2747                         if (temp_enc1)
2748                                 start_header = temp_enc1;
2749
2750                         start_header += strlen("Content-Transfer-Encoding:");
2751                         start_header = em_skip_whitespace_without_strdup(start_header);
2752
2753                         if (!start_header)
2754                                 EM_DEBUG_EXCEPTION(" Invalid parsing ");
2755                         else{
2756                                 enc_type = ENCOTHER;
2757                                 if (strncasecmp(start_header, "base64", strlen("base64")) == 0)
2758                                         enc_type = ENCBASE64;
2759                                 else if (strncasecmp(start_header, "quoted-printable", strlen("quoted-printable")) == 0)
2760                                         enc_type = ENCQUOTEDPRINTABLE;
2761
2762                                 EM_DEBUG_LOG("enc_type [%d]", enc_type);
2763                                 
2764                                 memcpy(text_html, start, end - txt_html);
2765                                 
2766                                 if (emcore_decode_body_text(text_html, end - txt_html, enc_type , &dec_len, &err) < 0) 
2767                                         EM_DEBUG_EXCEPTION("emcore_decode_body_text failed [%d]", err);
2768                                 html_length = dec_len;
2769                         }
2770                         
2771                         EM_DEBUG_LOG("Decoded length = %d", dec_len);
2772                         EM_DEBUG_LOG("start - %s", start);
2773                 }
2774                 else{
2775                         memcpy(text_html, start, end-txt_html);
2776                         html_length = (end-txt_html);
2777                 }
2778
2779                 /* EM_DEBUG_LOG(" Content-Type:  text/html [%s]\n", text_html);                                                          */
2780         }
2781         else
2782                 EM_DEBUG_EXCEPTION(" Invalid html body content ");
2783
2784         EM_DEBUG_FUNC_END();
2785         return true;
2786 }
2787
2788
2789
2790 /*For the following scenario
2791 *------= SAMSUNG_mySingle_MIME_MULTIPART_BOUNDARY
2792 *Content-Transfer-Encoding :  base64
2793 *Content-Type :  text/plain; charset = "windows-1252"
2794 *MIME-Version :  1.0
2795 *Message-ID:  <11512468.945901271910226702.JavaMail.weblogic@epml03>
2796 */
2797
2798 #define CONTENT_TRANSFER_ENCODING "Content-Transfer-Encoding"
2799
2800 static int emcore_parse_plain_part_for_partial_body(char *header_start_string, char *start_header, char *boundary_string, char *bufsendforparse, char *text_plain, int body_size)
2801 {
2802         EM_DEBUG_FUNC_BEGIN("header_start_string[%s], start_header[%s], boundary_string [%s], bufsendforparse [%s], text_plain [%s]", header_start_string, start_header, boundary_string, bufsendforparse, text_plain);
2803         int   err = EMAIL_ERROR_NONE, iEncodingHeader = 0, enc_type = ENCOTHER;
2804         int  dec_len = 0, strcmpret = -1;
2805         char *pHeaderStart = NULL, *pEncodingHeaderEnd = NULL;
2806         char  EncodingHeader[40] = {0, };
2807         char  Encoding[30] = {0, };
2808         char *temp_text_boundary = NULL;
2809         char *start = NULL, *end = NULL, *txt_plain = NULL, *temp_enc1 = NULL;
2810
2811         EM_DEBUG_LOG("Content-Type : text/plain");
2812
2813         pHeaderStart = header_start_string; 
2814         temp_text_boundary = start_header; 
2815
2816         memcpy(EncodingHeader, pHeaderStart, 25);
2817
2818         if (strcasecmp(EncodingHeader, "Content-Transfer-Encoding") == 0){
2819                 pEncodingHeaderEnd = strstr(pHeaderStart, CRLF_STRING);
2820                 memcpy(Encoding, pHeaderStart + 27, pEncodingHeaderEnd - (pHeaderStart + 27));
2821                 iEncodingHeader = 1;
2822         }
2823         
2824         /*  Plain text content found  */
2825         
2826         txt_plain = start_header;
2827         txt_plain = strstr(txt_plain, CRLF_STRING CRLF_STRING);
2828
2829         if (txt_plain != NULL){
2830                 txt_plain += strlen(CRLF_STRING CRLF_STRING); /*  txt_plain points at plain text content  */
2831                 
2832                 /* Fix is done for mail having "Content-Type: text/plain" but there is no content but having only attachment. */
2833                 
2834                 strcmpret = strncmp(txt_plain, boundary_string, strlen(boundary_string));
2835                 if (strcmpret == 0){
2836                 }
2837                 else{
2838                         start = txt_plain;
2839                         end = strstr(txt_plain, boundary_string);
2840                         
2841                         if (end == NULL){
2842                                 EM_DEBUG_LOG("Text body contents exceeds limited Bytes");
2843                                 end = txt_plain + body_size - (txt_plain - bufsendforparse);
2844                         }
2845                         else{
2846                                 /* EM_DEBUG_LOG("pbd_event[temp_count].partial_body_complete - %d", partial_body_complete); */
2847         
2848                                 if ((*(end-2) == CR) && (*(end-1) == LF))
2849                                         end -= 2;
2850                                 else if ((*(end-2) == CR) && (*(end-1) == LF) 
2851                                             && (*(end-4) == CR) && (*(end-3) == LF))
2852                                         end -= 4;
2853                                 else
2854                                         EM_DEBUG_EXCEPTION(" Content not per as grammar.");
2855                         }
2856
2857                         if (iEncodingHeader == 1){
2858                                 enc_type = ENCOTHER;
2859                                 if (strncasecmp(Encoding, "base64", strlen("base64")) == 0)
2860                                         enc_type = ENCBASE64;
2861                                 else if (strncasecmp(Encoding, "quoted-printable", strlen("quoted-printable")) == 0)
2862                                         enc_type = ENCQUOTEDPRINTABLE;
2863                 
2864                                 EM_DEBUG_LOG("enc_type [%d]", enc_type);
2865
2866                                 memcpy(text_plain, start, end - txt_plain);
2867                                 
2868                                 if (emcore_decode_body_text(text_plain, end - txt_plain, enc_type , &dec_len, &err) < 0) 
2869                                         EM_DEBUG_EXCEPTION("emcore_decode_body_text failed [%d]", err);
2870                         }
2871                         else if (start_header && ((temp_enc1 = (char *)strcasestr(start_header, "Content-transfer-encoding:"))  != NULL) && !(temp_enc1 && temp_enc1 >= end)){
2872                                 if (temp_enc1)
2873                                         start_header = temp_enc1;
2874
2875                                 start_header += strlen("Content-Transfer-Encoding:");
2876                                 start_header = em_skip_whitespace_without_strdup(start_header);
2877
2878                                 if (!start_header)
2879                                         EM_DEBUG_EXCEPTION(" Invalid parsing ");
2880                                 else{
2881                                         enc_type = ENCOTHER;
2882                                         if (strncasecmp(start_header, "base64", strlen("base64")) == 0)
2883                                                 enc_type = ENCBASE64;
2884                                         else if (strncasecmp(start_header, "quoted-printable", strlen("quoted-printable")) == 0)
2885                                                 enc_type = ENCQUOTEDPRINTABLE;
2886                         
2887                                         EM_DEBUG_LOG("enc_type [%d]", enc_type);
2888                                         memcpy(text_plain, start, end - txt_plain);
2889                                         if (emcore_decode_body_text(text_plain, end - txt_plain, enc_type , &dec_len, &err) < 0) 
2890                                                 EM_DEBUG_EXCEPTION("emcore_decode_body_text failed [%d]", err);
2891                                 }
2892                                 
2893                                 EM_DEBUG_LOG("Decoded length = %d", dec_len);
2894                                 /*  EM_DEBUG_LOG("start - %s", start); */ /* print raw MIME content. */
2895                         }
2896                         else
2897                                 memcpy(text_plain, start, end-txt_plain);
2898
2899                         /* EM_DEBUG_LOG(" Content-type: text/plain [%s]\n", text_plain); */
2900                 }
2901         }
2902         else
2903                 EM_DEBUG_EXCEPTION(" Invalid text body content ");
2904
2905         EM_DEBUG_FUNC_END();
2906         return 1;
2907 }
2908
2909
2910
2911 /*  Content-Type:  IMAGE/octet-stream; name = Default.png */
2912 /*  Content-Transfer-Encoding:  BASE64 */
2913 /*  Content-ID:  <4b0d6810b17291f9438783a8eb9d5228@org.tizen.email> */
2914 /*  Content-Disposition:  inline; filename = Default.png */
2915
2916 static int emcore_parse_image_part_for_partial_body(char *header_start_string, char *start_header, char *boundary_string, char *bufsendforparse, email_image_data *image_data, int body_size)
2917 {
2918         EM_DEBUG_FUNC_BEGIN();
2919
2920         int   err = EMAIL_ERROR_NONE;
2921         char *multiple_image = NULL;
2922         int   donot_parse_next_image = 0;
2923         char *image_boundary = NULL;
2924         char *image_boundary_end = NULL;
2925         char  temp_image_boundary[256] = {0};
2926         int   i = 0, ch_image = 0, cidno = 0;
2927         int   enc_type = ENCOTHER, dec_len = 0, image_length = 0;
2928         char *p = header_start_string;
2929         char *start = NULL, *end = NULL, *txt_image = NULL;
2930         char *temp_image = NULL;
2931         char *temp_cid1 = NULL;
2932         char *cid_end = NULL;
2933         char *temp_enc1 = NULL;
2934
2935         if(image_data == NULL) {
2936                 EM_DEBUG_EXCEPTION("EMAIL_ERROR_INVALID_PARAM");
2937                 err = EMAIL_ERROR_INVALID_PARAM;
2938                 return 0;
2939         }
2940
2941         image_boundary     = start_header;
2942         image_boundary_end = image_boundary - 2;
2943         image_boundary     = image_boundary - 2;
2944         
2945         EM_DEBUG_LOG("Content-type: image");
2946         
2947         while (*image_boundary != LF)
2948                 image_boundary--;
2949         
2950         image_boundary++;
2951         
2952         if (image_boundary  != NULL && image_boundary_end != NULL)
2953                 memcpy(temp_image_boundary, image_boundary, image_boundary_end-image_boundary);
2954         
2955         if ((char *)strcasestr((const char *)temp_image_boundary, "Content-type:") == NULL)
2956                 boundary_string = temp_image_boundary;
2957         do {
2958                 if (multiple_image != NULL){
2959                         p = multiple_image;
2960                         start_header = multiple_image;
2961                 }
2962
2963                 emcore_get_content_type_from_mime_string(start_header, &(image_data[i].mime_type));
2964
2965                 if ((strcasestr(p, "Content-Disposition: attachment")) || (!strcasestr(p, "Content-ID: <"))){
2966                         EM_DEBUG_EXCEPTION(" Body has attachment no need to parse ");
2967                         end = NULL;
2968                         multiple_image = NULL;
2969                 }
2970                 else {  /*  HTML Content found */
2971                         ch_image = 0;
2972                         cidno = 0;
2973                         int   boundarylen = -1;
2974                         char *cid = NULL;
2975                         char *temp_name = NULL;
2976                         char *decoded_filename = NULL;
2977
2978                         memset(image_data[i].image_file_name, 0, 100);
2979                         txt_image  = start_header;
2980                         temp_image = start_header;
2981
2982                         temp_name = strstr(txt_image, "name=");
2983                         if (temp_name  != NULL){
2984                                 temp_image = temp_name;
2985                                 if (*(temp_image+5) == '"')
2986                                         temp_image = temp_image+5;
2987                                 
2988                                 while (*temp_image  != CR){
2989                                         temp_image++;
2990                                         memcpy(image_data[i].image_file_name+ch_image, temp_image, 1);
2991                                         ch_image++;
2992                                 }
2993                                 
2994                                 if ((*(temp_name+4) == '=') && (*(temp_name+5) == '\"'))
2995                                         image_data[i].image_file_name[ch_image-2] = '\0';
2996                                 
2997                                 if ((*(temp_name+4) == '=') && (*(temp_name+5) != '\"'))
2998                                         image_data[i].image_file_name[ch_image-1] = '\0';
2999
3000                                 decoded_filename = emcore_decode_rfc2047_text(image_data[i].image_file_name, &err);
3001                                 if(decoded_filename) {
3002                                         memset(image_data[i].image_file_name, 0, 100);
3003                                         memcpy(image_data[i].image_file_name, decoded_filename, EM_SAFE_STRLEN(decoded_filename));
3004                                         EM_SAFE_FREE(decoded_filename);
3005                                 }
3006                         }               
3007                         
3008                         if (((temp_cid1 = (char *)strcasestr((const char *)start_header, "Content-ID: <")) != NULL)){
3009                                 if (temp_cid1){
3010                                         cid = temp_cid1;
3011                                         temp_image = temp_cid1;
3012                                 }
3013                                 
3014                                 cid += 13;
3015                                 cid_end = strstr(temp_image, "\076");           /*  076 == '>' */
3016                         
3017                                 image_data[i].content_id = (char *)em_malloc(cid_end-cid+5);
3018                                 if (image_data[i].content_id != NULL){
3019                                         strcpy(image_data[i].content_id, "cid:");
3020                                         memcpy(image_data[i].content_id+4, cid, cid_end-cid);
3021                                 }
3022                                 else
3023                                         EM_DEBUG_EXCEPTION("em_malloc() failed");
3024                                 
3025                                 if (image_data[i].image_file_name[0] == '\0')
3026                                         memcpy(image_data[i].image_file_name, cid, cid_end - cid);
3027                         }
3028
3029                         txt_image = strstr(txt_image, CRLF_STRING CRLF_STRING);
3030
3031                         if (txt_image != NULL){
3032                                 txt_image += 4; /*  txt_image points at image content */
3033                                 start = txt_image;
3034                                 end = strstr(txt_image, boundary_string);
3035
3036
3037                                 if (end == NULL){
3038                                         EM_DEBUG_LOG("HTML body contents exceeds limited Bytes");
3039                                         /*  end points to end of partial body data */
3040                                         end = txt_image + body_size - (txt_image-bufsendforparse);
3041                                 }
3042                                 else{
3043                                         boundarylen = strlen(boundary_string);
3044                                         end -= 2;
3045                                 }
3046                                                 
3047                                 if (start_header && ((temp_enc1 = (char *)strcasestr((const char *)start_header, "Content-transfer-encoding:"))  != NULL)){
3048                                         if (temp_enc1)
3049                                                 start_header = temp_enc1;
3050
3051                                         start_header  += strlen("Content-Transfer-Encoding:");
3052                                         start_header = em_skip_whitespace_without_strdup(start_header);
3053                                         
3054                                         if (!start_header)
3055                                                 EM_DEBUG_EXCEPTION(" Invalid parsing ");
3056                                         else{
3057                                                 enc_type = ENCOTHER;
3058                                                 if (strncasecmp(start_header, "base64", strlen("base64")) == 0)
3059                                                         enc_type = ENCBASE64;
3060                                                 else if (strncasecmp(start_header, "quoted-printable", strlen("quoted-printable")) == 0)
3061                                                         enc_type = ENCQUOTEDPRINTABLE;
3062
3063                                                 EM_DEBUG_LOG("enc_type [%d]", enc_type);
3064                                                 
3065                                                 image_data[i].text_image = (char *)em_malloc((end-txt_image)+1);
3066                                                 if (image_data[i].text_image){
3067                                                         memcpy(image_data[i].text_image, start, end-txt_image);
3068                                                         if (emcore_decode_body_text(image_data[i].text_image, end-txt_image, enc_type , &(image_data[i].dec_len), &err) < 0) 
3069                                                                 EM_DEBUG_EXCEPTION("emcore_decode_body_text failed [%d]", err);
3070                                                         else
3071                                                                 image_length = image_data[i].dec_len;
3072                                                 }
3073                                                 else
3074                                                         EM_DEBUG_EXCEPTION("em_malloc() failed");
3075                                         }
3076                                         
3077                                         EM_DEBUG_LOG("Decoded length [%d]", dec_len);
3078                                 }
3079                                 else{
3080                                         image_data[i].text_image = (char *)em_malloc(end-txt_image);
3081                                         if (image_data[i].text_image)
3082                                                 memcpy(image_data[i].text_image, start, end - txt_image);
3083                                         else
3084                                                 EM_DEBUG_EXCEPTION("em_malloc() failed");
3085                                 }                                                       
3086                         }
3087                         else{
3088                                 donot_parse_next_image = 1;
3089                                 EM_DEBUG_EXCEPTION(" Invalid html body content ");
3090                         }
3091                 }
3092
3093                 if (end != NULL) {
3094                         multiple_image = (char *)strcasestr((const char *)end, "Content-type: image");
3095                         i++;
3096                 }
3097         } while (multiple_image != NULL && donot_parse_next_image != 1 && (i < IMAGE_DISPLAY_PARTIAL_BODY_COUNT));
3098
3099         EM_DEBUG_FUNC_END();
3100         return 1;
3101 }
3102
3103 static int emcore_find_boundary_string_of_the_part(const char *whole_string, const char *first_line_of_part, char **result_boundary_string, int *error)
3104 {
3105         EM_DEBUG_FUNC_BEGIN("whole_string[%p], first_line_of_part[%p], result_boundary_string[%p]", whole_string, first_line_of_part, result_boundary_string);
3106         int ret = false, err = EMAIL_ERROR_NONE;
3107         char *boundary_cur = NULL, *boundary_end = NULL, *boundary_string = NULL;
3108
3109         if(!whole_string || !first_line_of_part || !result_boundary_string) {
3110                 EM_DEBUG_EXCEPTION("EMAIL_ERROR_INVALID_PARAM");
3111                 err = EMAIL_ERROR_INVALID_PARAM;
3112                 goto FINISH_OFF;
3113         }
3114
3115         if(first_line_of_part - 2 > whole_string) {
3116                 boundary_cur = (char*)first_line_of_part - 2; /* 2 means CRLF. */
3117                 boundary_end = boundary_cur;
3118
3119                 do{
3120                         boundary_cur--;
3121                 } while (whole_string < boundary_cur && *boundary_cur != LF && *boundary_cur != NULL_CHAR);
3122                 
3123                 boundary_cur++;
3124
3125                 if(boundary_end > boundary_cur && boundary_cur > whole_string) {
3126                         EM_DEBUG_LOG("boundary_end - boundary_cur + 15 [%d]", boundary_end - boundary_cur + 15);
3127                         boundary_string = em_malloc(boundary_end - boundary_cur + 15);
3128                         if(!boundary_string) {
3129                                 EM_DEBUG_EXCEPTION("em_malloc failed");
3130                                 err = EMAIL_ERROR_OUT_OF_MEMORY;
3131                                 goto FINISH_OFF;
3132                         }
3133                         memcpy(boundary_string, boundary_cur, boundary_end - boundary_cur);
3134                         EM_DEBUG_LOG("boundary_string [%s]", boundary_string);
3135                         *result_boundary_string = boundary_string;
3136                 }
3137                 else {
3138                         EM_DEBUG_EXCEPTION("There is no string before the part");
3139                         err = EMAIL_ERROR_ON_PARSING;
3140                         goto FINISH_OFF;
3141                 }
3142         }
3143         else {
3144                 EM_DEBUG_EXCEPTION("There is no string before the part");
3145                 err = EMAIL_ERROR_ON_PARSING;
3146                 goto FINISH_OFF;        
3147         }
3148         ret = true;
3149 FINISH_OFF:
3150
3151         if(error)
3152                 *error = err;
3153
3154         EM_DEBUG_FUNC_END("ret[%d], err[%d]", ret, err);
3155         return ret;
3156
3157
3158 #define TAG_LENGTH 16
3159 #define COMMAND_LENGTH 2000
3160 static int emcore_download_bulk_partial_mail_body_for_imap(MAILSTREAM *stream, int input_download_size, email_event_partial_body_thd *pbd_event, int item_count, int *error)
3161 {
3162         EM_DEBUG_FUNC_BEGIN("stream [%p], input_download_size[%d], pbd_event [%p], item_count [%d], error [%p]", stream, input_download_size, pbd_event, item_count, error);
3163         
3164         int ret = false, err = EMAIL_ERROR_NONE;
3165         int encoding = 0;
3166         int j = 0;
3167         int i32_index = 0, temp_string_index = 0;
3168         int no_alternative_part_flag = 0;
3169         int dec_len = 0, response_buffer_length = 0, mailparselen = 0, image_length = 0, tempmailparselen = 0;
3170         int temp_count = 0, total_mail_size = 0, attachment_num, body_size = 0, total_mail_size_except_attach = 0;
3171         int total_parsed_len_per_uid = 0, total_parsed_len = 0;
3172         unsigned long uidno = 0;
3173         char buf[512] = {0, };
3174         char *text_plain    = NULL;
3175         char *text_html     = NULL;
3176         char *temp_text_buf = NULL;
3177         char uid_range_string_to_be_downloaded[UID_RANGE_STRING_LENGTH] = {0, };        
3178         char imap_tag[TAG_LENGTH] = {0, };
3179         char command[COMMAND_LENGTH] = {0, };
3180         char *p = NULL, *s = NULL, *decoded_text_buffer = NULL;
3181         char *response_buffer = NULL;
3182         char *bufsendforparse = NULL;
3183         char *start_header = NULL;
3184         char *boundary_string = NULL;
3185         char *temp_content_type1 = NULL;
3186         char *temp_data_html = NULL;
3187         char *bodystructure_start = NULL, *bodystructure_end = NULL, *body_structure_string = NULL, *modified_body_structure_string = NULL;
3188         char *plain_text_file_name_from_content_info = NULL, *html_text_file_name_from_content_info = NULL, *plain_charset_from_content_info = NULL;
3189         char temp_string[TEMP_STRING_LENGTH] = {0, };
3190         IMAPLOCAL *imaplocal = NULL;
3191         IMAPPARSEDREPLY *reply_from_server = NULL;
3192         emstorage_mail_tbl_t *mail = NULL;
3193         email_partial_buffer *imap_response = NULL;
3194         BODY *body = NULL;
3195         struct _m_content_info *cnt_info = NULL;
3196         struct attachment_info *attach_info = NULL;
3197         emstorage_attachment_tbl_t attachment_tbl;
3198         email_event_partial_body_thd *stSectionNo = NULL;
3199         email_image_data  image_data[IMAGE_DISPLAY_PARTIAL_BODY_COUNT];
3200
3201         if (!(stream) || !(imaplocal = stream->local) || !imaplocal->netstream || !pbd_event) {
3202                 EM_DEBUG_EXCEPTION("invalid parameter");
3203                 err = EMAIL_ERROR_INVALID_PARAM;                
3204                 EM_DEBUG_FUNC_END("ret [%d]", ret);     
3205                 return ret;
3206         }
3207
3208         text_plain    = em_malloc(sizeof(char) * (input_download_size + 1));
3209         text_html     = em_malloc(sizeof(char) * (input_download_size + 1));
3210         temp_text_buf = em_malloc(sizeof(char) * (input_download_size + 1));
3211
3212         if(!text_plain || !text_plain || !temp_text_buf) {
3213                 EM_SAFE_FREE(text_plain);
3214                 EM_SAFE_FREE(text_html);
3215                 EM_SAFE_FREE(temp_text_buf);
3216
3217                 EM_DEBUG_EXCEPTION("em_malloc failed");
3218                 return EMAIL_ERROR_OUT_OF_MEMORY;
3219         }
3220
3221         memset(image_data, 0x00 , sizeof(email_image_data) * IMAGE_DISPLAY_PARTIAL_BODY_COUNT);
3222         
3223         EM_DEBUG_LOG("Start of emcore_get_section_for_partial_download, item_count = %d ", item_count);
3224                 
3225         /* For constructing UID list which is having 10 UID or less at a time */
3226         for (j = 0, stSectionNo = pbd_event; (stSectionNo  != NULL && j < item_count); j++)
3227         {               
3228                 EM_DEBUG_LOG("pbd_event[%d].account_id [%d], mail_id [%d], server_mail_id [%d], activity_id [%d]", \
3229                         j, stSectionNo[j].account_id, stSectionNo[j].mail_id, stSectionNo[j].server_mail_id, stSectionNo[j].activity_id);               
3230                 
3231                 if (i32_index >= UID_RANGE_STRING_LENGTH){
3232                         EM_DEBUG_EXCEPTION("String length exceeded its limitation!");
3233                         goto FINISH_OFF;
3234                 }                       
3235
3236                 if (j == item_count - 1)
3237                         i32_index += SNPRINTF(uid_range_string_to_be_downloaded + i32_index, UID_RANGE_STRING_LENGTH, "%lu", stSectionNo[j].server_mail_id);
3238                 else
3239                         i32_index += SNPRINTF(uid_range_string_to_be_downloaded + i32_index, UID_RANGE_STRING_LENGTH, "%lu,", stSectionNo[j].server_mail_id);
3240         }       
3241
3242         SNPRINTF(imap_tag, TAG_LENGTH, "%08lx", 0xffffffff & (stream->gensym++));
3243         SNPRINTF(command, COMMAND_LENGTH, "%s UID FETCH %s (BODYSTRUCTURE BODY.PEEK[TEXT]<0.%d>)\015\012", imap_tag, uid_range_string_to_be_downloaded, input_download_size);
3244
3245         EM_DEBUG_LOG("command : %s", command);
3246
3247         /*  Sending out the IMAP request */
3248         if (!net_sout(imaplocal->netstream, command, (int)strlen(command))) {
3249                 EM_DEBUG_EXCEPTION("net_sout failed...");
3250                 err = EMAIL_ERROR_CONNECTION_BROKEN;            
3251                 goto FINISH_OFF;
3252         }
3253
3254         /*  responce from the server */
3255         imap_response = emcore_get_response_from_server(imaplocal->netstream, imap_tag, &reply_from_server, input_download_size);
3256
3257         if (!imap_response || !reply_from_server ){
3258                 EM_DEBUG_EXCEPTION(" Invalid response from emcore_get_response_from_server");
3259                 goto FINISH_OFF;
3260         }
3261         
3262         if (!imap_response->buffer || imap_response->buflen == 0){
3263                 EM_DEBUG_EXCEPTION(" NULL partial BODY Content ");
3264                 goto FINISH_OFF;
3265         }
3266         EM_DEBUG_LOG("imap_response->buffer [%s]",imap_response->buffer);
3267         response_buffer        = imap_response->buffer;
3268         response_buffer_length = imap_response->buflen;
3269
3270         while (response_buffer && (bodystructure_start = strstr(response_buffer, "BODYSTRUCTURE (")) != NULL){
3271                 /*  if it has BODYSTRUCTURE */
3272                 EM_DEBUG_LOG("response_buffer [%s]",response_buffer);
3273                 bodystructure_start = bodystructure_start + strlen("BODYSTRUCTURE");
3274                 bodystructure_end = strstr(bodystructure_start, "BODY[");
3275                 
3276                 if (bodystructure_end != NULL) {
3277                         int bodystructure_length = bodystructure_end - bodystructure_start;
3278                         
3279                         EM_DEBUG_LOG("bodystructure_length [%d]", bodystructure_length);
3280
3281                         if (bodystructure_length > response_buffer_length){
3282                                 EM_DEBUG_EXCEPTION("bodystructure_length[%d] is longer than response_buffer_length[%d]", bodystructure_length, response_buffer_length);
3283                                 err = EMAIL_ERROR_INVALID_RESPONSE;
3284                                 goto FINISH_OFF;
3285                         }
3286                         
3287                         body_structure_string = (char *)em_malloc(sizeof(char) * bodystructure_length + 1);
3288
3289                         if (NULL == body_structure_string){
3290                                 EM_DEBUG_EXCEPTION("em_malloc failed...!");
3291                                 err = EMAIL_ERROR_OUT_OF_MEMORY;
3292                                 goto FINISH_OFF;
3293                         }
3294
3295                         memcpy(body_structure_string, bodystructure_start, bodystructure_length);
3296
3297                         body = mail_newbody();
3298                         
3299                         if (NULL == body){
3300                                 EM_DEBUG_EXCEPTION("New body creation failed...!");
3301                                 EM_SAFE_FREE(body_structure_string);
3302                                 goto FINISH_OFF;
3303                         }
3304
3305                         /*  Parse body_structure_string to BODY  */
3306                         EM_DEBUG_LOG("body_structure_string [%s]", body_structure_string);
3307                         /* body_structure_string modified */
3308                         modified_body_structure_string = em_replace_string(body_structure_string, "}\r\n", "} ");
3309                         if (modified_body_structure_string != NULL) {
3310                                 EM_SAFE_STRNCPY(body_structure_string, modified_body_structure_string, strlen(modified_body_structure_string));
3311                                 EM_DEBUG_LOG("modified_body_structure_string [%s]", modified_body_structure_string);
3312                         }
3313                         imap_parse_body_structure (stream, body, (unsigned char **)&body_structure_string, reply_from_server);
3314                         
3315                         total_mail_size = 0;
3316
3317                         if (emcore_set_fetch_body_section(body, true, &total_mail_size, &err) < 0) {
3318                                 EM_DEBUG_EXCEPTION("emcore_set_fetch_body_section failed - %d", err);
3319                                 goto FINISH_OFF;
3320                         }
3321                         
3322                         if (!(cnt_info = em_malloc(sizeof(struct _m_content_info)))) {
3323                                 EM_DEBUG_EXCEPTION("em_malloc failed...");
3324                                 err = EMAIL_ERROR_OUT_OF_MEMORY;
3325                                 goto FINISH_OFF;
3326                         }
3327
3328                         /*  getting content info from body  */
3329                                                 
3330                         if (emcore_get_body(stream, 0, 0, 0, body, cnt_info, &err) < 0 || !cnt_info) {
3331                                 EM_DEBUG_EXCEPTION("emcore_get_body falied [%d]", err);
3332                                 err = EMAIL_ERROR_IMAP4_FETCH_UID_FAILURE;
3333                                 goto FINISH_OFF;
3334                         }
3335
3336                         EM_DEBUG_LOG("Start parsing partial body...");
3337                         
3338                         int no_html = 0;
3339                         char *temp_alternative_plain_header = NULL;
3340                         
3341                         p = (char *)strstr(response_buffer, " {");
3342                         if (p  != NULL){
3343                                 EM_DEBUG_LOG("Getting the body size");
3344                                 p += strlen(" {");
3345                                 s = p;
3346
3347                                 temp_string_index = 0;
3348                                 memset(temp_string, 0, TEMP_STRING_LENGTH);
3349                         
3350                                 while (isdigit(*s) && temp_string_index < TEMP_STRING_LENGTH){
3351                                         memcpy(temp_string + temp_string_index, s, 1); /* ! */
3352                                         s++;
3353                                         temp_string_index++;
3354                                 }
3355                                 
3356                                 body_size = atoi(temp_string);
3357                                 if (body_size >= input_download_size)
3358                                         body_size = input_download_size + 2;
3359                                 EM_DEBUG_LOG("body_size [%d]", body_size);
3360                         }
3361                         else{
3362                                 body_size = 0;
3363                                 EM_DEBUG_EXCEPTION("Can't find body size from MIME header");
3364                                 /* err = EMAIL_ERROR_INVALID_RESPONSE; */
3365                                 /* goto FINISH_OFF; */
3366                         }
3367                                         
3368                         /*  Find next line */
3369                         tempmailparselen = 0;
3370                         while (tempmailparselen < response_buffer_length && response_buffer[tempmailparselen] != LF)
3371                                 tempmailparselen++;
3372                         tempmailparselen++;
3373
3374                         if (imap_response->buflen < (total_parsed_len + body_size)){
3375                                 err = EMAIL_ERROR_CONNECTION_BROKEN;
3376                                 EM_DEBUG_EXCEPTION("EMAIL_ERROR_CONNECTION_BROKEN  :  imap_response->buflen [%d], total_parsed_len [%d], body_size [%d]", imap_response->buflen, total_parsed_len, body_size);
3377                                 goto FINISH_OFF;
3378                         }
3379                         else {   
3380                                 if ((p = strstr(response_buffer, "UID "))) {
3381                                         EM_DEBUG_LOG("getting the UID number");
3382                                         p += strlen("UID ");
3383                                         s = p;
3384                                         
3385                                         temp_string_index = 0;
3386                                         memset(temp_string, 0, TEMP_STRING_LENGTH);                     
3387                 
3388                                         while (isdigit(*s) && temp_string_index < TEMP_STRING_LENGTH){
3389                                                 memcpy(temp_string + temp_string_index, s, 1);
3390                                                 s++;
3391                                                 temp_string_index++;
3392                                         }
3393                                         
3394                                         uidno = strtoul(temp_string, NULL, 0);
3395                                         EM_DEBUG_LOG("UID [%d]", uidno);
3396                                         
3397                                         for (temp_count = 0; temp_count < BULK_PARTIAL_BODY_DOWNLOAD_COUNT && 
3398                                                                                 pbd_event[temp_count].server_mail_id  != uidno && temp_count  != item_count; temp_count++)
3399                                                 continue;
3400
3401                                         if (temp_count >= BULK_PARTIAL_BODY_DOWNLOAD_COUNT){    
3402                                                 EM_DEBUG_EXCEPTION("Can't find proper server_mail_id");
3403                                                 goto FINISH_OFF;
3404                                         }
3405
3406                                         EM_SAFE_FREE(plain_text_file_name_from_content_info);
3407                                         EM_SAFE_FREE(html_text_file_name_from_content_info);
3408                                         EM_SAFE_FREE(plain_charset_from_content_info);
3409
3410                                         /*  partial_body_complete = -1; */ /* Meaningless */
3411                                         /*  encoding = -1; */ /* Meaningless */
3412                                         
3413                                         plain_text_file_name_from_content_info    = EM_SAFE_STRDUP(cnt_info->text.plain);
3414                                         html_text_file_name_from_content_info     = EM_SAFE_STRDUP(cnt_info->text.html);
3415                                         plain_charset_from_content_info           = EM_SAFE_STRDUP(cnt_info->text.plain_charset);
3416
3417                                         EM_DEBUG_LOG("plain_text_file_name_from_content_info    [%s]", plain_text_file_name_from_content_info);
3418                                         EM_DEBUG_LOG("html_text_file_name_from_content_info     [%s]", html_text_file_name_from_content_info);
3419                                         EM_DEBUG_LOG("plain_charset_from_content_info           [%s]", plain_charset_from_content_info);
3420
3421                                         encoding = body->encoding;
3422                                         
3423                                         if (!emstorage_get_maildata_by_servermailid(pbd_event[temp_count].account_id, temp_string, &mail , true, &err) || !mail){
3424                                                 EM_DEBUG_EXCEPTION("emstorage_get_maildata_by_servermailid failed [%d]", err);
3425                                                 if (err == EMAIL_ERROR_MAIL_NOT_FOUND || !mail)
3426                                                         goto FINISH_OFF;
3427                                         }
3428                                         
3429                                         /*  Assign calculated mail size  */
3430                                         mail->mail_size               = total_mail_size;
3431                                         total_mail_size_except_attach = total_mail_size;
3432
3433                                         /*  Update attachment details except inline content */
3434                                         if (cnt_info->file && cnt_info->file->name){
3435                                                 memset(&attachment_tbl, 0x00, sizeof(email_attachment_data_t));
3436
3437                                                 attachment_tbl.account_id             = pbd_event[temp_count].account_id;
3438                                                 attachment_tbl.mail_id                = mail->mail_id;
3439                                                 attachment_tbl.mailbox_id           = pbd_event[temp_count].mailbox_id;
3440                                                 attachment_tbl.attachment_save_status = 0;
3441
3442                                                 for (attachment_num = 1, attach_info = cnt_info->file; attach_info; attach_info = attach_info->next, attachment_num++) {
3443                                                         total_mail_size_except_attach                  -= attach_info->size;
3444                                                         attachment_tbl.attachment_size                  = attach_info->size;
3445                                                         attachment_tbl.attachment_path                  = attach_info->save;
3446                                                         attachment_tbl.attachment_name                  = attach_info->name;
3447                                                         attachment_tbl.attachment_drm_type              = attach_info->drm;
3448                                                         attachment_tbl.attachment_inline_content_status = (attach_info->type == 1) ? 1 : 0;
3449                                                         attachment_tbl.attachment_mime_type             = attach_info->attachment_mime_type;
3450 #ifdef __ATTACHMENT_OPTI__
3451                                                         attachment_tbl.encoding = attach_info->encoding;
3452                                                         attachment_tbl.section = attach_info->section;
3453 #endif
3454                                                         
3455                                                         if (attach_info->type == 1) {
3456                                                                 EM_DEBUG_LOG("Breaking attachment_num [%d] attach_info->type [%d]", attachment_num, attach_info->type);
3457                                                                 break;          /*  Inline images at end of list  not to be added  */
3458                                                         }
3459
3460                                                         EM_DEBUG_LOG("attach_info->type  != 1 [%d]", attachment_num);
3461
3462                                                         mail->attachment_count++;
3463                                                         if (!emstorage_add_attachment(&attachment_tbl, 0, false, &err)) {
3464                                                                 EM_DEBUG_EXCEPTION("emstorage_add_attachment failed [%d]", err);                                        
3465                                                 
3466                                                                 goto FINISH_OFF;
3467                                                         }
3468                                                         
3469                                                 }                                                               
3470                                         }
3471                                                                                         
3472                                         emcore_free_content_info(cnt_info);
3473                                         cnt_info = NULL;
3474                                         
3475                                         mail_free_body(&body);  
3476                                         body = NULL;
3477
3478                                 }
3479                 
3480                                 /*  Find next line. */
3481                                 mailparselen = 0;
3482                                 
3483                                 while (mailparselen < response_buffer_length && response_buffer[mailparselen] != LF)
3484                                         mailparselen++;
3485                                 
3486                                 mailparselen++;
3487         
3488                                 /*  Removed the response header and send the buffer for parsing */
3489                                 response_buffer        = response_buffer + mailparselen;
3490                                 response_buffer_length = response_buffer_length - mailparselen;
3491
3492                                 bufsendforparse = em_malloc(body_size + 1); /*  old */
3493                                 /*  bufsendforparse = em_malloc(response_buffer_length + 1); */ /* new */
3494
3495                                 EM_DEBUG_LOG("body_size [%d], response_buffer_length [%d]", body_size, response_buffer_length);
3496
3497                                 if (bufsendforparse == NULL){
3498                                         EM_DEBUG_EXCEPTION("Allocation for bufsendforparse failed.");
3499                                         err = EMAIL_ERROR_OUT_OF_MEMORY;
3500                                         goto FINISH_OFF;
3501                                 }
3502                                 
3503                                 memcpy(bufsendforparse, response_buffer, body_size); /* old */
3504                                 bufsendforparse[body_size] = NULL_CHAR; /* old */
3505                                 /* EM_SAFE_STRNCPY(bufsendforparse, response_buffer, response_buffer_length);*/ /* new */
3506                                 /* bufsendforparse[response_buffer_length] = '\0'; */ /* new */
3507                 
3508                                 if (strlen(bufsendforparse) == 0)
3509                                         EM_DEBUG_EXCEPTION(" NULL partial BODY Content ");
3510
3511                                 EM_DEBUG_LOG("string bufendforparse :[%s]", bufsendforparse);
3512                                 p = bufsendforparse;
3513                                 
3514                                 if (mail && mail->body_download_status == EMAIL_BODY_DOWNLOAD_STATUS_FULLY_DOWNLOADED) /*  No need to save */
3515                                         goto NEXTUIDPARSING;
3516                                 
3517                                 if (!strcasestr(p, "Content-Type: text/plain") &&  !strcasestr(p, "Content-Type: text/html") &&  !strcasestr(p, "Content-type: image/jpeg")
3518                                         &&  !strcasestr(p, "Content-Type: image/gif") && !strcasestr(p, "Content-Type: image/bmp")&&(plain_text_file_name_from_content_info || html_text_file_name_from_content_info)){
3519                                         /*  Encoded Content-Type: text/html or Content-Type: text/plain  */
3520                                         /*  No Partial body has No headers with Content-Type: text/html or Content-Type: text/plain  */
3521                                         
3522                                         EM_DEBUG_LOG("plain_text_file_name_from_content_info [%p] html_text_file_name_from_content_info[%p] ", plain_text_file_name_from_content_info, html_text_file_name_from_content_info);
3523                                         EM_DEBUG_LOG("mbody->encoding [%d] ", encoding);
3524
3525                                         if (emcore_decode_body_text(p, strlen(p), encoding , &dec_len, &err) < 0) {
3526                                                 EM_DEBUG_EXCEPTION("emcore_decode_body_text failed [%d]", err);
3527                                                 goto FINISH_OFF;
3528                                         }
3529
3530                                         decoded_text_buffer = p;
3531
3532                                         EM_DEBUG_LOG("Decoded length [%d]", dec_len);
3533                                         /*  EM_DEBUG_LOG("p - %s", p); */
3534                 
3535                                         if (dec_len > 0){
3536                                                 if (plain_text_file_name_from_content_info){
3537                                                         EM_DEBUG_LOG(" plain_text_file_name_from_content_info [%s]", plain_text_file_name_from_content_info);
3538                                                         memcpy(text_plain, decoded_text_buffer, dec_len);
3539                                                         /* EM_DEBUG_LOG(" Content-Type :  text/plain [%s]", text_plain); */
3540                                                 }
3541
3542                                                 if (html_text_file_name_from_content_info){
3543                                                         EM_DEBUG_LOG("html_text_file_name_from_content_info [%s]", html_text_file_name_from_content_info);
3544                                                         memcpy(text_html, decoded_text_buffer, dec_len);
3545                                                         /* EM_DEBUG_LOG(" Content-Type: text/html [%s]", text_html); */
3546                                                 }
3547                                         }
3548                                 }
3549                                 else{   /*  Partial body has headers with Content-Type: text/html or Content-Type: text/plain */
3550                                         no_alternative_part_flag = 0;
3551                                         if (((temp_alternative_plain_header = (char *)strcasestr(p, "Content-type: multipart/alternative"))  != NULL)){ /*  Found 'alternative' */
3552                                                 if (((temp_content_type1 = (char *)strcasestr(p, "Content-type: text/plain"))  != NULL)){   
3553                                                         if (temp_content_type1 < temp_alternative_plain_header) /*  This part is text/plain not alternative. */
3554                                                                 no_html = 1;
3555                                                         no_alternative_part_flag = 1;
3556                                                 }
3557                                                 else{
3558                                                         EM_DEBUG_LOG(" Content-type: multipart/alternative ");
3559                                                         p = strstr(bufsendforparse, CRLF_STRING CRLF_STRING);
3560                                                         
3561                                                         if (p == NULL)
3562                                                                 EM_DEBUG_EXCEPTION(" Incorrect parsing ");
3563                                                         else{
3564                                                                 p += strlen(CRLF_STRING CRLF_STRING);
3565                                                                 boundary_string = p;
3566                                                                 if (boundary_string[0] == CR){
3567                                                                         EM_DEBUG_EXCEPTION(" Incorrect Body structure ");
3568                                                                         goto NEXTUIDPARSING;
3569                                                                 }
3570                                                                 
3571                                                                 p = strstr(p, CRLF_STRING);
3572                                                                 
3573                                                                 if (p == NULL)
3574                                                                         EM_DEBUG_EXCEPTION(" Invalid parsing ");
3575                                                         }
3576                                                 }
3577                                         }                               
3578                                         else
3579                                                 no_alternative_part_flag = 1; 
3580
3581                                         if (no_alternative_part_flag){
3582                                                 p = strstr(bufsendforparse, "--");
3583
3584                                                 boundary_string = p;
3585                                                 if (boundary_string == NULL){
3586                                                         EM_DEBUG_EXCEPTION("Should not have come here ");
3587                                                         goto NEXTUIDPARSING;
3588                                                 }
3589                                                 
3590                                                 if (boundary_string[0] == CR){
3591                                                         EM_DEBUG_EXCEPTION(" Incorrect Body structure ");
3592                                                         goto NEXTUIDPARSING;
3593                                                 }
3594                                                 
3595                                                 p = strstr(p, CRLF_STRING);
3596                                                 if (p == NULL)
3597                                                         EM_DEBUG_EXCEPTION(" Invalid parsing ");
3598                                         }
3599                 
3600                                         /* EM_DEBUG_LOG("p[%s]", p); */
3601         
3602                                         if (p  != NULL){
3603                                                 *p = NULL_CHAR; /*  Boundary value set */
3604                                                 EM_DEBUG_LOG("Boundary value [%s]", boundary_string);
3605                                                 p  += 2; /*  p  points to content after boundary_string */
3606                         
3607                                                 if (((start_header = (char *)strcasestr(p, "Content-Type: text/html"))  != NULL) && (no_html  != 1) &&(((char *)strcasestr(p, "Content-Type: message/rfc822")) == NULL) &&
3608                                                         (((char *)strcasestr(p, "Content-Type: text/rfc822-headers")) == NULL))
3609                                                         emcore_parse_html_part_for_partial_body(start_header, boundary_string, bufsendforparse, text_html, body_size);
3610
3611                                                 if (((start_header = (char *)strcasestr(p, "Content-Type: text/plain"))  != NULL)) {
3612                                                         char *internal_boundary_string = NULL;
3613                                                         if(!emcore_find_boundary_string_of_the_part(bufsendforparse, start_header, &internal_boundary_string, &err)) {
3614                                                                 EM_DEBUG_EXCEPTION("internal_boundary_string failed [%d]", err);
3615                                                         }
3616
3617                                                         if(!internal_boundary_string)
3618                                                                 internal_boundary_string = EM_SAFE_STRDUP(boundary_string);
3619                                                                 
3620                                                         emcore_parse_plain_part_for_partial_body(p, start_header, internal_boundary_string, bufsendforparse, text_plain, body_size);
3621                                                         EM_SAFE_FREE(internal_boundary_string);
3622                                                 }
3623
3624                                                 if (((start_header = (char *)strcasestr((const char *)p, "Content-type: image/jpeg")) != (char *)NULL) ||
3625                                                         ((start_header = (char *)strcasestr((const char *)p, "Content-Type: image/jpg"))  != (char *)NULL) ||
3626                                                         ((start_header = (char *)strcasestr((const char *)p, "Content-Type: image/gif"))  != (char *)NULL) || 
3627                                                         ((start_header = (char *)strcasestr((const char *)p, "Content-Type: image/bmp"))  != (char *)NULL) ||
3628                                                         ((start_header = (char *)strcasestr((const char *)p, "Content-Type: image/png"))  != (char *)NULL))
3629                                                         emcore_parse_image_part_for_partial_body(p, start_header, boundary_string, bufsendforparse, image_data, body_size);
3630                                         }
3631                                 }
3632                                 
3633                                 /*  Updating mail information  */
3634                                 memset(buf, 0x00, sizeof(buf));
3635                         
3636                                 if (!emstorage_create_dir(pbd_event[temp_count].account_id, mail->mail_id, 0, &err))
3637                                         EM_DEBUG_EXCEPTION("emstorage_create_dir failed [%d]", err);
3638         
3639                                 if (!emstorage_get_save_name(pbd_event[temp_count].account_id, mail->mail_id, 0, 
3640                                                                         plain_charset_from_content_info ? plain_charset_from_content_info  :  "UTF-8", buf, &err)) 
3641                                         EM_DEBUG_EXCEPTION("emstorage_get_save_name failed [%d]", err);
3642         
3643                                 if (!emstorage_create_file(text_plain, strlen(text_plain), buf, &err))
3644                                         EM_DEBUG_EXCEPTION("emstorage_create_file failed [%d]", err);
3645
3646                                 mail->file_path_plain = EM_SAFE_STRDUP(buf); 
3647                                 EM_DEBUG_LOG("mail->file_path_plain [%s]", mail->file_path_plain);
3648
3649                                 if (image_data[0].text_image  != NULL && image_data[0].text_image[0]  != NULL_CHAR){
3650                                         char *result_string_of_replcaing = NULL;
3651                                         int store_file = 0;
3652                                         int content_index = 0;
3653
3654                                         temp_data_html = em_malloc(sizeof(char) * (input_download_size + 1));
3655
3656                                         if(!temp_data_html) {
3657                                                 EM_DEBUG_EXCEPTION("em_malloc failed");
3658                                                 err = EMAIL_ERROR_OUT_OF_MEMORY;
3659                                                 goto FINISH_OFF;
3660                                         }
3661
3662                                         memset(buf, 0x00, sizeof(buf));
3663                                         if (text_html[0]  != NULL_CHAR)
3664                                                 memcpy(temp_data_html, text_html, strlen(text_html));
3665                                                 /* EM_SAFE_STRNCPY(temp_data_html, text_html, text_html); */
3666
3667                                         do {
3668                                                 if (!emstorage_create_dir(pbd_event[temp_count].account_id, mail->mail_id, 0, &err))
3669                                                         EM_DEBUG_EXCEPTION("emstorage_create_dir failed [%d]", err);
3670
3671                                                 if (!emstorage_get_save_name(pbd_event[temp_count].account_id, mail->mail_id, 0, image_data[store_file].image_file_name, buf, &err)) 
3672                                                         EM_DEBUG_EXCEPTION("emstorage_get_save_name failed [%d]", err);
3673
3674                                                 if (!emstorage_create_file(image_data[store_file].text_image, image_data[store_file].dec_len, buf, &err))
3675                                                         EM_DEBUG_EXCEPTION("emstorage_create_file failed [%d]", err);
3676                                                 
3677                                                 if (mail->body_download_status  != EMAIL_BODY_DOWNLOAD_STATUS_PARTIALLY_DOWNLOADED){
3678                                                         memset(&attachment_tbl, 0x00, sizeof(emstorage_attachment_tbl_t));
3679                                                         attachment_tbl.mail_id                          = mail->mail_id;
3680                                                         attachment_tbl.account_id                       = pbd_event[temp_count].account_id;
3681                                                         attachment_tbl.mailbox_id                       = pbd_event[temp_count].mailbox_id;
3682                                                         attachment_tbl.attachment_name                  = image_data[store_file].image_file_name;
3683                                                         attachment_tbl.attachment_size                  = image_data[store_file].dec_len;
3684                                                         attachment_tbl.attachment_path                  = buf;
3685                                                         attachment_tbl.attachment_save_status           = 1;
3686                                                         attachment_tbl.attachment_inline_content_status = 1; /*  set to 1 for inline image */
3687                                                         attachment_tbl.attachment_mime_type             = image_data[store_file].mime_type;
3688                                                         mail->attachment_count++;
3689                                                         mail->inline_content_count++;
3690                                                         if (!emstorage_add_attachment (&attachment_tbl, false, false, &err))
3691                                                                 EM_DEBUG_EXCEPTION("emstorage_add_attachment failed - %d", err);                                                                        
3692                                                 }
3693                                                 
3694                                                 store_file++;
3695                                         } while (image_data[store_file].text_image  != NULL && image_data[store_file].text_image[0]  != NULL_CHAR && (store_file < IMAGE_DISPLAY_PARTIAL_BODY_COUNT));
3696                                         
3697                                         while (image_data[content_index].text_image  != NULL && image_data[content_index].text_image[0]  != NULL_CHAR &&
3698                                                   image_data[content_index].content_id && image_data[content_index].content_id[0]  != NULL_CHAR && (content_index < IMAGE_DISPLAY_PARTIAL_BODY_COUNT)){   /*  Finding CID in HTML and replacing with image name. */
3699                                                 result_string_of_replcaing = em_replace_string((char *)temp_data_html, (char *)image_data[content_index].content_id, (char *)image_data[content_index].image_file_name);
3700                                                 
3701                                                 EM_SAFE_STRNCPY(temp_data_html, result_string_of_replcaing, input_download_size);
3702                                                 EM_SAFE_FREE(result_string_of_replcaing);
3703
3704                                                 if (strstr(temp_data_html, image_data[content_index].content_id)  != NULL)
3705                                                         continue; /*  Replace content id on HTML with same file name one more time. */
3706                                                 
3707                                                 EM_SAFE_FREE(image_data[content_index].content_id);
3708                                                 EM_SAFE_FREE(image_data[content_index].text_image);
3709                                                 EM_SAFE_FREE(image_data[content_index].mime_type);
3710                                                 memset(image_data[content_index].image_file_name, 0x00, 100);
3711                                                 image_data[content_index].dec_len = 0;
3712                                                 content_index++;
3713                                         }
3714                                         
3715                                         image_length = 0;
3716                                         memset(text_html, 0, (input_download_size + 1));
3717                 
3718                                         if (temp_data_html[0]  != NULL_CHAR)
3719                                                 memcpy(text_html, temp_data_html, strlen(temp_data_html));
3720                                         memset(temp_data_html, 0x00, (input_download_size + 1));
3721
3722                                         EM_SAFE_FREE(temp_data_html);
3723                                 }
3724                                 
3725                                 if (strlen(text_html) > 0){
3726                                         memset(buf, 0x00, sizeof(buf));
3727                                         char html_body[MAX_CHARSET_VALUE] = {0x00, };
3728                                         if (plain_charset_from_content_info != NULL){
3729                                                 if (strlen(plain_charset_from_content_info) < MAX_CHARSET_VALUE)
3730                                                         memcpy(html_body, plain_charset_from_content_info, strlen(plain_charset_from_content_info));
3731                                                 else
3732                                                         memcpy(html_body, "UTF-8", strlen("UTF-8"));
3733                                         }
3734                                         if (html_body[0]  != NULL_CHAR)
3735                                                 strcat(html_body, HTML_EXTENSION_STRING);
3736                                         else
3737                                                 memcpy(html_body, "UTF-8.htm", strlen("UTF-8.htm"));
3738
3739                                         if (!emstorage_create_dir(pbd_event[temp_count].account_id, mail->mail_id, 0, &err))
3740                                                 EM_DEBUG_EXCEPTION("emstorage_create_dir failed [%d]", err);
3741
3742                                         if (!emstorage_get_save_name(pbd_event[temp_count].account_id, mail->mail_id, 0, html_body, buf, &err)) 
3743                                                 EM_DEBUG_EXCEPTION("emstorage_get_save_name failed [%d]", err);
3744
3745                                         if (!emstorage_create_file(text_html, strlen(text_html), buf, &err))
3746                                                 EM_DEBUG_EXCEPTION("emstorage_create_file failed [%d]", err);
3747
3748                                         mail->file_path_html = EM_SAFE_STRDUP(buf); 
3749                                                         
3750                                 }
3751         
3752                                 mail->body_download_status = (total_mail_size_except_attach < input_download_size) ? 1 : 2;
3753                                 EM_DEBUG_LOG("total_mail_size_except_attach [%d], mail->body_download_status [%d]", total_mail_size_except_attach, mail->body_download_status); 
3754
3755                                 /* Get preview text */ 
3756                                 if ( (err = emcore_get_preview_text_from_file(mail->file_path_plain, mail->file_path_html, MAX_PREVIEW_TEXT_LENGTH, &(mail->preview_text))) != EMAIL_ERROR_NONE)
3757                                         EM_DEBUG_EXCEPTION("emcore_get_preview_text_from_file() failed[%d]", err);
3758                                 
3759                                 /* Update body contents */
3760                                 if (!emstorage_change_mail_field(mail->mail_id, UPDATE_PARTIAL_BODY_DOWNLOAD, mail, true, &err))
3761                                         EM_DEBUG_EXCEPTION("emstorage_change_mail_field failed - %d", err);
3762                                 
3763 NEXTUIDPARSING: 
3764
3765                                 response_buffer = response_buffer + body_size; /*  Set pointer for next mail body.  */
3766         
3767                                 /*  Find end of body */
3768                                 if ((response_buffer[0] == CR) && (response_buffer[1] == LF)&& (response_buffer[2] == ')')
3769                                         && (response_buffer[3] == CR) && (response_buffer[4] == LF)){
3770                                         response_buffer = response_buffer + 5;
3771                                         total_parsed_len_per_uid = body_size+tempmailparselen + 5;
3772                                 }
3773                                 else if ((response_buffer[0] == ')') && (response_buffer[1] == CR) && (response_buffer[2] == LF)){
3774                                         response_buffer = response_buffer + 3;
3775                                         total_parsed_len_per_uid = body_size+tempmailparselen + 3;
3776                                 }
3777                                 else
3778                                         EM_DEBUG_EXCEPTION("Mail response end could not found, - %c : %c : %c", response_buffer[0], response_buffer[1], response_buffer[2]);
3779                         
3780                                 EM_SAFE_FREE(bufsendforparse);
3781                                 
3782                                 memset(text_html, 0, input_download_size+1);
3783                                 memset(text_plain, 0, input_download_size+1);
3784                                 memset(temp_text_buf, 0, input_download_size+1);
3785
3786                                 if (mail)
3787                                         emstorage_free_mail(&mail, 1, NULL);
3788                                 
3789                                 /*  Free the activity for mail id in partial body activity table */
3790                                 if (false == emcore_delete_pbd_activity(pbd_event[temp_count].account_id, pbd_event[temp_count].mail_id, pbd_event[temp_count].activity_id, &err)){
3791                                         EM_DEBUG_EXCEPTION("emcore_delete_pbd_activity failed [%d]", err);
3792                                         goto FINISH_OFF;
3793                                 }
3794                         }
3795                         
3796                         total_parsed_len  += total_parsed_len_per_uid;
3797                 }
3798         } 
3799
3800         EM_DEBUG_LOG("imap_response buflen is [%d]", imap_response->buflen);
3801         ret = true;
3802         
3803 FINISH_OFF: 
3804
3805         if (error)
3806                 *error = err;
3807
3808         if (true != ret)
3809                 EM_DEBUG_EXCEPTION("Failed download for the uid list %s", command);
3810
3811         if(reply_from_server) {
3812                 EM_SAFE_FREE(reply_from_server->key);
3813                 EM_SAFE_FREE(reply_from_server->line);
3814                 EM_SAFE_FREE(reply_from_server->tag);
3815                 EM_SAFE_FREE(reply_from_server->text);
3816                 EM_SAFE_FREE(reply_from_server);
3817         }
3818
3819         EM_SAFE_FREE(text_plain);
3820         EM_SAFE_FREE(text_html);
3821         EM_SAFE_FREE(temp_text_buf);
3822
3823         EM_SAFE_FREE(bufsendforparse);
3824         EM_SAFE_FREE(plain_text_file_name_from_content_info);
3825         EM_SAFE_FREE(html_text_file_name_from_content_info);
3826         EM_SAFE_FREE(plain_charset_from_content_info);
3827
3828         if (cnt_info)
3829                 emcore_free_content_info(cnt_info);
3830
3831         if (body)
3832                 mail_free_body(&body);
3833
3834         if (imap_response)
3835                 EM_SAFE_FREE(imap_response->buffer);    
3836         EM_SAFE_FREE(imap_response);    
3837
3838         if (mail)
3839                 emstorage_free_mail(&mail, 1, NULL);
3840         
3841         EM_DEBUG_FUNC_END("ret [%d]", ret);     
3842         return ret;
3843 }
3844
3845 INTERNAL_FUNC int emcore_download_bulk_partial_mail_body_for_pop3(MAILSTREAM *stream, int input_download_size, email_event_partial_body_thd *pbd_event, int item_count, int *error)
3846 {
3847         EM_DEBUG_FUNC_BEGIN("stream [%p], pbd_event [%p], item_count [%d], error [%p]", stream, pbd_event, item_count, error);
3848         int ret = false, err = EMAIL_ERROR_NONE;
3849         int i; 
3850
3851         if (!stream || !pbd_event) {
3852                 EM_DEBUG_EXCEPTION("EMAIL_ERROR_INVALID_PARAM");
3853                 err = EMAIL_ERROR_INVALID_PARAM;                
3854                 goto FINISH_OFF;
3855         }
3856         
3857         for (i = 0; i < item_count; i++) {              
3858                 EM_DEBUG_LOG("pbd_event[%d].account_id [%d], mail_id [%d], server_mail_id [%d], activity_id [%d]", \
3859                         i, pbd_event[i].account_id, pbd_event[i].mail_id, pbd_event[i].server_mail_id, pbd_event[i].activity_id);               
3860
3861                 if (!emcore_download_body_multi_sections_bulk(stream, pbd_event[i].account_id, pbd_event[i].mail_id, false, false, input_download_size, 0 , &err)){
3862                         EM_DEBUG_EXCEPTION("emcore_download_body_multi_sections_bulk failed");
3863                         goto FINISH_OFF;
3864                 }
3865                 
3866                 if (false == emcore_delete_pbd_activity(pbd_event[i].account_id, pbd_event[i].mail_id, pbd_event[i].activity_id, &err)){
3867                         EM_DEBUG_EXCEPTION("emcore_delete_pbd_activity failed [%d]", err);
3868                         goto FINISH_OFF;
3869                 }
3870         }       
3871
3872         ret = true;
3873
3874 FINISH_OFF: 
3875         if (error)
3876                 *error = err;
3877
3878         EM_DEBUG_FUNC_END("ret [%d] err [%d]", ret, err);       
3879         return ret;
3880 }
3881
3882
3883
3884 INTERNAL_FUNC int emcore_download_bulk_partial_mail_body(MAILSTREAM *stream, email_event_partial_body_thd *pbd_event, int item_count, int *error)
3885 {
3886         EM_DEBUG_FUNC_BEGIN("stream [%p], pbd_event [%p], item_count [%d], error [%p]", stream, pbd_event, item_count, error);
3887         int ret = false, err = EMAIL_ERROR_NONE;
3888         emstorage_account_tbl_t *pbd_account_tbl = NULL;
3889         int auto_download_size = 0;
3890
3891         if (!stream || !pbd_event) {
3892                 EM_DEBUG_EXCEPTION("EMAIL_ERROR_INVALID_PARAM");
3893                 err = EMAIL_ERROR_INVALID_PARAM;                
3894                 goto FINISH_OFF;
3895         }
3896
3897         if (!emstorage_get_account_by_id(pbd_event[0].account_id, EMAIL_ACC_GET_OPT_DEFAULT, &pbd_account_tbl, true, &err)) {
3898                 EM_DEBUG_EXCEPTION("emstorage_get_account_by_id failed [%d]", err);
3899                 goto FINISH_OFF;
3900         }
3901
3902         auto_download_size = (pbd_account_tbl->auto_download_size<4096)?4096:pbd_account_tbl->auto_download_size;
3903
3904         switch (pbd_account_tbl->incoming_server_type){
3905                 case EMAIL_SERVER_TYPE_IMAP4:
3906                         ret = emcore_download_bulk_partial_mail_body_for_imap(stream, auto_download_size, pbd_event, item_count, &err);
3907                         break;
3908                 case EMAIL_SERVER_TYPE_POP3: 
3909                         ret = emcore_download_bulk_partial_mail_body_for_pop3(stream, auto_download_size, pbd_event, item_count, &err);
3910                         break;
3911                 default: 
3912                         err = EMAIL_ERROR_NOT_SUPPORTED;
3913                         ret = false;
3914                         break;
3915         }       
3916
3917         ret = true;
3918 FINISH_OFF: 
3919         if (error)
3920                 *error = err;
3921
3922         EM_DEBUG_FUNC_END("ret [%d] err [%d]", ret, err);       
3923         return ret;
3924 }
3925
3926
3927 static email_partial_buffer *emcore_get_response_from_server (NETSTREAM *nstream, char *tag, IMAPPARSEDREPLY **reply, int input_download_size)
3928 {
3929         EM_DEBUG_FUNC_BEGIN();
3930
3931         if (!nstream || !tag || !reply){
3932                 EM_DEBUG_EXCEPTION("EMAIL_ERROR_INVALID_PARAM");
3933                 return NIL;
3934         }
3935
3936         email_partial_buffer *retPartialBuffer = NULL;
3937         IMAPPARSEDREPLY *ret_reply = NULL;
3938         char *pline = NULL;
3939         int linelen = 0;
3940         int bytes_copied = 0;
3941         int temp_body_buffer_size = 0;
3942         int flags = 0;
3943         int allocated_buffer_size = (BULK_PARTIAL_BODY_DOWNLOAD_COUNT + 2) * input_download_size ;
3944
3945         retPartialBuffer = (email_partial_buffer *)em_malloc(sizeof(email_partial_buffer));
3946
3947         if (NULL == retPartialBuffer){
3948                 EM_DEBUG_EXCEPTION("em_malloc failed");
3949                 return NIL;
3950         }
3951
3952         retPartialBuffer->buffer = (char *)em_malloc(allocated_buffer_size);
3953
3954         if (NULL == retPartialBuffer->buffer){
3955                 EM_DEBUG_EXCEPTION("em_malloc failed");
3956                 EM_SAFE_FREE(retPartialBuffer);
3957                 return NIL;
3958         }
3959
3960         while (nstream){        
3961                 if (!(pline = net_getline(nstream))) {
3962                         EM_DEBUG_EXCEPTION("net_getline failed...");
3963                         EM_SAFE_FREE(retPartialBuffer->buffer);
3964                         EM_SAFE_FREE(retPartialBuffer);
3965
3966                         return NIL;
3967                 }
3968         
3969                 linelen = strlen(pline);
3970                 
3971                 if (strcasestr(pline, "BODYSTRUCTURE") != NULL) {
3972                         temp_body_buffer_size = 0;
3973                         flags = 0;
3974                 } else {
3975                         temp_body_buffer_size = temp_body_buffer_size + linelen + 2;
3976                 }
3977
3978                 if (temp_body_buffer_size > input_download_size && !flags) {
3979                         linelen = linelen - (temp_body_buffer_size - input_download_size) + 2;
3980                         temp_body_buffer_size = input_download_size;
3981                         flags = 1;
3982                 }       
3983
3984                 if (temp_body_buffer_size <= input_download_size) {
3985                         memcpy(retPartialBuffer->buffer + bytes_copied, pline, linelen);
3986                         bytes_copied  += linelen;
3987                         memcpy(retPartialBuffer->buffer + bytes_copied, CRLF_STRING, 2);
3988                         bytes_copied += 2;                              
3989                 } 
3990                                 
3991                 if (0 == strncmp(pline, tag, strlen(tag))) {
3992
3993                         ret_reply = em_malloc(sizeof(IMAPPARSEDREPLY));
3994
3995                         if (!ret_reply){
3996                                 EM_DEBUG_EXCEPTION("em_malloc failed");
3997                                 return NIL;
3998                         }
3999
4000                         if(reply)
4001                                 *reply = ret_reply;
4002         
4003                         if (0 == strncmp(pline + strlen(tag) + 1, "OK", 2)) {
4004                                 ret_reply->line = (unsigned char*)EM_SAFE_STRDUP(tag);
4005                                 ret_reply->tag  = (unsigned char*)EM_SAFE_STRDUP(tag);
4006                                 ret_reply->key  = (unsigned char*)EM_SAFE_STRDUP("OK");
4007                                 ret_reply->text = (unsigned char*)EM_SAFE_STRDUP("Success");
4008                                 EM_SAFE_FREE(pline);    
4009                                 break;
4010                         }
4011                         else {
4012                                 EM_DEBUG_EXCEPTION("Tagged Response not OK. IMAP4 Response -> [%s]", pline);    
4013                                 ret_reply->line = (unsigned char*)EM_SAFE_STRDUP(tag);
4014                                 ret_reply->tag  = (unsigned char*)EM_SAFE_STRDUP(tag);
4015                                 ret_reply->key  = (unsigned char*)EM_SAFE_STRDUP("NO");
4016                                 ret_reply->text = (unsigned char*)EM_SAFE_STRDUP("Fail");
4017
4018                                 EM_SAFE_FREE(pline);
4019                                 EM_SAFE_FREE(retPartialBuffer->buffer);
4020                                 EM_SAFE_FREE(retPartialBuffer);
4021                                 
4022                                 return NIL;
4023                         }       
4024
4025                         EM_DEBUG_LOG("ret_reply->line [%s]", ret_reply->line);
4026                         EM_DEBUG_LOG("ret_reply->tag [%s]",  ret_reply->tag);
4027                         EM_DEBUG_LOG("ret_reply->key [%s]",  ret_reply->key);
4028                         EM_DEBUG_LOG("ret_reply->text [%s]", ret_reply->text);
4029         
4030                 }       
4031                 EM_SAFE_FREE(pline);            
4032         }
4033         
4034         retPartialBuffer->buflen = strlen(retPartialBuffer->buffer);
4035         
4036         EM_DEBUG_FUNC_END("retPartialBuffer [%p]", retPartialBuffer);   
4037         return retPartialBuffer;
4038 }
4039                 
4040 #endif /*  __FEATURE_PARTIAL_BODY_DOWNLOAD__ */
4041 /* EOF */