summaryrefslogtreecommitdiff
path: root/email-common-use/email-utilities.c
diff options
context:
space:
mode:
authorYeongil Jang <yg0577.jang@samsung.com>2012-09-21 00:18:57 +0900
committerYeongil Jang <yg0577.jang@samsung.com>2012-09-21 00:18:57 +0900
commitb163391a122d812058dc9ab211b81e60204fffc7 (patch)
tree0fdf86bf4dc67b14c8913f8fa01d4e6270b1ea39 /email-common-use/email-utilities.c
parent4a95e692f2a57a0c273b2ce1f255be9a7ba1d2e3 (diff)
downloademail-service-2.0alpha.tar.gz
email-service-2.0alpha.tar.bz2
email-service-2.0alpha.zip
Diffstat (limited to 'email-common-use/email-utilities.c')
-rwxr-xr-xemail-common-use/email-utilities.c1722
1 files changed, 1079 insertions, 643 deletions
diff --git a/email-common-use/email-utilities.c b/email-common-use/email-utilities.c
index 5cebaf9..d5ba501 100755
--- a/email-common-use/email-utilities.c
+++ b/email-common-use/email-utilities.c
@@ -1,643 +1,1079 @@
-/*
-* email-service
-*
-* Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved.
-*
-* Contact: Kyuho Jo <kyuho.jo@samsung.com>, Sunghyun Kwon <sh0701.kwon@samsung.com>
-*
-* Licensed under the Apache License, Version 2.0 (the "License");
-* you may not use this file except in compliance with the License.
-* You may obtain a copy of the License at
-*
-* http://www.apache.org/licenses/LICENSE-2.0
-*
-* Unless required by applicable law or agreed to in writing, software
-* distributed under the License is distributed on an "AS IS" BASIS,
-* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-* See the License for the specific language governing permissions and
-* limitations under the License.
-*
-*/
-
-/*
- * email-utilities.c
- *
- * Created on: 2012. 3. 6.
- * Author: kyuho.jo@samsung.com
- */
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <ctype.h>
-#include <errno.h>
-#include <sys/time.h>
-#include <sys/vfs.h>
-#include <unistd.h>
-#include <malloc.h>
-#include <pthread.h>
-#include <regex.h>
-
-#include "c-client.h"
-
-#include "email-types.h"
-#include "email-internal-types.h"
-#include "email-utilities.h"
-
-INTERNAL_FUNC void* em_malloc(unsigned len)
-{
- /* EM_DEBUG_LOG("Memory allocation size[%d] bytes", len); */
- void *p = NULL;
-
- if (len <= 0) {
- EM_DEBUG_EXCEPTION("len should be positive.[%d]", len);
- return NULL;
- }
-
- p = malloc(len);
-
- if (p)
- memset(p, 0x00, len);
- else
- EM_DEBUG_EXCEPTION("malloc failed");
- return p;
-}
-
-/* remove left space, tab, CR, L */
-INTERNAL_FUNC char *em_trim_left(char *str)
-{
- char *p, *temp_buffer = NULL;
-
- /* EM_DEBUG_FUNC_BEGIN() */
- if (!str) return NULL;
-
- p = str;
- while (*p && (*p == ' ' || *p == '\t' || *p == LF || *p == CR)) p++;
-
- if (!*p) return NULL;
-
- temp_buffer = EM_SAFE_STRDUP(p);
-
- strncpy(str, temp_buffer, strlen(str));
- str[strlen(temp_buffer)] = NULL_CHAR;
-
- EM_SAFE_FREE(temp_buffer);
-
- return str;
-}
-
-/* remove right space, tab, CR, L */
-INTERNAL_FUNC char *em_trim_right(char *str)
-{
- char *p;
-
- /* EM_DEBUG_FUNC_BEGIN() */
- if (!str) return NULL;
-
- p = str+strlen(str)-1;
- while (((int)p >= (int)str) && (*p == ' ' || *p == '\t' || *p == LF || *p == CR))
- *p --= '\0';
-
- if ((int) p < (int)str)
- return NULL;
-
- return str;
-}
-
-INTERNAL_FUNC char* em_upper_string(char *str)
-{
- char *p = str;
- while (*p) {
- *p = toupper(*p);
- p++;
- }
- return str;
-}
-
-INTERNAL_FUNC char* em_lower_string(char *str)
-{
- char *p = str;
- while (*p) {
- *p = tolower(*p);
- p++;
- }
- return str;
-}
-
-INTERNAL_FUNC int em_upper_path(char *path)
-{
- int i = 0, is_utf7 = 0, len = path ? (int)strlen(path) : -1;
- for (; i < len; i++) {
- if (path[i] == '&' || path[i] == 5) {
- is_utf7 = 1;
- }
- else {
- if (is_utf7) {
- if (path[i] == '-') is_utf7 = 0;
- }
- else {
- path[i] = toupper(path[i]);
- }
- }
- }
-
- return 1;
-}
-
-INTERNAL_FUNC void em_skip_whitespace(char *addr_str, char **pAddr)
-{
- EM_DEBUG_FUNC_BEGIN("addr_str[%p]", addr_str);
-
- if (!addr_str)
- return ;
- char *str = addr_str;
- char ptr[strlen(str)+1] ;
- int i, j = 0;
-
- str = addr_str ;
- for (i = 0; str[i] != NULL_CHAR ; i++) {
- if (str[i] != SPACE && str[i] != TAB && str[i] != CR && str[i] != LF)
- ptr[j++] = str[i];
- }
- ptr[j] = NULL_CHAR;
-
- *pAddr = EM_SAFE_STRDUP(ptr);
- EM_DEBUG_FUNC_END("ptr[%s]", ptr);
-}
-
-INTERNAL_FUNC char* em_skip_whitespace_without_strdup(char *source_string)
-{
- EM_DEBUG_FUNC_BEGIN("source_string[%p]", source_string);
-
- if (!source_string)
- return NULL;
- int i;
-
- for (i = 0; source_string[i] != NULL_CHAR ; i++) {
- if (source_string[i] != SPACE) /* || source_string[i] != TAB || source_string[i] != CR || source_string[i] || LF) */
- break;
- }
-
- EM_DEBUG_FUNC_END("i[%d]", i);
- return source_string + i;
-}
-
-INTERNAL_FUNC char* em_replace_string(char *source_string, char *old_string, char *new_string)
-{
- EM_DEBUG_FUNC_BEGIN();
- char *result_buffer = NULL;
- char *p = NULL;
- int buffer_length = 0;
-
- EM_IF_NULL_RETURN_VALUE(source_string, NULL);
- EM_IF_NULL_RETURN_VALUE(old_string, NULL);
- EM_IF_NULL_RETURN_VALUE(new_string, NULL);
-
- p = strstr(source_string, old_string);
-
- if (p == NULL) {
- EM_DEBUG_EXCEPTION("old_string not found in source_string");
- EM_DEBUG_FUNC_END("return NULL");
- return NULL;
- }
-
- buffer_length = strlen(source_string) + 1024;
- result_buffer = (char *)em_malloc(buffer_length);
-
- if (!result_buffer) {
- EM_DEBUG_EXCEPTION("em_malloc failed");
- return NULL;
- }
-
- strncpy(result_buffer, source_string, p - source_string);
- snprintf(result_buffer + strlen(result_buffer), buffer_length - strlen(result_buffer), "%s%s", new_string, p + strlen(old_string));
-
- EM_DEBUG_FUNC_END("result_buffer[%s]", result_buffer);
- return result_buffer;
-}
-
-/* Memory clean up */
-#include <sys/mman.h>
-
-/* #define GETSP() ({ unsigned int sp; asm volatile ("mov %0, sp " : "=r"(sp)); sp;}) */
-#define BUF_SIZE 256
-#define PAGE_SIZE (1 << 12)
-#define _ALIGN_UP(addr, size) (((addr)+((size)-1))&(~((size)-1)))
-#define _ALIGN_DOWN(addr, size) ((addr)&(~((size)-1)))
-#define PAGE_ALIGN(addr) _ALIGN_DOWN(addr, PAGE_SIZE)
-
-int stack_trim(void)
-{
- /*
- char buf[BUF_SIZE];
- FILE *file;
- unsigned int stacktop;
- int found = 0;
- unsigned int sp;
-
- asm volatile ("mov %0, sp " : "=r"(sp));
-
- sprintf(buf, "/proc/%d/maps", getpid());
- file = fopen(buf, "r");
- while (fgets(buf, BUF_SIZE, file) != NULL) {
- if (strstr(buf, "[stack]")) {
- found = 1;
- break;
- }
- }
-
- fclose(file);
-
- if (found) {
- sscanf(buf, "%x-", &stacktop);
- if (madvise((void *)PAGE_ALIGN(stacktop), PAGE_ALIGN(sp)-stacktop, MADV_DONTNEED) < 0)
- perror("stack madvise fail");
- }
- */
- return 1;
-}
-
-INTERNAL_FUNC void em_flush_memory()
-{
- EM_DEBUG_FUNC_BEGIN();
- /* flush memory in heap */
- malloc_trim(0);
-
- /* flush memory in stack */
- stack_trim();
-
- /* flush memory for sqlite */
- emstorage_flush_db_cache();
- EM_DEBUG_FUNC_END();
-}
-
-#define DATE_TIME_STRING_LEGNTH 14
-
-INTERNAL_FUNC char *em_get_extension_from_file_path(char *source_file_path, int *err_code)
-{
- EM_DEBUG_FUNC_BEGIN("source_file_path[%s]", source_file_path);
- int err = EMF_ERROR_NONE, pos_on_string = 0;
- char *extension = NULL;
-
- if (!source_file_path) {
- EM_DEBUG_EXCEPTION("Invalid Parameter");
- err = EMF_ERROR_INVALID_PARAM;
- goto FINISH_OFF;
- }
-
- pos_on_string = strlen(source_file_path) - 1;
-
- while(pos_on_string > 0 && source_file_path[pos_on_string--] != '.') ;
-
- if(pos_on_string > 0)
- extension = source_file_path + pos_on_string + 2;
-
- EM_DEBUG_LOG("*extension [%s] pos_on_string [%d]", extension, pos_on_string);
-
-FINISH_OFF:
- if (err_code)
- *err_code = err;
- EM_DEBUG_FUNC_END();
- return extension;
-}
-
-INTERNAL_FUNC int em_get_encoding_type_from_file_path(const char *input_file_path, char **output_encoding_type)
-{
- EM_DEBUG_FUNC_BEGIN("input_file_path[%d], output_encoding_type[%p]", input_file_path, output_encoding_type);
- int err = EMF_ERROR_NONE;
- int pos_of_filename = 0;
- int pos_of_dot = 0;
- int enf_of_string = 0;
- int result_string_length = 0;
- char *filename = NULL;
- char *result_encoding_type = NULL;
-
- if (!input_file_path || !output_encoding_type) {
- EM_DEBUG_EXCEPTION("Invalid Parameter");
- err = EMF_ERROR_INVALID_PARAM;
- goto FINISH_OFF;
- }
-
- enf_of_string = pos_of_filename = strlen(input_file_path) - 1;
-
- while(pos_of_filename >= 0 && input_file_path[pos_of_filename--] != '/') {
- if(input_file_path[pos_of_filename] == '.')
- pos_of_dot = pos_of_filename;
- }
-
- if(pos_of_filename != 0)
- pos_of_filename += 2;
-
- filename = (char*)input_file_path + pos_of_filename;
-
- if(pos_of_dot != 0 && pos_of_dot > pos_of_filename)
- result_string_length = pos_of_dot - pos_of_filename;
- else
- result_string_length = enf_of_string - pos_of_filename;
-
- EM_DEBUG_LOG("pos_of_dot [%d], pos_of_filename [%d], enf_of_string[%d],result_string_length [%d]", pos_of_dot, pos_of_filename, enf_of_string, result_string_length);
-
- if( !(result_encoding_type = em_malloc(sizeof(char) * (result_string_length + 1))) ) {
- EM_DEBUG_EXCEPTION("EMF_ERROR_OUT_OF_MEMORY");
- err = EMF_ERROR_OUT_OF_MEMORY;
- goto FINISH_OFF;
- }
-
- memcpy(result_encoding_type, input_file_path + pos_of_filename, result_string_length);
-
- EM_DEBUG_LOG("*result_encoding_type [%s]", result_encoding_type);
-
- *output_encoding_type = result_encoding_type;
-
-FINISH_OFF:
- EM_DEBUG_FUNC_END("err [%d]", err);
- return err;
-}
-
-INTERNAL_FUNC int em_get_content_type_from_extension_string(const char *extension_string, int *err_code)
-{
- EM_DEBUG_FUNC_BEGIN("extension_string[%s]", extension_string);
- int i = 0, err = EMF_ERROR_NONE, result_content_type = TYPEAPPLICATION;
- char *image_extension[] = { "jpeg", "jpg", "png", "gif", "bmp", "pic", "agif", "tif", "wbmp" , NULL};
-
- if (!extension_string) {
- EM_DEBUG_EXCEPTION("Invalid Parameter");
- err = EMF_ERROR_INVALID_PARAM;
- goto FINISH_OFF;
- }
-
- while(image_extension[i]) {
- EM_DEBUG_LOG("image_extension[%d] [%s]", i, image_extension[i]);
- if(strcasecmp(image_extension[i], extension_string) == 0) {
- result_content_type = TYPEIMAGE;
- break;
- }
- i++;
- }
-
-FINISH_OFF:
- if (err_code)
- *err_code = err;
- EM_DEBUG_FUNC_END();
- return result_content_type;
-}
-
-#define EMAIL_ACCOUNT_RGEX "([a-z0-9!#$%&'*+/=?^_`{|}~-]+.)*[a-z0-9!#$%&'*+/=?^_`{|}~-]+"
-#define EMAIL_DOMAIN_RGEX "([a-z0-9!#$%&'*+/=?^_`{|}~-]+.)+[a-z0-9!#$%&'*+/=?^_`{|}~-]+"
-
-#define EMAIL_ADDR_RGEX "[[:space:]]*<"EMAIL_ACCOUNT_RGEX"@"EMAIL_DOMAIN_RGEX">[[:space:]]*"
-#define EMAIL_ALIAS_RGEX "([[:space:]]*\"[^\"]*\")?"EMAIL_ADDR_RGEX
-#define EMAIL_ALIAS_LIST_RGEX "^("EMAIL_ALIAS_RGEX"[;,])*"EMAIL_ALIAS_RGEX"[;,]?[[:space:]]*$"
-
-#define EMAIL_ADDR_WITHOUT_BRACKET_RGEX "[[:space:]]*"EMAIL_ACCOUNT_RGEX"@"EMAIL_DOMAIN_RGEX"[[:space:]]*"
-#define EMAIL_ALIAS_WITHOUT_BRACKET_RGEX "([[:space:]]*\"[^\"]*\")?"EMAIL_ADDR_WITHOUT_BRACKET_RGEX
-#define EMAIL_ALIAS_LIST_WITHOUT_BRACKET_RGEX "("EMAIL_ALIAS_WITHOUT_BRACKET_RGEX"[;,])*"EMAIL_ADDR_WITHOUT_BRACKET_RGEX"[;,]?[[:space:]]*$"
-
-INTERNAL_FUNC int em_verify_email_address(char *address, int without_bracket, int *err_code)
-{
- EM_DEBUG_FUNC_BEGIN("address[%s] without_bracket[%d]", address, without_bracket);
-
- /* this following code verfies the email alias string using reg. exp. */
- regex_t alias_list_regex = {0};
- int ret = false, error = EMF_ERROR_NONE;
- char *reg_rule = NULL;
-
- if(!address || strlen(address) == 0) {
- EM_DEBUG_EXCEPTION("EMF_ERROR_INVALID_PARAM");
- if (err_code)
- *err_code = EMF_ERROR_INVALID_PARAM;
- return false;
- }
-
- if(without_bracket)
- reg_rule = EMAIL_ALIAS_LIST_WITHOUT_BRACKET_RGEX;
- else
- reg_rule = EMAIL_ALIAS_LIST_RGEX;
-
- if (regcomp(&alias_list_regex, reg_rule, REG_ICASE | REG_EXTENDED)) {
- EM_DEBUG_EXCEPTION("email alias regex unrecognized");
- if (err_code)
- *err_code = EMF_ERROR_UNKNOWN;
- return false;
- }
-
- int alias_len = strlen(address) + 1;
- regmatch_t pmatch[alias_len];
-
- bzero(pmatch, alias_len);
-
- if (regexec(&alias_list_regex, address, alias_len, pmatch, 0) == REG_NOMATCH)
- EM_DEBUG_LOG("failed :[%s]", address);
- else {
- EM_DEBUG_LOG("success :[%s]", address);
- ret = true;
- }
-
- regfree(&alias_list_regex);
-
- if (err_code)
- *err_code = error;
-
- EM_DEBUG_FUNC_END("ret [%d]", ret);
- return ret;
-}
-
-INTERNAL_FUNC int em_verify_email_address_of_mail_data(emf_mail_data_t *mail_data, int without_bracket, int *err_code)
-{
- EM_DEBUG_FUNC_BEGIN("mail_data[%p] without_bracket[%d]", mail_data, without_bracket);
- char *address_array[4] = { mail_data->full_address_from, mail_data->full_address_to, mail_data->full_address_cc, mail_data->full_address_bcc};
- int ret = false, err = EMF_ERROR_NONE, i;
-
- /* check for email_address validation */
- for (i = 0; i < 4; i++) {
- if (address_array[i] && address_array[i][0] != 0) {
- if (!em_verify_email_address(address_array[i] , without_bracket, &err)) {
- err = EMF_ERROR_INVALID_ADDRESS;
- EM_DEBUG_EXCEPTION("Invalid Email Address [%d][%s]", i, address_array[i]);
- goto FINISH_OFF;
- }
- }
- }
- ret = true;
-FINISH_OFF:
- EM_DEBUG_FUNC_END("ret [%d]", ret);
- return ret;
-}
-
-INTERNAL_FUNC int em_verify_email_address_of_mail_tbl(emstorage_mail_tbl_t *input_mail_tbl, int input_without_bracket)
-{
- EM_DEBUG_FUNC_BEGIN("input_mail_tbl[%p] input_without_bracket[%d]", input_mail_tbl, input_without_bracket);
- char *address_array[4] = { input_mail_tbl->full_address_to, input_mail_tbl->full_address_cc, input_mail_tbl->full_address_bcc, input_mail_tbl->full_address_from};
- int err = EMF_ERROR_NONE, i;
-
- /* check for email_address validation */
- for (i = 0; i < 4; i++) {
- if (address_array[i] && address_array[i][0] != 0) {
- if (!em_verify_email_address(address_array[i] , input_without_bracket, &err)) {
- err = EMF_ERROR_INVALID_ADDRESS;
- EM_DEBUG_EXCEPTION("Invalid Email Address [%d][%s]", i, address_array[i]);
- goto FINISH_OFF;
- }
- }
- }
-
-FINISH_OFF:
- EM_DEBUG_FUNC_END("err [%d]", err);
- return err;
-}
-
-INTERNAL_FUNC int em_find_tag_for_thread_view(char *subject, int *result)
-{
- EM_DEBUG_FUNC_BEGIN();
- int error_code = EMF_ERROR_NONE;
- char *copy_of_subject = NULL;
-
- EM_IF_NULL_RETURN_VALUE(subject, EMF_ERROR_INVALID_PARAM);
- EM_IF_NULL_RETURN_VALUE(result, EMF_ERROR_INVALID_PARAM);
-
- *result = FALSE;
-
- copy_of_subject = EM_SAFE_STRDUP(subject);
-
- if (copy_of_subject == NULL) {
- EM_DEBUG_EXCEPTION("strdup is failed.");
- goto FINISH_OFF;
- }
-
- em_upper_string(copy_of_subject);
- EM_DEBUG_LOG("em_upper_string result : %s\n", copy_of_subject);
-
- if (strstr(copy_of_subject, "RE:") == NULL) {
- if (strstr(copy_of_subject, "FWD:") == NULL) {
- if (strstr(copy_of_subject, "FW:") != NULL)
- *result = TRUE;
- }
- else
- *result = TRUE;
- }
- else
- *result = TRUE;
-
-FINISH_OFF:
- EM_SAFE_FREE(copy_of_subject);
-
- EM_DEBUG_FUNC_END("result : %d", *result);
-
- return error_code;
-}
-
-INTERNAL_FUNC int em_find_pos_stripped_subject_for_thread_view(char *subject, char *stripped_subject)
-{
- EM_DEBUG_FUNC_BEGIN();
- int error_code = EMF_ERROR_NONE;
- int gap;
- char *copy_of_subject = NULL, *curpos = NULL, *result;
-
- EM_IF_NULL_RETURN_VALUE(subject, EMF_ERROR_INVALID_PARAM);
- EM_IF_NULL_RETURN_VALUE(stripped_subject, EMF_ERROR_INVALID_PARAM);
-
- copy_of_subject = EM_SAFE_STRDUP(subject);
-
- if (copy_of_subject == NULL) {
- EM_DEBUG_EXCEPTION("strdup is failed");
- goto FINISH_OFF;
- }
-
- em_upper_string(copy_of_subject);
- curpos = copy_of_subject;
-
- EM_DEBUG_LOG("em_upper_string result : %s", copy_of_subject);
-
- while ((result = strstr(curpos, "RE:")) != NULL) {
- curpos = result + 3;
- EM_DEBUG_LOG("RE result : %s", curpos);
- }
-
- while ((result = strstr(curpos, "FWD:")) != NULL) {
- curpos = result + 4;
- EM_DEBUG_LOG("FWD result : %s", curpos);
- }
-
- while ((result = strstr(curpos, "FW:")) != NULL) {
- curpos = result + 3;
- EM_DEBUG_LOG("FW result : %s", curpos);
- }
-
- while (curpos != NULL && *curpos == ' ') {
- curpos++;
- }
-
- gap = curpos - copy_of_subject;
-
- strcpy(stripped_subject, subject + gap);
-
-FINISH_OFF:
- EM_SAFE_FREE(copy_of_subject);
-
- if (error_code == EMF_ERROR_NONE && stripped_subject)
- EM_DEBUG_LOG("result[%s]", stripped_subject);
-
- EM_DEBUG_FUNC_END("error_code[%d]", error_code);
- return error_code;
-}
-
-
-/*
- * encoding base64
- */
-INTERNAL_FUNC int em_encode_base64(char *src, unsigned long src_len, char **enc, unsigned long* enc_len, int *err_code)
-{
- EM_DEBUG_FUNC_BEGIN();
-
- unsigned char *content;
- int ret = true, err = EMF_ERROR_NONE;
-
- if (err_code != NULL) {
- *err_code = EMF_ERROR_NONE;
- }
-
- content = rfc822_binary(src, src_len, enc_len);
-
- if (content)
- *enc = (char *)content;
- else {
- err = EMF_ERROR_UNKNOWN;
- ret = false;
- }
-
- if (err_code)
- *err_code = err;
-
- EM_DEBUG_FUNC_END();
- return ret;
-}
-
-/*
- * decoding base64
- */
-INTERNAL_FUNC int em_decode_base64(unsigned char *enc_text, unsigned long enc_len, char **dec_text, unsigned long* dec_len, int *err_code)
-{
- unsigned char *text = enc_text;
- unsigned long size = enc_len;
- unsigned char *content;
- int ret = true, err = EMF_ERROR_NONE;
-
- if (err_code != NULL) {
- *err_code = EMF_ERROR_NONE;
- }
-
- EM_DEBUG_FUNC_BEGIN();
-
- content = rfc822_base64(text, size, dec_len);
- if (content)
- *dec_text = (char *)content;
- else
- {
- err = EMF_ERROR_UNKNOWN;
- ret = false;
- }
-
- if (err_code)
- *err_code = err;
-
- return ret;
-}
+/*
+* email-service
+*
+* Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved.
+*
+* Contact: Kyuho Jo <kyuho.jo@samsung.com>, Sunghyun Kwon <sh0701.kwon@samsung.com>
+*
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*
+*/
+
+/*
+ * email-utilities.c
+ *
+ * Created on: 2012. 3. 6.
+ * Author: kyuho.jo@samsung.com
+ */
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <ctype.h>
+#include <errno.h>
+#include <sys/time.h>
+#include <sys/vfs.h>
+#include <unistd.h>
+#include <malloc.h>
+#include <pthread.h>
+#include <regex.h>
+
+#include "c-client.h"
+
+#include "email-types.h"
+#include "email-internal-types.h"
+#include "email-utilities.h"
+
+INTERNAL_FUNC void* em_malloc(int len)
+{
+ /* EM_DEBUG_LOG("Memory allocation size[%d] bytes", len); */
+ if (len <= 0) {
+ EM_DEBUG_EXCEPTION("len should be positive.[%d]", len);
+ return NULL;
+ }
+
+ void *p = calloc(1,len);
+ if (!p)
+ EM_DEBUG_PERROR("malloc failed");
+
+ return p;
+}
+
+
+INTERNAL_FUNC void* em_memdup(void* src, int len)
+{
+ /* EM_DEBUG_LOG("Memory allocation size[%d] bytes", len); */
+ if (len <= 0) {
+ EM_DEBUG_EXCEPTION("len should be positive.[%d]", len);
+ return NULL;
+ }
+
+ void *p = calloc(1,len);
+ if (!p)
+ EM_DEBUG_EXCEPTION("malloc failed");
+
+ memcpy(p, src, len);
+
+ return p;
+}
+
+
+/* remove left space, tab, CR, L */
+INTERNAL_FUNC char *em_trim_left(char *str)
+{
+ char *p, *temp_buffer = NULL;
+
+ /* EM_DEBUG_FUNC_BEGIN() */
+ if (!str) return NULL;
+
+ p = str;
+ while (*p && (*p == ' ' || *p == '\t' || *p == LF || *p == CR)) p++;
+
+ if (!*p) return NULL;
+
+ temp_buffer = EM_SAFE_STRDUP(p);
+
+ strncpy(str, temp_buffer, strlen(str));
+ str[strlen(temp_buffer)] = NULL_CHAR;
+
+ EM_SAFE_FREE(temp_buffer);
+
+ return str;
+}
+
+/* remove right space, tab, CR, L */
+INTERNAL_FUNC char *em_trim_right(char *str)
+{
+ char *p;
+
+ /* EM_DEBUG_FUNC_BEGIN() */
+ if (!str) return NULL;
+
+ p = str+strlen(str)-1;
+ while (((int)p >= (int)str) && (*p == ' ' || *p == '\t' || *p == LF || *p == CR))
+ *p --= '\0';
+
+ if ((int) p < (int)str)
+ return NULL;
+
+ return str;
+}
+
+INTERNAL_FUNC char* em_upper_string(char *str)
+{
+ char *p = str;
+ while (*p) {
+ *p = toupper(*p);
+ p++;
+ }
+ return str;
+}
+
+INTERNAL_FUNC char* em_lower_string(char *str)
+{
+ char *p = str;
+ while (*p) {
+ *p = tolower(*p);
+ p++;
+ }
+ return str;
+}
+
+INTERNAL_FUNC int em_upper_path(char *path)
+{
+ int i = 0, is_utf7 = 0, len = path ? (int)strlen(path) : -1;
+ for (; i < len; i++) {
+ if (path[i] == '&' || path[i] == 5) {
+ is_utf7 = 1;
+ }
+ else {
+ if (is_utf7) {
+ if (path[i] == '-') is_utf7 = 0;
+ }
+ else {
+ path[i] = toupper(path[i]);
+ }
+ }
+ }
+
+ return 1;
+}
+
+INTERNAL_FUNC void em_skip_whitespace(char *addr_str, char **pAddr)
+{
+ EM_DEBUG_FUNC_BEGIN("addr_str[%p]", addr_str);
+
+ if (!addr_str)
+ return ;
+ char *str = addr_str;
+ char ptr[strlen(str)+1] ;
+ int i, j = 0;
+
+ str = addr_str ;
+ for (i = 0; str[i] != NULL_CHAR ; i++) {
+ if (str[i] != SPACE && str[i] != TAB && str[i] != CR && str[i] != LF)
+ ptr[j++] = str[i];
+ }
+ ptr[j] = NULL_CHAR;
+
+ *pAddr = EM_SAFE_STRDUP(ptr);
+ EM_DEBUG_FUNC_END("ptr[%s]", ptr);
+}
+
+INTERNAL_FUNC char* em_skip_whitespace_without_strdup(char *source_string)
+{
+ EM_DEBUG_FUNC_BEGIN("source_string[%p]", source_string);
+
+ if (!source_string)
+ return NULL;
+ int i;
+
+ for (i = 0; source_string[i] != NULL_CHAR ; i++) {
+ if (source_string[i] != SPACE) /* || source_string[i] != TAB || source_string[i] != CR || source_string[i] || LF) */
+ break;
+ }
+
+ EM_DEBUG_FUNC_END("i[%d]", i);
+ return source_string + i;
+}
+
+
+INTERNAL_FUNC char* em_replace_all_string(char *source_string, char *old_string, char *new_string)
+{
+ EM_DEBUG_FUNC_BEGIN();
+ char *result_buffer = NULL;
+ char *p = NULL;
+ int i = 0, count = 0;
+ int old_str_length = 0;
+ int new_str_length = 0;
+
+ EM_IF_NULL_RETURN_VALUE(source_string, NULL);
+ EM_IF_NULL_RETURN_VALUE(old_string, NULL);
+ EM_IF_NULL_RETURN_VALUE(new_string, NULL);
+
+ old_str_length = strlen(old_string);
+ new_str_length = strlen(new_string);
+
+ if (old_str_length != new_str_length) {
+ for (i = 0; source_string[i] != '\0';) {
+ if (memcmp(&source_string[i], old_string, old_str_length) == 0) {
+ count++;
+ i += old_str_length;
+ } else {
+ i++;
+ }
+ }
+ } else {
+ i = strlen(source_string);
+ }
+
+ result_buffer = (char *)malloc(i + 1 + count*(new_str_length-old_str_length));
+ if (result_buffer == NULL)
+ return NULL;
+
+ p = result_buffer;
+ while (*source_string) {
+ if (memcmp(source_string, old_string, old_str_length) == 0) {
+ memcpy(p, new_string, new_str_length);
+ p += new_str_length;
+ source_string += old_str_length;
+ } else {
+ *p++ = *source_string++;
+ }
+ }
+ *p = '\0';
+
+ EM_DEBUG_FUNC_END("result_buffer : %s", result_buffer);
+ return result_buffer;
+}
+
+INTERNAL_FUNC char* em_replace_string(char *source_string, char *old_string, char *new_string)
+{
+ EM_DEBUG_FUNC_BEGIN();
+ char *result_buffer = NULL;
+ char *p = NULL;
+ int buffer_length = 0;
+
+ EM_IF_NULL_RETURN_VALUE(source_string, NULL);
+ EM_IF_NULL_RETURN_VALUE(old_string, NULL);
+ EM_IF_NULL_RETURN_VALUE(new_string, NULL);
+
+ p = strstr(source_string, old_string);
+
+ if (p == NULL) {
+ EM_DEBUG_EXCEPTION("old_string not found in source_string");
+ EM_DEBUG_FUNC_END("return NULL");
+ return NULL;
+ }
+
+ buffer_length = strlen(source_string) + 1024;
+ result_buffer = (char *)em_malloc(buffer_length);
+
+ if (!result_buffer) {
+ EM_DEBUG_EXCEPTION("em_malloc failed");
+ return NULL;
+ }
+
+ strncpy(result_buffer, source_string, p - source_string);
+ snprintf(result_buffer + strlen(result_buffer), buffer_length - strlen(result_buffer), "%s%s", new_string, p + strlen(old_string));
+
+ EM_DEBUG_FUNC_END("result_buffer[%s]", result_buffer);
+ return result_buffer;
+}
+
+/* Memory clean up */
+#include <sys/mman.h>
+
+/* #define GETSP() ({ unsigned int sp; asm volatile ("mov %0, sp " : "=r"(sp)); sp;}) */
+#define BUF_SIZE 256
+#define PAGE_SIZE (1 << 12)
+#define _ALIGN_UP(addr, size) (((addr)+((size)-1))&(~((size)-1)))
+#define _ALIGN_DOWN(addr, size) ((addr)&(~((size)-1)))
+#define PAGE_ALIGN(addr) _ALIGN_DOWN(addr, PAGE_SIZE)
+
+int stack_trim(void)
+{
+ /*
+ char buf[BUF_SIZE];
+ FILE *file;
+ unsigned int stacktop;
+ int found = 0;
+ unsigned int sp;
+
+ asm volatile ("mov %0, sp " : "=r"(sp));
+
+ sprintf(buf, "/proc/%d/maps", getpid());
+ file = fopen(buf, "r");
+ while (fgets(buf, BUF_SIZE, file) != NULL) {
+ if (strstr(buf, "[stack]")) {
+ found = 1;
+ break;
+ }
+ }
+
+ fclose(file);
+
+ if (found) {
+ sscanf(buf, "%x-", &stacktop);
+ if (madvise((void *)PAGE_ALIGN(stacktop), PAGE_ALIGN(sp)-stacktop, MADV_DONTNEED) < 0)
+ perror("stack madvise fail");
+ }
+ */
+ return 1;
+}
+
+INTERNAL_FUNC void em_flush_memory()
+{
+ EM_DEBUG_FUNC_BEGIN();
+ /* flush memory in heap */
+ malloc_trim(0);
+
+ /* flush memory in stack */
+ stack_trim();
+
+ /* flush memory for sqlite */
+ emstorage_flush_db_cache();
+ EM_DEBUG_FUNC_END();
+}
+
+INTERNAL_FUNC int em_get_file_name_and_extension_from_file_path(char *input_source_file_path, char **output_file_name, char **output_extension)
+{
+ EM_DEBUG_FUNC_BEGIN("input_source_file_path[%s], output_file_name [%p], output_extension [%p]", input_source_file_path, output_file_name, output_extension);
+ int err = EMAIL_ERROR_NONE;
+ int pos_on_string = 0;
+ int file_name_length = 0;
+ int extention_length = 0;
+ char *start_pos_of_file_name = NULL;
+ char *end_pos_of_file_name = NULL;
+ char *dot_pos_of_file_path = NULL;
+ char *end_pos_of_file_path = NULL;
+ char file_name_string[MAX_PATH] = { 0, };
+ char extension_string[MAX_PATH] = { 0, };
+
+ if (!input_source_file_path || !output_file_name || !output_extension) {
+ EM_DEBUG_EXCEPTION("Invalid Parameter");
+ err = EMAIL_ERROR_INVALID_PARAM;
+ goto FINISH_OFF;
+ }
+
+ pos_on_string = strlen(input_source_file_path) - 1;
+ end_pos_of_file_path = input_source_file_path + pos_on_string;
+ end_pos_of_file_name = end_pos_of_file_path;
+
+ while(pos_on_string >= 0 && input_source_file_path[pos_on_string] != '/') {
+ if(input_source_file_path[pos_on_string] == '.') {
+ if(dot_pos_of_file_path == NULL) {
+ end_pos_of_file_name = input_source_file_path + pos_on_string;
+ dot_pos_of_file_path = end_pos_of_file_name;
+ }
+ }
+ pos_on_string--;
+ }
+
+ pos_on_string++;
+
+ if(pos_on_string >= 0) {
+ start_pos_of_file_name = input_source_file_path + pos_on_string;
+ file_name_length = end_pos_of_file_name - start_pos_of_file_name;
+ memcpy(file_name_string, start_pos_of_file_name, file_name_length);
+ }
+
+ if(dot_pos_of_file_path != NULL) {
+ extention_length = (end_pos_of_file_path + 1) - (dot_pos_of_file_path + 1);
+ memcpy(extension_string, dot_pos_of_file_path + 1, extention_length);
+ }
+
+ EM_DEBUG_LOG("*file_name_string [%s] pos_on_string [%d]", file_name_string, pos_on_string);
+
+ *output_file_name = EM_SAFE_STRDUP(file_name_string);
+ *output_extension = EM_SAFE_STRDUP(extension_string);
+
+FINISH_OFF:
+ EM_DEBUG_FUNC_END("err = [%d]", err);
+ return err;
+}
+
+INTERNAL_FUNC char *em_get_extension_from_file_path(char *source_file_path, int *err_code)
+{
+ EM_DEBUG_FUNC_BEGIN("source_file_path[%s]", source_file_path);
+ int err = EMAIL_ERROR_NONE, pos_on_string = 0;
+ char *extension = NULL;
+
+ if (!source_file_path) {
+ EM_DEBUG_EXCEPTION("Invalid Parameter");
+ err = EMAIL_ERROR_INVALID_PARAM;
+ goto FINISH_OFF;
+ }
+
+ pos_on_string = strlen(source_file_path) - 1;
+
+ while(pos_on_string > 0 && source_file_path[pos_on_string--] != '.') ;
+
+ if(pos_on_string > 0)
+ extension = source_file_path + pos_on_string + 2;
+
+ EM_DEBUG_LOG("*extension [%s] pos_on_string [%d]", extension, pos_on_string);
+
+FINISH_OFF:
+ if (err_code)
+ *err_code = err;
+ EM_DEBUG_FUNC_END();
+ return extension;
+}
+
+INTERNAL_FUNC int em_get_encoding_type_from_file_path(const char *input_file_path, char **output_encoding_type)
+{
+ EM_DEBUG_FUNC_BEGIN("input_file_path[%d], output_encoding_type[%p]", input_file_path, output_encoding_type);
+ int err = EMAIL_ERROR_NONE;
+ int pos_of_filename = 0;
+ int pos_of_dot = 0;
+ int enf_of_string = 0;
+ int result_string_length = 0;
+ char *filename = NULL;
+ char *result_encoding_type = NULL;
+
+ if (!input_file_path || !output_encoding_type) {
+ EM_DEBUG_EXCEPTION("Invalid Parameter");
+ err = EMAIL_ERROR_INVALID_PARAM;
+ goto FINISH_OFF;
+ }
+
+ enf_of_string = pos_of_filename = strlen(input_file_path);
+
+ while(pos_of_filename >= 0 && input_file_path[pos_of_filename--] != '/') {
+ if(input_file_path[pos_of_filename] == '.')
+ pos_of_dot = pos_of_filename;
+ }
+
+ if(pos_of_filename != 0)
+ pos_of_filename += 2;
+
+ filename = (char*)input_file_path + pos_of_filename;
+
+ if(pos_of_dot != 0 && pos_of_dot > pos_of_filename)
+ result_string_length = pos_of_dot - pos_of_filename;
+ else
+ result_string_length = enf_of_string - pos_of_filename;
+
+ EM_DEBUG_LOG("pos_of_dot [%d], pos_of_filename [%d], enf_of_string[%d],result_string_length [%d]", pos_of_dot, pos_of_filename, enf_of_string, result_string_length);
+
+ if( !(result_encoding_type = em_malloc(sizeof(char) * (result_string_length + 1))) ) {
+ EM_DEBUG_EXCEPTION("EMAIL_ERROR_OUT_OF_MEMORY");
+ err = EMAIL_ERROR_OUT_OF_MEMORY;
+ goto FINISH_OFF;
+ }
+
+ memcpy(result_encoding_type, input_file_path + pos_of_filename, result_string_length);
+
+ EM_DEBUG_LOG("*result_encoding_type [%s]", result_encoding_type);
+
+ *output_encoding_type = result_encoding_type;
+
+FINISH_OFF:
+ EM_DEBUG_FUNC_END("err [%d]", err);
+ return err;
+}
+
+INTERNAL_FUNC int em_get_content_type_from_extension_string(const char *extension_string, int *err_code)
+{
+ EM_DEBUG_FUNC_BEGIN("extension_string[%s]", extension_string);
+ int i = 0, err = EMAIL_ERROR_NONE, result_content_type = TYPEAPPLICATION;
+ char *image_extension[] = { "jpeg", "jpg", "png", "gif", "bmp", "pic", "agif", "tif", "wbmp" , NULL};
+
+ if (!extension_string) {
+ EM_DEBUG_EXCEPTION("Invalid Parameter");
+ err = EMAIL_ERROR_INVALID_PARAM;
+ goto FINISH_OFF;
+ }
+
+ while(image_extension[i]) {
+ EM_DEBUG_LOG("image_extension[%d] [%s]", i, image_extension[i]);
+ if(strcasecmp(image_extension[i], extension_string) == 0) {
+ result_content_type = TYPEIMAGE;
+ break;
+ }
+ i++;
+ }
+
+FINISH_OFF:
+ if (err_code)
+ *err_code = err;
+ EM_DEBUG_FUNC_END();
+ return result_content_type;
+}
+
+#define EMAIL_ACCOUNT_RGEX "([a-z0-9!#$%&'*+/=?^_`{|}~-]+.)*[a-z0-9!#$%&'*+/=?^_`{|}~-]+"
+#define EMAIL_DOMAIN_RGEX "([a-z0-9!#$%&'*+/=?^_`{|}~-]+.)+[a-z0-9!#$%&'*+/=?^_`{|}~-]+"
+
+#define EMAIL_ADDR_RGEX "[[:space:]]*<"EMAIL_ACCOUNT_RGEX"@"EMAIL_DOMAIN_RGEX">[[:space:]]*"
+#define EMAIL_ALIAS_RGEX "([[:space:]]*\"[^\"]*\")?"EMAIL_ADDR_RGEX
+#define EMAIL_ALIAS_LIST_RGEX "^("EMAIL_ALIAS_RGEX"[;,])*"EMAIL_ALIAS_RGEX"[;,]?[[:space:]]*$"
+
+#define EMAIL_ADDR_WITHOUT_BRACKET_RGEX "[[:space:]]*"EMAIL_ACCOUNT_RGEX"@"EMAIL_DOMAIN_RGEX"[[:space:]]*"
+#define EMAIL_ALIAS_WITHOUT_BRACKET_RGEX "([[:space:]]*\"[^\"]*\")?"EMAIL_ADDR_WITHOUT_BRACKET_RGEX
+#define EMAIL_ALIAS_LIST_WITHOUT_BRACKET_RGEX "("EMAIL_ALIAS_WITHOUT_BRACKET_RGEX"[;,])*"EMAIL_ADDR_WITHOUT_BRACKET_RGEX"[;,]?[[:space:]]*$"
+
+INTERNAL_FUNC int em_verify_email_address(char *address, int without_bracket, int *err_code)
+{
+ EM_DEBUG_FUNC_BEGIN("address[%s] without_bracket[%d]", address, without_bracket);
+
+ /* this following code verfies the email alias string using reg. exp. */
+ regex_t alias_list_regex = {0};
+ int ret = false, error = EMAIL_ERROR_NONE;
+ char *reg_rule = NULL;
+
+ if(!address || strlen(address) == 0) {
+ EM_DEBUG_EXCEPTION("EMAIL_ERROR_INVALID_PARAM");
+ if (err_code)
+ *err_code = EMAIL_ERROR_INVALID_PARAM;
+ return false;
+ }
+
+ if(without_bracket)
+ reg_rule = EMAIL_ALIAS_LIST_WITHOUT_BRACKET_RGEX;
+ else
+ reg_rule = EMAIL_ALIAS_LIST_RGEX;
+
+ if (regcomp(&alias_list_regex, reg_rule, REG_ICASE | REG_EXTENDED)) {
+ EM_DEBUG_EXCEPTION("email alias regex unrecognized");
+ if (err_code)
+ *err_code = EMAIL_ERROR_UNKNOWN;
+ return false;
+ }
+
+ int alias_len = strlen(address) + 1;
+ regmatch_t pmatch[alias_len];
+
+ bzero(pmatch, alias_len);
+
+ if (regexec(&alias_list_regex, address, alias_len, pmatch, 0) == REG_NOMATCH)
+ EM_DEBUG_LOG("failed :[%s]", address);
+ else {
+ EM_DEBUG_LOG("success :[%s]", address);
+ ret = true;
+ }
+
+ regfree(&alias_list_regex);
+
+ if (err_code)
+ *err_code = error;
+
+ EM_DEBUG_FUNC_END("ret [%d]", ret);
+ return ret;
+}
+
+INTERNAL_FUNC int em_verify_email_address_of_mail_data(email_mail_data_t *mail_data, int without_bracket, int *err_code)
+{
+ EM_DEBUG_FUNC_BEGIN("mail_data[%p] without_bracket[%d]", mail_data, without_bracket);
+ char *address_array[4] = { mail_data->full_address_from, mail_data->full_address_to, mail_data->full_address_cc, mail_data->full_address_bcc};
+ int ret = false, err = EMAIL_ERROR_NONE, i;
+
+ /* check for email_address validation */
+ for (i = 0; i < 4; i++) {
+ if (address_array[i] && address_array[i][0] != 0) {
+ if (!em_verify_email_address(address_array[i] , without_bracket, &err)) {
+ err = EMAIL_ERROR_INVALID_ADDRESS;
+ EM_DEBUG_EXCEPTION("Invalid Email Address [%d][%s]", i, address_array[i]);
+ goto FINISH_OFF;
+ }
+ }
+ }
+ ret = true;
+FINISH_OFF:
+ EM_DEBUG_FUNC_END("ret [%d]", ret);
+ return ret;
+}
+
+INTERNAL_FUNC int em_verify_email_address_of_mail_tbl(emstorage_mail_tbl_t *input_mail_tbl, int input_without_bracket)
+{
+ EM_DEBUG_FUNC_BEGIN("input_mail_tbl[%p] input_without_bracket[%d]", input_mail_tbl, input_without_bracket);
+ char *address_array[4] = { input_mail_tbl->full_address_to, input_mail_tbl->full_address_cc, input_mail_tbl->full_address_bcc, input_mail_tbl->full_address_from};
+ int err = EMAIL_ERROR_NONE, i;
+
+ /* check for email_address validation */
+ for (i = 0; i < 4; i++) {
+ if (address_array[i] && address_array[i][0] != 0) {
+ if (!em_verify_email_address(address_array[i] , input_without_bracket, &err)) {
+ err = EMAIL_ERROR_INVALID_ADDRESS;
+ EM_DEBUG_EXCEPTION("Invalid Email Address [%d][%s]", i, address_array[i]);
+ goto FINISH_OFF;
+ }
+ }
+ }
+
+FINISH_OFF:
+ EM_DEBUG_FUNC_END("err [%d]", err);
+ return err;
+}
+
+INTERNAL_FUNC int em_find_tag_for_thread_view(char *subject, int *result)
+{
+ EM_DEBUG_FUNC_BEGIN();
+ int error_code = EMAIL_ERROR_NONE;
+ char *copy_of_subject = NULL;
+
+ EM_IF_NULL_RETURN_VALUE(subject, EMAIL_ERROR_INVALID_PARAM);
+ EM_IF_NULL_RETURN_VALUE(result, EMAIL_ERROR_INVALID_PARAM);
+
+ *result = FALSE;
+
+ copy_of_subject = EM_SAFE_STRDUP(subject);
+
+ if (copy_of_subject == NULL) {
+ EM_DEBUG_EXCEPTION("strdup is failed.");
+ goto FINISH_OFF;
+ }
+
+ em_upper_string(copy_of_subject);
+ EM_DEBUG_LOG("em_upper_string result : %s\n", copy_of_subject);
+
+ if (strstr(copy_of_subject, "RE:") == NULL) {
+ if (strstr(copy_of_subject, "FWD:") == NULL) {
+ if (strstr(copy_of_subject, "FW:") != NULL)
+ *result = TRUE;
+ }
+ else
+ *result = TRUE;
+ }
+ else
+ *result = TRUE;
+
+FINISH_OFF:
+ EM_SAFE_FREE(copy_of_subject);
+
+ EM_DEBUG_FUNC_END("result : %d", *result);
+
+ return error_code;
+}
+
+INTERNAL_FUNC int em_find_pos_stripped_subject_for_thread_view(char *subject, char *stripped_subject)
+{
+ EM_DEBUG_FUNC_BEGIN();
+ int error_code = EMAIL_ERROR_NONE;
+ int gap;
+ char *copy_of_subject = NULL, *curpos = NULL, *result;
+
+ EM_IF_NULL_RETURN_VALUE(subject, EMAIL_ERROR_INVALID_PARAM);
+ EM_IF_NULL_RETURN_VALUE(stripped_subject, EMAIL_ERROR_INVALID_PARAM);
+
+ copy_of_subject = EM_SAFE_STRDUP(subject);
+
+ if (copy_of_subject == NULL) {
+ EM_DEBUG_EXCEPTION("strdup is failed");
+ goto FINISH_OFF;
+ }
+
+ em_upper_string(copy_of_subject);
+ curpos = copy_of_subject;
+
+ EM_DEBUG_LOG("em_upper_string result : %s", copy_of_subject);
+
+ while ((result = strstr(curpos, "RE:")) != NULL) {
+ curpos = result + 3;
+ EM_DEBUG_LOG("RE result : %s", curpos);
+ }
+
+ while ((result = strstr(curpos, "FWD:")) != NULL) {
+ curpos = result + 4;
+ EM_DEBUG_LOG("FWD result : %s", curpos);
+ }
+
+ while ((result = strstr(curpos, "FW:")) != NULL) {
+ curpos = result + 3;
+ EM_DEBUG_LOG("FW result : %s", curpos);
+ }
+
+ while (curpos != NULL && *curpos == ' ') {
+ curpos++;
+ }
+
+ gap = curpos - copy_of_subject;
+
+ strcpy(stripped_subject, subject + gap);
+
+FINISH_OFF:
+ EM_SAFE_FREE(copy_of_subject);
+
+ if (error_code == EMAIL_ERROR_NONE && stripped_subject)
+ EM_DEBUG_LOG("result[%s]", stripped_subject);
+
+ EM_DEBUG_FUNC_END("error_code[%d]", error_code);
+ return error_code;
+}
+
+
+/*
+ * encoding base64
+ */
+INTERNAL_FUNC int em_encode_base64(char *src, unsigned long src_len, char **enc, unsigned long* enc_len, int *err_code)
+{
+ EM_DEBUG_FUNC_BEGIN();
+
+ unsigned char *content;
+ int ret = true, err = EMAIL_ERROR_NONE;
+
+ if (err_code != NULL) {
+ *err_code = EMAIL_ERROR_NONE;
+ }
+
+ content = rfc822_binary(src, src_len, enc_len);
+
+ if (content)
+ *enc = (char *)content;
+ else {
+ err = EMAIL_ERROR_UNKNOWN;
+ ret = false;
+ }
+
+ if (err_code)
+ *err_code = err;
+
+ EM_DEBUG_FUNC_END();
+ return ret;
+}
+
+/*
+ * decoding base64
+ */
+INTERNAL_FUNC int em_decode_base64(unsigned char *enc_text, unsigned long enc_len, char **dec_text, unsigned long* dec_len, int *err_code)
+{
+ unsigned char *text = enc_text;
+ unsigned long size = enc_len;
+ unsigned char *content;
+ int ret = true, err = EMAIL_ERROR_NONE;
+
+ if (err_code != NULL) {
+ *err_code = EMAIL_ERROR_NONE;
+ }
+
+ EM_DEBUG_FUNC_BEGIN();
+
+ content = rfc822_base64(text, size, dec_len);
+ if (content)
+ *dec_text = (char *)content;
+ else
+ {
+ err = EMAIL_ERROR_UNKNOWN;
+ ret = false;
+ }
+
+ if (err_code)
+ *err_code = err;
+
+ return ret;
+}
+
+INTERNAL_FUNC int em_get_account_server_type_by_account_id(int account_id, email_account_server_t* account_server_type, int flag, int *error)
+{
+ EM_DEBUG_FUNC_BEGIN();
+ emstorage_account_tbl_t *account_tbl_data = NULL;
+ int ret = false;
+ int err= EMAIL_ERROR_NONE;
+
+ if (account_server_type == NULL ) {
+ EM_DEBUG_EXCEPTION("account_server_type is NULL");
+ err = EMAIL_ERROR_INVALID_PARAM;
+ ret = false;
+ goto FINISH_OFF;
+ }
+
+ if( !emstorage_get_account_by_id(account_id, WITHOUT_OPTION, &account_tbl_data, false, &err)) {
+ EM_DEBUG_EXCEPTION ("emstorage_get_account_by_id failed [%d] ", err);
+ ret = false;
+ goto FINISH_OFF;
+ }
+
+ if ( flag == false ) { /* sending server */
+ *account_server_type = account_tbl_data->outgoing_server_type;
+ } else if ( flag == true ) { /* receiving server */
+ *account_server_type = account_tbl_data->incoming_server_type;
+ }
+
+ ret = true;
+
+FINISH_OFF:
+ if ( account_tbl_data != NULL ) {
+ emstorage_free_account(&account_tbl_data, 1, NULL);
+ }
+ if ( error != NULL ) {
+ *error = err;
+ }
+
+ return ret;
+}
+
+#include <vconf.h>
+#include <dbus/dbus.h>
+
+#define ACTIVE_SYNC_HANDLE_INIT_VALUE (-1)
+#define ACTIVE_SYNC_HANDLE_BOUNDARY (-100000000)
+
+
+INTERNAL_FUNC int em_get_handle_for_activesync(int *handle, int *error)
+{
+ EM_DEBUG_FUNC_BEGIN();
+
+ static int next_handle = 0;
+ int ret = false;
+ int err = EMAIL_ERROR_NONE;
+
+ if ( handle == NULL ) {
+ EM_DEBUG_EXCEPTION("em_get_handle_for_activesync failed : handle is NULL");
+ err = EMAIL_ERROR_INVALID_PARAM;
+ goto FINISH_OFF;
+ }
+
+ if ( vconf_get_int(VCONFKEY_EMAIL_SERVICE_ACTIVE_SYNC_HANDLE, &next_handle) != 0 ) {
+ EM_DEBUG_EXCEPTION("vconf_get_int failed");
+ if ( next_handle != 0 ) {
+ err = EMAIL_ERROR_GCONF_FAILURE;
+ goto FINISH_OFF;
+ }
+ }
+
+ EM_DEBUG_LOG(">>>>>> VCONFKEY_EMAIL_SERVICE_ACTIVE_SYNC_HANDLE : get lastest handle[%d]", next_handle);
+
+ /* set the value of the handle for active sync */
+ next_handle--;
+ if ( next_handle < ACTIVE_SYNC_HANDLE_BOUNDARY ) {
+ next_handle = ACTIVE_SYNC_HANDLE_INIT_VALUE;
+ }
+ if ( vconf_set_int(VCONFKEY_EMAIL_SERVICE_ACTIVE_SYNC_HANDLE, next_handle) != 0) {
+ EM_DEBUG_EXCEPTION("vconf_set_int failed");
+ err = EMAIL_ERROR_GCONF_FAILURE;
+ goto FINISH_OFF;
+ }
+ ret = true;
+ *handle = next_handle;
+ EM_DEBUG_LOG(">>>>>> return next handle[%d]", *handle);
+
+FINISH_OFF:
+ if ( error != NULL ) {
+ *error = err;
+ }
+
+ return ret;
+}
+
+INTERNAL_FUNC int em_send_notification_to_active_sync_engine(int subType, ASNotiData *data)
+{
+ EM_DEBUG_FUNC_BEGIN("subType [%d], data [%p]", subType, data);
+
+ DBusConnection *connection;
+ DBusMessage *signal = NULL;
+ DBusError error;
+ const char *nullString = "";
+ int i = 0;
+
+ dbus_error_init (&error);
+ connection = dbus_bus_get(DBUS_BUS_SYSTEM, &error);
+
+ if(connection == NULL)
+ goto FINISH_OFF;
+
+ signal = dbus_message_new_signal("/User/Email/ActiveSync", EMAIL_ACTIVE_SYNC_NOTI, "email");
+
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &subType, DBUS_TYPE_INVALID);
+ switch ( subType ) {
+ case ACTIVE_SYNC_NOTI_SEND_MAIL:
+ EM_DEBUG_LOG("handle:[%d]", data->send_mail.handle);
+ EM_DEBUG_LOG("account_id:[%d]", data->send_mail.account_id);
+ EM_DEBUG_LOG("mail_id:[%d]", data->send_mail.mail_id);
+ EM_DEBUG_LOG("options.priority:[%d]", data->send_mail.options.priority);
+ EM_DEBUG_LOG("options.keep_local_copy:[%d]", data->send_mail.options.keep_local_copy);
+ EM_DEBUG_LOG("options.req_delivery_receipt:[%d]", data->send_mail.options.req_delivery_receipt);
+ EM_DEBUG_LOG("options.req_read_receipt:[%d]", data->send_mail.options.req_read_receipt);
+ /* download_limit, block_address, block_subject might not be needed */
+ EM_DEBUG_LOG("options.download_limit:[%d]", data->send_mail.options.download_limit);
+ EM_DEBUG_LOG("options.block_address:[%d]", data->send_mail.options.block_address);
+ EM_DEBUG_LOG("options.block_subject:[%d]", data->send_mail.options.block_subject);
+ EM_DEBUG_LOG("options.display_name_from:[%s]", data->send_mail.options.display_name_from);
+ EM_DEBUG_LOG("options.reply_with_body:[%d]", data->send_mail.options.reply_with_body);
+ EM_DEBUG_LOG("options.forward_with_files:[%d]", data->send_mail.options.forward_with_files);
+ EM_DEBUG_LOG("options.add_myname_card:[%d]", data->send_mail.options.add_myname_card);
+ EM_DEBUG_LOG("options.add_signature:[%d]", data->send_mail.options.add_signature);
+ EM_DEBUG_LOG("options.signature:[%s]", data->send_mail.options.signature);
+
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->send_mail.handle), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->send_mail.account_id), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->send_mail.mail_id), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->send_mail.options.priority), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->send_mail.options.keep_local_copy), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->send_mail.options.req_delivery_receipt), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->send_mail.options.req_read_receipt), DBUS_TYPE_INVALID);
+ if ( data->send_mail.options.display_name_from == NULL )
+ dbus_message_append_args(signal, DBUS_TYPE_STRING, &(nullString), DBUS_TYPE_INVALID);
+ else
+ dbus_message_append_args(signal, DBUS_TYPE_STRING, &(data->send_mail.options.display_name_from), DBUS_TYPE_INVALID);
+
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->send_mail.options.reply_with_body), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->send_mail.options.forward_with_files), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->send_mail.options.add_myname_card), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->send_mail.options.add_signature), DBUS_TYPE_INVALID);
+ if ( data->send_mail.options.signature == NULL )
+ dbus_message_append_args(signal, DBUS_TYPE_STRING, &(nullString), DBUS_TYPE_INVALID);
+ else
+ dbus_message_append_args(signal, DBUS_TYPE_STRING, &(data->send_mail.options.signature), DBUS_TYPE_INVALID);
+
+ break;
+ case ACTIVE_SYNC_NOTI_SEND_SAVED: /* publish a send notification to ASE (active sync engine) */
+ EM_DEBUG_EXCEPTION("Not support yet : subType[ACTIVE_SYNC_NOTI_SEND_SAVED]", subType);
+ break;
+ case ACTIVE_SYNC_NOTI_SEND_REPORT:
+ EM_DEBUG_EXCEPTION("Not support yet : subType[ACTIVE_SYNC_NOTI_SEND_REPORT]", subType);
+ break;
+ case ACTIVE_SYNC_NOTI_SYNC_HEADER:
+ EM_DEBUG_LOG("handle:[%d]", data->sync_header.handle);
+ EM_DEBUG_LOG("account_id:[%d]", data->sync_header.account_id);
+ EM_DEBUG_LOG("mailbox_id:[%d]", data->sync_header.mailbox_id);
+
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->sync_header.handle ), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->sync_header.account_id ), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->sync_header.mailbox_id ), DBUS_TYPE_INVALID);
+ break;
+ case ACTIVE_SYNC_NOTI_DOWNLOAD_BODY: /* publish a download body notification to ASE */
+ EM_DEBUG_LOG("handle:[%d]", data->download_body.handle);
+ EM_DEBUG_LOG("account_id:[%d]", data->download_body.account_id);
+ EM_DEBUG_LOG("mail_id:[%d]", data->download_body.mail_id);
+ EM_DEBUG_LOG("with_attachment:[%d]", data->download_body.with_attachment);
+
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->download_body.handle ), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->download_body.account_id ), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->download_body.mail_id ), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->download_body.with_attachment ), DBUS_TYPE_INVALID);
+ break;
+ case ACTIVE_SYNC_NOTI_DOWNLOAD_ATTACHMENT:
+ EM_DEBUG_LOG("handle:[%d]", data->download_attachment.handle);
+ EM_DEBUG_LOG("account_id:[%d]", data->download_attachment.account_id );
+ EM_DEBUG_LOG("mail_id:[%d]", data->download_attachment.mail_id);
+ EM_DEBUG_LOG("with_attachment:[%d]", data->download_attachment.attachment_order );
+
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->download_attachment.handle ), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->download_attachment.account_id ), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->download_attachment.mail_id ), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->download_attachment.attachment_order), DBUS_TYPE_INVALID);
+ break;
+ case ACTIVE_SYNC_NOTI_VALIDATE_ACCOUNT:
+ EM_DEBUG_EXCEPTION("Not support yet : subType[ACTIVE_SYNC_NOTI_VALIDATE_ACCOUNT]", subType);
+ break;
+ case ACTIVE_SYNC_NOTI_CANCEL_JOB:
+ EM_DEBUG_LOG("account_id:[%d]", data->cancel_job.account_id );
+ EM_DEBUG_LOG("handle to cancel:[%d]", data->cancel_job.handle);
+ EM_DEBUG_LOG("cancel_type:[%d]", data->cancel_job.cancel_type);
+
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->cancel_job.account_id ), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->cancel_job.handle ), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->cancel_job.cancel_type ), DBUS_TYPE_INVALID);
+ break;
+ case ACTIVE_SYNC_NOTI_SEARCH_ON_SERVER:
+ EM_DEBUG_LOG("account_id:[%d]", data->search_mail_on_server.account_id );
+ EM_DEBUG_LOG("mailbox_id:[%d]", data->search_mail_on_server.mailbox_id );
+ EM_DEBUG_LOG("search_filter_count:[%d]", data->search_mail_on_server.search_filter_count );
+ EM_DEBUG_LOG("handle to cancel:[%d]", data->search_mail_on_server.handle);
+
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->search_mail_on_server.account_id), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->search_mail_on_server.mailbox_id), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->search_mail_on_server.search_filter_count), DBUS_TYPE_INVALID);
+ for(i = 0; i < data->search_mail_on_server.search_filter_count; i++) {
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->search_mail_on_server.search_filter_list[i].search_filter_type), DBUS_TYPE_INVALID);
+ switch(data->search_mail_on_server.search_filter_list[i].search_filter_type) {
+ case EMAIL_SEARCH_FILTER_TYPE_MESSAGE_NO :
+ case EMAIL_SEARCH_FILTER_TYPE_UID :
+ case EMAIL_SEARCH_FILTER_TYPE_SIZE_LARSER :
+ case EMAIL_SEARCH_FILTER_TYPE_SIZE_SMALLER :
+ case EMAIL_SEARCH_FILTER_TYPE_FLAGS_ANSWERED :
+ case EMAIL_SEARCH_FILTER_TYPE_FLAGS_DELETED :
+ case EMAIL_SEARCH_FILTER_TYPE_FLAGS_DRAFT :
+ case EMAIL_SEARCH_FILTER_TYPE_FLAGS_FLAGED :
+ case EMAIL_SEARCH_FILTER_TYPE_FLAGS_RECENT :
+ case EMAIL_SEARCH_FILTER_TYPE_FLAGS_SEEN :
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->search_mail_on_server.search_filter_list[i].search_filter_key_value.integer_type_key_value), DBUS_TYPE_INVALID);
+ break;
+
+ case EMAIL_SEARCH_FILTER_TYPE_BCC :
+ case EMAIL_SEARCH_FILTER_TYPE_CC :
+ case EMAIL_SEARCH_FILTER_TYPE_FROM :
+ case EMAIL_SEARCH_FILTER_TYPE_KEYWORD :
+ case EMAIL_SEARCH_FILTER_TYPE_SUBJECT :
+ case EMAIL_SEARCH_FILTER_TYPE_TO :
+ case EMAIL_SEARCH_FILTER_TYPE_MESSAGE_ID :
+ dbus_message_append_args(signal, DBUS_TYPE_STRING, &(data->search_mail_on_server.search_filter_list[i].search_filter_key_value.string_type_key_value), DBUS_TYPE_INVALID);
+ break;
+
+ case EMAIL_SEARCH_FILTER_TYPE_SENT_DATE_BEFORE :
+ case EMAIL_SEARCH_FILTER_TYPE_SENT_DATE_ON :
+ case EMAIL_SEARCH_FILTER_TYPE_SENT_DATE_SINCE :
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->search_mail_on_server.search_filter_list[i].search_filter_key_value.time_type_key_value), DBUS_TYPE_INVALID);
+ break;
+ default :
+ EM_DEBUG_EXCEPTION("Invalid filter type [%d]", data->search_mail_on_server.search_filter_list[i].search_filter_type);
+ break;
+ }
+ }
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->search_mail_on_server.handle), DBUS_TYPE_INVALID);
+ break;
+
+ case ACTIVE_SYNC_NOTI_CLEAR_RESULT_OF_SEARCH_ON_SERVER :
+ EM_DEBUG_LOG("account_id:[%d]", data->clear_result_of_search_mail_on_server.account_id );
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->search_mail_on_server.account_id), DBUS_TYPE_INVALID);
+ break;
+
+ case ACTIVE_SYNC_NOTI_EXPUNGE_MAILS_DELETED_FLAGGED :
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->expunge_mails_deleted_flagged.mailbox_id ), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->expunge_mails_deleted_flagged.on_server ), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->expunge_mails_deleted_flagged.handle ), DBUS_TYPE_INVALID);
+ break;
+
+ case ACTIVE_SYNC_NOTI_RESOLVE_RECIPIENT :
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->get_resolve_recipients.account_id), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_STRING, &(data->get_resolve_recipients.email_address), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->get_resolve_recipients.handle), DBUS_TYPE_INVALID);
+ break;
+
+ case ACTIVE_SYNC_NOTI_VALIDATE_CERTIFICATE :
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->validate_certificate.account_id), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_STRING, &(data->validate_certificate.email_address), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->validate_certificate.handle), DBUS_TYPE_INVALID);
+ break;
+
+ case ACTIVE_SYNC_NOTI_ADD_MAILBOX :
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->add_mailbox.account_id), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_STRING, &(data->add_mailbox.mailbox_path), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_STRING, &(data->add_mailbox.mailbox_alias), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->add_mailbox.handle), DBUS_TYPE_INVALID);
+ break;
+
+ case ACTIVE_SYNC_NOTI_RENAME_MAILBOX :
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->rename_mailbox.account_id), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->rename_mailbox.mailbox_id), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_STRING, &(data->rename_mailbox.mailbox_name), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_STRING, &(data->rename_mailbox.mailbox_alias), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->rename_mailbox.handle), DBUS_TYPE_INVALID);
+ break;
+
+ case ACTIVE_SYNC_NOTI_DELETE_MAILBOX :
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->delete_mailbox.account_id), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->delete_mailbox.mailbox_id), DBUS_TYPE_INVALID);
+ dbus_message_append_args(signal, DBUS_TYPE_INT32, &(data->delete_mailbox.handle), DBUS_TYPE_INVALID);
+ break;
+
+ default:
+ EM_DEBUG_EXCEPTION("Invalid Notification type of Active Sync : subType[%d]", subType);
+ return FAILURE;
+ }
+
+ if(!dbus_connection_send (connection, signal, NULL)) {
+ EM_DEBUG_EXCEPTION("dbus_connection_send is failed");
+ return FAILURE;
+ } else
+ EM_DEBUG_LOG("dbus_connection_send is successful");
+
+ dbus_connection_flush(connection);
+
+FINISH_OFF:
+
+ if(signal)
+ dbus_message_unref(signal);
+
+ EM_DEBUG_FUNC_END();
+ return true;
+}