resolve TSAM-4264: subtract reserved size while getting free memory size
[platform/core/messaging/msg-service.git] / utils / MsgUtilStorage.cpp
1 /*
2  * Copyright (c) 2014 Samsung Electronics Co., Ltd. All rights reserved
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15 */
16
17 #include <stdio.h>
18 #include <string.h>
19 #include <stdlib.h>
20 #include <tr1/unordered_set>
21 #include <queue>
22 #include <glib.h>
23
24 #include <boost/filesystem.hpp>
25 #include <boost/chrono/detail/system.hpp>
26
27 #include "MsgDebug.h"
28 #include "MsgUtilFile.h"
29 #include "MsgContact.h"
30 #include "MsgCppTypes.h"
31 #include "MsgGconfWrapper.h"
32 #include "MsgUtilFunction.h"
33 #include "MsgUtilStorage.h"
34 #include "MsgException.h"
35
36
37 static int msgCntLimit[MSG_COUNT_LIMIT_MAILBOX_TYPE_MAX][MSG_COUNT_LIMIT_MSG_TYPE_MAX] = {{10, 10, 0, 10, 10}, {5, 10, 0, 0, 0}, {10, 10, 0, 0, 0}, {10, 10, 0, 0, 0}, {0, 0, 10, 0, 0}};
38
39 using namespace std;
40
41 #define CHECK_SIZE 1 * 1024 * 1024 * 1024
42 #define RESERVE 100 * 1024 * 1024
43 #define RESERVE_LITE 5 * 1024 * 1024
44
45 /*==================================================================================================
46                                      FUNCTION IMPLEMENTATION
47 ==================================================================================================*/
48
49 unsigned int MsgStoAddMessageTable(MsgDbHandler *pDbHandle, const MSG_MESSAGE_INFO_S *pMsgInfo)
50 {
51         MSG_BEGIN();
52
53         msg_error_t err = MSG_SUCCESS;
54
55         msg_message_id_t msgId = 0;
56
57         err = pDbHandle->getRowId(MSGFW_MESSAGE_TABLE_NAME, &msgId);
58
59         if (err != MSG_SUCCESS)
60                 return 0;
61
62         int fileSize = 0;
63
64         char* pFileData = NULL;
65         unique_ptr<char*, void(*)(char**)> buf(&pFileData, unique_ptr_deleter);
66
67         /* Get File Data */
68         if (pMsgInfo->bTextSms == false) {
69                 if (MsgOpenAndReadFile(pMsgInfo->msgData, &pFileData, &fileSize) == false)
70                         return 0;
71
72                 MSG_DEBUG("file size [%d]", fileSize);
73         }
74
75         char keyName[MAX_VCONFKEY_NAME_LEN];
76         memset(keyName, 0x00, sizeof(keyName));
77         snprintf(keyName, sizeof(keyName), "%s/%d", MSG_SIM_SUBS_ID, pMsgInfo->sim_idx);
78
79         char *imsi = NULL;
80         if (MsgSettingGetString(keyName, &imsi) != MSG_SUCCESS) {
81                 MSG_INFO("MsgSettingGetString() is failed");
82         }
83
84         /* Add Message */
85         char sqlQuery[MAX_QUERY_LEN+1];
86
87         memset(sqlQuery, 0x00, sizeof(sqlQuery));
88         snprintf(sqlQuery, sizeof(sqlQuery), "INSERT INTO %s VALUES (%d, %d, %d, %d, %d, %d, %u, %d, %d, %d, %d, %d, %d, %d, %d, ?, '', '', ?, 0, %d, '%s');",
89                         MSGFW_MESSAGE_TABLE_NAME, msgId, pMsgInfo->threadId, pMsgInfo->folderId, pMsgInfo->storageId, pMsgInfo->msgType.mainType,
90                         pMsgInfo->msgType.subType, (unsigned int)pMsgInfo->displayTime, pMsgInfo->dataSize, pMsgInfo->networkStatus, pMsgInfo->bRead, pMsgInfo->bProtected,
91                         pMsgInfo->priority, pMsgInfo->direction, 0, pMsgInfo->bBackup, pMsgInfo->sim_idx, imsi);
92
93         MSG_DEBUG("QUERY : %s", sqlQuery);
94
95         g_free(imsi);
96         imsi = NULL;
97
98         if (pDbHandle->prepareQuery(sqlQuery) != MSG_SUCCESS)
99                 return 0;
100
101         pDbHandle->bindText(pMsgInfo->subject, 1);
102
103         if (pMsgInfo->msgType.subType == MSG_NOTIFICATIONIND_MMS) {
104                 pDbHandle->bindText("", 2);
105         } else {
106                 if (pMsgInfo->bTextSms == false)
107                         pDbHandle->bindText(pFileData, 2);
108                 else
109                         pDbHandle->bindText(pMsgInfo->msgText, 2);
110         }
111
112         if (pDbHandle->stepQuery() != MSG_ERR_DB_DONE) {
113                 pDbHandle->finalizeQuery();
114                 return 0;
115         }
116
117         pDbHandle->finalizeQuery();
118
119         return msgId;
120 }
121
122
123 msg_error_t MsgStoSetReadStatus(MsgDbHandler *pDbHandle, msg_message_id_t msgId, bool bRead)
124 {
125         char sqlQuery[MAX_QUERY_LEN+1];
126
127         memset(sqlQuery, 0x00, sizeof(sqlQuery));
128         snprintf(sqlQuery, sizeof(sqlQuery), "UPDATE %s SET READ_STATUS = %d WHERE MSG_ID = %d;",
129                         MSGFW_MESSAGE_TABLE_NAME, (int)bRead, msgId);
130
131         if (pDbHandle->execQuery(sqlQuery) != MSG_SUCCESS)
132                 return MSG_ERR_DB_EXEC;
133
134         /* Get MAIN_TYPE, SUB_TYPE, STORAGE_ID */
135         memset(sqlQuery, 0x00, sizeof(sqlQuery));
136         snprintf(sqlQuery, sizeof(sqlQuery), "SELECT A.MAIN_TYPE, A.SUB_TYPE, B.CONV_ID \
137                         FROM %s A, %s B WHERE A.MSG_ID = %d AND A.CONV_ID = B.CONV_ID;",
138                         MSGFW_MESSAGE_TABLE_NAME, MSGFW_CONVERSATION_TABLE_NAME, msgId);
139
140         if (pDbHandle->prepareQuery(sqlQuery) != MSG_SUCCESS)
141                 return MSG_ERR_DB_PREPARE;
142
143         MSG_MESSAGE_TYPE_S msgType;
144         msg_thread_id_t convId;
145
146         if (pDbHandle->stepQuery() == MSG_ERR_DB_ROW) {
147                 msgType.mainType = pDbHandle->columnInt(0);
148                 msgType.subType = pDbHandle->columnInt(1);
149                 convId = pDbHandle->columnInt(2);
150         } else {
151                 pDbHandle->finalizeQuery();
152                 return MSG_ERR_DB_STEP;
153         }
154
155         pDbHandle->finalizeQuery();
156
157         MSG_DEBUG("Main Type:[%d] SubType:[%d] ConvId:[%d]", msgType.mainType, msgType.subType, convId);
158
159         if (MsgStoUpdateConversation(pDbHandle, convId) != MSG_SUCCESS) {
160                 MSG_DEBUG("MsgStoUpdateConversation() Error");
161                 return MSG_ERR_STORAGE_ERROR;
162         }
163
164         return MSG_SUCCESS;
165 }
166
167
168 msg_error_t MsgStoGetOldestMessage(MsgDbHandler *pDbHandle, const MSG_MESSAGE_INFO_S *pMsgInfo, msg_message_id_t *pMsgId)
169 {
170         char sqlQuery[MAX_QUERY_LEN+1];
171
172         memset(sqlQuery, 0x00, sizeof(sqlQuery));
173
174         snprintf(sqlQuery, sizeof(sqlQuery), "SELECT MSG_ID FROM %s \
175                         WHERE SUB_TYPE = %d AND FOLDER_ID = %d AND STORAGE_ID = %d AND PROTECTED = 0 \
176                         ORDER BY DISPLAY_TIME ASC",
177                         MSGFW_MESSAGE_TABLE_NAME, pMsgInfo->msgType.subType, pMsgInfo->folderId, MSG_STORAGE_PHONE);
178
179         if (pDbHandle->prepareQuery(sqlQuery) != MSG_SUCCESS)
180                 return MSG_ERR_DB_PREPARE;
181
182         if (pDbHandle->stepQuery() == MSG_ERR_DB_ROW) {
183                 *pMsgId = pDbHandle->columnInt(0);
184         } else {
185                 pDbHandle->finalizeQuery();
186                 return MSG_ERR_DB_STEP;
187         }
188
189         pDbHandle->finalizeQuery();
190
191         return MSG_SUCCESS;
192 }
193
194
195 msg_error_t MsgStoCheckMsgCntFull(MsgDbHandler *pDbHandle, const MSG_MESSAGE_TYPE_S* pMsgType, msg_folder_id_t folderId)
196 {
197         MSG_BEGIN();
198
199         msg_error_t err = MSG_SUCCESS;
200
201         boost::system::error_code ec;
202         boost::filesystem::space_info si = boost::filesystem::space(TZ_SYS_HOME_PATH, ec);
203         long long int available = 0;
204
205         if (ec) {
206                 MSG_ERR("Failed to get space info [%s]", ec.message().c_str());
207                 return MSG_ERR_STORAGE_ERROR;
208         } else {
209                 if (si.capacity < CHECK_SIZE)
210                         available = si.available - RESERVE_LITE;
211                 else
212                         available = si.available - RESERVE;
213
214                 if (available < 0)
215                         available = 0;
216
217                 MSG_DEBUG("Free space of storage is [%llu] Bytes.", available);
218
219                 if (available < SMS_MINIMUM_SPACE && pMsgType->mainType == MSG_SMS_TYPE)
220                         err = MSG_ERR_MESSAGE_COUNT_FULL;
221                 else if (available < MMS_MINIMUM_SPACE && pMsgType->mainType == MSG_MMS_TYPE)
222                         err = MSG_ERR_MESSAGE_COUNT_FULL;
223         }
224
225         MSG_END();
226
227         return err;
228 }
229
230
231 msg_error_t MsgStoCountMsgByLimitCategory(MsgDbHandler *pDbHandle, const MSG_MESSAGE_TYPE_S *pMsgType, int *pMsgCount, msg_folder_id_t folderId)
232 {
233         if (pMsgType == NULL) {
234                 MSG_DEBUG("pMsgType is NULL");
235                 return MSG_ERR_NULL_POINTER;
236         }
237
238         *pMsgCount = 0;
239
240         char sqlQuery[MAX_QUERY_LEN+1];
241         memset(sqlQuery, 0x00, sizeof(sqlQuery));
242
243         if ((pMsgType->mainType == MSG_SMS_TYPE) && (pMsgType->subType == MSG_WAP_SI_SMS ||pMsgType->subType == MSG_WAP_SL_SMS)) { /* PUSH */
244                 snprintf(sqlQuery, sizeof(sqlQuery), "SELECT COUNT(MSG_ID) FROM %s WHERE MAIN_TYPE = %d AND SUB_TYPE IN (%d, %d) AND FOLDER_ID = %d;",
245                                 MSGFW_MESSAGE_TABLE_NAME, pMsgType->mainType, MSG_WAP_SI_SMS, MSG_WAP_SL_SMS, MSG_INBOX_ID);
246         } else if ((pMsgType->mainType == MSG_SMS_TYPE) && (pMsgType->subType == MSG_CB_SMS)) { /* CB */
247                 snprintf(sqlQuery, sizeof(sqlQuery), "SELECT COUNT(MSG_ID) FROM %s WHERE MAIN_TYPE = %d AND SUB_TYPE IN (%d) AND FOLDER_ID = %d;",
248                                 MSGFW_MESSAGE_TABLE_NAME, pMsgType->mainType, MSG_CB_SMS, MSG_CBMSGBOX_ID);
249         } else if ((pMsgType->mainType == MSG_SMS_TYPE) && (pMsgType->subType == MSG_SYNCML_CP)) { /* Provision */
250                 snprintf(sqlQuery, sizeof(sqlQuery), "SELECT COUNT(MSG_ID) FROM %s WHERE MAIN_TYPE = %d AND SUB_TYPE IN (%d) AND FOLDER_ID = %d;",
251                                 MSGFW_MESSAGE_TABLE_NAME, pMsgType->mainType, MSG_SYNCML_CP, MSG_INBOX_ID);
252         } else if ((pMsgType->mainType == MSG_SMS_TYPE)) { /* SMS */
253                 snprintf(sqlQuery, sizeof(sqlQuery), "SELECT COUNT(MSG_ID) FROM %s WHERE MAIN_TYPE = %d AND SUB_TYPE NOT IN (%d, %d, %d, %d) AND FOLDER_ID = %d;",
254                                 MSGFW_MESSAGE_TABLE_NAME, pMsgType->mainType, MSG_WAP_SI_SMS, MSG_WAP_SL_SMS, MSG_CB_SMS, MSG_SYNCML_CP, MSG_INBOX_ID); /* etc SMS */
255         } else if ((pMsgType->mainType == MSG_MMS_TYPE) &&
256                         (pMsgType->subType == MSG_SENDREQ_MMS || pMsgType->subType == MSG_SENDCONF_MMS || pMsgType->subType == MSG_RETRIEVE_AUTOCONF_MMS ||
257                                         pMsgType->subType == MSG_RETRIEVE_MANUALCONF_MMS || pMsgType->subType == MSG_NOTIFICATIONIND_MMS)) { /* MMS */
258                 snprintf(sqlQuery, sizeof(sqlQuery), "SELECT COUNT(MSG_ID) FROM %s WHERE MAIN_TYPE = %d AND SUB_TYPE IN (%d, %d, %d, %d, %d) AND FOLDER_ID = %d;",
259                                 MSGFW_MESSAGE_TABLE_NAME, pMsgType->mainType, MSG_SENDREQ_MMS, MSG_SENDCONF_MMS, MSG_RETRIEVE_AUTOCONF_MMS, MSG_RETRIEVE_MANUALCONF_MMS, MSG_NOTIFICATIONIND_MMS, folderId);
260         } else {
261                 return MSG_ERR_INVALID_PARAMETER;
262         }
263
264         if (pDbHandle->prepareQuery(sqlQuery) != MSG_SUCCESS)
265                 return MSG_ERR_DB_PREPARE;
266
267         if (pDbHandle->stepQuery() == MSG_ERR_DB_ROW) {
268                 *pMsgCount = pDbHandle->columnInt(0);
269         } else {
270                 pDbHandle->finalizeQuery();
271                 return MSG_ERR_DB_STEP;
272         }
273
274         pDbHandle->finalizeQuery();
275
276         return MSG_SUCCESS;
277 }
278
279
280 int MsgStoCheckMsgCntLimit(const MSG_MESSAGE_TYPE_S* pMsgType, msg_folder_id_t folderId)
281 {
282         int msgboxType = -1;
283         int msgType = -1;
284
285         switch (folderId) {
286                 case MSG_INBOX_ID :
287                         msgboxType = MSG_COUNT_LIMIT_INBOX_TYPE;
288                 break;
289
290                 case MSG_OUTBOX_ID :
291                         msgboxType = MSG_COUNT_LIMIT_OUTBOX_TYPE;
292                 break;
293
294                 case MSG_SENTBOX_ID :
295                         msgboxType = MSG_COUNT_LIMIT_SENTBOX_TYPE;
296                 break;
297
298                 case MSG_DRAFT_ID :
299                         msgboxType = MSG_COUNT_LIMIT_DRAFTBOX_TYPE;
300                 break;
301
302                 case MSG_CBMSGBOX_ID :
303                         msgboxType = MSG_COUNT_LIMIT_CBMSGBOX_TYPE;
304                 break;
305
306                 default:
307                         MSG_DEBUG("Unknown mailbox Type [%d]", folderId);
308                 return -1;
309         }
310
311         switch (pMsgType->subType) {
312                 case MSG_NORMAL_SMS:
313                 case MSG_REPLACE_TYPE1_SMS:
314                 case MSG_REPLACE_TYPE2_SMS:
315                 case MSG_REPLACE_TYPE3_SMS:
316                 case MSG_REPLACE_TYPE4_SMS:
317                 case MSG_REPLACE_TYPE5_SMS:
318                 case MSG_REPLACE_TYPE6_SMS:
319                 case MSG_REPLACE_TYPE7_SMS:
320                 case MSG_MWI_VOICE_SMS:
321                 case MSG_MWI_FAX_SMS:
322                 case MSG_MWI_EMAIL_SMS:
323                 case MSG_MWI_OTHER_SMS:
324                 case MSG_STATUS_REPORT_SMS:
325                         msgType = MSG_COUNT_LIMIT_SMS_TYPE;
326                 break;
327
328                 case MSG_CB_SMS:
329                         msgType = MSG_COUNT_LIMIT_CB_TYPE;
330                 break;
331
332                 case MSG_WAP_SI_SMS:
333                 case MSG_WAP_SL_SMS:
334                         msgType = MSG_COUNT_LIMIT_WAPPUSH_TYPE;
335                 break;
336
337                 case MSG_SYNCML_CP:
338                         msgType = MSG_COUNT_LIMIT_PROVISION_TYPE;
339                 break;
340
341                 case MSG_SENDREQ_MMS:
342                 case MSG_SENDCONF_MMS:
343                 case MSG_NOTIFICATIONIND_MMS:
344                 case MSG_RETRIEVE_AUTOCONF_MMS:
345                 case MSG_RETRIEVE_MANUALCONF_MMS:
346                         msgType = MSG_COUNT_LIMIT_MMS_TYPE;
347                 break;
348
349                 default:
350                         MSG_DEBUG("Unknown Message Type [%d]", pMsgType->subType);
351                 return -1;
352         }
353
354         return msgCntLimit[msgboxType][msgType];
355 }
356
357
358 msg_error_t MsgStocheckMemoryStatus()
359 {
360         msg_error_t err = MSG_SUCCESS;
361         boost::system::error_code ec;
362         boost::filesystem::space_info si = boost::filesystem::space(TZ_SYS_HOME_PATH, ec);
363         long long int available = 0;
364
365         if (ec) {
366                 MSG_ERR("Failed to get space info [%s]", ec.message().c_str());
367                 return MSG_ERR_STORAGE_ERROR;
368         }
369
370         if (si.capacity < CHECK_SIZE)
371                 available = si.available - RESERVE_LITE;
372         else
373                 available = si.available - RESERVE;
374
375         if (available < 0)
376                 available = 0;
377
378         MSG_DEBUG("Free space of storage is [%llu] Bytes.", available);
379
380         if (available < SMS_MINIMUM_SPACE)
381                 err = MSG_ERR_MESSAGE_COUNT_FULL;
382
383         MSG_DEBUG("Memory status =[%d]", err);
384
385         return err;
386 }
387
388
389 msg_error_t MsgStoAddAddress(MsgDbHandler *pDbHandle, const MSG_MESSAGE_INFO_S *pMsg, msg_thread_id_t *pConvId)
390 {
391         msg_error_t err = MSG_SUCCESS;
392
393         char sqlQuery[MAX_QUERY_LEN+1];
394
395         /* Check if new address or not */
396         if (MsgExistAddress(pDbHandle, pMsg, pConvId) == true) {
397                 MSG_DEBUG("The address already exists. Conversation ID : [%d]", *pConvId);
398                 MsgStoUpdateAddress(pDbHandle, pMsg, *pConvId);
399         } else {
400                 *pConvId = 0;
401
402                 if (pMsg->threadId)
403                         *pConvId = pMsg->threadId;
404
405                 /* conversation insert */
406                 err = MsgStoAddConversation(pDbHandle, pConvId);
407                 if (err != MSG_SUCCESS) {
408                         MSG_DEBUG("MsgStoAddConversation() fail [%d]", err);
409                         return err;
410                 }
411
412                 /* insert address in loop */
413                 for (int i = 0; i < pMsg->nAddressCnt; i++) {
414                         unsigned int addrId;
415                         MSG_CONTACT_INFO_S contactInfo;
416                         memset(&contactInfo, 0x00, sizeof(MSG_CONTACT_INFO_S));
417
418                         /* Get Contact Info */
419 #if 0
420                         if (MsgGetContactInfo(&(pMsg->addressList[i]), &contactInfo) != MSG_SUCCESS) {
421                                 MSG_DEBUG("MsgGetContactInfo() fail.");
422                         }
423 #endif
424
425                         err = pDbHandle->getRowId(MSGFW_ADDRESS_TABLE_NAME, &addrId);
426                         if (err != MSG_SUCCESS) {
427                                 MSG_DEBUG("pDbHandle->getRowId fail. [%d]", err);
428                                 return err;
429                         }
430
431                         /* Add Address */
432                         memset(sqlQuery, 0x00, sizeof(sqlQuery));
433                         snprintf(sqlQuery, sizeof(sqlQuery), "INSERT INTO %s VALUES (%d, %d, %d, %d, '%s', %d, %d, ?, ?, ?, ?, ?, '%s', 0);",
434                                                 MSGFW_ADDRESS_TABLE_NAME, addrId, *pConvId, pMsg->addressList[i].addressType, pMsg->addressList[i].recipientType, pMsg->addressList[i].addressVal,
435                                                 contactInfo.contactId, contactInfo.addrbookId, contactInfo.imagePath);
436
437                         MSG_SEC_DEBUG("Add Address Info. [%s]", sqlQuery);
438
439                         if (pDbHandle->prepareQuery(sqlQuery) != MSG_SUCCESS)
440                                 return MSG_ERR_DB_PREPARE;
441
442                         pDbHandle->bindText(contactInfo.firstName, 1);
443                         pDbHandle->bindText(contactInfo.lastName, 2);
444                         pDbHandle->bindText(contactInfo.middleName, 3);
445                         pDbHandle->bindText(contactInfo.prefix, 4);
446                         pDbHandle->bindText(contactInfo.suffix, 5);
447
448                         if (pDbHandle->stepQuery() != MSG_ERR_DB_DONE) {
449                                 pDbHandle->finalizeQuery();
450                                 return MSG_ERR_DB_STEP;
451                         }
452
453                         pDbHandle->finalizeQuery();
454                 }
455         }
456
457         /* set conversation display name by conv id */
458         MsgStoSetConversationDisplayName(pDbHandle, *pConvId);
459
460         return err;
461 }
462
463 msg_error_t MsgStoGetAddressByMsgId(MsgDbHandler *pDbHandle, msg_message_id_t msgId, int *nAddressCnt, MSG_ADDRESS_INFO_S **pAddress)
464 {
465         char sqlQuery[MAX_QUERY_LEN+1];
466         int rowCnt = 0, index = 0;
467
468         *nAddressCnt = 0;
469
470         memset(sqlQuery, 0x00, sizeof(sqlQuery));
471         snprintf(sqlQuery, sizeof(sqlQuery), "SELECT "
472                         "A.ADDRESS_TYPE, "
473                         "A.RECIPIENT_TYPE, "
474                         "A.ADDRESS_VAL "
475                         "FROM %s A, %s B "
476                         "WHERE A.CONV_ID = B.CONV_ID "
477                         "AND B.MSG_ID = %d;",
478                         MSGFW_ADDRESS_TABLE_NAME, MSGFW_MESSAGE_TABLE_NAME,
479                         msgId);
480
481         msg_error_t err = pDbHandle->getTable(sqlQuery, &rowCnt, &index);
482
483         if (err == MSG_ERR_DB_NORECORD) {
484                 pDbHandle->freeTable();
485                 return MSG_SUCCESS;
486         } else if (err != MSG_SUCCESS) {
487                 MSG_DEBUG("Fail to getTable().");
488                 pDbHandle->freeTable();
489                 return err;
490         }
491
492         *nAddressCnt = rowCnt;
493
494         MSG_DEBUG("*nAddressCnt [%d]", *nAddressCnt);
495
496         MSG_ADDRESS_INFO_S *tmpAddressList = (MSG_ADDRESS_INFO_S *)new char[sizeof(MSG_ADDRESS_INFO_S) * rowCnt];
497         memset(tmpAddressList, 0x00, sizeof(MSG_ADDRESS_INFO_S) * rowCnt);
498         *pAddress = tmpAddressList;
499
500         for (int i = 0; i < rowCnt; i++) {
501                 tmpAddressList[i].addressType = pDbHandle->getColumnToInt(index++);
502                 tmpAddressList[i].recipientType = pDbHandle->getColumnToInt(index++);
503                 pDbHandle->getColumnToString(index++, MAX_ADDRESS_VAL_LEN, tmpAddressList[i].addressVal);
504
505                 strncpy(tmpAddressList[i].displayName, tmpAddressList[i].addressVal, MAX_DISPLAY_NAME_LEN);
506         }
507         pDbHandle->freeTable();
508
509         return MSG_SUCCESS;
510 }
511
512 msg_error_t MsgStoGetAddressByMsgId(MsgDbHandler *pDbHandle, msg_message_id_t msgId, msg_struct_list_s *pAddress)
513 {
514         char sqlQuery[MAX_QUERY_LEN+1];
515
516         int rowCnt = 0, index = 0;
517
518         pAddress->nCount = 0;
519         pAddress->msg_struct_info = NULL;
520
521         msg_struct_s *pTmp = NULL;
522         MSG_ADDRESS_INFO_S *pAddr = NULL;
523
524         pAddress->msg_struct_info = (msg_struct_t *)calloc(MAX_TO_ADDRESS_CNT, sizeof(msg_struct_t));
525         if (pAddress->msg_struct_info == NULL)
526                 return MSG_ERR_MEMORY_ERROR;
527
528         for (int i = 0; i < MAX_TO_ADDRESS_CNT; i++) {
529                 pAddress->msg_struct_info[i] = (msg_struct_t)new msg_struct_s;
530                 pTmp = (msg_struct_s *)pAddress->msg_struct_info[i];
531                 pTmp->type = MSG_STRUCT_ADDRESS_INFO;
532                 pTmp->data = new MSG_ADDRESS_INFO_S;
533                 memset(pTmp->data, 0x00, sizeof(MSG_ADDRESS_INFO_S));
534         }
535
536         memset(sqlQuery, 0x00, sizeof(sqlQuery));
537         snprintf(sqlQuery, sizeof(sqlQuery), "SELECT "
538                         "A.ADDRESS_TYPE, "
539                         "A.RECIPIENT_TYPE, "
540                         "A.ADDRESS_VAL "
541                         "FROM %s A, %s B "
542                         "WHERE A.CONV_ID = B.CONV_ID "
543                         "AND B.MSG_ID = %d;",
544                         MSGFW_ADDRESS_TABLE_NAME, MSGFW_MESSAGE_TABLE_NAME,
545                         msgId);
546
547         msg_error_t err = pDbHandle->getTable(sqlQuery, &rowCnt, &index);
548
549         if (err == MSG_ERR_DB_NORECORD) {
550                 pDbHandle->freeTable();
551                 return MSG_SUCCESS;
552         } else if (err != MSG_SUCCESS) {
553                 MSG_DEBUG("Fail to getTable().");
554                 pDbHandle->freeTable();
555                 return err;
556         }
557
558         rowCnt = (rowCnt > 10)? MAX_TO_ADDRESS_CNT: rowCnt;
559         pAddress->nCount = rowCnt;
560
561         for (int i = 0; i < rowCnt; i++) {
562                 pTmp = (msg_struct_s *)pAddress->msg_struct_info[i];
563                 pAddr = (MSG_ADDRESS_INFO_S *)pTmp->data;
564
565                 pAddr->addressType = pDbHandle->getColumnToInt(index++);
566                 pAddr->recipientType = pDbHandle->getColumnToInt(index++);
567
568                 pDbHandle->getColumnToString(index++, MAX_ADDRESS_VAL_LEN, pAddr->addressVal);
569
570                 strncpy(pAddr->displayName, pAddr->addressVal, MAX_DISPLAY_NAME_LEN);
571         }
572
573         pDbHandle->freeTable();
574
575         return MSG_SUCCESS;
576 }
577
578
579 msg_error_t MsgStoGetAddressByConvId(MsgDbHandler *pDbHandle, msg_thread_id_t convId, msg_struct_list_s *pAddrlist)
580 {
581         char sqlQuery[MAX_QUERY_LEN+1];
582
583         int rowCnt = 0, index = 0;
584
585         pAddrlist->nCount = 0;
586         pAddrlist->msg_struct_info = NULL;
587
588         memset(sqlQuery, 0x00, sizeof(sqlQuery));
589         snprintf(sqlQuery, sizeof(sqlQuery), "SELECT "
590                         "ADDRESS_TYPE, "
591                         "RECIPIENT_TYPE, "
592                         "ADDRESS_VAL "
593                         "FROM %s WHERE CONV_ID  = %d;",
594                         MSGFW_ADDRESS_TABLE_NAME, convId);
595
596         msg_error_t err = pDbHandle->getTable(sqlQuery, &rowCnt, &index);
597
598         if (err == MSG_ERR_DB_NORECORD) {
599                 pDbHandle->freeTable();
600                 return MSG_SUCCESS;
601         } else if (err != MSG_SUCCESS) {
602                 MSG_DEBUG("Fail to getTable().");
603                 pDbHandle->freeTable();
604                 return err;
605         }
606
607         pAddrlist->nCount = rowCnt;
608
609         MSG_DEBUG("pAddrlist->nCount [%d]", pAddrlist->nCount);
610
611         msg_struct_s *pTmp = NULL;
612         MSG_ADDRESS_INFO_S *pAddr = NULL;
613
614         pAddrlist->msg_struct_info = (msg_struct_t *)calloc(rowCnt, sizeof(msg_struct_t));
615
616         for (int i = 0; i < rowCnt; i++) {
617                 pAddrlist->msg_struct_info[i] = (msg_struct_t)new msg_struct_s;
618                 pTmp = (msg_struct_s *)pAddrlist->msg_struct_info[i];
619                 pTmp->type = MSG_STRUCT_ADDRESS_INFO;
620                 pTmp->data = new MSG_ADDRESS_INFO_S;
621                 memset(pTmp->data, 0x00, sizeof(MSG_ADDRESS_INFO_S));
622         }
623
624 /*      rowCnt = (rowCnt > 10)? MAX_TO_ADDRESS_CNT: rowCnt; */
625
626         for (int i = 0; i < rowCnt; i++) {
627                 pTmp = (msg_struct_s *)pAddrlist->msg_struct_info[i];
628                 pAddr = (MSG_ADDRESS_INFO_S *)pTmp->data;
629
630                 pAddr->addressType = pDbHandle->getColumnToInt(index++);
631                 pAddr->recipientType = pDbHandle->getColumnToInt(index++);
632                 pDbHandle->getColumnToString(index++, MAX_ADDRESS_VAL_LEN, pAddr->addressVal);
633
634                 strncpy(pAddr->displayName, pAddr->addressVal, MAX_DISPLAY_NAME_LEN);
635         }
636         pDbHandle->freeTable();
637
638         return MSG_SUCCESS;
639 }
640
641 /* Have to use trigger for this function. */
642 msg_error_t MsgStoUpdateConversation(MsgDbHandler *pDbHandle, msg_thread_id_t convId)
643 {
644         MSG_BEGIN();
645
646         char sqlQuery[MAX_QUERY_LEN];
647         unsigned int tmpSize = 0;
648
649 #ifdef MSG_NOTI_INTEGRATION
650         memset(sqlQuery, 0x00, MAX_QUERY_LEN);
651         snprintf(sqlQuery, sizeof(sqlQuery),
652                         "SELECT * "
653                         "FROM %s "
654                         "WHERE CONV_ID = %d "
655                         "AND FOLDER_ID > %d AND FOLDER_ID < %d "
656                         "AND STORAGE_ID = %d;",
657                         MSGFW_MESSAGE_TABLE_NAME,
658                         convId,
659                         MSG_ALLBOX_ID, MSG_SPAMBOX_ID,
660                         MSG_STORAGE_PHONE);
661 #else
662         memset(sqlQuery, 0x00, MAX_QUERY_LEN);
663         snprintf(sqlQuery, sizeof(sqlQuery),
664                         "SELECT * "
665                         "FROM %s "
666                         "WHERE CONV_ID = %d "
667                         "AND FOLDER_ID > %d AND FOLDER_ID < %d "
668                         "AND STORAGE_ID = %d;",
669                         MSGFW_MESSAGE_TABLE_NAME,
670                         convId,
671                         MSG_ALLBOX_ID, MSG_CBMSGBOX_ID,
672                         MSG_STORAGE_PHONE);
673 #endif
674
675         msg_error_t err = pDbHandle->prepareQuery(sqlQuery);
676         if (err != MSG_SUCCESS) {
677                         MSG_DEBUG("Fail to prepareQuery().");
678                         pDbHandle->finalizeQuery();
679                         return err;
680         }
681
682         if (pDbHandle->stepQuery() == MSG_ERR_DB_ROW) {
683                 pDbHandle->finalizeQuery();
684
685                 memset(sqlQuery, 0x00, MAX_QUERY_LEN);
686                 snprintf(sqlQuery, sizeof(sqlQuery),
687                                 "SELECT MAIN_TYPE, SUB_TYPE, MSG_DIRECTION, DISPLAY_TIME, LENGTH(SUBJECT), SUBJECT, MSG_TEXT "
688                                 "FROM %s "
689                                 "WHERE CONV_ID = %d AND FOLDER_ID > %d AND FOLDER_ID < %d AND STORAGE_ID = %d AND SCHEDULED_TIME = 0 ORDER BY DISPLAY_TIME DESC;",
690                                 MSGFW_MESSAGE_TABLE_NAME,
691                                 convId, MSG_ALLBOX_ID, MSG_SPAMBOX_ID, MSG_STORAGE_PHONE);
692
693                 err = pDbHandle->prepareQuery(sqlQuery);
694                 if (err != MSG_SUCCESS) {
695                         MSG_DEBUG("Fail to prepareQuery().");
696                         return err;
697                 }
698
699                 err = pDbHandle->stepQuery();
700                 if (err != MSG_ERR_DB_ROW) {
701                         MSG_DEBUG("Fail to stepQuery().");
702                         pDbHandle->finalizeQuery();
703                         return err;
704                 }
705
706                 int main_type = pDbHandle->columnInt(0);
707                 int sub_type = pDbHandle->columnInt(1);
708                 int msg_direction = pDbHandle->columnInt(2);
709                 time_t disp_time = (time_t)pDbHandle->columnInt(3);
710                 int subject_length = pDbHandle->columnInt(4);
711                 char subject[MAX_SUBJECT_LEN+1] = {0, };
712                 snprintf(subject, sizeof(subject), "%s", pDbHandle->columnText(5));
713                 char msg_text[MAX_MSG_TEXT_LEN+1] = {0, };
714                 snprintf(msg_text, sizeof(msg_text), "%s", pDbHandle->columnText(6));
715
716                 pDbHandle->finalizeQuery();
717                 memset(sqlQuery, 0x00, MAX_QUERY_LEN);
718                 snprintf(sqlQuery, sizeof(sqlQuery),
719                                 "UPDATE %s SET ",
720                                 MSGFW_CONVERSATION_TABLE_NAME);
721
722                 tmpSize = strlen(sqlQuery);
723 #ifdef MSG_NOTI_INTEGRATION
724                 snprintf(sqlQuery+tmpSize, MAX_QUERY_LEN-tmpSize,
725                                 "UNREAD_CNT = (SELECT COUNT(MSG_ID) FROM %s WHERE CONV_ID = %d AND (FOLDER_ID = %d OR FOLDER_ID = %d) AND STORAGE_ID = %d AND READ_STATUS = 0), ",
726                                 MSGFW_MESSAGE_TABLE_NAME, convId, MSG_INBOX_ID, MSG_CBMSGBOX_ID, MSG_STORAGE_PHONE);
727 #else
728                 snprintf(sqlQuery+tmpSize, MAX_QUERY_LEN-tmpSize,
729                                 "UNREAD_CNT = (SELECT COUNT(MSG_ID) FROM %s WHERE CONV_ID = %d AND FOLDER_ID = %d AND STORAGE_ID = %d AND READ_STATUS = 0), ",
730                                 MSGFW_MESSAGE_TABLE_NAME, convId, MSG_INBOX_ID, MSG_STORAGE_PHONE);
731 #endif
732
733                 tmpSize = strlen(sqlQuery);
734 #ifdef MSG_NOTI_INTEGRATION
735                 snprintf(sqlQuery+tmpSize, MAX_QUERY_LEN-tmpSize,
736                                 "SMS_CNT = (SELECT COUNT(MSG_ID) FROM %s WHERE CONV_ID = %d AND MAIN_TYPE = %d AND FOLDER_ID > %d AND FOLDER_ID < %d AND STORAGE_ID = %d), ",
737                                 MSGFW_MESSAGE_TABLE_NAME, convId, MSG_SMS_TYPE, MSG_ALLBOX_ID, MSG_SPAMBOX_ID, MSG_STORAGE_PHONE);
738 #else
739                 snprintf(sqlQuery+tmpSize, MAX_QUERY_LEN-tmpSize,
740                                 "SMS_CNT = (SELECT COUNT(MSG_ID) FROM %s WHERE CONV_ID = %d AND MAIN_TYPE = %d AND FOLDER_ID > %d AND FOLDER_ID < %d AND STORAGE_ID = %d), ",
741                                 MSGFW_MESSAGE_TABLE_NAME, convId, MSG_SMS_TYPE, MSG_ALLBOX_ID, MSG_CBMSGBOX_ID, MSG_STORAGE_PHONE);
742 #endif
743
744                 tmpSize = strlen(sqlQuery);
745                 snprintf(sqlQuery+tmpSize, MAX_QUERY_LEN-tmpSize,
746                                 "MMS_CNT = (SELECT COUNT(MSG_ID) FROM %s WHERE CONV_ID = %d AND MAIN_TYPE = %d AND SUB_TYPE NOT IN (%d, %d, %d) AND FOLDER_ID > %d AND FOLDER_ID < %d AND STORAGE_ID = %d), ",
747                                 MSGFW_MESSAGE_TABLE_NAME, convId, MSG_MMS_TYPE, MSG_DELIVERYIND_MMS, MSG_READRECIND_MMS, MSG_READORGIND_MMS, MSG_ALLBOX_ID, MSG_CBMSGBOX_ID, MSG_STORAGE_PHONE);
748
749 #if 0
750                 tmpSize = strlen(sqlQuery);
751                 snprintf(sqlQuery+tmpSize, MAX_QUERY_LEN-tmpSize,
752                                 "MAIN_TYPE = (SELECT MAIN_TYPE FROM %s WHERE CONV_ID = %d AND FOLDER_ID > %d AND FOLDER_ID < %d AND STORAGE_ID = %d ORDER BY DISPLAY_TIME DESC), ",
753                                 MSGFW_MESSAGE_TABLE_NAME, convId, MSG_ALLBOX_ID, MSG_SPAMBOX_ID, MSG_STORAGE_PHONE);
754
755                 tmpSize = strlen(sqlQuery);
756                 snprintf(sqlQuery+tmpSize, MAX_QUERY_LEN-tmpSize,
757                                 "SUB_TYPE = (SELECT SUB_TYPE FROM %s WHERE CONV_ID = %d AND FOLDER_ID > %d AND FOLDER_ID < %d AND STORAGE_ID = %d ORDER BY DISPLAY_TIME DESC), ",
758                                 MSGFW_MESSAGE_TABLE_NAME, convId, MSG_ALLBOX_ID, MSG_SPAMBOX_ID, MSG_STORAGE_PHONE);
759
760                 tmpSize = strlen(sqlQuery);
761                 snprintf(sqlQuery+tmpSize, MAX_QUERY_LEN-tmpSize,
762                                 "MSG_DIRECTION = (SELECT MSG_DIRECTION FROM %s WHERE CONV_ID = %d AND FOLDER_ID > %d AND FOLDER_ID < %d AND STORAGE_ID = %d ORDER BY DISPLAY_TIME DESC), ",
763                                 MSGFW_MESSAGE_TABLE_NAME, convId, MSG_ALLBOX_ID, MSG_SPAMBOX_ID, MSG_STORAGE_PHONE);
764
765                 tmpSize = strlen(sqlQuery);
766 #if 1
767                 snprintf(sqlQuery+tmpSize, MAX_QUERY_LEN-tmpSize,
768                                 "DISPLAY_TIME = CASE "
769                                 "WHEN (SELECT COUNT(MSG_ID) FROM %s WHERE CONV_ID = %d AND FOLDER_ID > %d AND FOLDER_ID < %d AND STORAGE_ID = %d AND SCHEDULED_TIME = 0 ORDER BY DISPLAY_TIME DESC) > 0 "
770                                 "THEN (SELECT DISPLAY_TIME FROM %s WHERE CONV_ID = %d AND FOLDER_ID > %d AND FOLDER_ID < %d AND STORAGE_ID = %d AND SCHEDULED_TIME = 0 ORDER BY DISPLAY_TIME DESC) "
771                                 "ELSE 0 "
772                                 "END, ",
773                                 MSGFW_MESSAGE_TABLE_NAME, convId, MSG_ALLBOX_ID, MSG_SPAMBOX_ID, MSG_STORAGE_PHONE,
774                                 MSGFW_MESSAGE_TABLE_NAME, convId, MSG_ALLBOX_ID, MSG_SPAMBOX_ID, MSG_STORAGE_PHONE);
775 #else
776                 snprintf(sqlQuery+tmpSize, MAX_QUERY_LEN-tmpSize,
777                                 "DISPLAY_TIME = CASE "
778                                 "WHEN (SELECT COUNT(MSG_ID) FROM %s WHERE CONV_ID = %d AND FOLDER_ID = %d AND STORAGE_ID = %d AND READ_STATUS = 0) > 0 "
779                                 "THEN (SELECT DISPLAY_TIME FROM %s WHERE CONV_ID = %d AND FOLDER_ID = %d AND STORAGE_ID = %d AND READ_STATUS = 0 ORDER BY DISPLAY_TIME DESC) "
780                                 "WHEN (SELECT COUNT(MSG_ID) FROM %s WHERE CONV_ID = %d AND FOLDER_ID = %d AND STORAGE_ID = %d) > 0 "
781                                 "THEN (SELECT DISPLAY_TIME FROM %s WHERE CONV_ID = %d AND FOLDER_ID = %d AND STORAGE_ID = %d ORDER BY DISPLAY_TIME DESC) "
782                                 "WHEN (SELECT COUNT(MSG_ID) FROM %s WHERE CONV_ID = %d AND FOLDER_ID = %d AND STORAGE_ID = %d AND NETWORK_STATUS = %d) > 0 "
783                                 "THEN (SELECT DISPLAY_TIME FROM %s WHERE CONV_ID = %d AND FOLDER_ID = %d AND STORAGE_ID = %d AND NETWORK_STATUS = %d ORDER BY DISPLAY_TIME DESC) "
784                                 "ELSE (SELECT DISPLAY_TIME FROM %s WHERE CONV_ID = %d AND FOLDER_ID > %d AND FOLDER_ID < %d AND STORAGE_ID = %d ORDER BY DISPLAY_TIME DESC) "
785                                 "END, ",
786                                 MSGFW_MESSAGE_TABLE_NAME, convId, MSG_INBOX_ID, MSG_STORAGE_PHONE,
787                                 MSGFW_MESSAGE_TABLE_NAME, convId, MSG_INBOX_ID, MSG_STORAGE_PHONE,
788                                 MSGFW_MESSAGE_TABLE_NAME, convId, MSG_DRAFT_ID, MSG_STORAGE_PHONE,
789                                 MSGFW_MESSAGE_TABLE_NAME, convId, MSG_DRAFT_ID, MSG_STORAGE_PHONE,
790                                 MSGFW_MESSAGE_TABLE_NAME, convId, MSG_OUTBOX_ID, MSG_STORAGE_PHONE, MSG_NETWORK_SEND_FAIL,
791                                 MSGFW_MESSAGE_TABLE_NAME, convId, MSG_OUTBOX_ID, MSG_STORAGE_PHONE, MSG_NETWORK_SEND_FAIL,
792                                 MSGFW_MESSAGE_TABLE_NAME, convId, MSG_ALLBOX_ID, MSG_SPAMBOX_ID, MSG_STORAGE_PHONE);
793 #endif
794
795 #endif
796                 tmpSize = strlen(sqlQuery);
797                 snprintf(sqlQuery+tmpSize, MAX_QUERY_LEN-tmpSize,
798                                 "MSG_TEXT = CASE "
799                                 "WHEN %d > 0 THEN ? ELSE ? "
800                                 "END, ",
801                                 subject_length);
802 #if 0
803                 snprintf(sqlQuery+tmpSize, MAX_QUERY_LEN-tmpSize,
804                                 "MSG_TEXT = CASE "
805                                 "WHEN (SELECT COUNT(MSG_ID) FROM %s WHERE CONV_ID = %d AND FOLDER_ID > %d AND FOLDER_ID < %d AND STORAGE_ID = %d AND SCHEDULED_TIME = 0 ORDER BY DISPLAY_TIME DESC) > 0 "
806                                 "THEN CASE "
807                                 "WHEN (SELECT LENGTH(SUBJECT) FROM %s WHERE CONV_ID = %d AND FOLDER_ID > %d AND FOLDER_ID < %d AND STORAGE_ID = %d AND SCHEDULED_TIME = 0 ORDER BY DISPLAY_TIME DESC) > 0 "
808                                 "THEN (SELECT SUBJECT FROM %s WHERE CONV_ID = %d AND FOLDER_ID > %d AND FOLDER_ID < %d AND STORAGE_ID = %d AND SCHEDULED_TIME = 0 ORDER BY DISPLAY_TIME DESC) "
809                                 "ELSE (SELECT MSG_TEXT FROM %s WHERE CONV_ID = %d AND FOLDER_ID > %d AND FOLDER_ID < %d AND STORAGE_ID = %d AND SCHEDULED_TIME = 0 ORDER BY DISPLAY_TIME DESC) "
810                                 "END ELSE '' "
811                                 "END ",
812                                 MSGFW_MESSAGE_TABLE_NAME, convId, MSG_ALLBOX_ID, MSG_SPAMBOX_ID, MSG_STORAGE_PHONE,
813                                 MSGFW_MESSAGE_TABLE_NAME, convId, MSG_ALLBOX_ID, MSG_SPAMBOX_ID, MSG_STORAGE_PHONE,
814                                 MSGFW_MESSAGE_TABLE_NAME, convId, MSG_ALLBOX_ID, MSG_SPAMBOX_ID, MSG_STORAGE_PHONE,
815                                 MSGFW_MESSAGE_TABLE_NAME, convId, MSG_ALLBOX_ID, MSG_SPAMBOX_ID, MSG_STORAGE_PHONE);
816 #endif
817                 tmpSize = strlen(sqlQuery);
818                 snprintf(sqlQuery+tmpSize, MAX_QUERY_LEN-tmpSize,
819                                 "MAIN_TYPE = %d, SUB_TYPE = %d, MSG_DIRECTION = %d, DISPLAY_TIME = %lu ",
820                                 main_type, sub_type, msg_direction, disp_time);
821
822                 tmpSize = strlen(sqlQuery);
823                 snprintf(sqlQuery+tmpSize, MAX_QUERY_LEN-tmpSize,
824                                 "WHERE CONV_ID = %d;",
825                                 convId);
826                 if (pDbHandle->prepareQuery(sqlQuery) != MSG_SUCCESS) {
827                         MSG_DEBUG("Query Failed [%s]", sqlQuery);
828                         return MSG_ERR_DB_PREPARE;
829                 }
830
831                 pDbHandle->bindText(subject, 1);
832                 pDbHandle->bindText(msg_text, 2);
833
834                 if (pDbHandle->stepQuery() != MSG_ERR_DB_DONE) {
835                         MSG_DEBUG("stepQuery() Failed");
836                         pDbHandle->finalizeQuery();
837                         return MSG_ERR_DB_STEP;
838                 }
839
840                 pDbHandle->finalizeQuery();
841         } else {
842                 pDbHandle->finalizeQuery();
843
844                 memset(sqlQuery, 0x00, MAX_QUERY_LEN);
845                 snprintf(sqlQuery, sizeof(sqlQuery),
846                                 "UPDATE %s SET UNREAD_CNT = 0, SMS_CNT = 0, MMS_CNT = 0, MAIN_TYPE = 0, SUB_TYPE = 0, MSG_DIRECTION = 0, DISPLAY_TIME = 0, MSG_TEXT = '' "
847                                 "WHERE CONV_ID = %d;",
848                                 MSGFW_CONVERSATION_TABLE_NAME, convId);
849
850                 if (pDbHandle->execQuery(sqlQuery) != MSG_SUCCESS) {
851                         MSG_DEBUG("Query Failed [%s]", sqlQuery);
852                         return MSG_ERR_DB_EXEC;
853                 }
854         }
855
856         MSG_END();
857
858         return MSG_SUCCESS;
859 }
860
861
862 /* consider to replcae this function to trigger. */
863 msg_error_t MsgStoClearConversationTable(MsgDbHandler *pDbHandle)
864 {
865         msg_error_t err = MSG_SUCCESS;
866
867         char sqlQuery[MAX_QUERY_LEN+1];
868
869         memset(sqlQuery, 0x00, sizeof(sqlQuery));
870
871         snprintf(sqlQuery, sizeof(sqlQuery), "DELETE FROM %s \
872                         WHERE CONV_ID NOT IN (SELECT CONV_ID FROM %s) AND CONV_ID <> 0;",
873                         MSGFW_CONVERSATION_TABLE_NAME, MSGFW_MESSAGE_TABLE_NAME);
874
875         err = pDbHandle->execQuery(sqlQuery);
876
877         snprintf(sqlQuery, sizeof(sqlQuery), "DELETE FROM %s WHERE CONV_ID NOT IN (SELECT CONV_ID FROM %s);",
878                         MSGFW_ADDRESS_TABLE_NAME, MSGFW_CONVERSATION_TABLE_NAME);
879
880         err = pDbHandle->execQuery(sqlQuery);
881
882         return err;
883 }
884
885
886 msg_thread_id_t MsgGetThreadId(MsgDbHandler *pDbHandle, msg_message_id_t msgId)
887 {
888         msg_thread_id_t conv_id = 0;
889
890         char sqlQuery[MAX_QUERY_LEN+1];
891         memset(sqlQuery, 0x00, sizeof(sqlQuery));
892         snprintf(sqlQuery, sizeof(sqlQuery), "SELECT CONV_ID FROM %s WHERE MSG_ID = %d;",
893                         MSGFW_MESSAGE_TABLE_NAME, msgId);
894
895         if (pDbHandle->prepareQuery(sqlQuery) != MSG_SUCCESS)
896                 return 0;
897
898         if (pDbHandle->stepQuery() == MSG_ERR_DB_ROW) {
899                 conv_id = pDbHandle->columnInt(0);
900         }
901
902         pDbHandle->finalizeQuery();
903
904         return conv_id;
905 }
906
907 /* Change the function name to conversation related. */
908 bool MsgExistAddress(MsgDbHandler *pDbHandle, const MSG_MESSAGE_INFO_S *pMsg, msg_thread_id_t *pConvId)
909 {
910         msg_error_t err = MSG_SUCCESS;
911
912         char sqlQuery[MAX_QUERY_LEN+1];
913         unsigned int tmpSize = 0;
914
915         *pConvId = 0;
916
917         memset(sqlQuery, 0x00, sizeof(sqlQuery));
918         snprintf(sqlQuery, sizeof(sqlQuery),
919                         "SELECT CONV_ID FROM ( SELECT CONV_ID FROM %s WHERE ( ",
920                         MSGFW_ADDRESS_TABLE_NAME);
921
922         for (int i = 0; i < pMsg->nAddressCnt; i++) {
923                 if (strlen(pMsg->addressList[i].addressVal) >= (unsigned int)MsgContactGetMinMatchDigit()
924                                 && pMsg->addressList[i].addressType != MSG_ADDRESS_TYPE_EMAIL
925                                 && MsgIsNumber(pMsg->addressList[i].addressVal)) {
926                         int addrSize = strlen(pMsg->addressList[i].addressVal);
927                         char newPhoneNum[addrSize+1];
928                         memset(newPhoneNum, 0x00, sizeof(newPhoneNum));
929                         MsgConvertNumber(pMsg->addressList[i].addressVal, newPhoneNum, addrSize);
930
931                         tmpSize = strlen(sqlQuery);
932                         snprintf(sqlQuery+tmpSize, MAX_QUERY_LEN-tmpSize,
933                                         "ADDRESS_VAL LIKE '%%%%%s' ",
934                                         newPhoneNum);
935
936                         if ((pMsg->nAddressCnt-1) == i) break;
937
938                         tmpSize = strlen(sqlQuery);
939                         snprintf(sqlQuery+tmpSize, MAX_QUERY_LEN-tmpSize, " OR ");
940
941                 } else {
942                         tmpSize = strlen(sqlQuery);
943                         snprintf(sqlQuery+tmpSize, MAX_QUERY_LEN-tmpSize,
944                                         "ADDRESS_VAL LIKE '%s' ",
945                                         pMsg->addressList[i].addressVal);
946
947                         if ((pMsg->nAddressCnt-1) == i) break;
948
949                         tmpSize = strlen(sqlQuery);
950                         snprintf(sqlQuery+tmpSize, MAX_QUERY_LEN-tmpSize, " OR ");
951                 }
952         }
953
954         tmpSize = strlen(sqlQuery);
955         snprintf(sqlQuery+tmpSize, MAX_QUERY_LEN-tmpSize,
956                         ") AND CONV_ID IN (SELECT CONV_ID FROM %s GROUP BY CONV_ID HAVING COUNT(CONV_ID)=%d) ",
957                         MSGFW_ADDRESS_TABLE_NAME, pMsg->nAddressCnt);
958
959
960         tmpSize = strlen(sqlQuery);
961         snprintf(sqlQuery+tmpSize, MAX_QUERY_LEN-tmpSize,
962                         ") GROUP BY CONV_ID HAVING COUNT(CONV_ID)=%d;",
963                         pMsg->nAddressCnt);
964
965         int rowCnt = 0;
966         int convId = 0;
967
968         err = pDbHandle->getTable(sqlQuery, &rowCnt, NULL);
969
970         /* No record or other error */
971         if (err != MSG_SUCCESS) {
972                 MSG_DEBUG("Fail to getTable().");
973                 pDbHandle->freeTable();
974                 return false;
975         }
976
977         convId = pDbHandle->getColumnToInt(1);
978
979         if (convId > 0) {
980                 MSG_DEBUG("Success  to get convId [%d]", convId);
981                 *pConvId = convId;
982                 pDbHandle->freeTable();
983                 return true;
984         }
985
986         pDbHandle->freeTable();
987
988         return false;
989 }
990
991
992 int MsgStoGetUnreadCnt(MsgDbHandler *pDbHandle, MSG_MAIN_TYPE_T msgType)
993 {
994         int msgCnt = 0;
995
996         char sqlQuery[MAX_QUERY_LEN+1];
997
998         memset(sqlQuery, 0x00, sizeof(sqlQuery));
999
1000         if (msgType == MSG_SMS_TYPE) {
1001                 snprintf(sqlQuery, sizeof(sqlQuery), "SELECT COUNT(MSG_ID) FROM %s "
1002                                 "WHERE MAIN_TYPE = %d "
1003                                 "AND (SUB_TYPE IN (%d, %d, %d, %d, %d, %d, %d) OR (SUB_TYPE >= %d AND SUB_TYPE <= %d)) "
1004                                 "AND FOLDER_ID = %d AND READ_STATUS = 0 AND STORAGE_ID = %d;",
1005                                 MSGFW_MESSAGE_TABLE_NAME,
1006                                 MSG_SMS_TYPE,
1007                                 MSG_NORMAL_SMS, MSG_STATUS_REPORT_SMS, MSG_CONCAT_SIM_SMS, MSG_WAP_SI_SMS, MSG_WAP_SL_SMS, MSG_MWI_VOICE_SMS, MSG_SYNCML_CP,
1008                                 MSG_REPLACE_TYPE1_SMS, MSG_REPLACE_TYPE7_SMS,
1009                                 MSG_INBOX_ID, MSG_STORAGE_PHONE);
1010         } else if (msgType == MSG_MMS_TYPE) {
1011                 snprintf(sqlQuery, sizeof(sqlQuery), "SELECT COUNT(MSG_ID) FROM %s "
1012                                 "WHERE MAIN_TYPE = %d AND SUB_TYPE IN (%d, %d, %d) "
1013                                 "AND FOLDER_ID = %d AND READ_STATUS = 0 AND STORAGE_ID = %d;",
1014                                 MSGFW_MESSAGE_TABLE_NAME,
1015                                 MSG_MMS_TYPE,
1016                                 MSG_RETRIEVE_AUTOCONF_MMS, MSG_RETRIEVE_MANUALCONF_MMS, MSG_NOTIFICATIONIND_MMS,
1017                                 MSG_INBOX_ID, MSG_STORAGE_PHONE);
1018         }
1019
1020         if (pDbHandle->prepareQuery(sqlQuery) != MSG_SUCCESS)
1021                 return 0;
1022
1023         if (pDbHandle->stepQuery() == MSG_ERR_DB_ROW) {
1024                 msgCnt = pDbHandle->columnInt(0);
1025         } else {
1026                 pDbHandle->finalizeQuery();
1027                 return 0;
1028         }
1029
1030         pDbHandle->finalizeQuery();
1031
1032         return msgCnt;
1033 }
1034
1035
1036 msg_error_t MsgStoGetMmsRawFilePath(MsgDbHandler *pDbHandle, msg_message_id_t msgId, char *pFilePath)
1037 {
1038         char sqlQuery[MAX_QUERY_LEN+1];
1039
1040         memset(sqlQuery, 0x00, sizeof(sqlQuery));
1041
1042         snprintf(sqlQuery, sizeof(sqlQuery), "SELECT A.FILE_PATH FROM %s A, %s B \
1043                         WHERE A.MSG_ID = B.MSG_ID AND B.MSG_ID = %d;",
1044                         MMS_PLUGIN_MESSAGE_TABLE_NAME, MSGFW_MESSAGE_TABLE_NAME, msgId);
1045
1046         if (pDbHandle->prepareQuery(sqlQuery) != MSG_SUCCESS)
1047                 return MSG_ERR_DB_PREPARE;
1048
1049         if (pDbHandle->stepQuery() == MSG_ERR_DB_ROW) {
1050                 if (pDbHandle->columnText(0) != NULL)
1051                         strncpy(pFilePath, (char*)pDbHandle->columnText(0), MSG_FILEPATH_LEN_MAX);
1052         } else {
1053                 pDbHandle->finalizeQuery();
1054                 return MSG_ERR_DB_STEP;
1055         }
1056
1057         pDbHandle->finalizeQuery();
1058
1059         return MSG_SUCCESS;
1060 }
1061
1062
1063 bool MsgStoCheckReadReportRequested(MsgDbHandler *pDbHandle, msg_message_id_t msgId)
1064 {
1065         msg_error_t err = MSG_SUCCESS;
1066
1067         char sqlQuery[MAX_QUERY_LEN+1];
1068         int rowCnt = 0;
1069         bool bReadReportRequested = false;
1070
1071         memset(sqlQuery, 0x00, sizeof(sqlQuery));
1072
1073         snprintf(sqlQuery, sizeof(sqlQuery), "SELECT A.ASK_READ_REPLY FROM %s A, %s B \
1074                         WHERE A.MSG_ID = B.MSG_ID AND B.MSG_ID = %d;",
1075                         MMS_PLUGIN_MESSAGE_TABLE_NAME, MSGFW_MESSAGE_TABLE_NAME, msgId);
1076
1077         err = pDbHandle->getTable(sqlQuery, &rowCnt, NULL);
1078
1079         if (err != MSG_SUCCESS && err != MSG_ERR_DB_NORECORD) {
1080                 pDbHandle->freeTable();
1081                 MSG_DEBUG("[Error]Failed to Get Table");
1082                 return bReadReportRequested;
1083         }
1084
1085         if (rowCnt != 1) {
1086                 pDbHandle->freeTable();
1087                 MSG_DEBUG("[Error]MSG_ERR_DB_NORECORD");
1088                 return bReadReportRequested;
1089         }
1090
1091         bReadReportRequested = pDbHandle->getColumnToInt(1);
1092
1093         pDbHandle->freeTable();
1094
1095         return bReadReportRequested;
1096 }
1097
1098
1099 bool MsgStoCheckReadReportIsSent(MsgDbHandler *pDbHandle, msg_message_id_t msgId)
1100 {
1101         msg_error_t err = MSG_SUCCESS;
1102
1103         char sqlQuery[MAX_QUERY_LEN+1];
1104
1105         int rowCnt = 0;
1106         bool bReadReportIsSent = true;
1107
1108         memset(sqlQuery, 0x00, sizeof(sqlQuery));
1109
1110         snprintf(sqlQuery, sizeof(sqlQuery), "SELECT A.READ_REPORT_SENT FROM %s A, %s B \
1111                         WHERE A.MSG_ID = B.MSG_ID AND B.MSG_ID = %d;",
1112                         MMS_PLUGIN_MESSAGE_TABLE_NAME, MSGFW_MESSAGE_TABLE_NAME, msgId);
1113
1114         err = pDbHandle->getTable(sqlQuery, &rowCnt, NULL);
1115
1116         if (err != MSG_SUCCESS && err != MSG_ERR_DB_NORECORD) {
1117                 pDbHandle->freeTable();
1118                 MSG_DEBUG("[Error]Failed to Get Table");
1119                 return bReadReportIsSent;
1120         }
1121
1122         if (rowCnt != 1) {
1123                 pDbHandle->freeTable();
1124                 MSG_DEBUG("[Error]MSG_ERR_DB_NORECORD");
1125                 return bReadReportIsSent;
1126         }
1127
1128         bReadReportIsSent = (bool)pDbHandle->getColumnToInt(1);
1129
1130         pDbHandle->freeTable();
1131
1132         return bReadReportIsSent;
1133 }
1134
1135
1136 msg_error_t MsgStoAddConversation(MsgDbHandler *pDbHandle, msg_thread_id_t *pConvId)
1137 {
1138         char sqlQuery[MAX_QUERY_LEN+1];
1139
1140         if(*pConvId == 0) {
1141                 if (pDbHandle->getRowId(MSGFW_CONVERSATION_TABLE_NAME, pConvId) != MSG_SUCCESS) {
1142                         return MSG_ERR_DB_EXEC;
1143                 }
1144         }
1145         /* Add Conversation */
1146         memset(sqlQuery, 0x00, sizeof(sqlQuery));
1147         snprintf(sqlQuery, sizeof(sqlQuery), "INSERT INTO %s VALUES (%d, 0, 0, 0, 0, 0, 0, 0, '', '');",
1148                         MSGFW_CONVERSATION_TABLE_NAME, *pConvId);
1149
1150         if (pDbHandle->execQuery(sqlQuery) != MSG_SUCCESS) {
1151                 MSG_DEBUG("Query Failed. [%s]", sqlQuery);
1152                 return MSG_ERR_DB_EXEC;
1153         }
1154
1155         return MSG_SUCCESS;
1156 }
1157
1158
1159 msg_error_t MsgStoSetConversationDisplayName(MsgDbHandler *pDbHandle, int contactId)
1160 {
1161         msg_error_t err = MSG_SUCCESS;
1162         int rowCnt = 0;
1163         char displayName[MAX_DISPLAY_NAME_LEN+1];
1164         char sqlQuery[MAX_QUERY_LEN+1];
1165
1166         MSG_DEBUG("contactId [%d]", contactId);
1167
1168         memset(sqlQuery, 0x00, sizeof(sqlQuery));
1169         snprintf(sqlQuery, sizeof(sqlQuery), "SELECT DISTINCT(CONV_ID) FROM %s WHERE CONTACT_ID = %d;",
1170                         MSGFW_ADDRESS_TABLE_NAME, contactId);
1171
1172         err = pDbHandle->getTable(sqlQuery, &rowCnt, NULL);
1173
1174         if (err != MSG_SUCCESS && err != MSG_ERR_DB_NORECORD) {
1175                 pDbHandle->freeTable();
1176                 MSG_DEBUG("Fail to getTable().");
1177                 return err;
1178         }
1179
1180         msg_struct_s *pAddrInfo = NULL;
1181         MSG_ADDRESS_INFO_S *address = NULL;
1182
1183         for (int i = 1; i <= rowCnt; i++) {
1184                 memset(displayName, 0x00, sizeof(displayName));
1185                 MsgDbHandler tmpDbHandle;
1186                 msg_struct_list_s addressList = {0, };
1187                 MsgStoGetAddressByConvId(&tmpDbHandle, (msg_thread_id_t)pDbHandle->getColumnToInt(i), &addressList);
1188
1189                 for (int j = 0; j < addressList.nCount; j++) {
1190                         if (j >0)
1191                                 strncat(displayName, ", ", MAX_DISPLAY_NAME_LEN-strlen(displayName));
1192
1193                         pAddrInfo = (msg_struct_s *)addressList.msg_struct_info[j];
1194                         address = (MSG_ADDRESS_INFO_S *)pAddrInfo->data;
1195
1196                         if (address->displayName[0] == '\0')
1197                                 strncat(displayName, address->addressVal, MAX_DISPLAY_NAME_LEN-strlen(displayName));
1198                         else
1199                                 strncat(displayName, address->displayName, MAX_DISPLAY_NAME_LEN-strlen(displayName));
1200                 }
1201
1202                 memset(sqlQuery, 0x00, sizeof(sqlQuery));
1203                 snprintf(sqlQuery, sizeof(sqlQuery), "UPDATE %s SET DISPLAY_NAME = ? WHERE CONV_ID = %d;",
1204                                 MSGFW_CONVERSATION_TABLE_NAME, pDbHandle->getColumnToInt(i));
1205
1206                 if (pDbHandle->prepareQuery(sqlQuery) != MSG_SUCCESS) {
1207                         pDbHandle->freeTable();
1208                         MSG_DEBUG("Query Failed [%s]", sqlQuery);
1209                         return MSG_ERR_DB_PREPARE;
1210                 }
1211
1212                 pDbHandle->bindText(displayName, 1);
1213
1214                 if (pDbHandle->stepQuery() != MSG_ERR_DB_DONE) {
1215                         pDbHandle->freeTable();
1216                         pDbHandle->finalizeQuery();
1217                         MSG_SEC_DEBUG("Update Conversation disply name. Fail [%s]", sqlQuery);
1218                         return MSG_ERR_DB_STEP;
1219                 }
1220
1221                 pDbHandle->finalizeQuery();
1222
1223                 /* free address list */
1224                 for (int j = 0; j < addressList.nCount; j++) {
1225                         msg_struct_s *pStruct = (msg_struct_s *)addressList.msg_struct_info[j];
1226                         delete (MSG_ADDRESS_INFO_S *)pStruct->data;
1227                         delete (msg_struct_s *)pStruct;
1228                 }
1229
1230                 if (addressList.msg_struct_info != NULL) {
1231                         g_free((msg_struct_t *)addressList.msg_struct_info);
1232                 }
1233         }
1234
1235         pDbHandle->freeTable();
1236
1237         return err;
1238 }
1239
1240
1241 msg_error_t MsgStoSetConversationDisplayName(MsgDbHandler *pDbHandle, msg_thread_id_t convId)
1242 {
1243         msg_error_t err = MSG_SUCCESS;
1244
1245         char displayName[MAX_DISPLAY_NAME_LEN+1];
1246         char sqlQuery[MAX_QUERY_LEN+1];
1247
1248         msg_struct_list_s addressList = {0, };
1249
1250         msg_struct_s *pAddrInfo = NULL;
1251         MSG_ADDRESS_INFO_S *address = NULL;
1252
1253         memset(displayName, 0x00, sizeof(displayName));
1254
1255         MsgStoGetAddressByConvId(pDbHandle, convId, &addressList);
1256
1257         for (int j = 0; j < addressList.nCount; j++) {
1258                 if (j >0)
1259                         strncat(displayName, ", ", MAX_DISPLAY_NAME_LEN-strlen(displayName));
1260
1261                 pAddrInfo = (msg_struct_s *)addressList.msg_struct_info[j];
1262                 address = (MSG_ADDRESS_INFO_S *)pAddrInfo->data;
1263
1264                 if (address->displayName[0] == '\0')
1265                         strncat(displayName, address->addressVal, MAX_DISPLAY_NAME_LEN-strlen(displayName));
1266                 else
1267                         strncat(displayName, address->displayName, MAX_DISPLAY_NAME_LEN-strlen(displayName));
1268         }
1269
1270         memset(sqlQuery, 0x00, sizeof(sqlQuery));
1271         snprintf(sqlQuery, sizeof(sqlQuery), "UPDATE %s SET DISPLAY_NAME = ? WHERE CONV_ID = %d;",
1272                         MSGFW_CONVERSATION_TABLE_NAME, convId);
1273
1274         if (pDbHandle->prepareQuery(sqlQuery) != MSG_SUCCESS) {
1275                 MSG_DEBUG("Query Failed [%s]", sqlQuery);
1276                 return MSG_ERR_DB_PREPARE;
1277         }
1278
1279         pDbHandle->bindText(displayName, 1);
1280
1281         if (pDbHandle->stepQuery() != MSG_ERR_DB_DONE) {
1282                 pDbHandle->finalizeQuery();
1283                 MSG_SEC_DEBUG("Update Conversation disply name. Fail [%s]", sqlQuery);
1284                 return MSG_ERR_DB_STEP;
1285         }
1286
1287         pDbHandle->finalizeQuery();
1288
1289         for (int j = 0; j < addressList.nCount; j++) {
1290                 msg_struct_s *pStruct = (msg_struct_s *)addressList.msg_struct_info[j];
1291                 delete (MSG_ADDRESS_INFO_S *)pStruct->data;
1292                 delete (msg_struct_s *)pStruct;
1293         }
1294
1295         if (addressList.msg_struct_info != NULL) {
1296                 g_free((msg_struct_t *)addressList.msg_struct_info);
1297         }
1298
1299         return err;
1300 }
1301
1302 msg_error_t MsgStoUpdateNetworkStatus(MsgDbHandler *pDbHandle, MSG_MESSAGE_INFO_S *pMsgInfo, msg_network_status_t status)
1303 {
1304         msg_error_t err = MSG_SUCCESS;
1305
1306         char sqlQuery[MAX_QUERY_LEN+1];
1307
1308         memset(sqlQuery, 0x00, sizeof(sqlQuery));
1309
1310         snprintf(sqlQuery, sizeof(sqlQuery), "UPDATE %s SET NETWORK_STATUS = %d WHERE MSG_ID = %d;",
1311                         MSGFW_MESSAGE_TABLE_NAME, status, pMsgInfo->msgId);
1312
1313         if (pDbHandle->execQuery(sqlQuery) != MSG_SUCCESS)
1314                 err = MSG_ERR_DB_EXEC;
1315
1316         pDbHandle->finalizeQuery();
1317
1318         return err;
1319 }
1320
1321 bool MsgExistConversation(MsgDbHandler *pDbHandle, msg_thread_id_t convId)
1322 {
1323         msg_error_t err = MSG_SUCCESS;
1324
1325         char sqlQuery[MAX_QUERY_LEN+1];
1326
1327         int rowCnt = 0;
1328
1329         memset(sqlQuery, 0x00, sizeof(sqlQuery));
1330
1331         snprintf(sqlQuery, sizeof(sqlQuery), "SELECT CONV_ID FROM %s WHERE CONV_ID = %d;",
1332                         MSGFW_CONVERSATION_TABLE_NAME, convId);
1333
1334         err = pDbHandle->getTable(sqlQuery, &rowCnt, NULL);
1335
1336         if (err == MSG_ERR_DB_NORECORD) {
1337                 pDbHandle->freeTable();
1338                 return false;
1339         } else if (err != MSG_SUCCESS) {
1340                 pDbHandle->freeTable();
1341                 return false;
1342         }
1343         pDbHandle->freeTable();
1344
1345         return true;
1346 }
1347
1348 bool MsgExistMessage(MsgDbHandler *pDbHandle, MSG_MESSAGE_INFO_S *pMsg)
1349 {
1350         msg_error_t err = MSG_SUCCESS;
1351
1352         char sqlQuery[MAX_QUERY_LEN+1];
1353
1354
1355         int rowCnt = 0;
1356
1357         memset(sqlQuery, 0x00, sizeof(sqlQuery));
1358
1359         snprintf(sqlQuery, sizeof(sqlQuery), "SELECT MSG_ID FROM %s WHERE CONV_ID = %ud AND DISPLAY_TIME = %ud;",
1360                         MSGFW_MESSAGE_TABLE_NAME, pMsg->threadId, (int)pMsg->displayTime);
1361
1362         err = pDbHandle->getTable(sqlQuery, &rowCnt, NULL);
1363
1364
1365         if (err != MSG_SUCCESS) {
1366                 pDbHandle->freeTable();
1367                 return false;
1368         }
1369
1370         if(rowCnt > 0) {
1371                 pMsg->msgId = pDbHandle->getColumnToInt(1);
1372         }
1373         pDbHandle->freeTable();
1374
1375         return true;
1376 }
1377
1378
1379 bool MsgExistAddress(MsgDbHandler *pDbHandle, MSG_MESSAGE_INFO_S *pMsg,  msg_thread_id_t convId, int index)
1380 {
1381         msg_error_t err = MSG_SUCCESS;
1382
1383         char sqlQuery[MAX_QUERY_LEN+1];
1384
1385
1386         int rowCnt = 0;
1387
1388         memset(sqlQuery, 0x00, sizeof(sqlQuery));
1389
1390         if (strlen(pMsg->addressList[index].addressVal) > (unsigned int)MsgContactGetMinMatchDigit()) {
1391                 int addrSize = strlen(pMsg->addressList[index].addressVal);
1392                 char newPhoneNum[addrSize+1];
1393                 memset(newPhoneNum, 0x00, sizeof(newPhoneNum));
1394                 MsgConvertNumber(pMsg->addressList[index].addressVal, newPhoneNum, addrSize);
1395
1396                 snprintf(sqlQuery, sizeof(sqlQuery),
1397                                 "SELECT ADDRESS_ID FROM %s WHERE ADDRESS_VAL LIKE '%%%%%s' AND CONV_ID= %d;",
1398                                 MSGFW_ADDRESS_TABLE_NAME, newPhoneNum, convId);
1399         } else {
1400                 snprintf(sqlQuery, sizeof(sqlQuery),
1401                                 "SELECT ADDRESS_ID FROM %s WHERE ADDRESS_VAL = '%s' AND CONV_ID= %d;",
1402                                 MSGFW_ADDRESS_TABLE_NAME, pMsg->addressList[index].addressVal, convId);
1403         }
1404
1405         err = pDbHandle->getTable(sqlQuery, &rowCnt, NULL);
1406
1407         if (err == MSG_ERR_DB_NORECORD) {
1408                 pDbHandle->freeTable();
1409                 return false;
1410         }
1411         else if (err != MSG_SUCCESS) {
1412                 pDbHandle->freeTable();
1413                 return false;
1414         }
1415         pDbHandle->freeTable();
1416
1417         return true;
1418 }
1419
1420
1421 void MsgStoUpdateAddress(MsgDbHandler *pDbHandle, const MSG_MESSAGE_INFO_S *pMsg, msg_thread_id_t convId)
1422 {
1423         MSG_BEGIN();
1424         msg_error_t err = MSG_SUCCESS;
1425
1426         char sqlQuery[MAX_QUERY_LEN+1];
1427
1428         for (int i = 0; i < pMsg->nAddressCnt; i++) {
1429                         if (strlen(pMsg->addressList[i].addressVal) > (unsigned int)MsgContactGetMinMatchDigit() && pMsg->addressList[i].addressType == MSG_ADDRESS_TYPE_PLMN) {
1430                                 int addrSize = strlen(pMsg->addressList[i].addressVal);
1431                                 char newPhoneNum[addrSize+1];
1432                                 memset(newPhoneNum, 0x00, sizeof(newPhoneNum));
1433                                 MsgConvertNumber(pMsg->addressList[i].addressVal, newPhoneNum, addrSize);
1434
1435                                 memset(sqlQuery, 0x00, sizeof(sqlQuery));
1436                                 snprintf(sqlQuery, sizeof(sqlQuery),
1437                                                 "UPDATE %s SET "
1438                                                 "ADDRESS_VAL = '%s', "
1439                                                 "ADDRESS_TYPE = %d, "
1440                                                 "RECIPIENT_TYPE = %d "
1441                                                 "WHERE CONV_ID = %d "
1442                                                 "AND ADDRESS_VAL LIKE '%%%%%s';",
1443                                                 MSGFW_ADDRESS_TABLE_NAME, pMsg->addressList[i].addressVal,
1444                                                 pMsg->addressList[i].addressType, pMsg->addressList[i].recipientType, convId, newPhoneNum);
1445
1446                                 err = pDbHandle->execQuery(sqlQuery);
1447                                 if (err != MSG_SUCCESS) MSG_DEBUG("Fail to execQuery(). [%s]", sqlQuery);
1448
1449                                 pDbHandle->finalizeQuery();
1450                         }
1451         }
1452
1453         MSG_END();
1454 }
1455
1456 msg_error_t MsgStoAddCBChannelInfo(MsgDbHandler *pDbHandle, MSG_CB_CHANNEL_S *pCBChannel, msg_sim_slot_id_t simIndex)
1457 {
1458 #ifndef FEATURE_SMS_CDMA
1459         MSG_BEGIN();
1460
1461         char sqlQuery[MAX_QUERY_LEN] = {0, };
1462
1463         pDbHandle->beginTrans();
1464
1465         memset(sqlQuery, 0x00, sizeof(sqlQuery));
1466         snprintf(sqlQuery, sizeof(sqlQuery), "DELETE FROM %s WHERE SIM_INDEX = %d;", MSGFW_CB_CHANNEL_INFO_TABLE_NAME, simIndex);
1467
1468         if (pDbHandle->execQuery(sqlQuery) != MSG_SUCCESS) {
1469                 pDbHandle->endTrans(false);
1470                 return MSG_ERR_DB_EXEC;
1471         }
1472
1473         for (int i = 0; i < pCBChannel->channelCnt; i++) {
1474                 int index = 1;
1475                 memset(sqlQuery, 0x00, sizeof(sqlQuery));
1476                 snprintf(sqlQuery, sizeof(sqlQuery), "INSERT INTO %s(CHANNEL_ACTIVATION, CHANNEL_FROM, CHANNEL_TO, CHANNEL_NAME, SIM_INDEX) VALUES (?, ?, ?, ?, ?);",
1477                                 MSGFW_CB_CHANNEL_INFO_TABLE_NAME);
1478
1479                 if (pDbHandle->prepareQuery(sqlQuery) != MSG_SUCCESS) {
1480                         pDbHandle->endTrans(false);
1481                         return MSG_ERR_DB_PREPARE;
1482                 }
1483                 pDbHandle->bindInt(pCBChannel->channelInfo[i].bActivate, index++);
1484                 pDbHandle->bindInt(pCBChannel->channelInfo[i].from, index++);
1485                 pDbHandle->bindInt(pCBChannel->channelInfo[i].to, index++);
1486                 pDbHandle->bindText(pCBChannel->channelInfo[i].name, index++);
1487                 pDbHandle->bindInt(simIndex, index++);
1488
1489                 if (pDbHandle->stepQuery() != MSG_ERR_DB_DONE) {
1490                         pDbHandle->finalizeQuery();
1491                         pDbHandle->endTrans(false);
1492                         return MSG_ERR_DB_STEP;
1493                 }
1494
1495                 pDbHandle->finalizeQuery();
1496         }
1497
1498         pDbHandle->endTrans(true);
1499
1500         MSG_END();
1501
1502         return MSG_SUCCESS;
1503 #else /* TODO: Add multisim for CDMA */
1504         MSG_BEGIN();
1505
1506         char sqlQuery[MAX_QUERY_LEN] = {0, };
1507
1508         pDbHandle->beginTrans();
1509
1510         memset(sqlQuery, 0x00, sizeof(sqlQuery));
1511         snprintf(sqlQuery, sizeof(sqlQuery), "DELETE FROM %s;", MSGFW_CDMA_CB_CHANNEL_INFO_TABLE_NAME);
1512
1513         if (pDbHandle->execQuery(sqlQuery) != MSG_SUCCESS) {
1514                 pDbHandle->endTrans(false);
1515                 return MSG_ERR_DB_EXEC;
1516         }
1517
1518         for (int i = 0; i < pCBChannel->channelCnt; i++) {
1519                 memset(sqlQuery, 0x00, sizeof(sqlQuery));
1520                 snprintf(sqlQuery, sizeof(sqlQuery), "INSERT INTO %s VALUES (%d, %d, %d, %d, '%s');", MSGFW_CDMA_CB_CHANNEL_INFO_TABLE_NAME,
1521                                 i, pCBChannel->channelInfo[i].bActivate, pCBChannel->channelInfo[i].ctg,
1522                                 pCBChannel->channelInfo[i].lang, pCBChannel->channelInfo[i].name);
1523
1524                 if (pDbHandle->execQuery(sqlQuery) != MSG_SUCCESS) {
1525                         pDbHandle->endTrans(false);
1526                         return MSG_ERR_DB_EXEC;
1527                 }
1528         }
1529
1530         pDbHandle->endTrans(true);
1531
1532         MSG_END();
1533
1534         return MSG_SUCCESS;
1535 #endif
1536 }
1537
1538
1539 msg_error_t MsgStoGetCBChannelInfo(MsgDbHandler *pDbHandle, MSG_CB_CHANNEL_S *pCBChannel, msg_sim_slot_id_t simIndex)
1540 {
1541 #ifndef FEATURE_SMS_CDMA
1542         MSG_BEGIN();
1543
1544         int rowCnt = 0, index = 0;
1545
1546         char sqlQuery[MAX_QUERY_LEN] = {0, };
1547
1548         memset(sqlQuery, 0x00, sizeof(sqlQuery));
1549         snprintf(sqlQuery, sizeof(sqlQuery), "SELECT CHANNEL_ACTIVATION, CHANNEL_FROM, CHANNEL_TO, CHANNEL_NAME FROM %s WHERE SIM_INDEX = %d;", MSGFW_CB_CHANNEL_INFO_TABLE_NAME, simIndex);
1550
1551         msg_error_t err = pDbHandle->getTable(sqlQuery, &rowCnt, &index);
1552
1553         pCBChannel->channelCnt = rowCnt;
1554
1555         if (err == MSG_ERR_DB_NORECORD) {
1556                 pDbHandle->freeTable();
1557                 return MSG_ERR_DB_NORECORD;
1558         } else if (err != MSG_SUCCESS) {
1559                 MSG_DEBUG("Fail to getTable().");
1560                 pDbHandle->freeTable();
1561                 return MSG_ERR_DB_GETTABLE;
1562         }
1563
1564         for (int i = 0; i < rowCnt; i++) {
1565                 pCBChannel->channelInfo[i].bActivate = pDbHandle->getColumnToInt(index++);
1566                 pCBChannel->channelInfo[i].from  = pDbHandle->getColumnToInt(index++);
1567                 pCBChannel->channelInfo[i].to = pDbHandle->getColumnToInt(index++);
1568                 pDbHandle->getColumnToString(index++, CB_CHANNEL_NAME_MAX, pCBChannel->channelInfo[i].name);
1569
1570                 MSG_DEBUG("CH_ACT = %d", pCBChannel->channelInfo[i].bActivate);
1571                 MSG_DEBUG("CH_FROM = %d", pCBChannel->channelInfo[i].from);
1572                 MSG_DEBUG("CH_TO = %d", pCBChannel->channelInfo[i].to);
1573                 MSG_DEBUG("CH_NAME = %s", pCBChannel->channelInfo[i].name);
1574         }
1575
1576         pDbHandle->freeTable();
1577
1578         MSG_END();
1579
1580         return MSG_SUCCESS;
1581 #else /* TODO: Add multisim for CDMA */
1582         MSG_BEGIN();
1583
1584         int rowCnt = 0, index = 0;
1585
1586         char sqlQuery[MAX_QUERY_LEN] = {0, };
1587
1588         memset(sqlQuery, 0x00, sizeof(sqlQuery));
1589         snprintf(sqlQuery, sizeof(sqlQuery), "SELECT CHANNEL_ACTIVATION, CHANNEL_CATEGORY, CHANNEL_LANGUAGE, CHANNEL_NAME FROM %s;", MSGFW_CDMA_CB_CHANNEL_INFO_TABLE_NAME);
1590
1591         msg_error_t err = pDbHandle->getTable(sqlQuery, &rowCnt, &index);
1592
1593         pCBChannel->channelCnt = rowCnt;
1594
1595         if (err == MSG_ERR_DB_NORECORD) {
1596                 pDbHandle->freeTable();
1597                 return MSG_ERR_DB_NORECORD;
1598         } else if (err != MSG_SUCCESS) {
1599                 MSG_DEBUG("Fail to getTable().");
1600                 pDbHandle->freeTable();
1601                 return MSG_ERR_DB_GETTABLE;
1602         }
1603
1604         for (int i = 0; i < rowCnt; i++) {
1605                 pCBChannel->channelInfo[i].bActivate = pDbHandle->getColumnToInt(index++);
1606                 pCBChannel->channelInfo[i].ctg  = pDbHandle->getColumnToInt(index++);
1607                 pCBChannel->channelInfo[i].lang = pDbHandle->getColumnToInt(index++);
1608                 pDbHandle->getColumnToString(index++, CB_CHANNEL_NAME_MAX, pCBChannel->channelInfo[i].name);
1609
1610                 MSG_DEBUG("CH_ACT = %d", pCBChannel->channelInfo[i].bActivate);
1611                 MSG_DEBUG("CH_CTG = %d", pCBChannel->channelInfo[i].ctg);
1612                 MSG_DEBUG("CH_LANG = %d", pCBChannel->channelInfo[i].lang);
1613                 MSG_DEBUG("CH_NAME = %s", pCBChannel->channelInfo[i].name);
1614         }
1615
1616         pDbHandle->freeTable();
1617
1618         MSG_END();
1619
1620         return MSG_SUCCESS;
1621 #endif
1622 }
1623
1624 msg_error_t MsgStoGetThreadViewList(const MSG_SORT_RULE_S *pSortRule, msg_struct_list_s *pThreadViewList)
1625 {
1626         MsgDbHandler *dbHandle = getDbHandle();
1627         dbHandle->connectReadOnly();
1628
1629         pThreadViewList->nCount = 0;
1630         pThreadViewList->msg_struct_info = NULL;
1631
1632         int rowCnt = 0, index = 0;
1633
1634         char sqlQuery[MAX_QUERY_LEN+1];
1635         memset(sqlQuery, 0x00, sizeof(sqlQuery));
1636
1637         snprintf(sqlQuery, sizeof(sqlQuery), "SELECT A.CONV_ID, A.UNREAD_CNT, A.SMS_CNT, A.MMS_CNT, A.MAIN_TYPE, A.SUB_TYPE, "
1638                         "A.MSG_DIRECTION, A.DISPLAY_TIME, A.DISPLAY_NAME, A.MSG_TEXT, "
1639                         "(COUNT(CASE WHEN B.PROTECTED = 1 THEN 1 END)) AS PROTECTED, "
1640                         "(COUNT(CASE WHEN B.FOLDER_ID = %d THEN 1 END)) AS DRAFT, "
1641                         "(COUNT(CASE WHEN B.NETWORK_STATUS = %d THEN 1 END)) AS FAILED, "
1642                         "(COUNT(CASE WHEN B.NETWORK_STATUS = %d THEN 1 END)) AS SENDING "
1643                         "FROM %s A, %s B ON A.SMS_CNT + A.MMS_CNT > 0 AND B.CONV_ID = A.CONV_ID "
1644                         "GROUP BY A.CONV_ID ORDER BY A.DISPLAY_TIME DESC;",
1645                         MSG_DRAFT_ID,
1646                         MSG_NETWORK_SEND_FAIL,
1647                         MSG_NETWORK_SENDING,
1648                         MSGFW_CONVERSATION_TABLE_NAME,
1649                         MSGFW_MESSAGE_TABLE_NAME);
1650
1651         msg_error_t err = dbHandle->getTable(sqlQuery, &rowCnt, &index);
1652
1653         if (err == MSG_ERR_DB_NORECORD) {
1654                 dbHandle->freeTable();
1655                 return MSG_SUCCESS;
1656         } else if (err != MSG_SUCCESS) {
1657                 MSG_DEBUG("Fail to getTable().");
1658                 dbHandle->freeTable();
1659                 return err;
1660         }
1661
1662         if (rowCnt < 1) {
1663                 MSG_DEBUG("rowCnt is %d", rowCnt);
1664                 dbHandle->freeTable();
1665                 return err;
1666         }
1667
1668         pThreadViewList->nCount = rowCnt;
1669
1670         MSG_DEBUG("pThreadViewList->nCount [%d]", pThreadViewList->nCount);
1671
1672         pThreadViewList->msg_struct_info = (msg_struct_t *)calloc(rowCnt, sizeof(msg_struct_t));
1673
1674         MSG_THREAD_VIEW_S *pTmp = NULL;
1675         msg_struct_s *thread_t = NULL;
1676
1677         for (int i = 0; i < rowCnt; i++) {
1678                 thread_t = (msg_struct_s *)new msg_struct_s;
1679                 pThreadViewList->msg_struct_info[i] = (msg_struct_t)thread_t;
1680
1681                 thread_t->type = MSG_STRUCT_THREAD_INFO;
1682                 thread_t->data = new MSG_THREAD_VIEW_S;
1683
1684                 pTmp = (MSG_THREAD_VIEW_S *)thread_t->data;
1685                 memset(pTmp, 0x00, sizeof(MSG_THREAD_VIEW_S));
1686
1687                 pTmp->threadId = dbHandle->getColumnToInt(index++);
1688
1689                 pTmp->unreadCnt = dbHandle->getColumnToInt(index++);
1690                 pTmp->smsCnt = dbHandle->getColumnToInt(index++);
1691                 pTmp->mmsCnt = dbHandle->getColumnToInt(index++);
1692
1693                 pTmp->mainType = dbHandle->getColumnToInt(index++);
1694                 pTmp->subType = dbHandle->getColumnToInt(index++);
1695
1696                 pTmp->direction = dbHandle->getColumnToInt(index++);
1697                 pTmp->threadTime = (time_t)dbHandle->getColumnToInt(index++);
1698
1699                 memset(pTmp->threadName, 0x00, sizeof(pTmp->threadName));
1700                 dbHandle->getColumnToString(index++, MAX_THREAD_NAME_LEN, pTmp->threadName);
1701
1702                 memset(pTmp->threadData, 0x00, sizeof(pTmp->threadData));
1703                 dbHandle->getColumnToString(index++, MAX_THREAD_DATA_LEN, pTmp->threadData);
1704
1705                 int protectedCnt = dbHandle->getColumnToInt(index++);
1706                 if (protectedCnt > 0)
1707                         pTmp->bProtected = true;
1708
1709                 int draftCnt = dbHandle->getColumnToInt(index++);
1710                 if (draftCnt > 0)
1711                         pTmp->bDraft = true;
1712
1713                 int failedCnt = dbHandle->getColumnToInt(index++);
1714                 if (failedCnt > 0)
1715                         pTmp->bSendFailed = true;
1716
1717                 int sendingCnt = dbHandle->getColumnToInt(index++);
1718                 if (sendingCnt > 0)
1719                         pTmp->bSending = true;
1720         }
1721
1722         dbHandle->freeTable();
1723
1724         return MSG_SUCCESS;
1725 }
1726
1727
1728 msg_error_t MsgStoGetConversationPreview(MsgDbHandler *pDbHandle, MSG_CONVERSATION_VIEW_S *pConv)
1729 {
1730         char sqlQuery[MAX_QUERY_LEN + 1];
1731         int rowCnt = 0, index = 0;
1732         memset(sqlQuery, 0x00, sizeof(sqlQuery));
1733
1734         if (pConv == NULL)
1735                 return MSG_ERR_NULL_POINTER;
1736
1737         pConv->tcs_bc_level = -1; /* init */
1738
1739         /*(MSG_ID INTEGER, TYPE INTEGER, VALUE TEXT, COUNT INTEGER) */
1740         snprintf(sqlQuery, sizeof(sqlQuery),
1741                         "SELECT TYPE, VALUE, COUNT "
1742                         "FROM %s WHERE MSG_ID=%d;",
1743                         MSGFW_MMS_PREVIEW_TABLE_NAME, pConv->msgId);
1744
1745         msg_error_t err = pDbHandle->getTable(sqlQuery, &rowCnt, &index);
1746         if (err == MSG_SUCCESS) {
1747                 for (int i = 0; i < rowCnt; i++) {
1748                         int type = pDbHandle->getColumnToInt(index++);
1749                         if (type == MSG_MMS_ITEM_TYPE_IMG) {
1750                                 pDbHandle->getColumnToString(index++, MSG_FILEPATH_LEN_MAX, pConv->imageThumbPath);
1751                                 pDbHandle->getColumnToInt(index++);
1752                         } else if (type == MSG_MMS_ITEM_TYPE_VIDEO) {
1753                                 pDbHandle->getColumnToString(index++, MSG_FILEPATH_LEN_MAX, pConv->videoThumbPath);
1754                                 pDbHandle->getColumnToInt(index++);
1755                         } else if (type == MSG_MMS_ITEM_TYPE_AUDIO) {
1756                                 pDbHandle->getColumnToString(index++, MSG_FILENAME_LEN_MAX, pConv->audioFileName);
1757                                 pDbHandle->getColumnToInt(index++);
1758                         } else if (type == MSG_MMS_ITEM_TYPE_ATTACH) {
1759                                 pDbHandle->getColumnToString(index++, MSG_FILENAME_LEN_MAX, pConv->attachFileName);
1760                                 pConv->attachCount = pDbHandle->getColumnToInt(index++);
1761                         } else if (type == MSG_MMS_ITEM_TYPE_PAGE) {
1762                                 index++;
1763                                 pConv->pageCount = pDbHandle->getColumnToInt(index++);
1764                         } else if (type == MSG_MMS_ITEM_TYPE_MALWARE) {
1765                                 index++;
1766                                 pConv->tcs_bc_level = pDbHandle->getColumnToInt(index++);
1767                         } else if (type == MSG_MMS_ITEM_TYPE_1ST_MEDIA) {
1768                                 pDbHandle->getColumnToString(index++, MSG_FILEPATH_LEN_MAX, pConv->firstMediaPath);
1769                                 pDbHandle->getColumnToInt(index++);
1770                         } else {
1771                                 MSG_DEBUG("Unknown item type [%d]", type);
1772                                 index+=2;
1773                         }
1774                 }
1775         }
1776
1777         pDbHandle->freeTable();
1778         return MSG_SUCCESS;
1779 }
1780
1781 msg_error_t MsgStoGetConversationMultipart(MsgDbHandler *pDbHandle, MSG_CONVERSATION_VIEW_S *pConv)
1782 {
1783         char sqlQuery[MAX_QUERY_LEN + 1];
1784         int rowCnt = 0, index = 0;
1785         memset(sqlQuery, 0x00, sizeof(sqlQuery));
1786
1787         if (pConv == NULL)
1788                 return MSG_ERR_NULL_POINTER;
1789
1790         snprintf(sqlQuery, sizeof(sqlQuery),
1791                         "SELECT CONTENT_TYPE, NAME, FILE_PATH, CONTENT_ID, CONTENT_LOCATION, TCS_LEVEL, MALWARE_ALLOW, THUMB_FILE_PATH "
1792                         "FROM %s WHERE MSG_ID=%d;",
1793                         MSGFW_MMS_MULTIPART_TABLE_NAME, pConv->msgId);
1794
1795         msg_error_t err = pDbHandle->getTable(sqlQuery, &rowCnt, &index);
1796         if (err == MSG_SUCCESS) {
1797                 GList *multipart_list = NULL;
1798                 for (int i = 0; i < rowCnt; i++) {
1799                         msg_struct_s *multipart_struct_s = new msg_struct_s;
1800                         multipart_struct_s->type = MSG_STRUCT_MULTIPART_INFO;
1801                         multipart_struct_s->data = new MMS_MULTIPART_DATA_S;
1802                         memset(multipart_struct_s->data, 0x00, sizeof(MMS_MULTIPART_DATA_S));
1803
1804                         MMS_MULTIPART_DATA_S *multipart = (MMS_MULTIPART_DATA_S *)multipart_struct_s->data;
1805
1806                         pDbHandle->getColumnToString(index++, sizeof(multipart->szContentType), multipart->szContentType);
1807                         pDbHandle->getColumnToString(index++, sizeof(multipart->szFileName), multipart->szFileName);
1808                         pDbHandle->getColumnToString(index++, sizeof(multipart->szFilePath), multipart->szFilePath);
1809                         pDbHandle->getColumnToString(index++, sizeof(multipart->szContentID), multipart->szContentID);
1810                         pDbHandle->getColumnToString(index++, sizeof(multipart->szContentLocation), multipart->szContentLocation);
1811
1812                         multipart->tcs_bc_level = pDbHandle->getColumnToInt(index++);
1813                         multipart->malware_allow = pDbHandle->getColumnToInt(index++);
1814                         pDbHandle->getColumnToString(index++, sizeof(multipart->szThumbFilePath), multipart->szThumbFilePath);
1815
1816                         multipart_list = g_list_append(multipart_list, multipart_struct_s);
1817                 }
1818                 pConv->multipart_list = (msg_list_handle_t)multipart_list;
1819         }
1820
1821         pDbHandle->freeTable();
1822         return MSG_SUCCESS;
1823 }
1824
1825 msg_error_t MsgStoGetConversationViewItem(msg_message_id_t msgId, MSG_CONVERSATION_VIEW_S *pConv)
1826 {
1827         MsgDbHandler *dbHandle = getDbHandle();
1828         dbHandle->connectReadOnly();
1829
1830         int rowCnt = 0, index = 0;
1831
1832         char sqlQuery[MAX_QUERY_LEN+1];
1833
1834         memset(sqlQuery, 0x00, sizeof(sqlQuery));
1835
1836         snprintf(sqlQuery, sizeof(sqlQuery), "SELECT MSG_ID, CONV_ID, FOLDER_ID, STORAGE_ID, MAIN_TYPE, SUB_TYPE, \
1837                         DISPLAY_TIME, DATA_SIZE, NETWORK_STATUS, READ_STATUS, PROTECTED, \
1838                         MSG_DIRECTION, SCHEDULED_TIME, SUBJECT, MSG_TEXT, ATTACHMENT_COUNT, SIM_INDEX\
1839                         FROM %s WHERE MSG_ID = %d;",
1840                         MSGFW_MESSAGE_TABLE_NAME, msgId);
1841
1842         msg_error_t err = dbHandle->getTable(sqlQuery, &rowCnt, &index);
1843
1844         if (err == MSG_ERR_DB_NORECORD) {
1845                 dbHandle->freeTable();
1846                 return MSG_SUCCESS;
1847         } else if (err != MSG_SUCCESS) {
1848                 MSG_DEBUG("Fail to getTable().");
1849                 dbHandle->freeTable();
1850                 return err;
1851         }
1852
1853         memset(pConv, 0x00, sizeof(MSG_CONVERSATION_VIEW_S));
1854         pConv->pText = NULL;
1855
1856         pConv->msgId = dbHandle->getColumnToInt(index++);
1857         pConv->threadId = dbHandle->getColumnToInt(index++);
1858         pConv->folderId = dbHandle->getColumnToInt(index++);
1859         pConv->storageId = dbHandle->getColumnToInt(index++);
1860         pConv->mainType = dbHandle->getColumnToInt(index++);
1861         pConv->subType = dbHandle->getColumnToInt(index++);
1862         pConv->displayTime = (time_t)dbHandle->getColumnToInt(index++);
1863         pConv->textSize = dbHandle->getColumnToInt(index++);
1864         pConv->networkStatus = dbHandle->getColumnToInt(index++);
1865         pConv->bRead = dbHandle->getColumnToInt(index++);
1866         pConv->bProtected = dbHandle->getColumnToInt(index++);
1867         pConv->direction = dbHandle->getColumnToInt(index++);
1868         pConv->scheduledTime = (time_t)dbHandle->getColumnToInt(index++);
1869
1870         dbHandle->getColumnToString(index++, MAX_SUBJECT_LEN, pConv->subject);
1871         char *tmpText = g_strdup(dbHandle->getColumnToString(index++));
1872
1873         /*It does Not need to Get attach count in MSG_MESSAGE_TABLE. see MsgStoGetConversationPreview */
1874         /*pConv->attachCount = dbHandle->getColumnToInt(index++); */
1875         index++;
1876         pConv->simIndex = dbHandle->getColumnToInt(index++);
1877
1878         dbHandle->freeTable();
1879
1880         if (pConv->mainType == MSG_MMS_TYPE &&
1881                 (pConv->networkStatus == MSG_NETWORK_RETRIEVING || pConv->networkStatus == MSG_NETWORK_RETRIEVE_FAIL || pConv->subType == MSG_NOTIFICATIONIND_MMS)) {
1882                 pConv->pText = NULL;
1883                 pConv->textSize = 0;
1884         } else {
1885                 if (pConv->mainType == MSG_SMS_TYPE) {
1886                         pConv->pText = new char[pConv->textSize+2];
1887                         memset(pConv->pText, 0x00, pConv->textSize+2);
1888                         snprintf(pConv->pText, pConv->textSize+1, "%s", tmpText);
1889                 } else if (pConv->mainType == MSG_MMS_TYPE) {
1890                         if (tmpText) {
1891                                 pConv->textSize = strlen(tmpText);
1892
1893                                 pConv->pText = new char[pConv->textSize+1];
1894                                 memset(pConv->pText, 0x00, pConv->textSize+1);
1895
1896                                 strncpy(pConv->pText, tmpText, pConv->textSize);
1897                         }
1898
1899                         MsgStoGetConversationPreview(dbHandle, pConv);
1900                         MsgStoGetConversationMultipart(dbHandle, pConv);
1901                 }
1902         }
1903
1904         if (tmpText) {
1905                 g_free(tmpText);
1906                 tmpText = NULL;
1907         }
1908
1909         MSG_END();
1910
1911         return MSG_SUCCESS;
1912 }
1913
1914
1915 msg_error_t MsgStoGetConversationViewList(msg_thread_id_t threadId, msg_struct_list_s *pConvViewList)
1916 {
1917         MSG_BEGIN();
1918
1919         MsgDbHandler *dbHandle = getDbHandle();
1920         dbHandle->connectReadOnly();
1921
1922         pConvViewList->nCount = 0;
1923         pConvViewList->msg_struct_info = NULL;
1924
1925         int rowCnt = 0, index = 0;
1926
1927         char sqlQuery[MAX_QUERY_LEN+1];
1928
1929         memset(sqlQuery, 0x00, sizeof(sqlQuery));
1930
1931 #ifdef MSG_NOTI_INTEGRATION
1932         snprintf(sqlQuery, sizeof(sqlQuery), "SELECT MSG_ID, CONV_ID, FOLDER_ID, STORAGE_ID, MAIN_TYPE, SUB_TYPE, \
1933                         DISPLAY_TIME, DATA_SIZE, NETWORK_STATUS, READ_STATUS, PROTECTED, \
1934                         MSG_DIRECTION, SCHEDULED_TIME, SUBJECT, MSG_TEXT, ATTACHMENT_COUNT, SIM_INDEX  \
1935                         FROM %s WHERE CONV_ID = %d AND FOLDER_ID > %d AND FOLDER_ID < %d AND STORAGE_ID = %d ORDER BY DISPLAY_TIME, MSG_ID ASC;",
1936                         MSGFW_MESSAGE_TABLE_NAME, threadId, MSG_ALLBOX_ID, MSG_SPAMBOX_ID, MSG_STORAGE_PHONE);
1937 #else
1938         snprintf(sqlQuery, sizeof(sqlQuery), "SELECT MSG_ID, CONV_ID, FOLDER_ID, STORAGE_ID, MAIN_TYPE, SUB_TYPE, \
1939                         DISPLAY_TIME, DATA_SIZE, NETWORK_STATUS, READ_STATUS, PROTECTED, \
1940                         MSG_DIRECTION, SCHEDULED_TIME, SUBJECT, MSG_TEXT, ATTACHMENT_COUNT \
1941                         FROM %s WHERE CONV_ID = %d AND FOLDER_ID > %d AND FOLDER_ID < %d AND STORAGE_ID = %d ORDER BY DISPLAY_TIME, MSG_ID ASC;",
1942                         MSGFW_MESSAGE_TABLE_NAME, threadId, MSG_ALLBOX_ID, MSG_CBMSGBOX_ID, MSG_STORAGE_PHONE);
1943 #endif
1944
1945         msg_error_t err = dbHandle->getTable(sqlQuery, &rowCnt, &index);
1946
1947         if (err == MSG_ERR_DB_NORECORD) {
1948                 dbHandle->freeTable();
1949                 return MSG_SUCCESS;
1950         } else if (err != MSG_SUCCESS) {
1951                 MSG_DEBUG("Fail to getTable().");
1952                 dbHandle->freeTable();
1953                 return err;
1954         }
1955
1956         pConvViewList->nCount = rowCnt;
1957         char *tmpText[rowCnt] = {NULL};
1958
1959         MSG_DEBUG("pConvViewList->nCount [%d]", pConvViewList->nCount);
1960
1961         pConvViewList->msg_struct_info = (msg_struct_t *)calloc(rowCnt, sizeof(msg_struct_t));
1962         memset(pConvViewList->msg_struct_info, 0x00, sizeof(msg_struct_t) * rowCnt);
1963
1964         msg_struct_s *conv = NULL;
1965         MSG_CONVERSATION_VIEW_S *pTmp = NULL;
1966
1967         for (int i = 0; i < rowCnt; i++) {
1968                 pConvViewList->msg_struct_info[i] = (msg_struct_t)new msg_struct_s;
1969                 memset(pConvViewList->msg_struct_info[i], 0x00, sizeof(msg_struct_s));
1970
1971                 conv = (msg_struct_s *)pConvViewList->msg_struct_info[i];
1972
1973                 conv->type = MSG_STRUCT_CONV_INFO;
1974                 conv->data = new MSG_CONVERSATION_VIEW_S;
1975                 memset(conv->data, 0x00, sizeof(MSG_CONVERSATION_VIEW_S));
1976
1977                 pTmp = (MSG_CONVERSATION_VIEW_S *)conv->data;
1978
1979                 pTmp->pText = NULL;
1980
1981                 pTmp->msgId = dbHandle->getColumnToInt(index++);
1982                 pTmp->threadId = dbHandle->getColumnToInt(index++);
1983                 pTmp->folderId = dbHandle->getColumnToInt(index++);
1984                 pTmp->storageId = dbHandle->getColumnToInt(index++);
1985                 pTmp->mainType = dbHandle->getColumnToInt(index++);
1986                 pTmp->subType = dbHandle->getColumnToInt(index++);
1987                 pTmp->displayTime = (time_t)dbHandle->getColumnToInt(index++);
1988                 pTmp->textSize = dbHandle->getColumnToInt(index++);
1989                 pTmp->networkStatus = dbHandle->getColumnToInt(index++);
1990                 pTmp->bRead = dbHandle->getColumnToInt(index++);
1991                 pTmp->bProtected = dbHandle->getColumnToInt(index++);
1992                 pTmp->direction = dbHandle->getColumnToInt(index++);
1993                 index++; /* This field is reserved. */
1994
1995                 dbHandle->getColumnToString(index++, MAX_SUBJECT_LEN, pTmp->subject);
1996                 tmpText[i] = g_strdup(dbHandle->getColumnToString(index++));
1997
1998                 /*It does Not need to Get attach count in MSG_MESSAGE_TABLE. see MsgStoGetConversationPreview */
1999                 /*pTmp->attachCount = dbHandle->getColumnToInt(index++); */
2000                 index++;
2001                 pTmp->simIndex = dbHandle->getColumnToInt(index++);
2002         }
2003         dbHandle->freeTable();
2004
2005         for (int i = 0; i < pConvViewList->nCount; i++) {
2006                 conv = (msg_struct_s *)pConvViewList->msg_struct_info[i];
2007                 pTmp = (MSG_CONVERSATION_VIEW_S *)conv->data;
2008
2009                 if (pTmp->mainType == MSG_MMS_TYPE &&
2010                         (pTmp->networkStatus == MSG_NETWORK_RETRIEVING || pTmp->networkStatus == MSG_NETWORK_RETRIEVE_FAIL || pTmp->subType == MSG_NOTIFICATIONIND_MMS)) {
2011                         pTmp->pText = NULL;
2012                         pTmp->textSize = 0;
2013                 } else {
2014                         if (pTmp->mainType == MSG_SMS_TYPE) {
2015                                 pTmp->pText = new char[pTmp->textSize+2];
2016                                 memset(pTmp->pText, 0x00, pTmp->textSize+2);
2017                                 snprintf(pTmp->pText, pTmp->textSize+1, "%s", tmpText[i]);
2018                         } else if (pTmp->mainType == MSG_MMS_TYPE) {
2019                                 if (tmpText[i]) {
2020                                         pTmp->textSize = strlen(tmpText[i]);
2021
2022                                         pTmp->pText = new char[pTmp->textSize+1];
2023                                         memset(pTmp->pText, 0x00, pTmp->textSize+1);
2024
2025                                         strncpy(pTmp->pText, tmpText[i], pTmp->textSize);
2026                                 }
2027
2028                                 MsgStoGetConversationPreview(dbHandle, pTmp);
2029                                 MsgStoGetConversationMultipart(dbHandle, pTmp);
2030                         }
2031                 }
2032                 if (tmpText[i]) {
2033                         g_free(tmpText[i]);
2034                         tmpText[i] = NULL;
2035                 }
2036         }
2037
2038         MSG_END();
2039
2040         return MSG_SUCCESS;
2041 }
2042
2043
2044 msg_error_t MsgStoSearchMessage(const char *pSearchString, msg_struct_list_s *pThreadViewList, int contactCount)
2045 {
2046         if (!pSearchString)
2047                 return MSG_ERR_NULL_POINTER;
2048
2049         MsgDbHandler *dbHandle = getDbHandle();
2050         dbHandle->connectReadOnly();
2051         char *escapeAddressStr = NULL;
2052
2053         /* Clear Out Parameter */
2054         pThreadViewList->nCount = 0;
2055         pThreadViewList->msg_struct_info = NULL;
2056
2057         tr1::unordered_set<msg_thread_id_t> IdList;
2058         queue<MSG_THREAD_VIEW_S> searchList;
2059
2060         MSG_THREAD_VIEW_S threadView;
2061
2062         char sqlQuery[MAX_QUERY_LEN+1];
2063
2064         /* Search - Address, Name */
2065         memset(sqlQuery, 0x00, MAX_QUERY_LEN+1);
2066         snprintf(sqlQuery, MAX_QUERY_LEN, "SELECT A.CONV_ID, A.UNREAD_CNT, A.SMS_CNT, A.MMS_CNT, A.DISPLAY_NAME, "
2067                         "A.MAIN_TYPE, A.SUB_TYPE, A.MSG_DIRECTION, A.DISPLAY_TIME, A.MSG_TEXT, "
2068                         "(SELECT COUNT(*) FROM %s B WHERE B.CONV_ID = A.CONV_ID AND B.PROTECTED = 1) AS PROTECTED, "
2069                         "(SELECT COUNT(*) FROM %s B WHERE B.CONV_ID = A.CONV_ID AND B.FOLDER_ID = %d) AS DRAFT, "
2070                         "(SELECT COUNT(*) FROM %s B WHERE B.CONV_ID = A.CONV_ID AND B.NETWORK_STATUS = %d) AS FAILED, "
2071                         "(SELECT COUNT(*) FROM %s B WHERE B.CONV_ID = A.CONV_ID AND B.NETWORK_STATUS = %d) AS SENDING "
2072                         "FROM %s A WHERE (A.SMS_CNT > 0 OR A.MMS_CNT > 0) "
2073                         "AND A.CONV_ID IN "
2074                         "(SELECT DISTINCT(CONV_ID) FROM %s WHERE "
2075                         "ADDRESS_VAL LIKE ? ESCAPE '%c' ",
2076                         MSGFW_MESSAGE_TABLE_NAME,
2077                         MSGFW_MESSAGE_TABLE_NAME, MSG_DRAFT_ID,
2078                         MSGFW_MESSAGE_TABLE_NAME, MSG_NETWORK_SEND_FAIL,
2079                         MSGFW_MESSAGE_TABLE_NAME, MSG_NETWORK_SENDING,
2080                         MSGFW_CONVERSATION_TABLE_NAME,
2081                         MSGFW_ADDRESS_TABLE_NAME,
2082                         MSGFW_DB_ESCAPE_CHAR);
2083
2084         unsigned int tmpSize = 0;
2085         if (contactCount > 0) {
2086                 tmpSize = strlen(sqlQuery);
2087                 snprintf(sqlQuery+tmpSize, MAX_QUERY_LEN-tmpSize,
2088                                 "OR ADDRESS_VAL IN (SELECT C.ADDRESS_VAL FROM %s C JOIN %s D ON (C.ADDRESS_VAL LIKE D.ADDRESS_VAL))"
2089                                 , MSGFW_ADDRESS_TABLE_NAME, MSGFW_ADDRESS_TEMP_TABLE_NAME);
2090         }
2091
2092         tmpSize = strlen(sqlQuery);
2093         snprintf(sqlQuery+tmpSize, MAX_QUERY_LEN-tmpSize,
2094                         ") ORDER BY A.DISPLAY_TIME DESC;");
2095
2096         MSG_DEBUG("sqlQuery=[%s]", sqlQuery);
2097
2098         if (dbHandle->prepareQuery(sqlQuery) != MSG_SUCCESS) {
2099                 MSG_DEBUG("Prepare query fail.");
2100                 return MSG_ERR_DB_PREPARE;
2101         }
2102
2103         MsgConvertStrWithEscape(pSearchString, &escapeAddressStr);
2104         MSG_DEBUG("escapeAddressStr [%s]", escapeAddressStr);
2105         dbHandle->bindText(escapeAddressStr, 1);
2106         /*dbHandle->bindText(escapeAddressStr, 2); */
2107         /*dbHandle->bindText(escapeAddressStr, 3); */
2108         /*dbHandle->bindText(escapeAddressStr, 4); */
2109
2110         while (dbHandle->stepQuery() == MSG_ERR_DB_ROW) {
2111                 memset(&threadView, 0x00, sizeof(threadView));
2112
2113                 threadView.threadId = dbHandle->columnInt(0);
2114                 threadView.unreadCnt = dbHandle->columnInt(1);
2115                 threadView.smsCnt = dbHandle->columnInt(2);
2116                 threadView.mmsCnt = dbHandle->columnInt(3);
2117
2118                 if (dbHandle->columnText(4))
2119                         strncpy(threadView.threadName, (char *)dbHandle->columnText(4), MAX_THREAD_NAME_LEN);
2120
2121                 threadView.mainType = dbHandle->columnInt(5);
2122                 threadView.subType = dbHandle->columnInt(6);
2123
2124                 threadView.direction = dbHandle->columnInt(7);
2125                 threadView.threadTime = (time_t)dbHandle->columnInt(8);
2126
2127                 if (dbHandle->columnText(9))
2128                         strncpy(threadView.threadData, (char *)dbHandle->columnText(9), MAX_THREAD_DATA_LEN);
2129
2130                 int protectedCnt = dbHandle->columnInt(10);
2131                 if (protectedCnt > 0)
2132                         threadView.bProtected = true;
2133
2134                 int draftCnt = dbHandle->columnInt(11);
2135                 if (draftCnt > 0)
2136                         threadView.bDraft = true;
2137
2138                 int failedCnt = dbHandle->columnInt(12);
2139                 if (failedCnt > 0)
2140                         threadView.bSendFailed = true;
2141
2142                 int sendingCnt = dbHandle->columnInt(13);
2143                 if (sendingCnt > 0)
2144                         threadView.bSending = true;
2145
2146                 tr1::unordered_set<msg_thread_id_t>::iterator it;
2147
2148                 it = IdList.find(threadView.threadId);
2149
2150                 if (it == IdList.end()) {
2151                         IdList.insert(threadView.threadId);
2152                         searchList.push(threadView);
2153                 }
2154         }
2155
2156         dbHandle->finalizeQuery();
2157
2158         if (escapeAddressStr) {
2159                 free(escapeAddressStr);
2160                 escapeAddressStr = NULL;
2161         }
2162
2163
2164         /* Add data to Out Parameter */
2165         pThreadViewList->nCount = searchList.size();
2166         pThreadViewList->msg_struct_info = (msg_struct_t *)calloc(searchList.size(), sizeof(msg_struct_t));
2167         if (pThreadViewList->msg_struct_info == NULL)
2168                 return MSG_ERR_MEMORY_ERROR;
2169
2170         MSG_THREAD_VIEW_S *pTmp = NULL;
2171         msg_struct_s *thread_t = NULL;
2172
2173         int index = 0;
2174
2175         while (!searchList.empty()) {
2176                 thread_t = (msg_struct_s *)new msg_struct_s;
2177                 pThreadViewList->msg_struct_info[index] = (msg_struct_t)thread_t;
2178
2179                 thread_t->type = MSG_STRUCT_THREAD_INFO;
2180                 thread_t->data = new MSG_THREAD_VIEW_S;
2181
2182                 pTmp = (MSG_THREAD_VIEW_S *)thread_t->data;
2183                 memset(pTmp, 0x00, sizeof(MSG_THREAD_VIEW_S));
2184
2185                 memcpy(pTmp, &(searchList.front()), sizeof(MSG_THREAD_VIEW_S));
2186
2187                 searchList.pop();
2188
2189                 index++;
2190         }
2191
2192         return MSG_SUCCESS;
2193 }
2194
2195
2196 msg_error_t MsgStoGetRejectMsgList(const char *pNumber, msg_struct_list_s *pRejectMsgList)
2197 {
2198         MsgDbHandler *dbHandle = getDbHandle();
2199         dbHandle->connectReadOnly();
2200
2201         /* Clear Out Parameter */
2202         pRejectMsgList->nCount = 0;
2203         pRejectMsgList->msg_struct_info = NULL;
2204
2205         int rowCnt = 0, index = 0;
2206
2207         char sqlQuery[MAX_QUERY_LEN+1];
2208
2209         /* Search Reject Msg */
2210         memset(sqlQuery, 0x00, sizeof(sqlQuery));
2211
2212         if (pNumber != NULL) {
2213                 int addrSize = strlen(pNumber);
2214                 char phoneNumber[addrSize+1];
2215                 memset(phoneNumber, 0x00, sizeof(phoneNumber));
2216
2217                 if (addrSize > MsgContactGetMinMatchDigit())
2218                         MsgConvertNumber(pNumber, phoneNumber, addrSize);
2219                 else
2220                         strncpy(phoneNumber, pNumber, addrSize);
2221
2222                 snprintf(sqlQuery, sizeof(sqlQuery), "SELECT "
2223                                 "B.MSG_ID, "
2224                                 "B.MSG_TEXT, "
2225                                 "B.DISPLAY_TIME "
2226                                 "FROM %s A, %s B "
2227                                 "WHERE A.CONV_ID = B.CONV_ID "
2228                                 "AND B.MAIN_TYPE = %d "
2229                                 "AND B.SUB_TYPE = %d "
2230                                 "AND A.ADDRESS_VAL LIKE '%%%s' "
2231                                 "ORDER BY B.DISPLAY_TIME DESC;",
2232                                 MSGFW_ADDRESS_TABLE_NAME, MSGFW_MESSAGE_TABLE_NAME,
2233                                 MSG_SMS_TYPE,
2234                                 MSG_REJECT_SMS,
2235                                 phoneNumber);
2236         } else {
2237                 snprintf(sqlQuery, sizeof(sqlQuery), "SELECT "
2238                                 "B.MSG_ID, "
2239                                 "B.MSG_TEXT, "
2240                                 "B.DISPLAY_TIME "
2241                                 "FROM %s A, %s B "
2242                                 "WHERE A.CONV_ID = B.CONV_ID "
2243                                 "AND B.MAIN_TYPE = %d "
2244                                 "AND B.SUB_TYPE = %d "
2245                                 "ORDER BY B.DISPLAY_TIME DESC;",
2246                                 MSGFW_ADDRESS_TABLE_NAME, MSGFW_MESSAGE_TABLE_NAME,
2247                                 MSG_SMS_TYPE,
2248                                 MSG_REJECT_SMS);
2249         }
2250
2251         msg_error_t err = dbHandle->getTable(sqlQuery, &rowCnt, &index);
2252
2253         if (err != MSG_SUCCESS) {
2254                 MSG_DEBUG("Fail to getTable().");
2255                 dbHandle->freeTable();
2256                 return err;
2257         }
2258
2259         pRejectMsgList->nCount = rowCnt;
2260
2261         MSG_DEBUG("pRejectMsgList->nCount [%d]", pRejectMsgList->nCount);
2262
2263         pRejectMsgList->msg_struct_info = (msg_struct_t *)calloc(rowCnt, sizeof(MSG_REJECT_MSG_INFO_S *));
2264
2265         msg_struct_s* pTmp = NULL;
2266
2267         for (int i = 0; i < rowCnt; i++) {
2268                 pRejectMsgList->msg_struct_info[i] = (msg_struct_t)new msg_struct_s;
2269
2270                 pTmp = (msg_struct_s *)pRejectMsgList->msg_struct_info[i];
2271                 pTmp->type = MSG_STRUCT_REJECT_MSG_INFO;
2272                 pTmp->data = new MSG_REJECT_MSG_INFO_S;
2273                 MSG_REJECT_MSG_INFO_S * pMsg = (MSG_REJECT_MSG_INFO_S *)pTmp->data;
2274                 memset(pMsg, 0x00, sizeof(MSG_REJECT_MSG_INFO_S));
2275
2276                 pMsg->msgId = dbHandle->getColumnToInt(index++);
2277                 memset(pMsg->msgText, 0x00, sizeof(pMsg->msgText));
2278                 dbHandle->getColumnToString(index++, MAX_MSG_TEXT_LEN, pMsg->msgText);
2279
2280                 pMsg->displayTime = (time_t)dbHandle->getColumnToInt(index++);
2281         }
2282
2283         dbHandle->freeTable();
2284
2285         return MSG_SUCCESS;
2286 }
2287
2288
2289 msg_error_t MsgStoGetAddressList(const msg_thread_id_t threadId, msg_struct_list_s *pAddrList)
2290 {
2291         MsgDbHandler *dbHandle = getDbHandle();
2292         dbHandle->connectReadOnly();
2293
2294         msg_error_t err = MSG_SUCCESS;
2295
2296         err = MsgStoGetAddressByConvId(dbHandle, threadId, pAddrList);
2297
2298         return err;
2299 }
2300
2301
2302 msg_error_t MsgStoGetMessageList(const MSG_LIST_CONDITION_S *pListCond, msg_struct_list_s *pMsgList, int contactCount)
2303 {
2304         MsgDbHandler *dbHandle = getDbHandle();
2305         dbHandle->connectReadOnly();
2306
2307         /* Clear Out Parameter */
2308         pMsgList->nCount = 0;
2309         pMsgList->msg_struct_info = NULL;
2310
2311         int index = 0;
2312         int multipartCnt = 0;
2313
2314         char sqlQuery[MAX_QUERY_LEN+1];
2315         char sqlQuerySubset[(MAX_QUERY_LEN/5)+1];
2316
2317         memset(sqlQuery, 0x00, sizeof(sqlQuery));
2318         snprintf(sqlQuery, sizeof(sqlQuery), "SELECT COUNT(*) FROM %s;", MSGFW_MMS_MULTIPART_TABLE_NAME);
2319
2320         if (dbHandle->prepareQuery(sqlQuery) != MSG_SUCCESS)
2321                 return MSG_ERR_DB_PREPARE;
2322
2323         if (dbHandle->stepQuery() == MSG_ERR_DB_ROW) {
2324                 multipartCnt = dbHandle->columnInt(0);
2325         } else {
2326                 dbHandle->finalizeQuery();
2327                 return MSG_ERR_DB_STEP;
2328         }
2329
2330         dbHandle->finalizeQuery();
2331
2332         memset(sqlQuery, 0x00, sizeof(sqlQuery));
2333         snprintf(sqlQuery, sizeof(sqlQuery), "SELECT DISTINCT "
2334                         "A.MSG_ID, "
2335                         "A.CONV_ID, "
2336                         "A.FOLDER_ID, "
2337                         "A.STORAGE_ID, "
2338                         "A.MAIN_TYPE, "
2339                         "A.SUB_TYPE, "
2340                         "A.DISPLAY_TIME, "
2341                         "A.DATA_SIZE, "
2342                         "A.NETWORK_STATUS, "
2343                         "A.READ_STATUS, "
2344                         "A.PROTECTED, "
2345                         "A.BACKUP, "
2346                         "A.PRIORITY, "
2347                         "A.MSG_DIRECTION, "
2348                         "A.SCHEDULED_TIME, "
2349                         "A.SUBJECT, "
2350                         "A.MSG_TEXT, "
2351                         "A.ATTACHMENT_COUNT, "
2352                         "A.THUMB_PATH, "
2353                         "A.SIM_INDEX, "
2354                         "B.ADDRESS_TYPE, "
2355                         "B.RECIPIENT_TYPE, "
2356                         "B.ADDRESS_VAL ");
2357
2358         if (pListCond->pTextVal != NULL && multipartCnt > 0) {
2359                 memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2360                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "FROM %s C, %s B, %s A WHERE A.CONV_ID > 0 AND A.CONV_ID = B.CONV_ID AND ",
2361                         MSGFW_MMS_MULTIPART_TABLE_NAME, MSGFW_ADDRESS_TABLE_NAME, MSGFW_MESSAGE_TABLE_NAME);
2362         }
2363         else {
2364                 memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2365                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset),        "FROM %s B, %s A WHERE A.CONV_ID > 0 AND A.CONV_ID = B.CONV_ID AND ",
2366                 MSGFW_ADDRESS_TABLE_NAME, MSGFW_MESSAGE_TABLE_NAME);
2367         }
2368
2369         strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2370
2371         /* folder */
2372         memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2373
2374         if (pListCond->folderId == MSG_ALLBOX_ID)
2375                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "A.FOLDER_ID > 0 AND A.FOLDER_ID < %d ", MSG_SPAMBOX_ID);
2376         else if (pListCond->folderId == MSG_IOSBOX_ID)
2377                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "A.FOLDER_ID > 0 AND A.FOLDER_ID < %d ", MSG_DRAFT_ID);
2378         else
2379                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "A.FOLDER_ID = %d ", pListCond->folderId);
2380
2381         strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2382
2383
2384         /* thread */
2385         if (pListCond->threadId > 0) {
2386                 memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2387                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "AND A.CONV_ID = %d ", pListCond->threadId);
2388                 strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2389         }
2390
2391
2392         /* msg type */
2393         memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2394
2395         switch (pListCond->msgType) {
2396                 case MSG_TYPE_SMS:
2397                         if (pListCond->pAddressVal == NULL)
2398                                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "AND A.MAIN_TYPE = %d ", MSG_SMS_TYPE);
2399                         else
2400                                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "AND A.MAIN_TYPE = %d AND A.SUB_TYPE = %d ", MSG_SMS_TYPE, MSG_NORMAL_SMS);
2401                         break;
2402
2403                 case MSG_TYPE_MMS:
2404                         snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "AND A.MAIN_TYPE = %d ", MSG_MMS_TYPE);
2405                         break;
2406
2407                 case MSG_TYPE_MMS_JAVA:
2408                         snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "AND A.MAIN_TYPE = %d AND A.SUB_TYPE = %d ", MSG_MMS_TYPE, MSG_SENDREQ_JAVA_MMS);
2409                         break;
2410
2411                 case MSG_TYPE_SMS_SYNCML:
2412                         snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "AND A.MAIN_TYPE = %d AND A.SUB_TYPE = %d ", MSG_SMS_TYPE, MSG_SYNCML_CP);
2413                         break;
2414                 case MSG_TYPE_SMS_REJECT:
2415                         snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "AND A.MAIN_TYPE = %d AND A.SUB_TYPE = %d ", MSG_SMS_TYPE, MSG_REJECT_SMS);
2416                         break;
2417
2418                 default:
2419                         MSG_DEBUG("msg type is not set.");
2420                         break;
2421         }
2422
2423         strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2424
2425
2426         /* storage */
2427         if (pListCond->storageId > MSG_STORAGE_UNKNOWN) {
2428                 memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2429                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "AND A.STORAGE_ID = %d ", pListCond->storageId);
2430                 strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2431         }
2432
2433
2434         /* protected */
2435         if (pListCond->bProtected) {
2436                 memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2437                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "AND A.PROTECTED = %d ", pListCond->bProtected);
2438                 strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2439         }
2440
2441
2442         /* scheduled */
2443         if (pListCond->bScheduled) {
2444                 memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2445                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "AND A.SCHEDULED_TIME > 0 ");
2446                 strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2447         }
2448
2449
2450         /* sim index */
2451         if (pListCond->simIndex > 0) {
2452                 memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2453                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "AND A.SIM_INDEX = %d ", pListCond->simIndex);
2454                 strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2455         }
2456
2457
2458         /* time range */
2459         if (pListCond->fromTime > 0) {
2460                 memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2461                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "AND A.DISPLAY_TIME >= %u ", (unsigned int)pListCond->fromTime);
2462                 strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2463         }
2464
2465         if (pListCond->toTime > 0) {
2466                 memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2467                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "AND A.DISPLAY_TIME <= %u ", (unsigned int)pListCond->toTime);
2468                 strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2469         }
2470
2471         if (pListCond->pAddressVal == NULL) {
2472                 /* Text */
2473                 if (pListCond->pTextVal != NULL) {
2474                         memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2475                         if (multipartCnt > 0) {
2476                                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset),
2477                                                 "AND ((A.MSG_TEXT LIKE ? ESCAPE '%c' OR A.SUBJECT LIKE ? ESCAPE '%c' OR (C.NAME LIKE ? ESCAPE '%c' AND A.MSG_ID = C.MSG_ID AND C.CONTENT_TYPE <> 'application/smil'))) ",
2478                                                 MSGFW_DB_ESCAPE_CHAR, MSGFW_DB_ESCAPE_CHAR, MSGFW_DB_ESCAPE_CHAR);
2479                         }
2480                         else {
2481                                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset),
2482                                                 "AND ((A.MSG_TEXT LIKE ? ESCAPE '%c' OR A.SUBJECT LIKE ? ESCAPE '%c')) ",
2483                                                 MSGFW_DB_ESCAPE_CHAR, MSGFW_DB_ESCAPE_CHAR);
2484                         }
2485                         strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2486                 }
2487         } else {
2488                 /* Text */
2489                 if (pListCond->pTextVal != NULL) {
2490                         memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2491                         if (multipartCnt > 0) {
2492                                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset),
2493                                                 "AND ((A.MSG_TEXT LIKE ? ESCAPE '%c' OR A.SUBJECT LIKE ? ESCAPE '%c' OR (C.NAME LIKE ? ESCAPE '%c' AND A.MSG_ID = C.MSG_ID AND C.CONTENT_TYPE <> 'application/smil')) ",
2494                                                 MSGFW_DB_ESCAPE_CHAR, MSGFW_DB_ESCAPE_CHAR, MSGFW_DB_ESCAPE_CHAR);
2495                         }
2496                         else {
2497                                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset),
2498                                                 "AND ((A.MSG_TEXT LIKE ? ESCAPE '%c' OR A.SUBJECT LIKE ? ESCAPE '%c') ",
2499                                                 MSGFW_DB_ESCAPE_CHAR, MSGFW_DB_ESCAPE_CHAR);
2500                         }
2501                         strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2502
2503                         memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2504                         if (pListCond->bAnd) {
2505                                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "AND ");
2506                         } else {
2507                                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "OR ");
2508                         }
2509                         strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2510
2511                         /* Address */
2512                         memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2513                         snprintf(sqlQuerySubset, sizeof(sqlQuerySubset),
2514                                         "(B.ADDRESS_VAL LIKE ? ESCAPE '%c' ", MSGFW_DB_ESCAPE_CHAR);
2515                         strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2516
2517                         if (contactCount > 0) {
2518                                 memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2519                                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset),
2520                                                 "OR B.ADDRESS_VAL IN (SELECT D.ADDRESS_VAL FROM %s D JOIN %s E ON (D.ADDRESS_VAL LIKE E.ADDRESS_VAL)) "
2521                                                 , MSGFW_ADDRESS_TABLE_NAME, MSGFW_ADDRESS_TEMP_TABLE_NAME);
2522                                 strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2523                         }
2524
2525                         memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2526                         snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), ")) ");
2527                         strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2528                 } else {
2529                         /* Address */
2530                         memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2531                         snprintf(sqlQuerySubset, sizeof(sqlQuerySubset),
2532                                         "AND (B.ADDRESS_VAL LIKE ? ESCAPE '%c' ", MSGFW_DB_ESCAPE_CHAR);
2533                         strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2534
2535                         if (contactCount > 0) {
2536                                 memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2537                                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset),
2538                                                 "OR B.ADDRESS_VAL IN (SELECT D.ADDRESS_VAL FROM %s D JOIN %s E ON (D.ADDRESS_VAL LIKE E.ADDRESS_VAL)) "
2539                                                 , MSGFW_ADDRESS_TABLE_NAME, MSGFW_ADDRESS_TEMP_TABLE_NAME);
2540                                 strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2541                         }
2542
2543                         memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2544                         snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), ") ");
2545                         strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2546                 }
2547         }
2548
2549         msg_struct_s *pSortRule = (msg_struct_s *)pListCond->sortRule;
2550
2551         if (pSortRule->type != MSG_STRUCT_SORT_RULE) {
2552                 /* Order */
2553                 memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2554                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "ORDER BY A.DISPLAY_TIME ");
2555
2556                 strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2557
2558                 /* Sorting type */
2559                 memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2560                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "DESC ");
2561
2562                 strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2563         } else {
2564                 MSG_SORT_RULE_S *pTmp = (MSG_SORT_RULE_S *)pSortRule->data;
2565                 /* order : TODO: have to finish this */
2566                 memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2567                 switch (pTmp->sortType) {
2568                 case MSG_SORT_BY_MSG_TYPE:
2569                         snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "ORDER BY A.MAIN_TYPE ");
2570                         break;
2571                 case MSG_SORT_BY_READ_STATUS:
2572                         snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "ORDER BY A.READ_STATUS ");
2573                         break;
2574                 case MSG_SORT_BY_STORAGE_TYPE:
2575                         snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "ORDER BY A.STORAGE_ID ");
2576                         break;
2577                 default:
2578                         snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "ORDER BY A.DISPLAY_TIME ");
2579                         break;
2580                 }
2581                 strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2582
2583                 /* Sorting type */
2584                 memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2585                 if (pTmp->bAscending)
2586                         snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "ASC ");
2587                 else
2588                         snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "DESC ");
2589
2590                 strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2591         }
2592
2593         /* offset & limit */
2594         memset(sqlQuerySubset, 0x00, sizeof(sqlQuerySubset));
2595         if (pListCond->offset >= 0 && pListCond->limit > 0)
2596                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), "LIMIT %d OFFSET %d;", pListCond->limit, pListCond->offset);
2597         else
2598                 snprintf(sqlQuerySubset, sizeof(sqlQuerySubset), ";");
2599
2600         strncat(sqlQuery, sqlQuerySubset, MAX_QUERY_LEN-strlen(sqlQuery));
2601
2602
2603         /* 'til here sqlQuery is complete. */
2604
2605         queue<MSG_MESSAGE_HIDDEN_S*> searchList;
2606
2607         MSG_DEBUG("[%s]", sqlQuery);
2608
2609         if (dbHandle->prepareQuery(sqlQuery) != MSG_SUCCESS) {
2610                 MSG_DEBUG("Prepare query fail.");
2611                 return MSG_ERR_DB_PREPARE;
2612         }
2613
2614         char *escapeTextStr = NULL;
2615         char *escapeAddressStr = NULL;
2616
2617         if (pListCond->pAddressVal == NULL) {
2618                 /* Text */
2619                 if (pListCond->pTextVal != NULL) {
2620                         MsgConvertStrWithEscape(pListCond->pTextVal, &escapeTextStr);
2621                         MSG_DEBUG("escapeTextStr [%s]", escapeTextStr);
2622                         dbHandle->bindText(escapeTextStr, 1);
2623                         dbHandle->bindText(escapeTextStr, 2);
2624                         if (multipartCnt > 0) dbHandle->bindText(escapeTextStr, 3);
2625                 }
2626         } else {
2627                 /* Text */
2628                 if (pListCond->pTextVal != NULL) {
2629                         MsgConvertStrWithEscape(pListCond->pTextVal, &escapeTextStr);
2630                         MSG_DEBUG("escapeTestStr [%s]", escapeTextStr);
2631
2632                         /* Address */
2633                         MsgConvertStrWithEscape(pListCond->pAddressVal, &escapeAddressStr);
2634                         MSG_DEBUG("escapeAddressStr [%s]", escapeAddressStr);
2635
2636                         dbHandle->bindText(escapeTextStr, 1);
2637                         dbHandle->bindText(escapeTextStr, 2);
2638                         if (multipartCnt > 0) {
2639                                 dbHandle->bindText(escapeTextStr, 3);
2640                                 dbHandle->bindText(escapeAddressStr, 4);
2641                         } else {
2642                                 dbHandle->bindText(escapeAddressStr, 3);
2643                         }
2644
2645                 } else {
2646                         /* Address */
2647                         MsgConvertStrWithEscape(pListCond->pAddressVal, &escapeAddressStr);
2648                         MSG_DEBUG("escapeAddressStr [%s]", escapeAddressStr);
2649                         dbHandle->bindText(escapeAddressStr, 1);
2650                 }
2651         }
2652
2653
2654         MSG_MESSAGE_HIDDEN_S *pTmp = NULL;
2655         int lastMsgId = 0;  /* for comparing same msg id. */
2656
2657         while (dbHandle->stepQuery() == MSG_ERR_DB_ROW) {
2658                 index = 0;
2659
2660                 int msgid = dbHandle->columnInt(index++);
2661                 MSG_DEBUG("msgid [%d]", msgid);
2662
2663                 if (lastMsgId != msgid) {
2664                         MSG_DEBUG("lastMsgId != msgid");
2665
2666                         lastMsgId = msgid;
2667
2668                         pTmp = new MSG_MESSAGE_HIDDEN_S;
2669
2670                         if(pTmp) {
2671                                 memset(pTmp, 0x00, sizeof(MSG_MESSAGE_HIDDEN_S));
2672
2673                                 pTmp->pData = NULL;
2674                                 pTmp->pMmsData = NULL;
2675                                 pTmp->addressList = NULL;
2676
2677                                 pTmp->msgId = msgid;
2678
2679                                 pTmp->threadId = dbHandle->columnInt(index++);
2680                                 pTmp->folderId = dbHandle->columnInt(index++);
2681                                 pTmp->storageId = dbHandle->columnInt(index++);
2682                                 pTmp->mainType = dbHandle->columnInt(index++);
2683                                 pTmp->subType = dbHandle->columnInt(index++);
2684                                 pTmp->displayTime = (time_t)dbHandle->columnInt(index++);
2685                                 pTmp->dataSize = dbHandle->columnInt(index++);
2686                                 pTmp->networkStatus = dbHandle->columnInt(index++);
2687                                 pTmp->bRead = dbHandle->columnInt(index++);
2688                                 pTmp->bProtected = dbHandle->columnInt(index++);
2689                                 pTmp->bBackup = dbHandle->columnInt(index++);
2690                                 pTmp->priority = dbHandle->columnInt(index++);
2691                                 pTmp->direction = dbHandle->columnInt(index++);
2692                                 index++; /* This field is reserved. */
2693
2694                                 strncpy(pTmp->subject, (char *)dbHandle->columnText(index++), MAX_SUBJECT_LEN);
2695
2696                                 if (pTmp->mainType == MSG_MMS_TYPE &&
2697                                         (pTmp->networkStatus == MSG_NETWORK_RETRIEVING || pTmp->networkStatus == MSG_NETWORK_RETRIEVE_FAIL || pTmp->subType == MSG_NOTIFICATIONIND_MMS)) {
2698                                         pTmp->pData = NULL;
2699                                         index++;
2700                                 } else {
2701                                         pTmp->pData = (void *)new char[pTmp->dataSize+2];
2702                                         memset(pTmp->pData, 0x00, pTmp->dataSize+2);
2703
2704                                         strncpy((char *)pTmp->pData, (char *)dbHandle->columnText(index++), pTmp->dataSize+1);
2705                                 }
2706
2707                                 pTmp->attachCount = dbHandle->columnInt(index++);
2708
2709                                 strncpy(pTmp->thumbPath, (char *)dbHandle->columnText(index++), MSG_FILEPATH_LEN_MAX);
2710
2711                                 pTmp->simIndex = dbHandle->columnInt(index++);
2712
2713                                 pTmp->addr_list = (msg_struct_list_s *)new msg_struct_list_s;
2714                                 pTmp->addr_list->nCount = 0;
2715                                 pTmp->addr_list->msg_struct_info = (msg_struct_t *)calloc(MAX_TO_ADDRESS_CNT, sizeof(msg_struct_t));
2716                                 for (int i = 0; i < MAX_TO_ADDRESS_CNT; i++) {
2717                                         pTmp->addr_list->msg_struct_info[i] = (msg_struct_t)new msg_struct_s;
2718                                         memset(pTmp->addr_list->msg_struct_info[i], 0x00, sizeof(msg_struct_s));
2719                                 }
2720
2721                                 searchList.push(pTmp);
2722                         }
2723
2724                 } else {
2725                         MSG_DEBUG("lastMsgId == msgid");
2726                         index += 19;
2727                 }
2728
2729                 if(pTmp) {
2730                         MSG_ADDRESS_INFO_S *pAddr = new MSG_ADDRESS_INFO_S;
2731                         memset(pAddr, 0x00, sizeof(MSG_ADDRESS_INFO_S));
2732
2733                         pAddr->addressType = dbHandle->columnInt(index++);
2734                         pAddr->recipientType = dbHandle->columnInt(index++);
2735
2736                         strncpy(pAddr->addressVal, (char *)dbHandle->columnText(index++), MAX_ADDRESS_VAL_LEN);
2737
2738                         strncpy(pAddr->displayName, pAddr->addressVal, MAX_DISPLAY_NAME_LEN);
2739
2740                         /* For GList *addressList */
2741                         msg_struct_s *addr_info_s = new msg_struct_s;
2742                         memset(addr_info_s, 0x00, sizeof(msg_struct_s));
2743                         addr_info_s->type = MSG_STRUCT_ADDRESS_INFO;
2744                         addr_info_s->data = new MSG_ADDRESS_INFO_S;
2745                         memset(addr_info_s->data, 0x00, sizeof(MSG_ADDRESS_INFO_S));
2746                         MSG_ADDRESS_INFO_S *addr_info = (MSG_ADDRESS_INFO_S *)addr_info_s->data;
2747                         addr_info->addressType = pAddr->addressType;
2748                         addr_info->recipientType = pAddr->recipientType;
2749                         addr_info->contactId = pAddr->contactId;
2750                         strncpy(addr_info->addressVal, pAddr->addressVal, MAX_ADDRESS_VAL_LEN);
2751                         strncpy(addr_info->displayName, pAddr->displayName, MAX_DISPLAY_NAME_LEN);
2752                         addr_info->displayName[MAX_DISPLAY_NAME_LEN] = '\0';
2753
2754                         pTmp->addressList = g_list_append(pTmp->addressList, addr_info_s);
2755
2756                         if (pTmp->addr_list->nCount >= MAX_TO_ADDRESS_CNT) {
2757                                 delete pAddr;
2758
2759                         } else {
2760                                 msg_struct_s *pStruct = (msg_struct_s *)pTmp->addr_list->msg_struct_info[pTmp->addr_list->nCount];
2761                                 pTmp->addr_list->nCount++;
2762                                 pStruct->type = MSG_STRUCT_ADDRESS_INFO;
2763                                 pStruct->data = pAddr;
2764                         }
2765                 }
2766         }
2767
2768         dbHandle->finalizeQuery();
2769
2770         pMsgList->nCount = searchList.size();
2771         MSG_DEBUG("pMsgList->nCount [%d]", pMsgList->nCount);
2772
2773         pMsgList->msg_struct_info = (msg_struct_t *)calloc(pMsgList->nCount, sizeof(msg_struct_t));
2774         if (pMsgList->msg_struct_info == NULL)
2775                 return MSG_ERR_MEMORY_ERROR;
2776
2777         int offset = 0;
2778         while (!searchList.empty()) {
2779                 msg_struct_s *msg = new msg_struct_s;
2780
2781                 pMsgList->msg_struct_info[offset++] = (msg_struct_t)msg;
2782
2783                 msg->type = MSG_STRUCT_MESSAGE_INFO;
2784                 msg->data = searchList.front();
2785
2786                 searchList.pop();
2787         }
2788
2789
2790         if (escapeTextStr)
2791                 free(escapeTextStr);
2792
2793         if (escapeAddressStr)
2794                 free(escapeAddressStr);
2795
2796         return MSG_SUCCESS;
2797 }
2798
2799
2800 msg_error_t MsgStoGetMediaList(const msg_thread_id_t threadId, msg_list_handle_t *pMediaList)
2801 {
2802         MSG_BEGIN();
2803         msg_error_t err = MSG_SUCCESS;
2804         MsgDbHandler *dbHandle = getDbHandle();
2805         dbHandle->connectReadOnly();
2806         char sqlQuery[MAX_QUERY_LEN+1];
2807         int msgIdCnt = 0;
2808
2809         memset(sqlQuery, 0x00, sizeof(sqlQuery));
2810         snprintf(sqlQuery, sizeof(sqlQuery), "SELECT MSG_ID FROM %s WHERE MAIN_TYPE = %d AND CONV_ID = %d;",
2811                         MSGFW_MESSAGE_TABLE_NAME, MSG_MMS_TYPE, threadId);
2812
2813         MSG_DEBUG("sqlQuery = [%s]", sqlQuery);
2814
2815         err = dbHandle->getTable(sqlQuery, &msgIdCnt, NULL);
2816         if (err != MSG_SUCCESS && err != MSG_ERR_DB_NORECORD) {
2817                 dbHandle->freeTable();
2818                 return err;
2819         } else if (err == MSG_ERR_DB_NORECORD) {
2820                 dbHandle->freeTable();
2821                 return MSG_SUCCESS;
2822         }
2823
2824         msg_message_id_t msgIds[msgIdCnt];
2825
2826         for (int i = 1; i <= msgIdCnt; i++) {
2827                 msgIds[i-1] = dbHandle->getColumnToInt(i);
2828         }
2829
2830         dbHandle->freeTable();
2831
2832         GList *media_list = NULL;
2833
2834         for (int i = 0; i < msgIdCnt; i++) {
2835                 memset(sqlQuery, 0x00, sizeof(sqlQuery));
2836                 snprintf(sqlQuery, sizeof(sqlQuery), "SELECT MSG_ID, CONTENT_TYPE, FILE_PATH, THUMB_FILE_PATH "
2837                                 "FROM %s WHERE MSG_ID = %d AND SEQ <> -1 AND (TCS_LEVEL = -1 OR MALWARE_ALLOW = 1);",
2838                                 MSGFW_MMS_MULTIPART_TABLE_NAME, msgIds[i]);
2839
2840                 int rowCnt = 0, msg_id = 0, index = 0;
2841
2842                 err = dbHandle->getTable(sqlQuery, &rowCnt, &index);
2843
2844                 if (err != MSG_SUCCESS && err != MSG_ERR_DB_NORECORD) {
2845                         dbHandle->freeTable();
2846                         return err;
2847                 }
2848
2849                 MSG_MEDIA_INFO_S *pMedia = NULL;
2850                 char mime_type[MAX_MIME_TYPE_LEN+1], media_item[MSG_FILEPATH_LEN_MAX+1], thumb_path[MSG_FILEPATH_LEN_MAX+1];
2851
2852                 for (int j = 0; j < rowCnt; j++) {
2853                         msg_id = dbHandle->getColumnToInt(index++);
2854                         memset(mime_type, 0x00, sizeof(mime_type));
2855                         dbHandle->getColumnToString(index++, MAX_MIME_TYPE_LEN, mime_type);
2856                         memset(media_item, 0x00, sizeof(media_item));
2857                         dbHandle->getColumnToString(index++, MSG_FILEPATH_LEN_MAX, media_item);
2858                         memset(thumb_path, 0x00, sizeof(thumb_path));
2859                         dbHandle->getColumnToString(index++, MSG_FILEPATH_LEN_MAX, thumb_path);
2860
2861                         if (strstr(mime_type, "image") || strstr(mime_type, "video")) {
2862                                 msg_struct_s *media_struct_s = new msg_struct_s;
2863                                 media_struct_s->type = MSG_STRUCT_MEDIA_INFO;
2864                                 media_struct_s->data = new MSG_MEDIA_INFO_S;
2865                                 memset(media_struct_s->data, 0x00, sizeof(MSG_MEDIA_INFO_S));
2866
2867                                 pMedia = (MSG_MEDIA_INFO_S *)media_struct_s->data;
2868
2869                                 pMedia->msg_id = msg_id;
2870                                 snprintf(pMedia->mime_type, MAX_MIME_TYPE_LEN, "%s", mime_type);
2871                                 snprintf(pMedia->media_item, MSG_FILEPATH_LEN_MAX, "%s", media_item);
2872                                 snprintf(pMedia->thumb_path, MSG_FILEPATH_LEN_MAX, "%s", thumb_path);
2873
2874                                 media_list = g_list_append(media_list, media_struct_s);
2875                         }
2876                 }
2877
2878                 dbHandle->freeTable();
2879
2880                 *pMediaList = (msg_list_handle_t)media_list;
2881         }
2882
2883         MSG_END();
2884         return MSG_SUCCESS;
2885 }
2886
2887
2888 msg_error_t MsgStoDbSelectWithQuery(const char *szQuery, char ***db_res, int *row_count, int *col_count)
2889 {
2890         MSG_BEGIN();
2891
2892         msg_error_t err = MSG_SUCCESS;
2893
2894         MsgDbHandler *dbHandle = getDbHandle();
2895         err = dbHandle->connectReadOnly();
2896         if (err != MSG_SUCCESS) {
2897                 MSG_ERR("db connect (read only) is failed [%d]", err);
2898                 return err;
2899         }
2900
2901         char *zSQL = sqlite3_mprintf("SELECT %q;", szQuery);
2902
2903         if (zSQL) {
2904                 err = dbHandle->getTableWithResult((const char *)zSQL, db_res, row_count, col_count);
2905                 sqlite3_free(zSQL);
2906                 zSQL = NULL;
2907         } else {
2908                 THROW(MsgException::INVALID_RESULT, "sqlite3_mprintf() is failed");
2909         }
2910
2911         MSG_DEBUG("getTableWithResult :: row_count=[%d], col_count=[%d]", *row_count, *col_count);
2912
2913         if (err == MSG_ERR_DB_NORECORD) {
2914                 dbHandle->freeTable(*db_res);
2915                 err = MSG_SUCCESS;
2916                 *db_res = NULL;
2917         } else if (err != MSG_SUCCESS) {
2918                 MSG_DEBUG("Fail to getTable().");
2919                 dbHandle->freeTable(*db_res);
2920                 *db_res = NULL;
2921         }
2922
2923         return err;
2924 }
2925
2926
2927 void MsgStoDbFree(char **db_res)
2928 {
2929         MsgDbHandler *dbHandle = getDbHandle();
2930         dbHandle->freeTable(db_res);
2931 }
2932
2933
2934 #ifdef FEATURE_SMS_CDMA
2935 msg_error_t MsgStoClearUniquenessTable()
2936 {
2937         MSG_BEGIN();
2938
2939         msg_error_t err = MSG_SUCCESS;
2940
2941         MsgDbHandler *dbHandle = getDbHandle();
2942
2943         char sqlQuery[MAX_QUERY_LEN+1] = {0, };
2944         snprintf(sqlQuery, sizeof(sqlQuery), "DELETE FROM %s WHERE MSG_ID = 0", MSGFW_UNIQUENESS_INFO_TABLE_NAME);
2945
2946         err = dbHandle->execQuery(sqlQuery);
2947
2948         MSG_END();
2949
2950         return err;
2951 }
2952 #endif