Fix crashing nfc-manager in boot
[framework/system/smartcard-service.git] / client / ClientIPC.cpp
1 /*
2  * Copyright (c) 2012, 2013 Samsung Electronics Co., Ltd.
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 /* standard library header */
18 #include <sys/socket.h>
19 #include <unistd.h>
20
21 /* SLP library header */
22 #ifdef SECURITY_SERVER
23 #include "security-server.h"
24 #endif
25
26 /* local header */
27 #include "Debug.h"
28 #include "ClientIPC.h"
29 #include "DispatcherMsg.h"
30
31 namespace smartcard_service_api
32 {
33         ClientIPC::ClientIPC():IPCHelper()
34         {
35 #ifdef USE_AUTOSTART
36                 _launch_daemon();
37 #endif
38 #ifdef SECURITY_SERVER
39                 int length;
40
41                 if ((length = security_server_get_cookie_size()) > 0)
42                 {
43                         uint8_t *buffer = NULL;
44
45                         buffer = new uint8_t[length];
46                         if (buffer != NULL)
47                         {
48                                 int error;
49
50                                 if ((error = security_server_request_cookie(buffer, length))
51                                         == SECURITY_SERVER_API_SUCCESS)
52                                 {
53                                         cookie.setBuffer(buffer, length);
54
55                                         SCARD_DEBUG("cookie : %s", cookie.toString());
56                                 }
57                                 else
58                                 {
59                                         SCARD_DEBUG_ERR("security_server_request_cookie failed [%d]", error);
60                                 }
61
62                                 delete []buffer;
63                         }
64                 }
65                 else
66                 {
67                         SCARD_DEBUG_ERR("security_server_get_cookie_size failed");
68                 }
69 #endif
70         }
71
72         ClientIPC::~ClientIPC()
73         {
74         }
75
76         ClientIPC &ClientIPC::getInstance()
77         {
78                 static ClientIPC clientIPC;
79
80                 return clientIPC;
81         }
82
83 #ifdef USE_AUTOSTART
84         void ClientIPC::_launch_daemon()
85         {
86                 DBusGConnection *connection;
87                 GError *error = NULL;
88
89                 SCARD_BEGIN();
90
91                 dbus_g_thread_init();
92
93                 g_type_init();
94
95                 connection = dbus_g_bus_get(DBUS_BUS_SYSTEM, &error);
96                 if (error == NULL)
97                 {
98                         DBusGProxy *proxy;
99
100                         proxy = dbus_g_proxy_new_for_name(connection, "org.tizen.smartcard_service",
101                                 "/org/tizen/smartcard_service", "org.tizen.smartcard_service");
102                         if (proxy != NULL)
103                         {
104                                 gint result = 0;
105
106                                 if (dbus_g_proxy_call(proxy, "launch", &error, G_TYPE_INVALID,
107                                         G_TYPE_INT, &result, G_TYPE_INVALID) == false)
108                                 {
109                                         SCARD_DEBUG_ERR("org_tizen_smartcard_service_launch failed");
110                                         if (error != NULL)
111                                         {
112                                                 SCARD_DEBUG_ERR("message : [%s]", error->message);
113                                                 g_error_free(error);
114                                         }
115                                 }
116                         }
117                         else
118                         {
119                                 SCARD_DEBUG_ERR("ERROR: Can't make dbus proxy");
120                         }
121                 }
122                 else
123                 {
124                         SCARD_DEBUG_ERR("ERROR: Can't get on system bus [%s]", error->message);
125                         g_error_free(error);
126                 }
127
128                 SCARD_END();
129         }
130 #endif
131
132         bool ClientIPC::sendMessage(Message *msg)
133         {
134                 ByteArray stream;
135                 unsigned int length;
136
137                 if (ipcSocket == -1)
138                         return false;
139
140 #ifdef SECURITY_SERVER
141                 stream = cookie + msg->serialize();
142 #else
143                 stream = msg->serialize();
144 #endif
145                 length = stream.getLength();
146
147                 SCARD_DEBUG(">>>[SEND]>>> socket [%d], msg [%d], length [%d]",
148                         ipcSocket, msg->message, stream.getLength());
149
150                 return IPCHelper::sendMessage(ipcSocket, stream);
151         }
152
153         int ClientIPC::handleIOErrorCondition(void *channel, GIOCondition condition)
154         {
155                 SCARD_BEGIN();
156
157                 if (dispatcher != NULL)
158                 {
159                         DispatcherMsg dispMsg;
160
161                         /* push or process disconnect message */
162                         dispMsg.message = Message::MSG_OPERATION_RELEASE_CLIENT;
163                         dispMsg.error = -1;
164
165 #ifdef CLIENT_IPC_THREAD
166                         dispatcher->processMessage(&dispMsg);
167 #else
168                         dispatcher->pushMessage(&dispMsg);
169 #endif
170                 }
171
172                 SCARD_END();
173
174                 return FALSE;
175         }
176
177         int ClientIPC::handleInvalidSocketCondition(void *channel, GIOCondition condition)
178         {
179                 SCARD_BEGIN();
180
181                 /* finalize context */
182                 destroyConnectSocket();
183
184                 SCARD_END();
185
186                 return FALSE;
187         }
188
189         int ClientIPC::handleIncomingCondition(void *channel, GIOCondition condition)
190         {
191                 int result = FALSE;
192
193                 SCARD_BEGIN();
194
195 #ifndef CLIENT_IPC_THREAD
196                 if (channel == ioChannel)
197                 {
198 #endif
199                         Message *msg = NULL;
200
201                         SCARD_DEBUG("message from server to client socket");
202
203                         /* read message */
204                         msg = retrieveMessage();
205                         if (msg != NULL)
206                         {
207                                 DispatcherMsg dispMsg(msg);
208
209                                 /* set peer socket */
210                                 dispMsg.setPeerSocket(ipcSocket);
211
212                                 /* push to dispatcher */
213                                 if (dispatcher != NULL)
214                                 {
215 #ifdef CLIENT_IPC_THREAD
216                                         dispatcher->processMessage(&dispMsg);
217 #else
218                                         dispatcher->pushMessage(&dispMsg);
219 #endif
220                                 }
221
222                                 delete msg;
223                         }
224                         else
225                         {
226                                 /* clear client connection */
227 #ifdef CLIENT_IPC_THREAD
228                                 handleIOErrorCondition(channel, condition);
229                                 result = -1;
230 #endif
231                         }
232
233 #ifndef CLIENT_IPC_THREAD
234                 }
235                 else
236                 {
237                         SCARD_DEBUG_ERR("Unknown channel event [%p]", channel);
238                 }
239 #endif
240
241                 SCARD_END();
242
243                 return result;
244         }
245
246 } /* namespace open_mobile_api */