Enable auto connect while calling bt_gatt_connect
[platform/upstream/iotivity.git] / resource / csdk / connectivity / src / bt_le_adapter / tizen / calenwmonitor.c
1 /******************************************************************
2 *
3 * Copyright 2014 Samsung Electronics All Rights Reserved.
4 *
5 *
6 *
7 * Licensed under the Apache License, Version 2.0 (the "License");
8 * you may not use this file except in compliance with the License.
9 * You may obtain a copy of the License at
10 *
11 *      http://www.apache.org/licenses/LICENSE-2.0
12 *
13 * Unless required by applicable law or agreed to in writing, software
14 * distributed under the License is distributed on an "AS IS" BASIS,
15 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16 * See the License for the specific language governing permissions and
17 * limitations under the License.
18 *
19 ******************************************************************/
20
21 #include "caleinterface.h"
22
23 #include <stdio.h>
24 #include <stdlib.h>
25 #include <string.h>
26 #include <glib.h>
27 #include <arpa/inet.h>
28 #include <sys/types.h>
29 #include <sys/socket.h>
30 #include <netinet/in.h>
31
32 #include <bluetooth.h>
33 #include <bluetooth_type.h>
34
35 #include "octhread.h"
36 #include "caleadapter.h"
37 #include "caadapterutils.h"
38 #include "oic_string.h"
39 #include "oic_malloc.h"
40
41 /**
42  * Logging tag for module name
43  */
44 #define TAG "OIC_CA_LE_MONITOR"
45
46 static GMainLoop *g_mainloop = NULL;
47 static ca_thread_pool_t g_threadPoolHandle = NULL;
48
49 /**
50  * Maintains the callback to be notified on device state changed.
51  */
52 static CALEDeviceStateChangedCallback g_bleDeviceStateChangedCallback = NULL;
53
54 /**
55  * Maintains the callback to be notified on device state changed.
56  */
57 static CALEConnectionStateChangedCallback g_bleConnectionStateChangedCallback = NULL;
58
59 /**
60  * Mutex to synchronize access to the deviceStateChanged Callback when the state
61  *           of the LE adapter gets change.
62  */
63 static oc_mutex g_bleDeviceStateChangedCbMutex = NULL;
64
65 /**
66  * Mutex to synchronize access to the ConnectionStateChanged Callback when the state
67  * of the LE adapter gets change.
68  */
69 static oc_mutex g_bleConnectionStateChangedCbMutex = NULL;
70
71 /**
72 * This is the callback which will be called when the adapter state gets changed.
73 *
74 * @param result         [IN] Result of the query done to the platform.
75 * @param adapter_state  [IN] State of the LE adapter.
76 * @param user_data      [IN] User data passed by the caller when querying for the state changed cb.
77 *
78 * @return  None.
79 */
80 void CALEAdapterStateChangedCb(int result, bt_adapter_state_e adapter_state,
81                                void *user_data);
82
83 void CALEMainLoopThread(void *param)
84 {
85     g_main_loop_run(g_mainloop);
86 }
87
88 /**
89 * This is the callback which will be called when the connection state gets changed.
90 *
91 * @param result         [IN] Result of the query done to the platform.
92 * @param connected      [IN] State of connection.
93 * @param remoteAddress  [IN] LE address of the device to be notified.
94 * @param user_data      [IN] User data passed by the caller when querying for the state changed cb.
95 *
96 * @return  None.
97 */
98 void CALENWConnectionStateChangedCb(int result, bool connected,
99                                     const char *remoteAddress, void *userData);
100
101 CAResult_t CAInitializeLENetworkMonitor()
102 {
103     OIC_LOG(DEBUG, TAG, "IN");
104
105     if (NULL == g_bleDeviceStateChangedCbMutex)
106     {
107         g_bleDeviceStateChangedCbMutex = oc_mutex_new();
108         if (NULL == g_bleDeviceStateChangedCbMutex)
109         {
110             OIC_LOG(ERROR, TAG, "oc_mutex_new failed");
111             return CA_STATUS_FAILED;
112         }
113     }
114
115     if (NULL == g_bleConnectionStateChangedCbMutex)
116     {
117         g_bleConnectionStateChangedCbMutex = oc_mutex_new();
118         if (NULL == g_bleConnectionStateChangedCbMutex)
119         {
120             OIC_LOG(ERROR, TAG, "oc_mutex_new failed");
121             oc_mutex_free(g_bleDeviceStateChangedCbMutex);
122             return CA_STATUS_FAILED;
123         }
124     }
125
126     OIC_LOG(DEBUG, TAG, "OUT");
127
128     return CA_STATUS_OK;
129 }
130
131 void CATerminateLENetworkMonitor()
132 {
133     OIC_LOG(DEBUG, TAG, "IN");
134
135     oc_mutex_free(g_bleDeviceStateChangedCbMutex);
136     g_bleDeviceStateChangedCbMutex = NULL;
137
138     oc_mutex_free(g_bleConnectionStateChangedCbMutex);
139     g_bleConnectionStateChangedCbMutex = NULL;
140
141     OIC_LOG(DEBUG, TAG, "OUT");
142 }
143
144 CAResult_t CAInitializeLEAdapter()
145 {
146     OIC_LOG(DEBUG, TAG, "IN");
147     CAResult_t res = ca_thread_pool_init(2, &g_threadPoolHandle);
148     if (CA_STATUS_OK != res)
149     {
150         OIC_LOG(ERROR, TAG, "thread pool initialize error.");
151         return res;
152     }
153
154     OIC_LOG(DEBUG, TAG, "OUT");
155     return CA_STATUS_OK;
156 }
157
158 CAResult_t CAStartLEAdapter()
159 {
160     OIC_LOG(DEBUG, TAG, "IN");
161
162     g_mainloop = g_main_loop_new(NULL, 0);
163     if(!g_mainloop)
164     {
165         OIC_LOG(ERROR, TAG, "g_main_loop_new failed\n");
166         return CA_STATUS_FAILED;
167     }
168
169     if (CA_STATUS_OK != ca_thread_pool_add_task(g_threadPoolHandle, CALEMainLoopThread,
170                                                 (void *) NULL, NULL))
171     {
172         OIC_LOG(ERROR, TAG, "Failed to create thread!");
173         return CA_STATUS_FAILED;
174     }
175
176     int ret = bt_initialize();
177     if (BT_ERROR_NONE != ret)
178     {
179         OIC_LOG(ERROR, TAG, "bt_initialize failed");
180         return CA_STATUS_FAILED;
181     }
182
183     ret = bt_adapter_set_state_changed_cb(CALEAdapterStateChangedCb, NULL);
184     if (BT_ERROR_NONE != ret)
185     {
186         OIC_LOG(DEBUG, TAG, "bt_adapter_set_state_changed_cb failed");
187         return CA_STATUS_FAILED;
188     }
189
190     ret = bt_gatt_set_connection_state_changed_cb(CALENWConnectionStateChangedCb, NULL);
191     if (BT_ERROR_NONE != ret)
192     {
193         OIC_LOG_V(ERROR, TAG,
194                   "bt_gatt_set_connection_state_changed_cb has failed");
195         return CA_STATUS_FAILED;
196     }
197
198     OIC_LOG(DEBUG, TAG, "OUT");
199     return CA_STATUS_OK;
200 }
201
202 CAResult_t CAStopLEAdapter()
203 {
204     int ret = bt_gatt_unset_connection_state_changed_cb();
205     if (BT_ERROR_NONE != ret)
206     {
207         OIC_LOG(DEBUG, TAG, "bt_gatt_unset_connection_state_changed_cb failed");
208         return CA_STATUS_FAILED;
209     }
210
211     ret = bt_adapter_unset_state_changed_cb();
212     if (BT_ERROR_NONE != ret)
213     {
214         OIC_LOG(DEBUG, TAG, "bt_adapter_unset_state_changed_cb failed");
215         return CA_STATUS_FAILED;
216     }
217
218     ret = bt_deinitialize();
219     if (BT_ERROR_NONE != ret)
220     {
221         OIC_LOG(ERROR, TAG, "bt_deinitialize failed");
222         return CA_STATUS_FAILED;
223     }
224
225     if (g_mainloop)
226     {
227         g_main_loop_quit(g_mainloop);
228     }
229
230     ca_thread_pool_free(g_threadPoolHandle);
231     g_threadPoolHandle = NULL;
232     return CA_STATUS_OK;
233 }
234
235 CAResult_t CAGetLEAdapterState()
236 {
237     OIC_LOG(DEBUG, TAG, "IN");
238
239     bt_adapter_state_e adapterState = BT_ADAPTER_DISABLED;
240
241     //Get Bluetooth adapter state
242     int ret = bt_adapter_get_state(&adapterState);
243     if (BT_ERROR_NONE != ret)
244     {
245         OIC_LOG_V(ERROR, TAG, "Bluetooth get state failed!, error num [%x]",
246                   ret);
247         return CA_STATUS_FAILED;
248     }
249
250     if (BT_ADAPTER_ENABLED != adapterState)
251     {
252         OIC_LOG(DEBUG, TAG, "BT Adapter is not enabled");
253         return CA_ADAPTER_NOT_ENABLED;
254     }
255
256     OIC_LOG(DEBUG, TAG, "OUT");
257     return CA_STATUS_OK;
258 }
259
260 CAResult_t CAGetLEAddress(char **local_address)
261 {
262     OIC_LOG(DEBUG, TAG, "IN");
263
264     VERIFY_NON_NULL(local_address, TAG, "local_address is null")
265
266     char *address = NULL;
267
268     int ret = bt_adapter_get_address(&address);
269     if (BT_ERROR_NONE != ret || !address)
270     {
271         OIC_LOG_V(ERROR, TAG, "bt_adapter_get_address failed!, error num [%x]",
272                   ret);
273         return CA_STATUS_FAILED;
274     }
275
276     OIC_LOG_V(DEBUG, TAG, "bd address[%s]", address);
277
278     *local_address = address;
279
280     OIC_LOG(DEBUG, TAG, "OUT");
281
282     return CA_STATUS_OK;
283 }
284
285 CAResult_t CASetLEAdapterStateChangedCb(CALEDeviceStateChangedCallback callback)
286 {
287     OIC_LOG(DEBUG, TAG, "IN");
288     oc_mutex_lock(g_bleDeviceStateChangedCbMutex);
289     g_bleDeviceStateChangedCallback = callback;
290     oc_mutex_unlock(g_bleDeviceStateChangedCbMutex);
291     OIC_LOG(DEBUG, TAG, "OUT");
292     return CA_STATUS_OK;
293 }
294
295 CAResult_t CAUnSetLEAdapterStateChangedCb()
296 {
297     OIC_LOG(DEBUG, TAG, "IN");
298     oc_mutex_lock(g_bleDeviceStateChangedCbMutex);
299     g_bleDeviceStateChangedCallback = NULL;
300     oc_mutex_unlock(g_bleDeviceStateChangedCbMutex);
301     OIC_LOG(DEBUG, TAG, "OUT");
302     return CA_STATUS_OK;
303 }
304
305 CAResult_t CASetLENWConnectionStateChangedCb(CALEConnectionStateChangedCallback callback)
306 {
307     OIC_LOG(DEBUG, TAG, "IN");
308     oc_mutex_lock(g_bleConnectionStateChangedCbMutex);
309     g_bleConnectionStateChangedCallback = callback;
310     oc_mutex_unlock(g_bleConnectionStateChangedCbMutex);
311     OIC_LOG(DEBUG, TAG, "OUT");
312     return CA_STATUS_OK;
313 }
314
315 CAResult_t CAUnSetLENWConnectionStateChangedCb()
316 {
317     OIC_LOG(DEBUG, TAG, "IN");
318     oc_mutex_lock(g_bleConnectionStateChangedCbMutex);
319     g_bleConnectionStateChangedCallback = NULL;
320     oc_mutex_unlock(g_bleConnectionStateChangedCbMutex);
321     OIC_LOG(DEBUG, TAG, "OUT");
322     return CA_STATUS_OK;
323 }
324
325 void CALEAdapterStateChangedCb(int result, bt_adapter_state_e adapter_state,
326                                           void *user_data)
327 {
328     OIC_LOG(DEBUG, TAG, "IN");
329
330     oc_mutex_lock(g_bleDeviceStateChangedCbMutex);
331
332     if (NULL == g_bleDeviceStateChangedCallback)
333     {
334         OIC_LOG(ERROR, TAG, "g_bleDeviceStateChangedCallback is NULL!");
335         oc_mutex_unlock(g_bleDeviceStateChangedCbMutex);
336         return;
337     }
338
339     if (BT_ADAPTER_DISABLED == adapter_state)
340     {
341         OIC_LOG(DEBUG, TAG, "Adapter is disabled");
342         g_bleDeviceStateChangedCallback(CA_ADAPTER_DISABLED);
343         oc_mutex_unlock(g_bleDeviceStateChangedCbMutex);
344         return;
345     }
346
347     OIC_LOG(DEBUG, TAG, "Adapter is Enabled");
348
349     g_bleDeviceStateChangedCallback(CA_ADAPTER_ENABLED);
350     oc_mutex_unlock(g_bleDeviceStateChangedCbMutex);
351
352     OIC_LOG(DEBUG, TAG, "OUT");
353 }
354
355 void CALENWConnectionStateChangedCb(int result, bool connected,
356                                     const char *remoteAddress, void *userData)
357 {
358     OIC_LOG(DEBUG, TAG, "IN");
359
360     VERIFY_NON_NULL_VOID(remoteAddress, TAG, "remote address is NULL");
361
362     oc_mutex_lock(g_bleConnectionStateChangedCbMutex);
363     char *addr = OICStrdup(remoteAddress);
364     if (NULL == addr)
365     {
366         OIC_LOG(ERROR, TAG, "addr is NULL");
367         oc_mutex_unlock(g_bleConnectionStateChangedCbMutex);
368         return;
369     }
370     g_bleConnectionStateChangedCallback(CA_ADAPTER_GATT_BTLE, addr, connected);
371     OICFree(addr);
372     oc_mutex_unlock(g_bleConnectionStateChangedCbMutex);
373
374     OIC_LOG(DEBUG, TAG, "OUT");
375 }