Merge "Fixed PLM issue P120731-3308 Disable 'Expect: 100-continue' option to avoid...
[platform/core/messaging/msg-service.git] / framework / main.cpp
1 /*
2 * Copyright 2012  Samsung Electronics Co., Ltd
3 *
4 * Licensed under the Flora License, Version 1.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.tizenopensource.org/license
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 /*==================================================================================================
18                                          INCLUDE FILES
19 ==================================================================================================*/
20 #include "MsgDebug.h"
21 #include "MsgException.h"
22 #include "MsgContact.h"
23 #include "MsgMemory.h"
24 #include "MsgGconfWrapper.h"
25 #include "MsgSpamFilter.h"
26 #include "MsgPluginManager.h"
27 #include "MsgSettingHandler.h"
28 #include "MsgStorageHandler.h"
29 #include "MsgSubmitHandler.h"
30 #include "MsgDeliverHandler.h"
31 #include "MsgTransManager.h"
32 #include "MsgStorageTypes.h"
33 #include "MsgSoundPlayer.h"
34
35 #include <errno.h>
36 #include <glib.h>
37 #include <dbus/dbus-glib.h>
38 #include <sys/stat.h>
39 #include <wait.h>
40
41 static GMainLoop* mainloop = NULL;
42
43
44 /*==================================================================================================
45                                      DEFINES
46 ==================================================================================================*/
47 #define MSG_MOBILE_TRACKER_MSG "Mobile Tracker Alert"
48
49
50 /*==================================================================================================
51                                      FUNCTION IMPLEMENTATION
52 ==================================================================================================*/
53 msg_error_t InitMmsDir()
54 {
55         if (mkdir(MSG_DATA_ROOT_PATH, S_IRWXU | S_IRWXG | S_IROTH | S_IXOTH) < 0)
56         {
57                 if (errno == EEXIST)
58                 {
59                         MSG_DEBUG("The %s already exists", MSG_DATA_ROOT_PATH);
60                 }
61                 else
62                 {
63                         MSG_DEBUG("Error while mkdir %s", MSG_DATA_ROOT_PATH);
64                         return MSG_ERR_DB_MAKE_DIR;
65                 }
66         }
67
68         if (mkdir(MSG_SMIL_FILE_PATH, S_IRWXU | S_IRWXG | S_IROTH | S_IXOTH) < 0)
69         {
70                 if (errno == EEXIST)
71                 {
72                         MSG_DEBUG("The %s already exists", MSG_SMIL_FILE_PATH);
73                 }
74                 else
75                 {
76                         MSG_DEBUG("Error while mkdir %s", MSG_SMIL_FILE_PATH);
77                         return MSG_ERR_DB_MAKE_DIR;
78                 }
79         }
80
81         if (mkdir(MSG_DATA_PATH, S_IRWXU | S_IRWXG | S_IROTH | S_IXOTH) < 0)
82         {
83                 if (errno == EEXIST)
84                 {
85                         MSG_DEBUG("The %s already exists", MSG_DATA_PATH);
86                 }
87                 else
88                 {
89                         MSG_DEBUG("Error while mkdir %s", MSG_DATA_PATH);
90                         return MSG_ERR_DB_MAKE_DIR;
91                 }
92         }
93
94         if (mkdir(MSG_THUMBNAIL_PATH, S_IRWXU | S_IRWXG | S_IROTH | S_IXOTH) < 0) {
95                 if (errno == EEXIST) {
96                         MSG_DEBUG("The %s already exists.", MSG_THUMBNAIL_PATH);
97                 } else {
98                         MSG_DEBUG(" Error while mkdir %s", MSG_THUMBNAIL_PATH);
99                         return MSG_ERR_DB_MAKE_DIR;
100                 }
101         }
102
103         if (mkdir(MSG_IPC_DATA_PATH, S_IRWXU ) < 0)
104         {
105                 if (errno == EEXIST)
106                 {
107                         MSG_DEBUG("The %s already exists", MSG_IPC_DATA_PATH);
108
109                         // if IPC data path is already exist, clear all files in folder.
110                         char exeStr[1024];
111                         snprintf(exeStr, 1024, "rm %s*.DATA", MSG_IPC_DATA_PATH);
112                         system(exeStr);
113                 }
114                 else
115                 {
116                         MSG_DEBUG("Error while mkdir %s", MSG_IPC_DATA_PATH);
117                         return MSG_ERR_DB_MAKE_DIR;
118                 }
119         }
120
121         chmod( MSG_IPC_DATA_PATH, S_IRWXU | S_IRWXG ); //public shared file: pass data by file
122         chown( MSG_IPC_DATA_PATH, 0, 6502 );
123
124         return MSG_SUCCESS;
125 }
126
127
128 void SendMobileTrackerMsg()
129 {
130         MSG_BEGIN();
131
132         bool bEnabled = false;
133
134         if (MsgSettingGetBool(VCONFKEY_SETAPPL_FIND_MY_MOBILE_SIM_CHANGE_ALERT_BOOL, &bEnabled) < 0)
135         {
136                 MSG_DEBUG("Can't read VCONFKEY_SETAPPL_FIND_MY_MOBILE_SIM_CHANGE_ALERT_BOOL");
137                 return;
138         }
139
140         if (bEnabled == false)
141         {
142                 MSG_DEBUG("Mobile Tracker Option [%d]", bEnabled);
143                 return;
144         }
145         // to wait modem init
146         // temporary code.
147         else
148         {
149                 MSG_DEBUG("Waiting for modem ready, 22 sec.");
150                 sleep(22);
151         }
152
153         MSG_REQUEST_INFO_S req = {0};
154
155         req.sendOptInfo.bSetting = false;
156
157         req.msgInfo.msgId = 0;
158         req.msgInfo.threadId = 0;
159         req.msgInfo.folderId = MSG_DRAFT_ID;
160         req.msgInfo.msgType.mainType = MSG_SMS_TYPE;
161         req.msgInfo.msgType.subType = MSG_NORMAL_SMS;
162         req.msgInfo.msgType.classType = MSG_CLASS_NONE;
163         req.msgInfo.storageId = MSG_STORAGE_PHONE;
164         req.msgInfo.displayTime = 0;
165         req.msgInfo.networkStatus = MSG_NETWORK_NOT_SEND;
166         req.msgInfo.encodeType = MSG_ENCODE_AUTO;
167         req.msgInfo.bRead = false;
168         req.msgInfo.bProtected = false;
169         req.msgInfo.priority = MSG_MESSAGE_PRIORITY_NORMAL;
170         req.msgInfo.direction = MSG_DIRECTION_TYPE_MO;
171         req.msgInfo.msgPort.valid = false;
172         req.msgInfo.bTextSms = true;
173
174         // Get Message Text
175         char* msgText = NULL;
176
177         msgText = MsgSettingGetString(VCONFKEY_SETAPPL_FIND_MY_MOBILE_MESSAGE_STR);
178
179         if (msgText == NULL)
180         {
181                 MSG_DEBUG("Assign Default Msg");
182                 msgText = strdup(MSG_MOBILE_TRACKER_MSG);
183         }
184
185         MSG_DEBUG("mobile tracker msg : [%s]", msgText);
186
187         req.msgInfo.dataSize = strlen(msgText);
188         strncpy(req.msgInfo.msgText, msgText, req.msgInfo.dataSize);
189
190         // Get Address List
191         char *orgRecipientList = NULL;
192
193         orgRecipientList = MsgSettingGetString(VCONFKEY_SETAPPL_FIND_MY_MOBILE_RECIPIENTS_STR);
194
195         if (orgRecipientList == NULL)
196         {
197                 MSG_DEBUG("recipient list is NULL");
198                 return;
199         }
200
201         int len = strlen(orgRecipientList);
202         char recipientList[len + 1];
203
204         memset(recipientList, 0, len + 1);
205         memcpy(recipientList, orgRecipientList, len);
206
207         MSG_DEBUG("recipient list : [%s]", recipientList);
208
209         req.msgInfo.nAddressCnt = 1;
210
211         char *token;
212
213         token = strtok(recipientList, "|");
214
215         MSG_MAIN_TYPE_T mainType = MSG_SMS_TYPE;
216         MsgPlugin* plg = MsgPluginManager::instance()->getPlugin(mainType);
217
218         msg_error_t err = MSG_SUCCESS;
219
220         while (token)
221         {
222                 req.msgInfo.addressList[0].addressType = MSG_ADDRESS_TYPE_PLMN;
223                 req.msgInfo.addressList[0].recipientType = MSG_RECIPIENTS_TYPE_TO;
224
225                 memset(req.msgInfo.addressList[0].addressVal, 0x00, MAX_ADDRESS_VAL_LEN);
226                 strncpy(req.msgInfo.addressList[0].addressVal, token, MAX_ADDRESS_VAL_LEN);
227
228                 MSG_DEBUG("address : [%s]", req.msgInfo.addressList[0].addressVal);
229
230                 if (plg != NULL)
231                 {
232                         MSG_DEBUG("mobile tracker msg : [%s]", msgText);
233
234                         err = plg->submitReq(&req);
235
236                         if (err != MSG_SUCCESS)
237                         {
238                                 MSG_DEBUG("fail to send mobile tracker msg : [%d]", err);
239                                 break;
240                         }
241                 }
242
243                 token = strtok(NULL, "|");
244         }
245
246         if (msgText) {
247                 free(msgText);
248                 msgText = NULL;
249         }
250
251         if (orgRecipientList) {
252                 free(orgRecipientList);
253                 orgRecipientList = NULL;
254         }
255
256
257         MSG_END();
258
259         return;
260 }
261
262
263 void* StartMsgServer(void*)
264 {
265         try
266         {
267                 MsgTransactionManager::instance()->run();
268         }
269         catch (MsgException& e)
270         {
271                 MSG_FATAL("%s", e.what());
272         }
273         catch (exception& e)
274         {
275                 MSG_FATAL("%s", e.what());
276         }
277
278         if (g_main_loop_is_running(mainloop))
279                 g_main_loop_quit(mainloop);
280
281         return (void*)0;
282 }
283
284
285 void* InitMsgServer(void*)
286 {
287         msg_error_t err = MSG_SUCCESS;
288
289         MSG_MAIN_TYPE_T mainType = MSG_SMS_TYPE;
290         MsgPlugin* plg = MsgPluginManager::instance()->getPlugin(mainType);
291
292         // storage handler initialize
293         err = MsgStoInitDB(false);
294
295         if (err != MSG_SUCCESS) {
296                 MSG_DEBUG("FAIL TO INITIALIZE STORAGE HANDLER [%d]", err);
297         }
298
299         // Set Msg FW Ready Flag
300         MsgSettingSetBool(VCONFKEY_MSG_SERVER_READY, true);
301         MSG_DEBUG("### VCONFKEY_MSG_SERVER_READY ###");
302
303         if (plg == NULL) {
304                 MSG_DEBUG("No plugin for %d type", mainType);
305
306                 MsgReleaseMemory();
307                 return (void*)0;
308         }
309
310         MSG_SIM_STATUS_T simStatus = MSG_SIM_STATUS_NORMAL;
311
312         // Check Sim Status
313         if (plg->checkSimStatus(&simStatus) == MSG_SUCCESS) {
314
315                 // Add the change of SIM to vconf
316                 if (MsgSettingSetInt(MSG_SIM_CHANGED, (int)simStatus) != MSG_SUCCESS) {
317                         MSG_DEBUG("Error to set config data [%s]", MSG_SIM_CHANGED);
318                 }
319
320                 if (simStatus != MSG_SIM_STATUS_NOT_FOUND) {
321                         // Check Device Status
322                         if (plg->checkDeviceStatus() != MSG_SUCCESS) {
323                                 MSG_DEBUG("checkDeviceStatus() error");
324
325                                 MsgReleaseMemory();
326
327                                 return (void*)0;
328                         }
329                 }
330
331                 // Init SIM Message
332                 if (MsgInitSimMessage(simStatus) != MSG_SUCCESS) {
333                         MSG_DEBUG("Fail to Initialize SIM Message");
334                 }
335
336                 // Init SIM Configuration
337                 if (MsgInitSimConfig(simStatus) != MSG_SUCCESS) {
338                         MSG_DEBUG("Fail to Initialize SIM Configuration");
339                 }
340
341                 // Add SendMobileTrackerMsg() to GMainLoop
342                 if (simStatus == MSG_SIM_STATUS_CHANGED) {
343                         MSG_DEBUG("Send Mobile Tracker Message");
344
345                         SendMobileTrackerMsg();
346                 }
347         } else {
348                 MSG_DEBUG("checkSimStatus() error");
349         }
350
351         MsgReleaseMemory();
352
353         // Try to connect contact server  if it is not opened.
354         MsgOpenContactSvc();
355
356         // Register Callback to get the change of contact
357         MsgInitContactSvc(&MsgContactChangedCallback);
358
359         MsgSoundPlayStart();
360         return (void*)0;
361 }
362
363
364 static gboolean InitThreadFunc(void* pData)
365 {
366         MSG_BEGIN();
367
368         pthread_t initThreadId;
369
370         // initialize msg fw
371         if (pthread_create(&initThreadId, NULL, InitMsgServer, NULL) != 0)
372         {
373                 MSG_DEBUG("InitMsgFw not invoked: %s", strerror(errno));
374                 return -1;
375         }
376
377         pthread_detach(initThreadId);
378
379         MSG_END();
380
381         return FALSE;
382 }
383
384
385 int main(void)
386 {
387 #if !GLIB_CHECK_VERSION(2, 31, 0)
388         g_thread_init(NULL);
389 #endif
390         dbus_g_thread_init();
391
392 ////////////////////////////////////
393
394 /// set to ignore child process terminated signal.
395 signal( SIGCHLD, SIG_IGN );
396
397 ////////////////////////////////////
398
399
400         MSG_DEBUG("===========START MESSAGING FRAMEWORK==========");
401
402         // Reset message server ready flag
403         MsgSettingSetBool(VCONFKEY_MSG_SERVER_READY, false);
404
405         // Connect to DB
406         //      MsgStoConnectDB();
407
408         // Open Contact Service
409         MsgOpenContactSvc();
410
411         // Clean up mms dir
412         InitMmsDir();
413
414         // Regist vconf CB.
415         MsgSettingRegVconfCB();
416
417         try
418         {
419                 // plugin manager initialize
420                 MsgPluginManager::instance()->initialize();
421         }
422         catch (MsgException& e)
423         {
424                 MSG_FATAL("%s", e.what());
425         }
426         catch (exception& e)
427         {
428                 MSG_FATAL("%s", e.what());
429         }
430
431         pthread_t startThreadId;
432
433         // start transaction manager
434         if (pthread_create(&startThreadId, NULL, StartMsgServer, NULL) != 0)
435         {
436                 MSG_DEBUG("StartMsgServer not invoked: %s", strerror(errno));
437                 return -1;
438         }
439
440         MsgTransactionManager::instance()->getTMStatus();
441
442         mainloop = g_main_loop_new(NULL, FALSE);
443
444         g_type_init();
445
446         g_idle_add(InitThreadFunc, NULL);
447
448         if (mainloop != NULL)
449         {
450                 MSG_DEBUG("Start Messaging Framework!!!");
451
452                 // Run GMainLoop
453                 g_main_loop_run(mainloop);
454         }
455         else
456         {
457                 MSG_DEBUG("Fail to start Messaging Framework!!!");
458         }
459
460         // Remove vconf CB
461         MsgSettingRemoveVconfCB();
462
463         // Close Contact Sevice
464         MsgCloseContactSvc();
465
466         // Disconnect to DB
467         MsgStoDisconnectDB();
468
469         return 0;
470 }
471