Apply the initial codes for BT emulator
[platform/core/connectivity/bluetooth-frwk.git] / bt-service-emul / bt-service-common.c
1 /*
2  * Copyright (c) 2011 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
18 #include <stdio.h>
19 #include <string.h>
20 #include <glib.h>
21 #include <dlog.h>
22 #include <fcntl.h>
23 #include <errno.h>
24 #include <termios.h>
25 #include <dbus/dbus.h>
26 #include <bundle.h>
27 #include <glib.h>
28 #include <dlog.h>
29 #include <fcntl.h>
30 #include <errno.h>
31 #include <termios.h>
32 #include <eventsystem.h>
33
34 #include "bluetooth-api.h"
35 #include "bt-service-common.h"
36
37 static GDBusConnection *system_conn;
38 static GDBusConnection *session_conn;
39 static GDBusConnection *system_gconn = NULL;
40
41 GDBusConnection *_bt_gdbus_init_system_gconn(void)
42 {
43         GError *error = NULL;
44
45         dbus_threads_init_default();
46
47         if (system_gconn != NULL)
48                 return system_gconn;
49
50         system_gconn = g_bus_get_sync(G_BUS_TYPE_SYSTEM, NULL, &error);
51
52         if (!system_gconn) {
53                 BT_ERR("Unable to connect to dbus: %s", error->message);
54                 g_clear_error(&error);
55         }
56
57         return system_gconn;
58 }
59
60 GDBusConnection *_bt_gdbus_get_system_gconn(void)
61 {
62         GDBusConnection *local_system_gconn = NULL;
63         GError *error = NULL;
64
65         if (system_gconn == NULL) {
66                 system_gconn = _bt_gdbus_init_system_gconn();
67         } else if (g_dbus_connection_is_closed(system_gconn)) {
68
69                 local_system_gconn = g_bus_get_sync(G_BUS_TYPE_SYSTEM, NULL, &error);
70
71                 if (!local_system_gconn) {
72                         BT_ERR("Unable to connect to dbus: %s", error->message);
73                         g_clear_error(&error);
74                 }
75
76                 system_gconn = local_system_gconn;
77         }
78
79         return system_gconn;
80 }
81
82 GDBusConnection *__bt_init_system_gconn(void)
83 {
84         if (system_conn == NULL)
85                 system_conn = g_bus_get_sync(G_BUS_TYPE_SYSTEM, NULL, NULL);
86
87         return system_conn;
88 }
89
90 GDBusConnection *__bt_init_session_conn(void)
91 {
92         if (session_conn == NULL)
93                 session_conn = g_bus_get_sync(G_BUS_TYPE_SESSION, NULL, NULL);
94
95         return session_conn;
96 }
97
98 GDBusConnection *_bt_get_session_gconn(void)
99 {
100         return (session_conn) ? session_conn : __bt_init_session_conn();
101 }
102
103 GDBusConnection *_bt_get_system_gconn(void)
104 {
105         return (system_conn) ? system_conn : __bt_init_system_gconn();
106 }
107
108 GDBusConnection *_bt_get_system_conn(void)
109 {
110         GDBusConnection *g_conn;
111
112         if (system_conn == NULL) {
113                 g_conn = __bt_init_system_gconn();
114         } else {
115                 g_conn = system_conn;
116         }
117
118         retv_if(g_conn == NULL, NULL);
119
120         return g_conn;
121 }
122
123 void _bt_deinit_proxys(void)
124 {
125         if (system_conn) {
126                 g_object_unref(system_conn);
127                 system_conn = NULL;
128         }
129
130         if (session_conn) {
131                 g_object_unref(session_conn);
132                 session_conn = NULL;
133         }
134 }
135
136 void _bt_convert_device_path_to_address(const char *device_path,
137                                                 char *device_address)
138 {
139         char address[BT_ADDRESS_STRING_SIZE] = { 0 };
140         char *dev_addr;
141
142         ret_if(device_path == NULL);
143         ret_if(device_address == NULL);
144
145         dev_addr = strstr(device_path, "dev_");
146         if (dev_addr != NULL) {
147                 char *pos = NULL;
148                 dev_addr += 4;
149                 g_strlcpy(address, dev_addr, sizeof(address));
150
151                 while ((pos = strchr(address, '_')) != NULL) {
152                         *pos = ':';
153                 }
154
155                 g_strlcpy(device_address, address, BT_ADDRESS_STRING_SIZE);
156         }
157 }
158
159
160 void _bt_convert_addr_string_to_type(unsigned char *addr,
161                                         const char *address)
162 {
163         int i;
164         char *ptr = NULL;
165
166         ret_if(address == NULL);
167         ret_if(addr == NULL);
168
169         for (i = 0; i < BT_ADDRESS_LENGTH_MAX; i++) {
170                 addr[i] = strtol(address, &ptr, 16);
171                 if (ptr[0] != '\0') {
172                         if (ptr[0] != ':')
173                                 return;
174
175                         address = ptr + 1;
176                 }
177         }
178 }
179
180 void _bt_convert_addr_type_to_string(char *address,
181                                 unsigned char *addr)
182 {
183         ret_if(address == NULL);
184         ret_if(addr == NULL);
185
186         snprintf(address, BT_ADDRESS_STRING_SIZE,
187                         "%2.2X:%2.2X:%2.2X:%2.2X:%2.2X:%2.2X",
188                         addr[0], addr[1], addr[2],
189                         addr[3], addr[4], addr[5]);
190 }
191
192 void _bt_print_device_address_t(const bluetooth_device_address_t *addr)
193 {
194         BT_DBG("%2.2X:%2.2X:%2.2X:%2.2X:%2.2X:%2.2X\n", addr->addr[0], addr->addr[1], addr->addr[2],
195                                 addr->addr[3], addr->addr[4], addr->addr[5]);
196 }
197
198 void _bt_divide_device_class(bluetooth_device_class_t *device_class,
199                                 unsigned int cod)
200 {
201         ret_if(device_class == NULL);
202
203         device_class->major_class = (unsigned short)(cod & 0x00001F00) >> 8;
204         device_class->minor_class = (unsigned short)((cod & 0x000000FC));
205         device_class->service_class = (unsigned long)((cod & 0x00FF0000));
206
207         if (cod & 0x002000) {
208                 device_class->service_class |=
209                 BLUETOOTH_DEVICE_SERVICE_CLASS_LIMITED_DISCOVERABLE_MODE;
210         }
211 }
212
213 void _bt_free_device_info(bt_remote_dev_info_t *dev_info)
214 {
215         int i;
216
217         ret_if(dev_info == NULL);
218
219         g_free(dev_info->address);
220         g_free(dev_info->name);
221         g_free(dev_info->manufacturer_data);
222
223         if (dev_info->uuids) {
224                 for (i = 0; i < dev_info->uuid_count && dev_info->uuids[i]; i++)
225                         g_free(dev_info->uuids[i]);
226
227                 g_free(dev_info->uuids);
228         }
229
230         g_free(dev_info);
231 }
232
233 void _bt_free_le_device_info(bt_remote_le_dev_info_t *le_dev_info)
234 {
235         ret_if(le_dev_info == NULL);
236
237         g_free(le_dev_info->adv_data);
238         g_free(le_dev_info);
239 }
240
241 int _bt_copy_utf8_string(char *dest, const char *src, unsigned int length)
242 {
243         int i;
244         const char *p = src;
245         char *next;
246         int count;
247
248         if (dest == NULL || src == NULL)
249                 return BLUETOOTH_ERROR_INVALID_PARAM;
250
251         BT_DBG("+src : %s", src);
252         BT_DBG("+dest : %s", dest);
253
254         i = 0;
255         while (*p != '\0' && i < length) {
256                 next = g_utf8_next_char(p);
257                 count = next - p;
258
259                 while (count > 0 && ((i + count) < length)) {
260                         dest[i++] = *p;
261                         p++;
262                         count--;
263                 }
264                 p = next;
265         }
266         return BLUETOOTH_ERROR_NONE;
267 }
268
269 gboolean _bt_utf8_validate(char *name)
270 {
271         BT_DBG("+");
272         gunichar2 *u16;
273         glong items_written = 0;
274
275         if (FALSE == g_utf8_validate(name, -1, NULL))
276                 return FALSE;
277
278         u16 = g_utf8_to_utf16(name, -1, NULL, &items_written, NULL);
279         if (u16 == NULL)
280                 return FALSE;
281
282         g_free(u16);
283
284         if (items_written != g_utf8_strlen(name, -1))
285                 return FALSE;
286
287         BT_DBG("-");
288         return TRUE;
289 }
290
291 int _bt_register_osp_server_in_agent(int type, char *uuid, char *path, int fd)
292 {
293         return BLUETOOTH_ERROR_NOT_SUPPORT;
294 }
295
296 int _bt_unregister_osp_server_in_agent(int type, char *uuid)
297 {
298         return BLUETOOTH_ERROR_NOT_SUPPORT;
299 }
300
301 int _bt_set_socket_non_blocking(int socket_fd)
302 {
303         /* Set Nonblocking */
304         long arg;
305
306         arg = fcntl(socket_fd, F_GETFL);
307
308         if (arg < 0)
309                 return -errno;
310
311         if (arg & O_NONBLOCK) {
312                 BT_ERR("Already Non-blocking \n");
313         }
314
315         arg |= O_NONBLOCK;
316
317         if (fcntl(socket_fd, F_SETFL, arg) < 0)
318                 return -errno;
319
320         return BLUETOOTH_ERROR_NONE;
321 }
322
323 int _bt_set_non_blocking_tty(int sk)
324 {
325         struct termios ti = {0,};
326         int err;
327
328         err = _bt_set_socket_non_blocking(sk);
329
330         if (err < 0) {
331                 BT_ERR("Error in set non blocking!\n");
332                 return err;
333         }
334
335         tcflush(sk, TCIOFLUSH);
336
337         /* Switch tty to RAW mode */
338         cfmakeraw(&ti);
339         tcsetattr(sk, TCSANOW, &ti);
340
341         return BLUETOOTH_ERROR_NONE;
342 }
343
344 char *_bt_get_profile_uuid128(bt_profile_type_t profile_type)
345 {
346         switch (profile_type) {
347         case BT_PROFILE_CONN_RFCOMM:
348                 return strdup(RFCOMM_UUID_STR);
349         case BT_PROFILE_CONN_A2DP:
350                 return strdup(A2DP_SINK_UUID);
351         case BT_PROFILE_CONN_A2DP_SINK:
352                 return strdup(A2DP_SOURCE_UUID);
353         case BT_PROFILE_CONN_HSP:
354                 return strdup(HFP_HS_UUID);
355         case BT_PROFILE_CONN_HID:
356                 return strdup(HID_UUID);
357         case BT_PROFILE_CONN_NAP:
358                 return strdup(NAP_UUID);
359         case BT_PROFILE_CONN_HFG:
360                 return strdup(HFP_AG_UUID);
361         case BT_PROFILE_CONN_GATT:
362         case BT_PROFILE_CONN_ALL: /* NULL UUID will connect to both the audio profiles*/
363         default:
364                 return NULL;
365         };
366 }
367
368 char *_bt_convert_error_to_string(int error)
369 {
370         switch (error) {
371         case BLUETOOTH_ERROR_CANCEL:
372                 return "CANCELLED";
373         case BLUETOOTH_ERROR_INVALID_PARAM:
374                 return "INVALID_PARAMETER";
375         case BLUETOOTH_ERROR_INVALID_DATA:
376                 return "INVALID DATA";
377         case BLUETOOTH_ERROR_MEMORY_ALLOCATION:
378         case BLUETOOTH_ERROR_OUT_OF_MEMORY:
379                 return "OUT_OF_MEMORY";
380         case BLUETOOTH_ERROR_TIMEOUT:
381                 return "TIMEOUT";
382         case BLUETOOTH_ERROR_NO_RESOURCES:
383                 return "NO_RESOURCES";
384         case BLUETOOTH_ERROR_INTERNAL:
385                 return "INTERNAL";
386         case BLUETOOTH_ERROR_NOT_SUPPORT:
387                 return "NOT_SUPPORT";
388         case BLUETOOTH_ERROR_DEVICE_NOT_ENABLED:
389                 return "NOT_ENABLED";
390         case BLUETOOTH_ERROR_DEVICE_ALREADY_ENABLED:
391                 return "ALREADY_ENABLED";
392         case BLUETOOTH_ERROR_DEVICE_BUSY:
393                 return "DEVICE_BUSY";
394         case BLUETOOTH_ERROR_ACCESS_DENIED:
395                 return "ACCESS_DENIED";
396         case BLUETOOTH_ERROR_MAX_CLIENT:
397                 return "MAX_CLIENT";
398         case BLUETOOTH_ERROR_NOT_FOUND:
399                 return "NOT_FOUND";
400         case BLUETOOTH_ERROR_SERVICE_SEARCH_ERROR:
401                 return "SERVICE_SEARCH_ERROR";
402         case BLUETOOTH_ERROR_PARING_FAILED:
403                 return "PARING_FAILED";
404         case BLUETOOTH_ERROR_NOT_PAIRED:
405                 return "NOT_PAIRED";
406         case BLUETOOTH_ERROR_SERVICE_NOT_FOUND:
407                 return "SERVICE_NOT_FOUND";
408         case BLUETOOTH_ERROR_NOT_CONNECTED:
409                 return "NOT_CONNECTED";
410         case BLUETOOTH_ERROR_ALREADY_CONNECT:
411                 return "ALREADY_CONNECT";
412         case BLUETOOTH_ERROR_CONNECTION_BUSY:
413                 return "CONNECTION_BUSY";
414         case BLUETOOTH_ERROR_CONNECTION_ERROR:
415                 return "CONNECTION_ERROR";
416         case BLUETOOTH_ERROR_MAX_CONNECTION:
417                 return "MAX_CONNECTION";
418         case BLUETOOTH_ERROR_NOT_IN_OPERATION:
419                 return "NOT_IN_OPERATION";
420         case BLUETOOTH_ERROR_CANCEL_BY_USER:
421                 return "CANCEL_BY_USER";
422         case BLUETOOTH_ERROR_REGISTRATION_FAILED:
423                 return "REGISTRATION_FAILED";
424         case BLUETOOTH_ERROR_IN_PROGRESS:
425                 return "IN_PROGRESS";
426         case BLUETOOTH_ERROR_AUTHENTICATION_FAILED:
427                 return "AUTHENTICATION_FAILED";
428         case BLUETOOTH_ERROR_HOST_DOWN:
429                 return "HOST_DOWN";
430         case BLUETOOTH_ERROR_END_OF_DEVICE_LIST:
431                 return "END_OF_DEVICE_LIST";
432         case BLUETOOTH_ERROR_AGENT_ALREADY_EXIST:
433                 return "AGENT_ALREADY_EXIST";
434         case BLUETOOTH_ERROR_AGENT_DOES_NOT_EXIST:
435                 return "AGENT_DOES_NOT_EXIST";
436         case BLUETOOTH_ERROR_ALREADY_INITIALIZED:
437                 return "ALREADY_INITIALIZED";
438         case BLUETOOTH_ERROR_PERMISSION_DEINED:
439                 return "PERMISSION_DEINED";
440         case BLUETOOTH_ERROR_ALREADY_DEACTIVATED:
441                 return "ALREADY_DEACTIVATED";
442         case BLUETOOTH_ERROR_NOT_INITIALIZED:
443                 return "NOT_INITIALIZED";
444         default:
445                 return "UNKNOWN";
446         }
447 }
448
449 char * _bt_convert_disc_reason_to_string(int reason)
450 {
451         switch (reason) {
452         case 1:
453                 return "Link loss";
454         case 2:
455                 return "Connection terminated by local host";
456         case 3:
457                 return "Remote user terminated connection";
458         case 0:
459         default:
460                 return "Unknown";
461         }
462 }
463
464 void _bt_logging_connection(gboolean connect, int addr_type)
465 {
466         static int le_conn = 0;
467         static int le_disc = 0;
468         static int edr_conn = 0;
469         static int edr_disc = 0;
470
471         if (connect) {
472                 if (addr_type)
473                         le_conn++;
474                 else
475                         edr_conn++;
476         } else {
477                 if (addr_type)
478                         le_disc++;
479                 else
480                         edr_disc++;
481         }
482
483         BT_INFO("[PM] Number of LE conn: %d disc: %d, Number of BR/EDR conn: %d disc: %d",
484                         le_conn, le_disc, edr_conn, edr_disc);
485 }
486
487 int _bt_eventsystem_set_value(const char *event, const char *key, const char *value)
488 {
489         int ret;
490         bundle *b = NULL;
491
492         b = bundle_create();
493
494         bundle_add_str(b, key, value);
495
496         ret = eventsystem_send_system_event(event, b);
497
498         BT_DBG("eventsystem_send_system_event result: %d", ret);
499
500         bundle_free(b);
501
502         return ret;
503 }
504
505 void _bt_swap_byte_ordering(char *data, int data_len)
506 {
507         char temp;
508         int i, j;
509
510         ret_if(data == NULL);
511         /* Swap to opposite endian */
512         for (i = 0, j = data_len - 1; i < data_len; i++, j--) {
513                 temp = data[i];
514                 data[i] = data[j];
515                 data[j] = temp;
516                 }
517 }
518
519 int _bt_byte_arr_cmp(const char *data1, const char *data2, int data_len)
520 {
521         int i;
522
523         retv_if(data1 == NULL, -1);
524         retv_if(data2 == NULL, -1);
525         for (i = 0; i < data_len; i++) {
526                 if (data1[i] != data2[i])
527                         return data1[i] - data2[i];
528                 }
529         return 0;
530 }
531 int _bt_byte_arr_cmp_with_mask(const char *data1, const char *data2,
532         const char *mask, int data_len)
533 {
534         int i;
535         char a, b;
536
537         retv_if(data1 == NULL, -1);
538         retv_if(data2 == NULL, -1);
539         retv_if(mask == NULL, -1);
540         for (i = 0; i < data_len; i++) {
541                 a = data1[i] & mask[i];
542                 b = data2[i] & mask[i];
543                 if (a != b)
544                         return (int)(a - b);
545                 }
546         return 0;
547 }