Merge with master
[platform/core/pim/contacts-service.git] / client / ctsvc_client_service.c
1 /*
2  * Contacts Service
3  *
4  * Copyright (c) 2010 - 2012 Samsung Electronics Co., Ltd. All rights reserved.
5  *
6  * Contact: Dohyung Jin <dh.jin@samsung.com>
7  *                 Jongwon Lee <gogosing.lee@samsung.com>
8  *                 Donghee Ye <donghee.ye@samsung.com>
9  *
10  * Licensed under the Apache License, Version 2.0 (the "License");
11  * you may not use this file except in compliance with the License.
12  * You may obtain a copy of the License at
13  *
14  * http://www.apache.org/licenses/LICENSE-2.0
15  *
16  * Unless required by applicable law or agreed to in writing, software
17  * distributed under the License is distributed on an "AS IS" BASIS,
18  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
19  * See the License for the specific language governing permissions and
20  * limitations under the License.
21  *
22  */
23 #include <errno.h>
24 #include <sys/socket.h>
25 #include <sys/un.h>
26 #include <unistd.h>
27 #include <pims-ipc-data.h>
28
29 #include "contacts.h"
30 #include "ctsvc_internal.h"
31 #include "ctsvc_socket.h"
32 #include "ctsvc_mutex.h"
33 #include "ctsvc_inotify.h"
34 #include "ctsvc_setting.h"
35 #include "ctsvc_client_ipc.h"
36
37 static int ctsvc_connection = 0;
38
39 static __thread int ctsvc_connection_on_thread = 0;
40
41 API int contacts_connect_with_flags(unsigned int flags)
42 {
43         CTS_FN_CALL;
44         int ret = CONTACTS_ERROR_NONE;
45
46         ret = contacts_connect2();
47         if (ret == CONTACTS_ERROR_NONE)
48                 return ret;
49
50         if (flags & CONTACTS_CONNECT_FLAG_RETRY) {
51                 int i;
52                 int waiting_time = 500;
53                 for (i=0;i<9;i++) {
54                         usleep(waiting_time * 1000);
55                         DBG("retry cnt=%d, ret=%x, %d",(i+1), ret, waiting_time);
56                         ret = contacts_connect2();
57                         if (ret == CONTACTS_ERROR_NONE)
58                                 break;
59                         if (6 < i)
60                                 waiting_time += 30000;
61                         else
62                                 waiting_time *= 2;
63                 }
64         }
65
66         return ret;
67 }
68
69 API int contacts_connect2()
70 {
71         CTS_FN_CALL;
72         int ret;
73
74         ctsvc_mutex_lock(CTS_MUTEX_CONNECTION);
75         if (0 == ctsvc_connection) {
76
77                 ret = ctsvc_ipc_connect();
78                 if (ret != CONTACTS_ERROR_NONE) {
79                         CTS_ERR("ctsvc_ipc_connect() Failed(%d)", ret);
80                         ctsvc_mutex_unlock(CTS_MUTEX_CONNECTION);
81                         return ret;
82                 }
83
84                 ret = ctsvc_socket_init();
85                 if (ret != CONTACTS_ERROR_NONE) {
86                         CTS_ERR("ctsvc_socket_init() Failed(%d)", ret);
87                         ctsvc_mutex_unlock(CTS_MUTEX_CONNECTION);
88                         return ret;
89                 }
90
91                 ret = ctsvc_inotify_init();
92                 if (ret != CONTACTS_ERROR_NONE) {
93                         CTS_ERR("ctsvc_inotify_init() Failed(%d)", ret);
94                         ctsvc_socket_final();
95                         ctsvc_mutex_unlock(CTS_MUTEX_CONNECTION);
96                         return ret;
97                 }
98
99                 ctsvc_view_uri_init();
100                 ctsvc_register_vconf();
101                 ctsvc_ipc_create_for_change_subscription();
102         }
103         else
104                 CTS_DBG("System : Contacts service has been already connected(%d)", ctsvc_connection + 1);
105
106         ctsvc_connection++;
107         ctsvc_mutex_unlock(CTS_MUTEX_CONNECTION);
108
109         return CONTACTS_ERROR_NONE;
110 }
111
112 API int contacts_disconnect2()
113 {
114         int ret;
115
116         CTS_FN_CALL;
117
118         ctsvc_mutex_lock(CTS_MUTEX_CONNECTION);
119         if (1 == ctsvc_connection) {
120                 ctsvc_ipc_destroy_for_change_subscription();
121
122                 ret = ctsvc_ipc_disconnect();
123                 if (ret != CONTACTS_ERROR_NONE) {
124                         ctsvc_mutex_unlock(CTS_MUTEX_CONNECTION);
125                         CTS_ERR("ctsvc_ipc_disconnect() Failed(%d)", ret);
126                         return ret;
127                 }
128
129                 ctsvc_view_uri_deinit();
130                 ctsvc_inotify_close();
131                 ctsvc_socket_final();
132                 ctsvc_deregister_vconf();
133
134         }
135         else if (1 < ctsvc_connection)
136                 CTS_DBG("System : connection count is %d", ctsvc_connection);
137         else {
138                 CTS_DBG("System : please call contacts_connect2(), connection count is (%d)", ctsvc_connection);
139                 ctsvc_mutex_unlock(CTS_MUTEX_CONNECTION);
140                 return CONTACTS_ERROR_INVALID_PARAMETER;
141         }
142
143         ctsvc_connection--;
144         ctsvc_mutex_unlock(CTS_MUTEX_CONNECTION);
145
146         return CONTACTS_ERROR_NONE;
147 }
148
149 API int contacts_connect_on_thread()
150 {
151         int ret;
152
153         ctsvc_mutex_lock(CTS_MUTEX_CONNECTION);
154
155         ret = ctsvc_ipc_connect_on_thread();
156         if (ret != CONTACTS_ERROR_NONE) {
157                 CTS_ERR("ctsvc_ipc_connect_on_thread() Failed(%d)", ret);
158                 ctsvc_mutex_unlock(CTS_MUTEX_CONNECTION);
159                 return ret;
160         }
161
162         if (0 < ctsvc_connection_on_thread)
163                 CTS_DBG("System : Contacts service has been already connected");
164
165         ctsvc_connection_on_thread++;
166
167         ctsvc_mutex_unlock(CTS_MUTEX_CONNECTION);
168
169         return CONTACTS_ERROR_NONE;
170 }
171
172 API int contacts_disconnect_on_thread()
173 {
174         int ret;
175
176         ctsvc_mutex_lock(CTS_MUTEX_CONNECTION);
177
178         ret = ctsvc_ipc_disconnect_on_thread();
179         if (ret != CONTACTS_ERROR_NONE) {
180                 CTS_ERR("ctsvc_ipc_disconnect_on_thread() Failed(%d)", ret);
181                 ctsvc_mutex_unlock(CTS_MUTEX_CONNECTION);
182                 return ret;
183         }
184
185         if (1 == ctsvc_connection_on_thread) {
186                 CTS_DBG("System : connection_on_thread was destroyed successfully");
187         }
188         else if (1 < ctsvc_connection_on_thread) {
189                 CTS_DBG("System : connection count is %d", ctsvc_connection_on_thread);
190         }
191         else {
192                 CTS_DBG("System : please call contacts_connect_on_thread(), connection count is (%d)", ctsvc_connection_on_thread);
193                 ctsvc_mutex_unlock(CTS_MUTEX_CONNECTION);
194                 return CONTACTS_ERROR_INVALID_PARAMETER;
195         }
196
197         ctsvc_connection_on_thread--;
198
199         ctsvc_mutex_unlock(CTS_MUTEX_CONNECTION);
200
201         return CONTACTS_ERROR_NONE;
202 }