Listen and process remote name resolving failure
[platform/upstream/bluez.git] / src / device.c
1 // SPDX-License-Identifier: GPL-2.0-or-later
2 /*
3  *
4  *  BlueZ - Bluetooth protocol stack for Linux
5  *
6  *  Copyright (C) 2006-2010  Nokia Corporation
7  *  Copyright (C) 2004-2010  Marcel Holtmann <marcel@holtmann.org>
8  *
9  *
10  */
11
12 #ifdef HAVE_CONFIG_H
13 #include <config.h>
14 #endif
15
16 #include <stdio.h>
17 #include <stdlib.h>
18 #include <unistd.h>
19 #include <fcntl.h>
20 #include <stdbool.h>
21 #include <errno.h>
22 #include <dirent.h>
23 #include <time.h>
24
25 #include <glib.h>
26 #include <dbus/dbus.h>
27
28 #include "lib/bluetooth.h"
29 #include "lib/sdp.h"
30 #include "lib/sdp_lib.h"
31 #include "lib/uuid.h"
32
33 #include "gdbus/gdbus.h"
34
35 #include "log.h"
36 #include "src/shared/util.h"
37 #include "src/shared/att.h"
38 #include "src/shared/queue.h"
39 #include "src/shared/gatt-db.h"
40 #include "src/shared/gatt-client.h"
41 #include "src/shared/gatt-server.h"
42 #include "src/shared/ad.h"
43 #include "src/shared/timeout.h"
44 #include "btio/btio.h"
45 #include "lib/mgmt.h"
46 #include "attrib/att.h"
47 #include "btd.h"
48 #include "adapter.h"
49 #include "gatt-database.h"
50 #include "attrib/gattrib.h"
51 #include "device.h"
52 #include "gatt-client.h"
53 #include "profile.h"
54 #include "service.h"
55 #include "dbus-common.h"
56 #include "error.h"
57 #include "uuid-helper.h"
58 #include "sdp-client.h"
59 #include "attrib/gatt.h"
60 #include "agent.h"
61 #include "textfile.h"
62 #include "storage.h"
63 #include "attrib-server.h"
64 #include "eir.h"
65
66 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
67 #include "sdp-xml.h"
68 #ifdef TIZEN_FEATURE_BLUEZ_BATTERY_WATCH
69 #include <sys/ioctl.h>
70 #endif  /* TIZEN_FEATURE_BLUEZ_BATTERY_WATCH */
71 #endif
72
73 #define DISCONNECT_TIMER        2
74 #define DISCOVERY_TIMER         1
75 #define INVALID_FLAGS           0xff
76
77 #ifndef MIN
78 #define MIN(a, b) ((a) < (b) ? (a) : (b))
79 #endif
80
81 #define RSSI_THRESHOLD          8
82
83 #define GATT_PRIM_SVC_UUID_STR "2800"
84 #define GATT_SND_SVC_UUID_STR  "2801"
85 #define GATT_INCLUDE_UUID_STR "2802"
86 #define GATT_CHARAC_UUID_STR "2803"
87 #define NAME_RESOLVE_RETRY_DELAY       300 /* seconds */
88
89 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
90 #define DEV_MAX_MANUFACTURER_DATA_LEN   248
91 #endif
92
93 static DBusConnection *dbus_conn = NULL;
94 static unsigned service_state_cb_id;
95
96 struct btd_disconnect_data {
97         guint id;
98         disconnect_watch watch;
99         void *user_data;
100         GDestroyNotify destroy;
101 };
102
103 struct bonding_req {
104         DBusMessage *msg;
105         guint listener_id;
106         struct btd_device *device;
107         uint8_t bdaddr_type;
108         struct agent *agent;
109         struct btd_adapter_pin_cb_iter *cb_iter;
110         uint8_t status;
111         guint retry_timer;
112         struct timespec attempt_start_time;
113         long last_attempt_duration_ms;
114 };
115
116 typedef enum {
117         AUTH_TYPE_PINCODE,
118         AUTH_TYPE_PASSKEY,
119         AUTH_TYPE_CONFIRM,
120         AUTH_TYPE_NOTIFY_PASSKEY,
121         AUTH_TYPE_NOTIFY_PINCODE,
122 } auth_type_t;
123
124 struct authentication_req {
125         auth_type_t type;
126         struct agent *agent;
127         struct btd_device *device;
128         uint8_t addr_type;
129         uint32_t passkey;
130         char *pincode;
131         gboolean secure;
132 };
133
134 enum {
135         BROWSE_SDP,
136         BROWSE_GATT
137 };
138
139 struct browse_req {
140         DBusMessage *msg;
141         struct btd_device *device;
142         uint8_t type;
143         GSList *match_uuids;
144         GSList *profiles_added;
145         sdp_list_t *records;
146         int search_uuid;
147         int reconnect_attempt;
148         guint listener_id;
149         uint16_t sdp_flags;
150 };
151
152 struct included_search {
153         struct browse_req *req;
154         GSList *services;
155         GSList *current;
156 };
157
158 struct svc_callback {
159         unsigned int id;
160         guint idle_id;
161         struct btd_device *dev;
162         device_svc_cb_t func;
163         void *user_data;
164 };
165
166 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
167 struct le_adv_report_info {
168         uint8_t flags;
169         char manufacturer_data[DEV_MAX_MANUFACTURER_DATA_LEN];
170         uint8_t manufacturer_data_len;
171 };
172 #endif
173
174 /* Per-bearer (LE or BR/EDR) device state */
175 struct bearer_state {
176         bool paired;
177         bool bonded;
178         bool connected;
179         bool svc_resolved;
180 };
181
182 struct csrk_info {
183         uint8_t key[16];
184         uint32_t counter;
185 };
186
187 enum {
188         WAKE_FLAG_DEFAULT = 0,
189         WAKE_FLAG_ENABLED,
190         WAKE_FLAG_DISABLED,
191 };
192
193
194 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
195 typedef enum {
196         DEV_PAIRED_NONE = 0,
197         DEV_PAIRED_BREDR = 1,
198         DEV_PAIRED_LE,
199         DEV_PAIRED_BREDR_LE,
200 } dev_paired_state;
201
202 typedef enum {
203         DEV_CONNECTED_NONE = 0,
204         DEV_CONNECTED_BREDR = 1,
205         DEV_CONNECTED_LE,
206         DEV_CONNECTED_BREDR_LE,
207 } dev_connected_state;
208
209 struct trusted_profile_t {
210         uint32_t        pbap:2;
211         uint32_t        map:2;
212         uint32_t        sap:2;
213         uint32_t        hfp_hs:2;
214         uint32_t        a2dp:2;
215 } __packed;
216 #endif
217
218 struct btd_device {
219         int ref_count;
220
221         bdaddr_t        conn_bdaddr;
222         uint8_t         conn_bdaddr_type;
223         bdaddr_t        bdaddr;
224         uint8_t         bdaddr_type;
225         char            *path;
226         bool            bredr;
227         bool            le;
228         bool            pending_paired;         /* "Paired" waiting for SDP */
229         bool            svc_refreshed;
230         bool            refresh_discovery;
231
232         /* Manage whether this device can wake the system from suspend.
233          * - wake_support: Requires a profile that supports wake (i.e. HID)
234          * - wake_allowed: Is wake currently allowed?
235          * - pending_wake_allowed - Wake flag sent via set_device_flags
236          * - wake_override - User configured wake setting
237          */
238         bool            wake_support;
239         bool            wake_allowed;
240         bool            pending_wake_allowed;
241         uint8_t         wake_override;
242         GDBusPendingPropertySet wake_id;
243
244         uint32_t        supported_flags;
245         uint32_t        current_flags;
246         GSList          *svc_callbacks;
247         GSList          *eir_uuids;
248         struct bt_ad    *ad;
249         uint8_t         ad_flags[1];
250         char            name[MAX_NAME_LENGTH + 1];
251         char            *alias;
252         uint32_t        class;
253         uint16_t        vendor_src;
254         uint16_t        vendor;
255         uint16_t        product;
256         uint16_t        version;
257         uint16_t        appearance;
258         char            *modalias;
259         struct btd_adapter      *adapter;
260         GSList          *uuids;
261         GSList          *primaries;             /* List of primary services */
262         GSList          *services;              /* List of btd_service */
263         GSList          *pending;               /* Pending services */
264         GSList          *watches;               /* List of disconnect_data */
265         bool            temporary;
266         bool            connectable;
267         unsigned int    disconn_timer;
268         unsigned int    discov_timer;
269         unsigned int    temporary_timer;        /* Temporary/disappear timer */
270         struct browse_req *browse;              /* service discover request */
271         struct bonding_req *bonding;
272         struct authentication_req *authr;       /* authentication request */
273         GSList          *disconnects;           /* disconnects message */
274         DBusMessage     *connect;               /* connect message */
275         DBusMessage     *disconnect;            /* disconnect message */
276         GAttrib         *attrib;
277
278         struct bt_att *att;                     /* The new ATT transport */
279         uint16_t att_mtu;                       /* The ATT MTU */
280         unsigned int att_disconn_id;
281
282         /*
283          * TODO: For now, device creates and owns the client-role gatt_db, but
284          * this needs to be persisted in a more central place so that proper
285          * attribute cache support can be built.
286          */
287         struct gatt_db *db;                     /* GATT db cache */
288         unsigned int db_id;
289         struct bt_gatt_client *client;          /* GATT client instance */
290         struct bt_gatt_server *server;          /* GATT server instance */
291         unsigned int gatt_ready_id;
292
293         struct btd_gatt_client *client_dbus;
294
295         struct bearer_state bredr_state;
296         struct bearer_state le_state;
297
298         struct csrk_info *local_csrk;
299         struct csrk_info *remote_csrk;
300         uint8_t ltk_enc_size;
301
302         sdp_list_t      *tmp_records;
303
304         time_t          bredr_seen;
305         time_t          le_seen;
306
307         gboolean        trusted;
308 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
309         struct trusted_profile_t trusted_profiles;
310 #endif
311         gboolean        blocked;
312         gboolean        auto_connect;
313         gboolean        disable_auto_connect;
314         gboolean        general_connect;
315
316         bool            legacy;
317         int8_t          rssi;
318         int8_t          tx_power;
319
320         GIOChannel      *att_io;
321         guint           store_id;
322
323         time_t          name_resolve_failed_time;
324 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
325         bool    legacy_pairing;
326         char            *manufacturer_data;
327         int             manufacturer_data_len;
328         struct le_adv_report_info le_adv_data;
329         int     remote_feature_flags;
330         guint   attio_id;
331         gboolean        gatt_connected;
332         uint16_t        auth_payload_timeout;
333         uint8_t disc_reason;
334         uint8_t         last_bdaddr_type;
335         uint8_t         auth_bdaddr_type;
336         gboolean        ipsp_connected; /* IPSP Connection state */
337         char            if_name[16 + 1]; /* BT interface UP after IPSP connection */
338         uint8_t         rpa_res_support; /* RPA Resolution capability of device */
339         uint16_t        max_tx_octets;
340         uint16_t        max_tx_time;
341         uint16_t        max_rx_octets;
342         uint16_t        max_rx_time;
343         bdaddr_t        *rpa;
344         DBusMessage *req_att_mtu;       /* Attribute MTU request message */
345         uint8_t         irk_val[16];
346         bool pending_conn_update;
347         bool le_connectable;
348 #endif
349 };
350
351 static const uint16_t uuid_list[] = {
352         L2CAP_UUID,
353         PNP_INFO_SVCLASS_ID,
354         PUBLIC_BROWSE_GROUP,
355         0
356 };
357
358 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
359 typedef enum {
360         SHOW_AUTHORIZATION = 0x0, /* 0b00 */
361         SUPPORTED_BLOCKED = 0x1, /* 0b01 */
362         SUPPORTED_TRUSTED= 0x2, /* 0b10 */
363 } bt_profile_trusted_states;
364
365 #define PBAP_SHIFT_OFFSET 0
366 #define MAP_SHIFT_OFFSET 2
367 #define SAP_SHIFT_OFFSET 4
368 #define HFP_HS_SHIFT_OFFSET 6
369 #define A2DP_SHIFT_OFFSET 8
370
371 #define PROFILE_SUPPORTED 0x3 /* This corresponds to binary 0b11*/
372
373 #endif
374
375 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
376 #define OTP_PSM 0x0025
377
378 /* OTP Client */
379 #define BT_OTC_SERVICE_NAME     "org.otp.client"
380 #define BT_OTC_OBJECT_PATH      "/org/otp/client"
381 #define BT_OTC_INTERFACE_NAME   "org.otp.otc_channel"
382
383 /* OTP Server */
384 #define BT_OTS_SERVICE_NAME     "org.projectx.otp"
385 #define BT_OTS_OBJECT_PATH      "/org/projectx/otp"
386 #define BT_OTS_INTERFACE_NAME   "org.projectx.otp_service"
387
388 typedef enum {
389         BT_OTP_CLIENT_ROLE = 0x00,
390         BT_OTP_SERVER_ROLE,
391 } bt_otp_role_e;
392
393 struct otc_conn_info {
394         const char *dev_path;
395         bt_otp_role_e role;
396         GIOChannel *io;
397         bool otc_connected;
398 };
399
400 GSList *otc_connection_list = NULL;
401 #endif
402
403 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
404 #define BT_L2CAP_LE_INTERFACE_NAME "org.bluez.l2cap_le"
405 #define BTD_L2CAP_LE_PSM_MAX 0xFFFF
406 #define UUID_LEN 37
407
408 typedef enum {
409         BT_L2CAP_LE_CLIENT_ROLE = 0x00,
410         BT_L2CAP_LE_SERVER_ROLE,
411 } bt_l2cap_le_role_e;
412
413 struct l2cap_le_conn_info {
414         struct l2cap_le_profile_info *profile_info;
415         GIOChannel *io;
416         guint io_id;
417         bool connected;
418         const char *dev_path;
419         int psm;
420         guint auth_id;
421         char *auth_uuid;
422 };
423
424 struct l2cap_le_profile_info {
425         char *name;
426         char *owner;
427         char *path;
428         bt_l2cap_le_role_e role;
429         int psm;
430         BtIOSecLevel sec_level;
431         bool authorize;
432         guint id;
433         struct l2cap_le_conn_info *server;
434         GSList *conn;
435 };
436
437 GSList *l2cap_le_socket_list = NULL;
438 #endif
439
440
441 static int device_browse_gatt(struct btd_device *device, DBusMessage *msg);
442 static int device_browse_sdp(struct btd_device *device, DBusMessage *msg);
443
444 static struct bearer_state *get_state(struct btd_device *dev,
445                                                         uint8_t bdaddr_type)
446 {
447         if (bdaddr_type == BDADDR_BREDR)
448                 return &dev->bredr_state;
449         else
450                 return &dev->le_state;
451 }
452
453 static GSList *find_service_with_profile(GSList *list, struct btd_profile *p)
454 {
455         GSList *l;
456
457         for (l = list; l != NULL; l = g_slist_next(l)) {
458                 struct btd_service *service = l->data;
459
460                 if (btd_service_get_profile(service) == p)
461                         return l;
462         }
463
464         return NULL;
465 }
466
467 static GSList *find_service_with_state(GSList *list,
468                                                 btd_service_state_t state)
469 {
470         GSList *l;
471
472         for (l = list; l != NULL; l = g_slist_next(l)) {
473                 struct btd_service *service = l->data;
474
475                 if (btd_service_get_state(service) == state)
476                         return l;
477         }
478
479         return NULL;
480 }
481
482 static GSList *find_service_with_uuid(GSList *list, char *uuid)
483 {
484         GSList *l;
485
486         for (l = list; l != NULL; l = g_slist_next(l)) {
487                 struct btd_service *service = l->data;
488                 struct btd_profile *profile = btd_service_get_profile(service);
489
490                 if (bt_uuid_strcmp(profile->remote_uuid, uuid) == 0)
491                         return l;
492         }
493
494         return NULL;
495 }
496
497 static void update_technologies(GKeyFile *file, struct btd_device *dev)
498 {
499         const char *list[2];
500         size_t len = 0;
501
502         if (dev->bredr)
503                 list[len++] = "BR/EDR";
504
505         if (dev->le) {
506                 const char *type;
507
508                 if (dev->bdaddr_type == BDADDR_LE_PUBLIC)
509                         type = "public";
510                 else
511                         type = "static";
512
513                 g_key_file_set_string(file, "General", "AddressType", type);
514
515                 list[len++] = "LE";
516         }
517
518         g_key_file_set_string_list(file, "General", "SupportedTechnologies",
519                                                                 list, len);
520 }
521
522 static void store_csrk(struct csrk_info *csrk, GKeyFile *key_file,
523                                                         const char *group)
524 {
525         char key[33];
526         int i;
527
528         for (i = 0; i < 16; i++)
529                 sprintf(key + (i * 2), "%2.2X", csrk->key[i]);
530
531         g_key_file_set_string(key_file, group, "Key", key);
532         g_key_file_set_integer(key_file, group, "Counter", csrk->counter);
533 }
534
535 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
536 static char *manufacturer_data2str(char *data, int size)
537 {
538         char str[DEV_MAX_MANUFACTURER_DATA_LEN * 3 + 1];
539         char tmp[5];
540         int i;
541
542         str[0] = '\0';
543         for(i = 0; i < size; i++) {
544                 snprintf(tmp, sizeof(tmp), "%d ", data[i]);
545                 g_strlcat(str, tmp, sizeof(str));
546         }
547
548         return g_strdup(str);
549 }
550
551 static void load_manufacturer_data_2digit(char *data, int len, char *buf)
552 {
553         int i;
554         char **split;
555
556         split = g_strsplit(data, " ", 0);
557
558         for (i = 0; i < len; i++) {
559                 if (split[i] == NULL)
560                         break;
561
562                 buf[i] = (char)g_ascii_strtoull(split[i], NULL, 10);
563         }
564
565         g_strfreev(split);
566
567         return;
568 }
569 #endif
570
571 static gboolean store_device_info_cb(gpointer user_data)
572 {
573         struct btd_device *device = user_data;
574         GKeyFile *key_file;
575         GError *gerr = NULL;
576         char filename[PATH_MAX];
577         char device_addr[18];
578         char *str;
579         char class[9];
580         char **uuids = NULL;
581         gsize length = 0;
582 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
583         gboolean svc_change_regd = false;
584 #endif
585
586         device->store_id = 0;
587
588         ba2str(&device->bdaddr, device_addr);
589
590 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
591         if (device->rpa)
592                 ba2str(device->rpa, device_addr);
593 #endif
594         snprintf(filename, PATH_MAX, STORAGEDIR "/%s/%s/info",
595                                 btd_adapter_get_storage_dir(device->adapter),
596                                 device_addr);
597         create_file(filename, 0600);
598
599         key_file = g_key_file_new();
600         if (!g_key_file_load_from_file(key_file, filename, 0, &gerr)) {
601                 error("Unable to load key file from %s: (%s)", filename,
602                                                                 gerr->message);
603                 g_error_free(gerr);
604                 g_key_file_free(key_file);
605                 return FALSE;
606         }
607
608         g_key_file_set_string(key_file, "General", "Name", device->name);
609
610         if (device->alias != NULL)
611                 g_key_file_set_string(key_file, "General", "Alias",
612                                                                 device->alias);
613         else
614                 g_key_file_remove_key(key_file, "General", "Alias", NULL);
615
616         if (device->class) {
617                 sprintf(class, "0x%6.6x", device->class & 0xffffff);
618                 g_key_file_set_string(key_file, "General", "Class", class);
619         } else {
620                 g_key_file_remove_key(key_file, "General", "Class", NULL);
621         }
622
623         if (device->appearance) {
624                 sprintf(class, "0x%4.4x", device->appearance);
625                 g_key_file_set_string(key_file, "General", "Appearance", class);
626         } else {
627                 g_key_file_remove_key(key_file, "General", "Appearance", NULL);
628         }
629
630 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
631         if (device->rpa_res_support) {
632                 g_key_file_set_integer(key_file, "General", "RPAResSupport",
633                                         device->rpa_res_support);
634         } else {
635                 g_key_file_remove_key(key_file, "General", "RPAResSupport", NULL);
636         }
637 #endif
638
639         update_technologies(key_file, device);
640
641         g_key_file_set_boolean(key_file, "General", "Trusted",
642                                                         device->trusted);
643 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
644         struct trusted_profile_t trust_profile = device->trusted_profiles;
645         int trusted_profiles = (trust_profile.pbap << PBAP_SHIFT_OFFSET) |
646                         (trust_profile.map << MAP_SHIFT_OFFSET) |
647                         (trust_profile.sap << SAP_SHIFT_OFFSET) |
648                         (trust_profile.hfp_hs << HFP_HS_SHIFT_OFFSET) |
649                         (trust_profile.a2dp << A2DP_SHIFT_OFFSET);
650         DBG("Storing TrustedProfiles %d", trusted_profiles);
651         g_key_file_set_integer(key_file, "General", "TrustedProfiles",
652                                                         trusted_profiles);
653 #endif
654         g_key_file_set_boolean(key_file, "General", "Blocked",
655                                                         device->blocked);
656
657         if (device->wake_override != WAKE_FLAG_DEFAULT) {
658                 g_key_file_set_boolean(key_file, "General", "WakeAllowed",
659                                        device->wake_override ==
660                                                WAKE_FLAG_ENABLED);
661         }
662
663         if (device->uuids) {
664                 GSList *l;
665                 int i;
666
667                 uuids = g_new0(char *, g_slist_length(device->uuids) + 1);
668                 for (i = 0, l = device->uuids; l; l = g_slist_next(l), i++)
669                         uuids[i] = l->data;
670                 g_key_file_set_string_list(key_file, "General", "Services",
671                                                 (const char **)uuids, i);
672         } else {
673                 g_key_file_remove_key(key_file, "General", "Services", NULL);
674         }
675
676 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
677         if (device->le_adv_data.flags) {
678                 g_key_file_set_integer(key_file, "General", "Flags",
679                                         device->le_adv_data.flags);
680         } else {
681                 g_key_file_remove_key(key_file, "General", "Flags", NULL);
682         }
683
684         if (device->manufacturer_data) {
685                 str = manufacturer_data2str(device->manufacturer_data,
686                                         device->manufacturer_data_len);
687                 g_key_file_set_string(key_file, "General",
688                                 "LegacyManufacturerData",
689                                 str);
690                 g_free(str);
691                 g_key_file_set_integer(key_file, "General",
692                                 "LegacyManufacturerDataLen",
693                                 device->manufacturer_data_len);
694         } else {
695                 g_key_file_remove_key(key_file, "General",
696                                                 "LegacyManufacturerData", NULL);
697                 g_key_file_remove_key(key_file, "General",
698                                                 "LegacyManufacturerDataLen", NULL);
699         }
700
701         if (device->rpa) {
702                 char irk_addr[18];
703
704                 ba2str(&device->bdaddr, irk_addr);
705                 g_key_file_set_string(key_file, "General", "IdentityAddress",
706                                                                 irk_addr);
707         } else {
708                 g_key_file_remove_key(key_file, "General", "IdentityAddress",
709                                                                 NULL);
710         }
711 #endif
712
713         if (device->vendor_src) {
714                 g_key_file_set_integer(key_file, "DeviceID", "Source",
715                                         device->vendor_src);
716                 g_key_file_set_integer(key_file, "DeviceID", "Vendor",
717                                         device->vendor);
718                 g_key_file_set_integer(key_file, "DeviceID", "Product",
719                                         device->product);
720                 g_key_file_set_integer(key_file, "DeviceID", "Version",
721                                         device->version);
722         } else {
723                 g_key_file_remove_group(key_file, "DeviceID", NULL);
724         }
725
726 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
727         svc_change_regd = bt_att_get_svc_changed_indication_registered(device->att);
728         g_key_file_set_boolean(key_file, "Att", "SvcChangeRegd",
729                                                 svc_change_regd);
730 #endif
731
732         if (device->local_csrk)
733                 store_csrk(device->local_csrk, key_file, "LocalSignatureKey");
734
735         if (device->remote_csrk)
736                 store_csrk(device->remote_csrk, key_file, "RemoteSignatureKey");
737
738         str = g_key_file_to_data(key_file, &length, NULL);
739         if (!g_file_set_contents(filename, str, length, &gerr)) {
740                 error("Unable set contents for %s: (%s)", filename,
741                                                                 gerr->message);
742                 g_error_free(gerr);
743         }
744
745         g_free(str);
746
747         g_key_file_free(key_file);
748         g_free(uuids);
749
750         return FALSE;
751 }
752
753 static bool device_address_is_private(struct btd_device *dev)
754 {
755         if (dev->bdaddr_type != BDADDR_LE_RANDOM)
756                 return false;
757
758         switch (dev->bdaddr.b[5] >> 6) {
759         case 0x00:      /* Private non-resolvable */
760         case 0x01:      /* Private resolvable */
761                 return true;
762         default:
763                 return false;
764         }
765 }
766
767 static void store_device_info(struct btd_device *device)
768 {
769         if (device->temporary || device->store_id > 0)
770                 return;
771
772         if (device_address_is_private(device)) {
773                 DBG("Can't store info for private addressed device %s",
774                                                                 device->path);
775                 return;
776         }
777
778         device->store_id = g_idle_add(store_device_info_cb, device);
779 }
780
781 void device_store_cached_name(struct btd_device *dev, const char *name)
782 {
783         char filename[PATH_MAX];
784         char d_addr[18];
785         GKeyFile *key_file;
786         GError *gerr = NULL;
787         char *data;
788         char *data_old;
789         gsize length = 0;
790         gsize length_old = 0;
791
792         if (device_address_is_private(dev)) {
793                 DBG("Can't store name for private addressed device %s",
794                                                                 dev->path);
795                 return;
796         }
797
798         ba2str(&dev->bdaddr, d_addr);
799
800 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
801         if (dev->rpa)
802                 ba2str(dev->rpa, d_addr);
803 #endif
804
805         snprintf(filename, PATH_MAX, STORAGEDIR "/%s/cache/%s",
806                         btd_adapter_get_storage_dir(dev->adapter), d_addr);
807         create_file(filename, 0600);
808
809         key_file = g_key_file_new();
810         if (!g_key_file_load_from_file(key_file, filename, 0, &gerr)) {
811                 error("Unable to load key file from %s: (%s)", filename,
812                                                                 gerr->message);
813                 g_error_free(gerr);
814         }
815
816         data_old = g_key_file_to_data(key_file, &length_old, NULL);
817
818         g_key_file_set_string(key_file, "General", "Name", name);
819
820         data = g_key_file_to_data(key_file, &length, NULL);
821
822         if ((length != length_old) || (memcmp(data, data_old, length))) {
823                 if (!g_file_set_contents(filename, data, length, &gerr)) {
824                         error("Unable set contents for %s: (%s)", filename,
825                                                                 gerr->message);
826                         g_error_free(gerr);
827                 }
828         }
829         g_free(data);
830         g_free(data_old);
831
832         g_key_file_free(key_file);
833 }
834
835 static void browse_request_free(struct browse_req *req)
836 {
837 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
838         DBG("");
839 #endif
840         struct btd_device *device = req->device;
841
842         if (device->browse == req)
843                 device->browse = NULL;
844
845         if (req->listener_id)
846                 g_dbus_remove_watch(dbus_conn, req->listener_id);
847         if (req->msg)
848                 dbus_message_unref(req->msg);
849         g_slist_free_full(req->profiles_added, g_free);
850         if (req->records)
851                 sdp_list_free(req->records, (sdp_free_func_t) sdp_record_free);
852
853         g_free(req);
854 }
855
856 static bool gatt_cache_is_enabled(struct btd_device *device)
857 {
858         switch (btd_opts.gatt_cache) {
859         case BT_GATT_CACHE_YES:
860                 return device_is_paired(device, device->bdaddr_type);
861         case BT_GATT_CACHE_NO:
862                 return false;
863         case BT_GATT_CACHE_ALWAYS:
864         default:
865                 return true;
866         }
867 }
868
869 static void gatt_cache_cleanup(struct btd_device *device)
870 {
871         if (gatt_cache_is_enabled(device))
872                 return;
873
874         bt_gatt_client_cancel_all(device->client);
875         gatt_db_clear(device->db);
876         device->le_state.svc_resolved = false;
877 }
878
879 static void gatt_client_cleanup(struct btd_device *device)
880 {
881         if (!device->client)
882                 return;
883
884         gatt_cache_cleanup(device);
885         bt_gatt_client_set_service_changed(device->client, NULL, NULL, NULL);
886
887         if (device->gatt_ready_id > 0) {
888                 bt_gatt_client_ready_unregister(device->client,
889                                                 device->gatt_ready_id);
890                 device->gatt_ready_id = 0;
891         }
892
893         bt_gatt_client_unref(device->client);
894         device->client = NULL;
895 }
896
897 static void gatt_server_cleanup(struct btd_device *device)
898 {
899         if (!device->server)
900                 return;
901
902         btd_gatt_database_att_disconnected(
903                         btd_adapter_get_database(device->adapter), device);
904
905         bt_gatt_server_unref(device->server);
906         device->server = NULL;
907 }
908
909 static void attio_cleanup(struct btd_device *device)
910 {
911         if (device->att_disconn_id)
912                 bt_att_unregister_disconnect(device->att,
913                                                         device->att_disconn_id);
914
915         if (device->att_io) {
916                 g_io_channel_shutdown(device->att_io, FALSE, NULL);
917                 g_io_channel_unref(device->att_io);
918                 device->att_io = NULL;
919         }
920
921         gatt_client_cleanup(device);
922         gatt_server_cleanup(device);
923
924         if (device->att) {
925                 bt_att_unref(device->att);
926                 device->att = NULL;
927         }
928
929         if (device->attrib) {
930                 GAttrib *attrib = device->attrib;
931
932                 device->attrib = NULL;
933                 g_attrib_cancel_all(attrib);
934                 g_attrib_unref(attrib);
935         }
936 }
937
938 static void browse_request_cancel(struct browse_req *req)
939 {
940         struct btd_device *device = req->device;
941         struct btd_adapter *adapter = device->adapter;
942
943         DBG("");
944
945         bt_cancel_discovery(btd_adapter_get_address(adapter), &device->bdaddr);
946
947         attio_cleanup(device);
948
949         browse_request_free(req);
950 }
951
952 static void svc_dev_remove(gpointer user_data)
953 {
954         struct svc_callback *cb = user_data;
955
956         if (cb->idle_id > 0)
957                 g_source_remove(cb->idle_id);
958
959         cb->func(cb->dev, -ENODEV, cb->user_data);
960
961         g_free(cb);
962 }
963
964 static void device_free(gpointer user_data)
965 {
966         struct btd_device *device = user_data;
967
968         btd_gatt_client_destroy(device->client_dbus);
969         device->client_dbus = NULL;
970
971         g_slist_free_full(device->uuids, g_free);
972         g_slist_free_full(device->primaries, g_free);
973         g_slist_free_full(device->svc_callbacks, svc_dev_remove);
974
975         /* Reset callbacks since the device is going to be freed */
976         gatt_db_unregister(device->db, device->db_id);
977
978         attio_cleanup(device);
979
980         gatt_db_unref(device->db);
981
982         bt_ad_unref(device->ad);
983
984         if (device->tmp_records)
985                 sdp_list_free(device->tmp_records,
986                                         (sdp_free_func_t) sdp_record_free);
987
988         if (device->disconn_timer)
989                 timeout_remove(device->disconn_timer);
990
991         if (device->discov_timer)
992                 timeout_remove(device->discov_timer);
993
994         if (device->temporary_timer)
995                 timeout_remove(device->temporary_timer);
996
997         if (device->connect)
998                 dbus_message_unref(device->connect);
999
1000         if (device->disconnect)
1001                 dbus_message_unref(device->disconnect);
1002
1003         DBG("%p", device);
1004
1005         if (device->authr) {
1006                 if (device->authr->agent)
1007                         agent_unref(device->authr->agent);
1008                 g_free(device->authr->pincode);
1009                 g_free(device->authr);
1010         }
1011
1012         if (device->eir_uuids)
1013                 g_slist_free_full(device->eir_uuids, g_free);
1014
1015 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
1016         g_free(device->rpa);
1017 #endif
1018         g_free(device->local_csrk);
1019         g_free(device->remote_csrk);
1020         g_free(device->path);
1021         g_free(device->alias);
1022         free(device->modalias);
1023         g_free(device);
1024 }
1025
1026 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
1027 void device_set_remote_feature_flag(struct btd_device *device, int flags)
1028 {
1029         device->remote_feature_flags = flags;
1030 }
1031
1032 gboolean device_is_bredrle(struct btd_device *device)
1033 {
1034         return (device->remote_feature_flags & (EIR_CONTROLLER | EIR_SIM_HOST));
1035 }
1036 #endif
1037
1038 bool device_is_paired(struct btd_device *device, uint8_t bdaddr_type)
1039 {
1040         struct bearer_state *state = get_state(device, bdaddr_type);
1041
1042         return state->paired;
1043 }
1044
1045 bool device_is_bonded(struct btd_device *device, uint8_t bdaddr_type)
1046 {
1047         struct bearer_state *state = get_state(device, bdaddr_type);
1048
1049         return state->bonded;
1050 }
1051
1052 gboolean device_is_trusted(struct btd_device *device)
1053 {
1054         return device->trusted;
1055 }
1056
1057 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
1058 gboolean device_is_profile_trusted(struct btd_device *device,
1059                 const char *uuid)
1060 {
1061         if (g_strcmp0(uuid, OBEX_PSE_UUID) == 0) {
1062                 if (device->trusted_profiles.pbap == SUPPORTED_TRUSTED)
1063                         return TRUE;
1064         } else if (g_strcmp0(uuid, OBEX_MAS_UUID) == 0) {
1065                 if (device->trusted_profiles.map == SUPPORTED_TRUSTED)
1066                         return TRUE;
1067         } else if (g_strcmp0(uuid, SAP_UUID) == 0) {
1068                 if (device->trusted_profiles.sap == SUPPORTED_TRUSTED)
1069                         return TRUE;
1070         } else if (g_strcmp0(uuid, HFP_HS_UUID) == 0) {
1071                 if (device->trusted_profiles.hfp_hs == SUPPORTED_TRUSTED)
1072                         return TRUE;
1073         } else if (g_strcmp0(uuid, A2DP_SINK_UUID) == 0) {
1074                 if (device->trusted_profiles.a2dp == SUPPORTED_TRUSTED)
1075                         return TRUE;
1076         }
1077         return FALSE;
1078 }
1079
1080 gboolean device_is_profile_blocked(struct btd_device *device,
1081                 const char *uuid)
1082 {
1083         if (g_strcmp0(uuid, OBEX_PSE_UUID) == 0) {
1084                 if (device->trusted_profiles.pbap == SUPPORTED_BLOCKED)
1085                         return TRUE;
1086         } else if (g_strcmp0(uuid, OBEX_MAS_UUID) == 0) {
1087                 if (device->trusted_profiles.map == SUPPORTED_BLOCKED)
1088                         return TRUE;
1089         } else if (g_strcmp0(uuid, SAP_UUID) == 0) {
1090                 if (device->trusted_profiles.sap == SUPPORTED_BLOCKED)
1091                         return TRUE;
1092         } else if (g_strcmp0(uuid, HFP_HS_UUID) == 0) {
1093                 if (device->trusted_profiles.hfp_hs == SUPPORTED_BLOCKED)
1094                         return TRUE;
1095         } else if (g_strcmp0(uuid, A2DP_SINK_UUID) == 0) {
1096                 if (device->trusted_profiles.a2dp == SUPPORTED_BLOCKED)
1097                         return TRUE;
1098         }
1099         return FALSE;
1100 }
1101 #endif
1102
1103 static gboolean dev_property_get_address(const GDBusPropertyTable *property,
1104                                         DBusMessageIter *iter, void *data)
1105 {
1106         struct btd_device *device = data;
1107         char dstaddr[18];
1108         const char *ptr = dstaddr;
1109
1110 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
1111         if (device->rpa)
1112                 ba2str(device->rpa, dstaddr);
1113         else
1114 #endif
1115         ba2str(&device->bdaddr, dstaddr);
1116         dbus_message_iter_append_basic(iter, DBUS_TYPE_STRING, &ptr);
1117
1118         return TRUE;
1119 }
1120
1121 static gboolean property_get_address_type(const GDBusPropertyTable *property,
1122                                         DBusMessageIter *iter, void *user_data)
1123 {
1124         struct btd_device *device = user_data;
1125         const char *str;
1126
1127         if (device->le && device->bdaddr_type == BDADDR_LE_RANDOM)
1128                 str = "random";
1129         else
1130                 str = "public";
1131
1132         dbus_message_iter_append_basic(iter, DBUS_TYPE_STRING, &str);
1133
1134         return TRUE;
1135 }
1136
1137 static gboolean dev_property_get_name(const GDBusPropertyTable *property,
1138                                         DBusMessageIter *iter, void *data)
1139 {
1140         struct btd_device *device = data;
1141         const char *ptr = device->name;
1142
1143         dbus_message_iter_append_basic(iter, DBUS_TYPE_STRING, &ptr);
1144
1145         return TRUE;
1146 }
1147
1148 static gboolean dev_property_exists_name(const GDBusPropertyTable *property,
1149                                                                 void *data)
1150 {
1151         struct btd_device *dev = data;
1152
1153         return device_name_known(dev);
1154 }
1155
1156 static gboolean dev_property_get_alias(const GDBusPropertyTable *property,
1157                                         DBusMessageIter *iter, void *data)
1158 {
1159         struct btd_device *device = data;
1160         char dstaddr[18];
1161         const char *ptr;
1162
1163         /* Alias (fallback to name or address) */
1164         if (device->alias != NULL)
1165                 ptr = device->alias;
1166         else if (strlen(device->name) > 0) {
1167                 ptr = device->name;
1168         } else {
1169                 ba2str(&device->bdaddr, dstaddr);
1170 #ifndef TIZEN_FEATURE_BLUEZ_MODIFY
1171                 g_strdelimit(dstaddr, ":", '-');
1172 #endif
1173                 ptr = dstaddr;
1174         }
1175
1176         dbus_message_iter_append_basic(iter, DBUS_TYPE_STRING, &ptr);
1177
1178         return TRUE;
1179 }
1180
1181 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
1182 static gboolean dev_property_get_alias_set(const GDBusPropertyTable *property,
1183                                         DBusMessageIter *iter, void *data)
1184 {
1185         struct btd_device *device = data;
1186         dbus_bool_t val;
1187
1188         if (device->alias != NULL)
1189                 val = TRUE;
1190         else
1191                 val = FALSE;
1192
1193         dbus_message_iter_append_basic(iter, DBUS_TYPE_BOOLEAN, &val);
1194
1195         return TRUE;
1196 }
1197 #endif
1198
1199 static void set_alias(GDBusPendingPropertySet id, const char *alias,
1200                                                                 void *data)
1201 {
1202         struct btd_device *device = data;
1203
1204         /* No change */
1205         if ((device->alias == NULL && g_str_equal(alias, "")) ||
1206                                         g_strcmp0(device->alias, alias) == 0) {
1207                 g_dbus_pending_property_success(id);
1208                 return;
1209         }
1210
1211         g_free(device->alias);
1212         device->alias = g_str_equal(alias, "") ? NULL : g_strdup(alias);
1213
1214         store_device_info(device);
1215
1216         g_dbus_emit_property_changed(dbus_conn, device->path,
1217                                                 DEVICE_INTERFACE, "Alias");
1218
1219         g_dbus_pending_property_success(id);
1220 }
1221
1222 static void dev_property_set_alias(const GDBusPropertyTable *property,
1223                                         DBusMessageIter *value,
1224                                         GDBusPendingPropertySet id, void *data)
1225 {
1226         const char *alias;
1227
1228         if (dbus_message_iter_get_arg_type(value) != DBUS_TYPE_STRING) {
1229                 g_dbus_pending_property_error(id,
1230                                         ERROR_INTERFACE ".InvalidArguments",
1231                                         "Invalid arguments in method call");
1232                 return;
1233         }
1234
1235         dbus_message_iter_get_basic(value, &alias);
1236
1237         set_alias(id, alias, data);
1238 }
1239
1240 static gboolean dev_property_exists_class(const GDBusPropertyTable *property,
1241                                                                 void *data)
1242 {
1243         struct btd_device *device = data;
1244
1245         return device->class != 0;
1246 }
1247
1248 static gboolean dev_property_get_class(const GDBusPropertyTable *property,
1249                                         DBusMessageIter *iter, void *data)
1250 {
1251         struct btd_device *device = data;
1252
1253         if (device->class == 0)
1254                 return FALSE;
1255
1256         dbus_message_iter_append_basic(iter, DBUS_TYPE_UINT32, &device->class);
1257
1258         return TRUE;
1259 }
1260
1261 static gboolean get_appearance(const GDBusPropertyTable *property, void *data,
1262                                                         uint16_t *appearance)
1263 {
1264         struct btd_device *device = data;
1265
1266         if (dev_property_exists_class(property, data))
1267                 return FALSE;
1268
1269         if (device->appearance) {
1270                 *appearance = device->appearance;
1271                 return TRUE;
1272         }
1273
1274         return FALSE;
1275 }
1276
1277 static gboolean dev_property_exists_appearance(
1278                         const GDBusPropertyTable *property, void *data)
1279 {
1280         uint16_t appearance;
1281
1282         return get_appearance(property, data, &appearance);
1283 }
1284
1285 static gboolean dev_property_get_appearance(const GDBusPropertyTable *property,
1286                                         DBusMessageIter *iter, void *data)
1287 {
1288         uint16_t appearance;
1289
1290         if (!get_appearance(property, data, &appearance))
1291                 return FALSE;
1292
1293         dbus_message_iter_append_basic(iter, DBUS_TYPE_UINT16, &appearance);
1294
1295         return TRUE;
1296 }
1297
1298 static const char *get_icon(const GDBusPropertyTable *property, void *data)
1299 {
1300         struct btd_device *device = data;
1301         const char *icon = NULL;
1302         uint16_t appearance;
1303
1304         if (device->class != 0)
1305                 icon = class_to_icon(device->class);
1306         else if (get_appearance(property, data, &appearance))
1307                 icon = gap_appearance_to_icon(appearance);
1308
1309         return icon;
1310 }
1311
1312 static gboolean dev_property_exists_icon(
1313                         const GDBusPropertyTable *property, void *data)
1314 {
1315         return get_icon(property, data) != NULL;
1316 }
1317
1318 static gboolean dev_property_get_icon(const GDBusPropertyTable *property,
1319                                         DBusMessageIter *iter, void *data)
1320 {
1321         const char *icon;
1322
1323         icon = get_icon(property, data);
1324         if (icon == NULL)
1325                 return FALSE;
1326
1327         dbus_message_iter_append_basic(iter, DBUS_TYPE_STRING, &icon);
1328
1329         return TRUE;
1330 }
1331
1332 static gboolean dev_property_get_paired(const GDBusPropertyTable *property,
1333                                         DBusMessageIter *iter, void *data)
1334 {
1335         struct btd_device *dev = data;
1336         dbus_bool_t val;
1337
1338         if (dev->bredr_state.paired || dev->le_state.paired)
1339                 val = TRUE;
1340         else
1341                 val = FALSE;
1342
1343         dbus_message_iter_append_basic(iter, DBUS_TYPE_BOOLEAN, &val);
1344
1345         return TRUE;
1346 }
1347
1348 static gboolean dev_property_get_legacy(const GDBusPropertyTable *property,
1349                                         DBusMessageIter *iter, void *data)
1350 {
1351         struct btd_device *device = data;
1352         dbus_bool_t val = device->legacy;
1353
1354         dbus_message_iter_append_basic(iter, DBUS_TYPE_BOOLEAN, &val);
1355
1356         return TRUE;
1357 }
1358
1359 static gboolean dev_property_get_rssi(const GDBusPropertyTable *property,
1360                                         DBusMessageIter *iter, void *data)
1361 {
1362         struct btd_device *dev = data;
1363         dbus_int16_t val = dev->rssi;
1364
1365         dbus_message_iter_append_basic(iter, DBUS_TYPE_INT16, &val);
1366
1367         return TRUE;
1368 }
1369
1370 static gboolean dev_property_exists_rssi(const GDBusPropertyTable *property,
1371                                                                 void *data)
1372 {
1373         struct btd_device *dev = data;
1374
1375         if (dev->rssi == 0)
1376                 return FALSE;
1377
1378         return TRUE;
1379 }
1380
1381 static gboolean dev_property_get_tx_power(const GDBusPropertyTable *property,
1382                                         DBusMessageIter *iter, void *data)
1383 {
1384         struct btd_device *dev = data;
1385         dbus_int16_t val = dev->tx_power;
1386
1387         dbus_message_iter_append_basic(iter, DBUS_TYPE_INT16, &val);
1388
1389         return TRUE;
1390 }
1391
1392 static gboolean dev_property_exists_tx_power(const GDBusPropertyTable *property,
1393                                                                 void *data)
1394 {
1395         struct btd_device *dev = data;
1396
1397         if (dev->tx_power == 127)
1398                 return FALSE;
1399
1400         return TRUE;
1401 }
1402
1403 static gboolean
1404 dev_property_get_svc_resolved(const GDBusPropertyTable *property,
1405                                         DBusMessageIter *iter, void *data)
1406 {
1407         struct btd_device *device = data;
1408         gboolean val = device->svc_refreshed;
1409
1410         dbus_message_iter_append_basic(iter, DBUS_TYPE_BOOLEAN, &val);
1411
1412         return TRUE;
1413 }
1414
1415 static gboolean dev_property_flags_exist(const GDBusPropertyTable *property,
1416                                                                 void *data)
1417 {
1418         struct btd_device *device = data;
1419
1420         return device->ad_flags[0] != INVALID_FLAGS;
1421 }
1422
1423 static gboolean
1424 dev_property_get_flags(const GDBusPropertyTable *property,
1425                                         DBusMessageIter *iter, void *data)
1426 {
1427         struct btd_device *device = data;
1428         uint8_t *flags = device->ad_flags;
1429         DBusMessageIter array;
1430
1431         dbus_message_iter_open_container(iter, DBUS_TYPE_ARRAY,
1432                                         DBUS_TYPE_BYTE_AS_STRING, &array);
1433         dbus_message_iter_append_fixed_array(&array, DBUS_TYPE_BYTE,
1434                                         &flags, sizeof(device->ad_flags));
1435         dbus_message_iter_close_container(iter, &array);
1436
1437         return TRUE;
1438 }
1439
1440 static gboolean dev_property_get_trusted(const GDBusPropertyTable *property,
1441                                         DBusMessageIter *iter, void *data)
1442 {
1443         struct btd_device *device = data;
1444         gboolean val = device_is_trusted(device);
1445
1446         dbus_message_iter_append_basic(iter, DBUS_TYPE_BOOLEAN, &val);
1447
1448         return TRUE;
1449 }
1450
1451 static void set_trust(GDBusPendingPropertySet id, gboolean value, void *data)
1452 {
1453         struct btd_device *device = data;
1454
1455         btd_device_set_trusted(device, value);
1456
1457         g_dbus_pending_property_success(id);
1458 }
1459
1460 static void dev_property_set_trusted(const GDBusPropertyTable *property,
1461                                         DBusMessageIter *value,
1462                                         GDBusPendingPropertySet id, void *data)
1463 {
1464         dbus_bool_t b;
1465
1466         if (dbus_message_iter_get_arg_type(value) != DBUS_TYPE_BOOLEAN) {
1467                 g_dbus_pending_property_error(id,
1468                                         ERROR_INTERFACE ".InvalidArguments",
1469                                         "Invalid arguments in method call");
1470                 return;
1471         }
1472
1473         dbus_message_iter_get_basic(value, &b);
1474
1475         set_trust(id, b, data);
1476 }
1477
1478 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
1479 static gboolean dev_property_get_trusted_profiles(const GDBusPropertyTable *property,
1480                                         DBusMessageIter *iter, void *data)
1481 {
1482         struct btd_device *device = data;
1483         uint32_t pbap = device->trusted_profiles.pbap;
1484         uint32_t map = device->trusted_profiles.map;
1485         uint32_t sap = device->trusted_profiles.sap;
1486         uint32_t hfp_hs = device->trusted_profiles.hfp_hs;
1487         uint32_t a2dp = device->trusted_profiles.a2dp;
1488
1489         unsigned int val = (pbap << PBAP_SHIFT_OFFSET) |
1490                         (map << MAP_SHIFT_OFFSET) |
1491                         (sap << SAP_SHIFT_OFFSET) |
1492                         (hfp_hs << HFP_HS_SHIFT_OFFSET) |
1493                         (a2dp << A2DP_SHIFT_OFFSET);
1494
1495         dbus_message_iter_append_basic(iter, DBUS_TYPE_UINT32, &val);
1496
1497         return TRUE;
1498 }
1499 #endif
1500
1501 static gboolean dev_property_get_blocked(const GDBusPropertyTable *property,
1502                                         DBusMessageIter *iter, void *data)
1503 {
1504         struct btd_device *device = data;
1505
1506         dbus_message_iter_append_basic(iter, DBUS_TYPE_BOOLEAN,
1507                                                         &device->blocked);
1508
1509         return TRUE;
1510 }
1511
1512 static void set_blocked(GDBusPendingPropertySet id, gboolean value, void *data)
1513 {
1514         struct btd_device *device = data;
1515         int err;
1516
1517         if (value)
1518                 err = device_block(device, FALSE);
1519         else
1520                 err = device_unblock(device, FALSE, FALSE);
1521
1522         switch (-err) {
1523         case 0:
1524                 g_dbus_pending_property_success(id);
1525                 break;
1526         case EINVAL:
1527                 g_dbus_pending_property_error(id, ERROR_INTERFACE ".Failed",
1528                                         "Kernel lacks reject list support");
1529                 break;
1530         default:
1531                 g_dbus_pending_property_error(id, ERROR_INTERFACE ".Failed",
1532                                                         strerror(-err));
1533                 break;
1534         }
1535 }
1536
1537
1538 static void dev_property_set_blocked(const GDBusPropertyTable *property,
1539                                         DBusMessageIter *value,
1540                                         GDBusPendingPropertySet id, void *data)
1541 {
1542         dbus_bool_t b;
1543
1544         if (dbus_message_iter_get_arg_type(value) != DBUS_TYPE_BOOLEAN) {
1545                 g_dbus_pending_property_error(id,
1546                                         ERROR_INTERFACE ".InvalidArguments",
1547                                         "Invalid arguments in method call");
1548                 return;
1549         }
1550
1551         dbus_message_iter_get_basic(value, &b);
1552
1553         set_blocked(id, b, data);
1554 }
1555
1556 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
1557 static uint8_t device_get_connected_state(struct btd_device *device)
1558 {
1559         if (device->bredr_state.connected && device->le_state.connected)
1560                 return DEV_CONNECTED_BREDR_LE;
1561         else if (device->bredr_state.connected)
1562                 return DEV_CONNECTED_BREDR;
1563         else if (device->le_state.connected)
1564                 return DEV_CONNECTED_LE;
1565         else
1566                 return DEV_CONNECTED_NONE;
1567 }
1568
1569 static gboolean dev_property_get_payload(const GDBusPropertyTable *property,
1570                                         DBusMessageIter *iter, void *data)
1571 {
1572         struct btd_device *dev = data;
1573         dbus_uint16_t payload_timeout = dev->auth_payload_timeout;
1574
1575         dbus_message_iter_append_basic(iter,
1576                         DBUS_TYPE_UINT16, &payload_timeout);
1577
1578         return TRUE;
1579 }
1580
1581 static gboolean dev_property_get_last_addr_type(const GDBusPropertyTable *property,
1582                                         DBusMessageIter *iter, void *data)
1583 {
1584         struct btd_device *dev = data;
1585         uint8_t last_addr_type = dev->last_bdaddr_type;
1586
1587         dbus_message_iter_append_basic(iter,
1588                         DBUS_TYPE_BYTE, &last_addr_type);
1589
1590         return TRUE;
1591 }
1592
1593 static gboolean dev_property_get_att_mtu(const GDBusPropertyTable *property,
1594                                         DBusMessageIter *iter, void *data)
1595 {
1596         struct btd_device *device = data;
1597         dbus_uint16_t mtu = bt_gatt_client_get_mtu(device->client);
1598
1599         dbus_message_iter_append_basic(iter, DBUS_TYPE_UINT16, &mtu);
1600
1601         return TRUE;
1602 }
1603
1604 static gboolean dev_property_get_gatt_connected(const GDBusPropertyTable *property,
1605                                         DBusMessageIter *iter, void *data)
1606 {
1607         struct btd_device *device = data;
1608         dbus_bool_t gatt_connected;
1609
1610         if (device->gatt_connected)
1611                 gatt_connected = TRUE;
1612         else
1613                 gatt_connected = FALSE;
1614
1615         dbus_message_iter_append_basic(iter, DBUS_TYPE_BOOLEAN,
1616                                         &gatt_connected);
1617
1618         return TRUE;
1619 }
1620
1621 static gboolean dev_property_get_ipsp_conn_state(const GDBusPropertyTable *property,
1622                                         DBusMessageIter *iter, void *data)
1623 {
1624         struct btd_device *dev = data;
1625         dbus_bool_t ipsp_connected;
1626
1627         if (dev->ipsp_connected)
1628                 ipsp_connected = TRUE;
1629         else
1630                 ipsp_connected = FALSE;
1631
1632         dbus_message_iter_append_basic(iter,
1633                         DBUS_TYPE_BOOLEAN, &ipsp_connected);
1634
1635         return TRUE;
1636 }
1637
1638 static gboolean dev_property_get_ipsp_conn_bt_iface_name(const GDBusPropertyTable *property,
1639                                 DBusMessageIter *iter, void *data)
1640 {
1641         struct btd_device *dev = data;
1642         char *ptr = g_strdup(dev->if_name);
1643
1644         dbus_message_iter_append_basic(iter, DBUS_TYPE_STRING, (const char **)&ptr);
1645
1646         g_free(ptr);
1647
1648         return TRUE;
1649 }
1650 #endif
1651
1652 static gboolean dev_property_get_connected(const GDBusPropertyTable *property,
1653                                         DBusMessageIter *iter, void *data)
1654 {
1655         struct btd_device *dev = data;
1656
1657 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
1658         uint8_t connected = device_get_connected_state(dev);
1659
1660         dbus_message_iter_append_basic(iter, DBUS_TYPE_BYTE, &connected);
1661 #else
1662         dbus_bool_t connected;
1663
1664         if (dev->bredr_state.connected || dev->le_state.connected)
1665                 connected = TRUE;
1666         else
1667                 connected = FALSE;
1668
1669         dbus_message_iter_append_basic(iter, DBUS_TYPE_BOOLEAN, &connected);
1670 #endif
1671
1672         return TRUE;
1673 }
1674
1675 static gboolean dev_property_get_uuids(const GDBusPropertyTable *property,
1676                                         DBusMessageIter *iter, void *data)
1677 {
1678         struct btd_device *dev = data;
1679         DBusMessageIter entry;
1680         GSList *l;
1681
1682         dbus_message_iter_open_container(iter, DBUS_TYPE_ARRAY,
1683                                 DBUS_TYPE_STRING_AS_STRING, &entry);
1684
1685         if (dev->bredr_state.svc_resolved || dev->le_state.svc_resolved)
1686                 l = dev->uuids;
1687         else if (dev->eir_uuids)
1688                 l = dev->eir_uuids;
1689         else
1690                 l = dev->uuids;
1691
1692         for (; l != NULL; l = l->next)
1693                 dbus_message_iter_append_basic(&entry, DBUS_TYPE_STRING,
1694                                                         &l->data);
1695
1696         dbus_message_iter_close_container(iter, &entry);
1697
1698         return TRUE;
1699 }
1700
1701 static gboolean dev_property_get_modalias(const GDBusPropertyTable *property,
1702                                         DBusMessageIter *iter, void *data)
1703 {
1704         struct btd_device *device = data;
1705
1706         if (!device->modalias)
1707                 return FALSE;
1708
1709         dbus_message_iter_append_basic(iter, DBUS_TYPE_STRING,
1710                                                         &device->modalias);
1711
1712         return TRUE;
1713 }
1714
1715 static gboolean dev_property_exists_modalias(const GDBusPropertyTable *property,
1716                                                                 void *data)
1717 {
1718         struct btd_device *device = data;
1719
1720         return device->modalias ? TRUE : FALSE;
1721 }
1722
1723 static gboolean dev_property_get_adapter(const GDBusPropertyTable *property,
1724                                         DBusMessageIter *iter, void *data)
1725 {
1726         struct btd_device *device = data;
1727         const char *str = adapter_get_path(device->adapter);
1728
1729         dbus_message_iter_append_basic(iter, DBUS_TYPE_OBJECT_PATH, &str);
1730
1731         return TRUE;
1732 }
1733
1734 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
1735 static gboolean property_get_manufacturer_data_len(const GDBusPropertyTable *property,
1736                                         DBusMessageIter *iter, void *user_data)
1737 {
1738         struct btd_device *device = user_data;
1739         dbus_uint16_t val = device->manufacturer_data_len;
1740
1741         dbus_message_iter_append_basic(iter, DBUS_TYPE_UINT16, &val);
1742
1743         return TRUE;
1744 }
1745
1746 static gboolean property_get_manufacturer_data(const GDBusPropertyTable *property,
1747                                         DBusMessageIter *iter, void *user_data)
1748 {
1749         struct btd_device *device = user_data;
1750         char str[DEV_MAX_MANUFACTURER_DATA_LEN] = {0};
1751         DBusMessageIter array;
1752
1753         memset(str, 0, DEV_MAX_MANUFACTURER_DATA_LEN);
1754         if (device->manufacturer_data_len)
1755                 memcpy(str, device->manufacturer_data,
1756                                         device->manufacturer_data_len);
1757
1758         dbus_message_iter_open_container(iter, DBUS_TYPE_ARRAY,
1759                                         DBUS_TYPE_BYTE_AS_STRING, &array);
1760
1761         dbus_message_iter_append_fixed_array(&array, DBUS_TYPE_BYTE,
1762                                                 &device->manufacturer_data,
1763                                                 device->manufacturer_data_len);
1764
1765         dbus_message_iter_close_container(iter, &array);
1766
1767         return TRUE;
1768 }
1769
1770 gboolean device_get_gatt_connected(const struct btd_device *device)
1771 {
1772         return device->gatt_connected;
1773 }
1774 #endif
1775
1776 static void append_manufacturer_data(void *data, void *user_data)
1777 {
1778         struct bt_ad_manufacturer_data *md = data;
1779         DBusMessageIter *dict = user_data;
1780
1781         g_dbus_dict_append_basic_array(dict,
1782                                 DBUS_TYPE_UINT16, &md->manufacturer_id,
1783                                 DBUS_TYPE_BYTE, &md->data, md->len);
1784 }
1785
1786 static gboolean
1787 dev_property_get_manufacturer_data(const GDBusPropertyTable *property,
1788                                         DBusMessageIter *iter, void *data)
1789 {
1790         struct btd_device *device = data;
1791         DBusMessageIter dict;
1792
1793         dbus_message_iter_open_container(iter, DBUS_TYPE_ARRAY,
1794                                         DBUS_DICT_ENTRY_BEGIN_CHAR_AS_STRING
1795                                         DBUS_TYPE_UINT16_AS_STRING
1796                                         DBUS_TYPE_VARIANT_AS_STRING
1797                                         DBUS_DICT_ENTRY_END_CHAR_AS_STRING,
1798                                         &dict);
1799
1800         bt_ad_foreach_manufacturer_data(device->ad, append_manufacturer_data,
1801                                                                         &dict);
1802
1803         dbus_message_iter_close_container(iter, &dict);
1804
1805         return TRUE;
1806 }
1807
1808 static gboolean
1809 dev_property_manufacturer_data_exist(const GDBusPropertyTable *property,
1810                                                                 void *data)
1811 {
1812         struct btd_device *device = data;
1813
1814         return bt_ad_has_manufacturer_data(device->ad, NULL);
1815 }
1816
1817 static void append_service_data(void *data, void *user_data)
1818 {
1819         struct bt_ad_service_data *sd = data;
1820         DBusMessageIter *dict = user_data;
1821         char uuid_str[MAX_LEN_UUID_STR];
1822
1823         bt_uuid_to_string(&sd->uuid, uuid_str, sizeof(uuid_str));
1824
1825         dict_append_array(dict, uuid_str, DBUS_TYPE_BYTE, &sd->data, sd->len);
1826 }
1827
1828 static gboolean
1829 dev_property_get_service_data(const GDBusPropertyTable *property,
1830                                         DBusMessageIter *iter, void *data)
1831 {
1832         struct btd_device *device = data;
1833         DBusMessageIter dict;
1834
1835         dbus_message_iter_open_container(iter, DBUS_TYPE_ARRAY,
1836                                         DBUS_DICT_ENTRY_BEGIN_CHAR_AS_STRING
1837                                         DBUS_TYPE_STRING_AS_STRING
1838                                         DBUS_TYPE_VARIANT_AS_STRING
1839                                         DBUS_DICT_ENTRY_END_CHAR_AS_STRING,
1840                                         &dict);
1841
1842         bt_ad_foreach_service_data(device->ad, append_service_data, &dict);
1843
1844         dbus_message_iter_close_container(iter, &dict);
1845
1846         return TRUE;
1847 }
1848
1849 static gboolean
1850 dev_property_service_data_exist(const GDBusPropertyTable *property,
1851                                                                 void *data)
1852 {
1853         struct btd_device *device = data;
1854
1855         return bt_ad_has_service_data(device->ad, NULL);
1856 }
1857
1858 static void append_advertising_data(void *data, void *user_data)
1859 {
1860         struct bt_ad_data *ad = data;
1861         DBusMessageIter *dict = user_data;
1862
1863         g_dbus_dict_append_basic_array(dict,
1864                                 DBUS_TYPE_BYTE, &ad->type,
1865                                 DBUS_TYPE_BYTE, &ad->data, ad->len);
1866 }
1867
1868 static gboolean
1869 dev_property_get_advertising_data(const GDBusPropertyTable *property,
1870                                         DBusMessageIter *iter, void *data)
1871 {
1872         struct btd_device *device = data;
1873         DBusMessageIter dict;
1874
1875         dbus_message_iter_open_container(iter, DBUS_TYPE_ARRAY,
1876                                         DBUS_DICT_ENTRY_BEGIN_CHAR_AS_STRING
1877                                         DBUS_TYPE_BYTE_AS_STRING
1878                                         DBUS_TYPE_VARIANT_AS_STRING
1879                                         DBUS_DICT_ENTRY_END_CHAR_AS_STRING,
1880                                         &dict);
1881
1882         bt_ad_foreach_data(device->ad, append_advertising_data, &dict);
1883
1884         dbus_message_iter_close_container(iter, &dict);
1885
1886         return TRUE;
1887 }
1888
1889 static gboolean
1890 dev_property_advertising_data_exist(const GDBusPropertyTable *property,
1891                                                                 void *data)
1892 {
1893         struct btd_device *device = data;
1894
1895         return bt_ad_has_data(device->ad, NULL);
1896 }
1897
1898 static bool device_get_wake_support(struct btd_device *device)
1899 {
1900         return device->wake_support;
1901 }
1902
1903 void device_set_wake_support(struct btd_device *device, bool wake_support)
1904 {
1905         device->wake_support = wake_support;
1906
1907         /* If wake configuration has not been made yet, set the initial
1908          * configuration.
1909          */
1910         if (device->wake_override == WAKE_FLAG_DEFAULT) {
1911                 device_set_wake_override(device, wake_support);
1912                 device_set_wake_allowed(device, wake_support, -1U);
1913         }
1914 }
1915
1916 static bool device_get_wake_allowed(struct btd_device *device)
1917 {
1918         return device->wake_allowed;
1919 }
1920
1921 void device_set_wake_override(struct btd_device *device, bool wake_override)
1922 {
1923         if (wake_override) {
1924                 device->wake_override = WAKE_FLAG_ENABLED;
1925                 device->current_flags |= DEVICE_FLAG_REMOTE_WAKEUP;
1926         } else {
1927                 device->wake_override = WAKE_FLAG_DISABLED;
1928                 device->current_flags &= ~DEVICE_FLAG_REMOTE_WAKEUP;
1929         }
1930 }
1931
1932 static void device_set_wake_allowed_complete(struct btd_device *device)
1933 {
1934         if (device->wake_id != -1U) {
1935                 g_dbus_pending_property_success(device->wake_id);
1936                 device->wake_id = -1U;
1937         }
1938
1939         device->wake_allowed = device->pending_wake_allowed;
1940         g_dbus_emit_property_changed(dbus_conn, device->path,
1941                                         DEVICE_INTERFACE, "WakeAllowed");
1942
1943         store_device_info(device);
1944 }
1945
1946 static void set_wake_allowed_complete(uint8_t status, uint16_t length,
1947                                          const void *param, void *user_data)
1948 {
1949         const struct mgmt_rp_set_device_flags *rp = param;
1950         struct btd_device *dev = user_data;
1951
1952         if (status != MGMT_STATUS_SUCCESS) {
1953                 error("Set device flags return status: %s",
1954                                         mgmt_errstr(status));
1955                 return;
1956         }
1957
1958         if (length < sizeof(*rp)) {
1959                 error("Too small Set Device Flags complete event: %d", length);
1960                 return;
1961         }
1962
1963         device_set_wake_allowed_complete(dev);
1964 }
1965
1966 void device_set_wake_allowed(struct btd_device *device, bool wake_allowed,
1967                              GDBusPendingPropertySet id)
1968 {
1969         uint32_t flags;
1970         /* Pending and current value are the same unless there is a change in
1971          * progress. Only update wake allowed if pending value doesn't match the
1972          * new value.
1973          */
1974         if (wake_allowed == device->pending_wake_allowed)
1975                 return;
1976
1977         device->wake_id = id;
1978         device->pending_wake_allowed = wake_allowed;
1979         flags = device->current_flags;
1980         if (wake_allowed)
1981                 flags |= DEVICE_FLAG_REMOTE_WAKEUP;
1982         else
1983                 flags &= ~DEVICE_FLAG_REMOTE_WAKEUP;
1984
1985         adapter_set_device_flags(device->adapter, device, flags,
1986                                         set_wake_allowed_complete, device);
1987 }
1988
1989
1990 static gboolean
1991 dev_property_get_wake_allowed(const GDBusPropertyTable *property,
1992                              DBusMessageIter *iter, void *data)
1993 {
1994         struct btd_device *device = data;
1995         dbus_bool_t wake_allowed = device_get_wake_allowed(device);
1996
1997         dbus_message_iter_append_basic(iter, DBUS_TYPE_BOOLEAN, &wake_allowed);
1998
1999         return TRUE;
2000 }
2001
2002 static void dev_property_set_wake_allowed(const GDBusPropertyTable *property,
2003                                          DBusMessageIter *value,
2004                                          GDBusPendingPropertySet id, void *data)
2005 {
2006         struct btd_device *device = data;
2007         dbus_bool_t b;
2008
2009         if (dbus_message_iter_get_arg_type(value) != DBUS_TYPE_BOOLEAN) {
2010                 g_dbus_pending_property_error(id,
2011                                         ERROR_INTERFACE ".InvalidArguments",
2012                                         "Invalid arguments in method call");
2013                 return;
2014         }
2015
2016         if (device->temporary) {
2017                 g_dbus_pending_property_error(id,
2018                                         ERROR_INTERFACE ".Unsupported",
2019                                         "Cannot set property while temporary");
2020                 return;
2021         }
2022
2023         /* Emit busy or success depending on current value. */
2024         if (b == device->pending_wake_allowed) {
2025                 if (device->wake_allowed == device->pending_wake_allowed)
2026                         g_dbus_pending_property_success(id);
2027                 else
2028                         g_dbus_pending_property_error(
2029                                 id, ERROR_INTERFACE ".Busy",
2030                                 "Property change in progress");
2031
2032                 return;
2033         }
2034
2035         dbus_message_iter_get_basic(value, &b);
2036         device_set_wake_override(device, b);
2037         device_set_wake_allowed(device, b, id);
2038 }
2039
2040 static gboolean dev_property_wake_allowed_exist(
2041                 const GDBusPropertyTable *property, void *data)
2042 {
2043         struct btd_device *device = data;
2044
2045         return device_get_wake_support(device);
2046 }
2047
2048
2049 static bool disconnect_all(gpointer user_data)
2050 {
2051         struct btd_device *device = user_data;
2052
2053         device->disconn_timer = 0;
2054
2055         if (device->bredr_state.connected)
2056                 btd_adapter_disconnect_device(device->adapter, &device->bdaddr,
2057                                                                 BDADDR_BREDR);
2058
2059         if (device->le_state.connected)
2060                 btd_adapter_disconnect_device(device->adapter, &device->bdaddr,
2061                                                         device->bdaddr_type);
2062
2063         return FALSE;
2064 }
2065
2066 int device_block(struct btd_device *device, gboolean update_only)
2067 {
2068         int err = 0;
2069
2070         if (device->blocked)
2071                 return 0;
2072
2073         if (device->disconn_timer > 0)
2074                 timeout_remove(device->disconn_timer);
2075
2076         disconnect_all(device);
2077
2078         while (device->services != NULL) {
2079                 struct btd_service *service = device->services->data;
2080
2081                 device->services = g_slist_remove(device->services, service);
2082                 service_remove(service);
2083         }
2084
2085         if (!update_only) {
2086                 if (device->le)
2087                         err = btd_adapter_block_address(device->adapter,
2088                                                         &device->bdaddr,
2089                                                         device->bdaddr_type);
2090                 if (!err && device->bredr)
2091                         err = btd_adapter_block_address(device->adapter,
2092                                                         &device->bdaddr,
2093                                                         BDADDR_BREDR);
2094         }
2095
2096         if (err < 0)
2097                 return err;
2098
2099         device->blocked = TRUE;
2100
2101         store_device_info(device);
2102
2103         btd_device_set_temporary(device, false);
2104
2105         g_dbus_emit_property_changed(dbus_conn, device->path,
2106                                                 DEVICE_INTERFACE, "Blocked");
2107
2108         return 0;
2109 }
2110
2111 int device_unblock(struct btd_device *device, gboolean silent,
2112                                                         gboolean update_only)
2113 {
2114         int err = 0;
2115
2116         if (!device->blocked)
2117                 return 0;
2118
2119         if (!update_only) {
2120                 if (device->le)
2121                         err = btd_adapter_unblock_address(device->adapter,
2122                                                         &device->bdaddr,
2123                                                         device->bdaddr_type);
2124                 if (!err && device->bredr)
2125                         err = btd_adapter_unblock_address(device->adapter,
2126                                                         &device->bdaddr,
2127                                                         BDADDR_BREDR);
2128         }
2129
2130         if (err < 0)
2131                 return err;
2132
2133         device->blocked = FALSE;
2134
2135         store_device_info(device);
2136
2137         if (!silent) {
2138                 g_dbus_emit_property_changed(dbus_conn, device->path,
2139                                                 DEVICE_INTERFACE, "Blocked");
2140                 device_probe_profiles(device, device->uuids);
2141         }
2142
2143         return 0;
2144 }
2145
2146 static void browse_request_exit(DBusConnection *conn, void *user_data)
2147 {
2148         struct browse_req *req = user_data;
2149
2150         DBG("Requestor exited");
2151
2152         browse_request_cancel(req);
2153 }
2154
2155 static void bonding_request_cancel(struct bonding_req *bonding)
2156 {
2157         struct btd_device *device = bonding->device;
2158         struct btd_adapter *adapter = device->adapter;
2159
2160         adapter_cancel_bonding(adapter, &device->bdaddr, device->bdaddr_type);
2161 }
2162
2163 static void dev_disconn_service(gpointer a, gpointer b)
2164 {
2165         btd_service_disconnect(a);
2166 }
2167
2168 void device_request_disconnect(struct btd_device *device, DBusMessage *msg)
2169 {
2170         if (device->bonding)
2171                 bonding_request_cancel(device->bonding);
2172
2173         if (device->browse)
2174                 browse_request_cancel(device->browse);
2175
2176         if (device->att_io) {
2177                 g_io_channel_shutdown(device->att_io, FALSE, NULL);
2178                 g_io_channel_unref(device->att_io);
2179                 device->att_io = NULL;
2180         }
2181
2182         if (device->connect) {
2183                 DBusMessage *reply = btd_error_failed(device->connect,
2184                                                 ERR_BREDR_CONN_CANCELED);
2185                 g_dbus_send_message(dbus_conn, reply);
2186                 dbus_message_unref(device->connect);
2187                 device->connect = NULL;
2188         }
2189
2190         if (btd_device_is_connected(device) && msg)
2191                 device->disconnects = g_slist_append(device->disconnects,
2192                                                 dbus_message_ref(msg));
2193
2194         if (device->disconn_timer)
2195                 return;
2196
2197         g_slist_foreach(device->services, dev_disconn_service, NULL);
2198
2199         g_slist_free(device->pending);
2200         device->pending = NULL;
2201
2202         while (device->watches) {
2203                 struct btd_disconnect_data *data = device->watches->data;
2204
2205                 if (data->watch)
2206                         /* temporary is set if device is going to be removed */
2207                         data->watch(device, device->temporary,
2208                                                         data->user_data);
2209
2210                 /* Check if the watch has been removed by callback function */
2211                 if (!g_slist_find(device->watches, data))
2212                         continue;
2213
2214                 device->watches = g_slist_remove(device->watches, data);
2215                 g_free(data);
2216         }
2217
2218         if (!btd_device_is_connected(device)) {
2219                 if (msg)
2220                         g_dbus_send_reply(dbus_conn, msg, DBUS_TYPE_INVALID);
2221                 return;
2222         }
2223
2224         device->disconn_timer = timeout_add_seconds(DISCONNECT_TIMER,
2225                                                         disconnect_all,
2226                                                         device, NULL);
2227 }
2228
2229 bool device_is_disconnecting(struct btd_device *device)
2230 {
2231         return device->disconn_timer > 0;
2232 }
2233
2234 void device_set_ltk_enc_size(struct btd_device *device, uint8_t enc_size)
2235 {
2236         device->ltk_enc_size = enc_size;
2237         bt_att_set_enc_key_size(device->att, device->ltk_enc_size);
2238 }
2239
2240 static void device_set_auto_connect(struct btd_device *device, gboolean enable)
2241 {
2242         char addr[18];
2243
2244         if (!device || !device->le)
2245                 return;
2246
2247         ba2str(&device->bdaddr, addr);
2248
2249         DBG("%s auto connect: %d", addr, enable);
2250
2251         if (device->auto_connect == enable)
2252                 return;
2253
2254         device->auto_connect = enable;
2255
2256         /* Disabling auto connect */
2257         if (enable == FALSE) {
2258                 adapter_connect_list_remove(device->adapter, device);
2259                 adapter_auto_connect_remove(device->adapter, device);
2260                 return;
2261         }
2262
2263         /* Enabling auto connect */
2264         adapter_auto_connect_add(device->adapter, device);
2265
2266         if (device->attrib) {
2267                 DBG("Already connected");
2268                 return;
2269         }
2270
2271         adapter_connect_list_add(device->adapter, device);
2272 }
2273
2274 static DBusMessage *dev_disconnect(DBusConnection *conn, DBusMessage *msg,
2275                                                         void *user_data)
2276 {
2277         struct btd_device *device = user_data;
2278
2279         /*
2280          * If device is not trusted disable connections through passive
2281          * scanning until Device1.Connect is called
2282          */
2283         if (device->auto_connect && !device->trusted) {
2284                 device->disable_auto_connect = TRUE;
2285                 device_set_auto_connect(device, FALSE);
2286         }
2287
2288         device_request_disconnect(device, msg);
2289
2290         return NULL;
2291 }
2292
2293 static int connect_next(struct btd_device *dev)
2294 {
2295         struct btd_service *service;
2296         int err = -ENOENT;
2297
2298         while (dev->pending) {
2299                 service = dev->pending->data;
2300
2301                 err = btd_service_connect(service);
2302                 if (!err)
2303                         return 0;
2304
2305                 dev->pending = g_slist_delete_link(dev->pending, dev->pending);
2306         }
2307
2308         return err;
2309 }
2310
2311 static void device_profile_connected(struct btd_device *dev,
2312                                         struct btd_profile *profile, int err)
2313 {
2314         struct btd_service *pending;
2315         GSList *l;
2316
2317         DBG("%s %s (%d)", profile->name, strerror(-err), -err);
2318
2319         if (!err)
2320                 btd_device_set_temporary(dev, false);
2321
2322         if (dev->pending == NULL)
2323                 goto done;
2324
2325         if (!btd_device_is_connected(dev)) {
2326                 switch (-err) {
2327                 case EHOSTDOWN: /* page timeout */
2328                 case EHOSTUNREACH: /* adapter not powered */
2329                 case ECONNABORTED: /* adapter powered down */
2330                         goto done;
2331                 }
2332         }
2333
2334         pending = dev->pending->data;
2335         l = find_service_with_profile(dev->pending, profile);
2336         if (l != NULL)
2337                 dev->pending = g_slist_delete_link(dev->pending, l);
2338
2339         /* Only continue connecting the next profile if it matches the first
2340          * pending, otherwise it will trigger another connect to the same
2341          * profile
2342          */
2343         if (profile != btd_service_get_profile(pending))
2344                 return;
2345
2346         if (connect_next(dev) == 0)
2347                 return;
2348
2349 done:
2350         g_slist_free(dev->pending);
2351         dev->pending = NULL;
2352
2353         if (!dev->connect)
2354                 return;
2355
2356         if (dbus_message_is_method_call(dev->connect, DEVICE_INTERFACE,
2357                                                         "Connect")) {
2358                 if (!err)
2359                         dev->general_connect = TRUE;
2360                 else if (find_service_with_state(dev->services,
2361                                                 BTD_SERVICE_STATE_CONNECTED))
2362                         /* Reset error if there are services connected */
2363                         err = 0;
2364         }
2365
2366         DBG("returning response to %s", dbus_message_get_sender(dev->connect));
2367
2368         if (err) {
2369                 /* Fallback to LE bearer if supported */
2370                 if (err == -EHOSTDOWN && dev->le && !dev->le_state.connected) {
2371                         err = device_connect_le(dev);
2372                         if (err == 0)
2373                                 return;
2374                 }
2375
2376                 g_dbus_send_message(dbus_conn,
2377                         btd_error_failed(dev->connect,
2378                                         btd_error_bredr_conn_from_errno(err)));
2379         } else {
2380 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
2381                 /* SDP is not required for Samsung TV Power on */
2382                 if (g_strcmp0(profile->name, "hid-device") == 0) {
2383                         DBG("Skip SDP discovery.");
2384                 } else {
2385 #endif
2386                 /* Start passive SDP discovery to update known services */
2387                 if (dev->bredr && !dev->svc_refreshed && dev->refresh_discovery)
2388                         device_browse_sdp(dev, NULL);
2389 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
2390                 }
2391 #endif
2392
2393                 g_dbus_send_reply(dbus_conn, dev->connect, DBUS_TYPE_INVALID);
2394         }
2395
2396         dbus_message_unref(dev->connect);
2397         dev->connect = NULL;
2398 }
2399
2400 void device_add_eir_uuids(struct btd_device *dev, GSList *uuids)
2401 {
2402         GSList *l;
2403         bool added = false;
2404
2405         if (dev->bredr_state.svc_resolved || dev->le_state.svc_resolved)
2406                 return;
2407
2408         for (l = uuids; l != NULL; l = l->next) {
2409                 const char *str = l->data;
2410                 if (g_slist_find_custom(dev->eir_uuids, str, bt_uuid_strcmp))
2411                         continue;
2412                 added = true;
2413                 dev->eir_uuids = g_slist_append(dev->eir_uuids, g_strdup(str));
2414         }
2415
2416         if (added)
2417                 g_dbus_emit_property_changed(dbus_conn, dev->path,
2418                                                 DEVICE_INTERFACE, "UUIDs");
2419 }
2420
2421 static void add_manufacturer_data(void *data, void *user_data)
2422 {
2423         struct eir_msd *msd = data;
2424         struct btd_device *dev = user_data;
2425
2426         if (!bt_ad_add_manufacturer_data(dev->ad, msd->company, msd->data,
2427                                                                 msd->data_len))
2428                 return;
2429
2430         g_dbus_emit_property_changed(dbus_conn, dev->path,
2431                                         DEVICE_INTERFACE, "ManufacturerData");
2432 }
2433
2434 void device_set_manufacturer_data(struct btd_device *dev, GSList *list,
2435                                                                 bool duplicate)
2436 {
2437         if (duplicate)
2438                 bt_ad_clear_manufacturer_data(dev->ad);
2439
2440         g_slist_foreach(list, add_manufacturer_data, dev);
2441 }
2442
2443 static void add_service_data(void *data, void *user_data)
2444 {
2445         struct eir_sd *sd = data;
2446         struct btd_device *dev = user_data;
2447         bt_uuid_t uuid;
2448
2449         if (bt_string_to_uuid(&uuid, sd->uuid) < 0)
2450                 return;
2451
2452         if (!bt_ad_add_service_data(dev->ad, &uuid, sd->data, sd->data_len))
2453                 return;
2454
2455         g_dbus_emit_property_changed(dbus_conn, dev->path,
2456                                         DEVICE_INTERFACE, "ServiceData");
2457 }
2458
2459 void device_set_service_data(struct btd_device *dev, GSList *list,
2460                                                         bool duplicate)
2461 {
2462         if (duplicate)
2463                 bt_ad_clear_service_data(dev->ad);
2464
2465         g_slist_foreach(list, add_service_data, dev);
2466 }
2467
2468 static void add_data(void *data, void *user_data)
2469 {
2470         struct eir_ad *ad = data;
2471         struct btd_device *dev = user_data;
2472
2473         if (!bt_ad_add_data(dev->ad, ad->type, ad->data, ad->len))
2474                 return;
2475
2476         if (ad->type == EIR_TRANSPORT_DISCOVERY)
2477                 g_dbus_emit_property_changed(dbus_conn, dev->path,
2478                                                 DEVICE_INTERFACE,
2479                                                 "AdvertisingData");
2480 }
2481
2482 void device_set_data(struct btd_device *dev, GSList *list,
2483                                                         bool duplicate)
2484 {
2485         if (duplicate)
2486                 bt_ad_clear_data(dev->ad);
2487
2488         g_slist_foreach(list, add_data, dev);
2489 }
2490
2491 static struct btd_service *find_connectable_service(struct btd_device *dev,
2492                                                         const char *uuid)
2493 {
2494         GSList *l;
2495 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
2496         struct btd_service *s = NULL;
2497 #endif
2498         for (l = dev->services; l != NULL; l = g_slist_next(l)) {
2499                 struct btd_service *service = l->data;
2500                 struct btd_profile *p = btd_service_get_profile(service);
2501
2502                 if (!p->connect || !p->remote_uuid)
2503                         continue;
2504
2505 #ifndef TIZEN_FEATURE_BLUEZ_MODIFY
2506                 if (strcasecmp(uuid, p->remote_uuid) == 0)
2507                         return service;
2508 #else
2509                 if (strcasecmp(uuid, p->remote_uuid) == 0) {
2510                         s = service;
2511                         if (ext_profile_is_registered_as_client_role(p) == TRUE) {
2512                                 return service;
2513                         } else {
2514                                 continue;
2515                         }
2516                 }
2517 #endif
2518         }
2519 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
2520         if (s)
2521                 return s;
2522 #endif
2523
2524         return NULL;
2525 }
2526
2527 static int service_prio_cmp(gconstpointer a, gconstpointer b)
2528 {
2529         struct btd_profile *p1 = btd_service_get_profile(a);
2530         struct btd_profile *p2 = btd_service_get_profile(b);
2531
2532         return p2->priority - p1->priority;
2533 }
2534
2535 bool btd_device_all_services_allowed(struct btd_device *dev)
2536 {
2537         GSList *l;
2538         struct btd_adapter *adapter = dev->adapter;
2539         struct btd_service *service;
2540         struct btd_profile *profile;
2541
2542         for (l = dev->services; l != NULL; l = g_slist_next(l)) {
2543                 service = l->data;
2544                 profile = btd_service_get_profile(service);
2545
2546                 if (!profile || !profile->auto_connect)
2547                         continue;
2548
2549                 if (!btd_adapter_is_uuid_allowed(adapter, profile->remote_uuid))
2550                         return false;
2551         }
2552
2553         return true;
2554 }
2555
2556 void btd_device_update_allowed_services(struct btd_device *dev)
2557 {
2558         struct btd_adapter *adapter = dev->adapter;
2559         struct btd_service *service;
2560         struct btd_profile *profile;
2561         GSList *l;
2562         bool is_allowed;
2563         char addr[18];
2564
2565         /* If service discovery is ongoing, let the service discovery complete
2566          * callback call this function.
2567          */
2568         if (dev->browse) {
2569                 ba2str(&dev->bdaddr, addr);
2570                 DBG("service discovery of %s is ongoing. Skip updating allowed "
2571                                                         "services", addr);
2572                 return;
2573         }
2574
2575         for (l = dev->services; l != NULL; l = g_slist_next(l)) {
2576                 service = l->data;
2577                 profile = btd_service_get_profile(service);
2578
2579                 is_allowed = btd_adapter_is_uuid_allowed(adapter,
2580                                                         profile->remote_uuid);
2581                 btd_service_set_allowed(service, is_allowed);
2582         }
2583 }
2584
2585 static GSList *create_pending_list(struct btd_device *dev, const char *uuid)
2586 {
2587         struct btd_service *service;
2588         struct btd_profile *p;
2589         GSList *l;
2590 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
2591         bool hs_hf_verify = FALSE;
2592 #endif
2593
2594         if (uuid) {
2595                 service = find_connectable_service(dev, uuid);
2596                 if (!service)
2597                         return dev->pending;
2598
2599                 if (btd_service_is_allowed(service))
2600                         return g_slist_prepend(dev->pending, service);
2601
2602 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
2603                 else if ((service == NULL) &&
2604                                         (g_strcmp0(uuid, HFP_HS_UUID) == 0)) {
2605                         DBG("HFP service not found check for HSP service");
2606                         service = find_connectable_service(dev, HSP_HS_UUID);
2607                         if (service)
2608                                 return g_slist_prepend(dev->pending, service);
2609                 } else if (g_strcmp0(uuid, HID_UUID) == 0) {
2610                         DBG("HID service not found, add HID service");
2611                         btd_device_add_uuid(dev, uuid);
2612                         service = find_connectable_service(dev, HID_UUID);
2613                         if (service)
2614                                 return g_slist_prepend(dev->pending, service);
2615                 }
2616 #endif
2617                 return dev->pending;
2618         }
2619
2620         for (l = dev->services; l != NULL; l = g_slist_next(l)) {
2621                 service = l->data;
2622                 p = btd_service_get_profile(service);
2623
2624 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
2625                 DBG("profile uuid %s", p->remote_uuid);
2626                 if (g_strcmp0(p->remote_uuid, HSP_HS_UUID) == 0) {
2627                         DBG("HSP service is found check for HFP service");
2628                         struct btd_service *service;
2629                         struct btd_profile *p;
2630                         GSList *h;
2631
2632                         for (h = dev->services; h != NULL; h = g_slist_next(h)) {
2633                                 service = h->data;
2634                                 p = btd_service_get_profile(service);
2635
2636                                 if (g_strcmp0(p->remote_uuid, HFP_HS_UUID) == 0) {
2637                                         DBG("HFP found,ignore HSP ");
2638                                         hs_hf_verify = TRUE;
2639                                         break;
2640                                 }
2641                         }
2642                         if (hs_hf_verify)
2643                                 continue;
2644                 }
2645 #endif
2646                 if (!p->auto_connect)
2647                         continue;
2648
2649                 if (!btd_service_is_allowed(service)) {
2650                         info("service %s is blocked", p->remote_uuid);
2651                         continue;
2652                 }
2653
2654                 if (g_slist_find(dev->pending, service))
2655                         continue;
2656
2657                 if (btd_service_get_state(service) !=
2658                                                 BTD_SERVICE_STATE_DISCONNECTED)
2659                         continue;
2660
2661                 dev->pending = g_slist_insert_sorted(dev->pending, service,
2662                                                         service_prio_cmp);
2663         }
2664
2665         return dev->pending;
2666 }
2667
2668 int btd_device_connect_services(struct btd_device *dev, GSList *services)
2669 {
2670         GSList *l;
2671
2672         if (dev->pending || dev->connect || dev->browse)
2673                 return -EBUSY;
2674
2675         if (!btd_adapter_get_powered(dev->adapter))
2676                 return -ENETDOWN;
2677
2678         if (!dev->bredr_state.svc_resolved)
2679                 return -ENOENT;
2680
2681         if (services) {
2682                 for (l = services; l; l = g_slist_next(l)) {
2683                         struct btd_service *service = l->data;
2684
2685                         dev->pending = g_slist_append(dev->pending, service);
2686                 }
2687         } else {
2688                 dev->pending = create_pending_list(dev, NULL);
2689         }
2690
2691         return connect_next(dev);
2692 }
2693
2694 static DBusMessage *connect_profiles(struct btd_device *dev, uint8_t bdaddr_type,
2695                                         DBusMessage *msg, const char *uuid)
2696 {
2697         struct bearer_state *state = get_state(dev, bdaddr_type);
2698         int err;
2699
2700         DBG("%s %s, client %s", dev->path, uuid ? uuid : "(all)",
2701                                                 dbus_message_get_sender(msg));
2702
2703 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
2704         if (dev->pending || dev->connect)
2705                 return btd_error_in_progress_str(msg, ERR_BREDR_CONN_BUSY);
2706 #else
2707         if (dev->pending || dev->connect || dev->browse)
2708                 return btd_error_in_progress_str(msg, ERR_BREDR_CONN_BUSY);
2709 #endif
2710
2711         if (!btd_adapter_get_powered(dev->adapter)) {
2712                 return btd_error_not_ready_str(msg,
2713                                         ERR_BREDR_CONN_ADAPTER_NOT_POWERED);
2714         }
2715
2716         btd_device_set_temporary(dev, false);
2717
2718         if (!state->svc_resolved)
2719                 goto resolve_services;
2720
2721         dev->pending = create_pending_list(dev, uuid);
2722         if (!dev->pending) {
2723                 if (dev->svc_refreshed) {
2724 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
2725                         if (!uuid && dbus_message_is_method_call(msg, DEVICE_INTERFACE,
2726                                                         "Connect") &&
2727                                 find_service_with_state(dev->services,
2728                                                 BTD_SERVICE_STATE_CONNECTED)) {
2729 #else
2730                         if (dbus_message_is_method_call(msg, DEVICE_INTERFACE,
2731                                                         "Connect") &&
2732                                 find_service_with_state(dev->services,
2733                                                 BTD_SERVICE_STATE_CONNECTED)) {
2734 #endif
2735                                 return dbus_message_new_method_return(msg);
2736                         } else {
2737                                 return btd_error_not_available_str(msg,
2738                                         ERR_BREDR_CONN_PROFILE_UNAVAILABLE);
2739                         }
2740                 }
2741
2742                 goto resolve_services;
2743         }
2744
2745         err = connect_next(dev);
2746         if (err < 0) {
2747                 if (err == -EALREADY)
2748 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
2749                         return btd_error_already_connected(msg);
2750 #else
2751                         return dbus_message_new_method_return(msg);
2752 #endif
2753                 return btd_error_failed(msg,
2754                                         btd_error_bredr_conn_from_errno(err));
2755         }
2756
2757         dev->connect = dbus_message_ref(msg);
2758
2759         return NULL;
2760
2761 resolve_services:
2762         DBG("Resolving services for %s", dev->path);
2763
2764         if (bdaddr_type == BDADDR_BREDR)
2765                 err = device_browse_sdp(dev, msg);
2766         else
2767                 err = device_browse_gatt(dev, msg);
2768         if (err < 0) {
2769                 return btd_error_failed(msg, bdaddr_type == BDADDR_BREDR ?
2770                         ERR_BREDR_CONN_SDP_SEARCH : ERR_LE_CONN_GATT_BROWSE);
2771         }
2772
2773         return NULL;
2774 }
2775
2776 #define NVAL_TIME ((time_t) -1)
2777 #define SEEN_TRESHHOLD 300
2778
2779 static uint8_t select_conn_bearer(struct btd_device *dev)
2780 {
2781         time_t bredr_last = NVAL_TIME, le_last = NVAL_TIME;
2782         time_t current = time(NULL);
2783
2784         /* Prefer bonded bearer in case only one is bonded */
2785         if (dev->bredr_state.bonded && !dev->le_state.bonded )
2786                 return BDADDR_BREDR;
2787         else if (!dev->bredr_state.bonded && dev->le_state.bonded)
2788                 return dev->bdaddr_type;
2789
2790         /* If the address is random it can only be connected over LE */
2791         if (dev->bdaddr_type == BDADDR_LE_RANDOM)
2792                 return dev->bdaddr_type;
2793
2794         if (dev->bredr_seen) {
2795                 bredr_last = current - dev->bredr_seen;
2796                 if (bredr_last > SEEN_TRESHHOLD)
2797                         bredr_last = NVAL_TIME;
2798         }
2799
2800         if (dev->le_seen) {
2801                 le_last = current - dev->le_seen;
2802                 if (le_last > SEEN_TRESHHOLD)
2803                         le_last = NVAL_TIME;
2804         }
2805
2806         if (le_last == NVAL_TIME && bredr_last == NVAL_TIME)
2807                 return dev->bdaddr_type;
2808
2809         if (dev->bredr && (!dev->le || le_last == NVAL_TIME))
2810                 return BDADDR_BREDR;
2811
2812         if (dev->le && (!dev->bredr || bredr_last == NVAL_TIME))
2813                 return dev->bdaddr_type;
2814
2815         /*
2816          * Prefer BR/EDR if time is the same since it might be from an
2817          * advertisement with BR/EDR flag set.
2818          */
2819         if (bredr_last <= le_last && btd_adapter_get_bredr(dev->adapter))
2820                 return BDADDR_BREDR;
2821
2822         return dev->bdaddr_type;
2823 }
2824
2825 static DBusMessage *dev_connect(DBusConnection *conn, DBusMessage *msg,
2826                                                         void *user_data)
2827 {
2828         struct btd_device *dev = user_data;
2829         uint8_t bdaddr_type;
2830
2831         if (dev->bredr_state.connected) {
2832                 /*
2833                  * Check if services have been resolved and there is at least
2834                  * one connected before switching to connect LE.
2835                  */
2836                 if (dev->bredr_state.svc_resolved &&
2837                         find_service_with_state(dev->services,
2838                                                 BTD_SERVICE_STATE_CONNECTED))
2839                         bdaddr_type = dev->bdaddr_type;
2840                 else
2841                         bdaddr_type = BDADDR_BREDR;
2842         } else if (dev->le_state.connected && dev->bredr)
2843                 bdaddr_type = BDADDR_BREDR;
2844         else
2845                 bdaddr_type = select_conn_bearer(dev);
2846
2847         if (bdaddr_type != BDADDR_BREDR) {
2848                 int err;
2849
2850                 if (dev->le_state.connected)
2851                         return dbus_message_new_method_return(msg);
2852
2853                 btd_device_set_temporary(dev, false);
2854
2855                 if (dev->disable_auto_connect) {
2856                         dev->disable_auto_connect = FALSE;
2857                         device_set_auto_connect(dev, TRUE);
2858                 }
2859
2860                 err = device_connect_le(dev);
2861                 if (err < 0)
2862                         return btd_error_failed(msg, strerror(-err));
2863
2864                 dev->connect = dbus_message_ref(msg);
2865
2866                 return NULL;
2867         }
2868
2869         return connect_profiles(dev, bdaddr_type, msg, NULL);
2870 }
2871
2872 static DBusMessage *connect_profile(DBusConnection *conn, DBusMessage *msg,
2873                                                         void *user_data)
2874 {
2875         struct btd_device *dev = user_data;
2876         const char *pattern;
2877         char *uuid;
2878         DBusMessage *reply;
2879
2880         if (!dbus_message_get_args(msg, NULL, DBUS_TYPE_STRING, &pattern,
2881                                                         DBUS_TYPE_INVALID)) {
2882                 return btd_error_invalid_args_str(msg,
2883                                         ERR_BREDR_CONN_INVALID_ARGUMENTS);
2884         }
2885
2886         uuid = bt_name2string(pattern);
2887         reply = connect_profiles(dev, BDADDR_BREDR, msg, uuid);
2888         free(uuid);
2889
2890         return reply;
2891 }
2892
2893 static void device_profile_disconnected(struct btd_device *dev,
2894                                         struct btd_profile *profile, int err)
2895 {
2896         if (!dev->disconnect)
2897                 return;
2898
2899         if (err)
2900                 g_dbus_send_message(dbus_conn,
2901                                         btd_error_failed(dev->disconnect,
2902                                                         strerror(-err)));
2903         else
2904                 g_dbus_send_reply(dbus_conn, dev->disconnect,
2905                                                         DBUS_TYPE_INVALID);
2906
2907         dbus_message_unref(dev->disconnect);
2908         dev->disconnect = NULL;
2909 }
2910
2911 static DBusMessage *disconnect_profile(DBusConnection *conn, DBusMessage *msg,
2912                                                         void *user_data)
2913 {
2914         struct btd_device *dev = user_data;
2915         struct btd_service *service;
2916         const char *pattern;
2917         char *uuid;
2918         int err;
2919
2920         if (!dbus_message_get_args(msg, NULL, DBUS_TYPE_STRING, &pattern,
2921                                                         DBUS_TYPE_INVALID))
2922                 return btd_error_invalid_args(msg);
2923
2924         uuid = bt_name2string(pattern);
2925         if (uuid == NULL)
2926                 return btd_error_invalid_args(msg);
2927
2928         service = find_connectable_service(dev, uuid);
2929 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
2930         if ((service == NULL) && (g_strcmp0(uuid, HFP_HS_UUID) == 0)) {
2931                 DBG("HFP service is not found check for HSP service");
2932                 service = find_connectable_service(dev, HSP_HS_UUID);
2933         }
2934 #endif
2935         free(uuid);
2936
2937         if (!service)
2938                 return btd_error_invalid_args(msg);
2939
2940         if (dev->disconnect)
2941                 return btd_error_in_progress(msg);
2942
2943         if (btd_service_get_state(service) == BTD_SERVICE_STATE_DISCONNECTED)
2944                 return dbus_message_new_method_return(msg);
2945
2946         dev->disconnect = dbus_message_ref(msg);
2947
2948         err = btd_service_disconnect(service);
2949         if (err == 0)
2950                 return NULL;
2951
2952 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
2953         if (dev->disconnect)
2954 #endif
2955         dbus_message_unref(dev->disconnect);
2956         dev->disconnect = NULL;
2957
2958         if (err == -ENOTSUP)
2959                 return btd_error_not_supported(msg);
2960         else if (err == -EALREADY)
2961                 return dbus_message_new_method_return(msg);
2962
2963         return btd_error_failed(msg, strerror(-err));
2964 }
2965
2966 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
2967 static DBusMessage *disconnect_ext_profile(DBusConnection *conn,
2968                                            DBusMessage *msg, void *user_data)
2969 {
2970         struct btd_device *dev = user_data;
2971         struct btd_profile *profile;
2972         struct btd_service *service;
2973         const char *sender, *path;
2974         GSList *l;
2975         int err;
2976
2977         sender = dbus_message_get_sender(msg);
2978
2979         DBG("sender %s", sender);
2980
2981         if (!dbus_message_get_args(msg, NULL, DBUS_TYPE_OBJECT_PATH, &path,
2982                                                         DBUS_TYPE_INVALID))
2983                 return btd_error_invalid_args(msg);
2984
2985         profile = btd_profile_find_ext(sender, path);
2986         if (!profile)
2987                 return btd_error_invalid_args(msg);
2988
2989         l = find_service_with_profile(dev->services, profile);
2990         if (!l)
2991                 return btd_error_invalid_args(msg);
2992
2993         service = l->data;
2994
2995         if (dev->disconnect)
2996                 return btd_error_in_progress(msg);
2997
2998         dev->disconnect = dbus_message_ref(msg);
2999
3000         err = btd_service_disconnect(service);
3001         if (err == 0)
3002                 return NULL;
3003
3004         if (dev->disconnect)
3005                 dbus_message_unref(dev->disconnect);
3006         dev->disconnect = NULL;
3007
3008         if (err == -ENOTSUP)
3009                 return btd_error_not_supported(msg);
3010
3011         return btd_error_failed(msg, strerror(-err));
3012 }
3013 #endif
3014
3015 static void store_services(struct btd_device *device)
3016 {
3017         char filename[PATH_MAX];
3018         char dst_addr[18];
3019         uuid_t uuid;
3020         char *prim_uuid;
3021         GKeyFile *key_file;
3022         GError *gerr = NULL;
3023         GSList *l;
3024         char *data;
3025         gsize length = 0;
3026
3027         if (device_address_is_private(device)) {
3028                 DBG("Can't store services for private addressed device %s",
3029                                                                 device->path);
3030                 return;
3031         }
3032
3033         sdp_uuid16_create(&uuid, GATT_PRIM_SVC_UUID);
3034         prim_uuid = bt_uuid2string(&uuid);
3035         if (prim_uuid == NULL)
3036                 return;
3037
3038         ba2str(&device->bdaddr, dst_addr);
3039
3040 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
3041         if (device->rpa)
3042                 ba2str(device->rpa, dst_addr);
3043 #endif
3044
3045         snprintf(filename, PATH_MAX, STORAGEDIR "/%s/%s/attributes",
3046                                 btd_adapter_get_storage_dir(device->adapter),
3047                                 dst_addr);
3048         key_file = g_key_file_new();
3049
3050         for (l = device->primaries; l; l = l->next) {
3051                 struct gatt_primary *primary = l->data;
3052                 char handle[6], uuid_str[33];
3053                 int i;
3054
3055                 sprintf(handle, "%hu", primary->range.start);
3056
3057                 bt_string2uuid(&uuid, primary->uuid);
3058                 sdp_uuid128_to_uuid(&uuid);
3059
3060                 switch (uuid.type) {
3061                 case SDP_UUID16:
3062                         sprintf(uuid_str, "%4.4X", uuid.value.uuid16);
3063                         break;
3064                 case SDP_UUID32:
3065                         sprintf(uuid_str, "%8.8X", uuid.value.uuid32);
3066                         break;
3067                 case SDP_UUID128:
3068                         for (i = 0; i < 16; i++)
3069                                 sprintf(uuid_str + (i * 2), "%2.2X",
3070                                                 uuid.value.uuid128.data[i]);
3071                         break;
3072                 default:
3073                         uuid_str[0] = '\0';
3074                 }
3075
3076                 g_key_file_set_string(key_file, handle, "UUID", prim_uuid);
3077                 g_key_file_set_string(key_file, handle, "Value", uuid_str);
3078                 g_key_file_set_integer(key_file, handle, "EndGroupHandle",
3079                                         primary->range.end);
3080         }
3081
3082         data = g_key_file_to_data(key_file, &length, NULL);
3083         if (length > 0) {
3084                 create_file(filename, 0600);
3085                 if (!g_file_set_contents(filename, data, length, &gerr)) {
3086                         error("Unable set contents for %s: (%s)", filename,
3087                                                                 gerr->message);
3088                         g_error_free(gerr);
3089                 }
3090         }
3091
3092         free(prim_uuid);
3093         g_free(data);
3094         g_key_file_free(key_file);
3095 }
3096
3097 struct gatt_saver {
3098         struct btd_device *device;
3099         uint16_t ext_props;
3100         GKeyFile *key_file;
3101 };
3102
3103 static void db_hash_read_value_cb(struct gatt_db_attribute *attrib,
3104                                                 int err, const uint8_t *value,
3105                                                 size_t length, void *user_data)
3106 {
3107         const uint8_t **hash = user_data;
3108
3109         if (err || (length != 16))
3110                 return;
3111
3112         *hash = value;
3113 }
3114
3115 static void store_desc(struct gatt_db_attribute *attr, void *user_data)
3116 {
3117         struct gatt_saver *saver = user_data;
3118         GKeyFile *key_file = saver->key_file;
3119         char handle[6], value[100], uuid_str[MAX_LEN_UUID_STR];
3120         const bt_uuid_t *uuid;
3121         bt_uuid_t ext_uuid;
3122         uint16_t handle_num;
3123
3124         handle_num = gatt_db_attribute_get_handle(attr);
3125         sprintf(handle, "%04hx", handle_num);
3126
3127         uuid = gatt_db_attribute_get_type(attr);
3128         bt_uuid_to_string(uuid, uuid_str, sizeof(uuid_str));
3129
3130         bt_uuid16_create(&ext_uuid, GATT_CHARAC_EXT_PROPER_UUID);
3131         if (!bt_uuid_cmp(uuid, &ext_uuid) && saver->ext_props)
3132                 sprintf(value, "%04hx:%s", saver->ext_props, uuid_str);
3133         else
3134                 sprintf(value, "%s", uuid_str);
3135
3136         g_key_file_set_string(key_file, "Attributes", handle, value);
3137 }
3138
3139 static void store_chrc(struct gatt_db_attribute *attr, void *user_data)
3140 {
3141         struct gatt_saver *saver = user_data;
3142         GKeyFile *key_file = saver->key_file;
3143         char handle[6], value[100], uuid_str[MAX_LEN_UUID_STR];
3144         uint16_t handle_num, value_handle;
3145         uint8_t properties;
3146         bt_uuid_t uuid, hash_uuid;
3147
3148         if (!gatt_db_attribute_get_char_data(attr, &handle_num, &value_handle,
3149                                                 &properties, &saver->ext_props,
3150                                                 &uuid)) {
3151                 warn("Error storing characteristic - can't get data");
3152                 return;
3153         }
3154
3155         sprintf(handle, "%04hx", handle_num);
3156         bt_uuid_to_string(&uuid, uuid_str, sizeof(uuid_str));
3157
3158         /* Store Database Hash  value if available */
3159         bt_uuid16_create(&hash_uuid, GATT_CHARAC_DB_HASH);
3160         if (!bt_uuid_cmp(&uuid, &hash_uuid)) {
3161                 const uint8_t *hash = NULL;
3162
3163                 attr = gatt_db_get_attribute(saver->device->db, value_handle);
3164
3165                 gatt_db_attribute_read(attr, 0, BT_ATT_OP_READ_REQ, NULL,
3166                                         db_hash_read_value_cb, &hash);
3167                 if (hash)
3168                         sprintf(value, GATT_CHARAC_UUID_STR ":%04hx:%02hhx:"
3169                                 "%02hhx%02hhx%02hhx%02hhx%02hhx%02hhx%02hhx"
3170                                 "%02hhx%02hhx%02hhx%02hhx%02hhx%02hhx%02hhx"
3171                                 "%02hhx%02hhx:%s", value_handle, properties,
3172                                 hash[0], hash[1], hash[2], hash[3],
3173                                 hash[4], hash[5], hash[6], hash[7],
3174                                 hash[8], hash[9], hash[10], hash[11],
3175                                 hash[12], hash[13], hash[14], hash[15],
3176                                 uuid_str);
3177                 else
3178                         sprintf(value, GATT_CHARAC_UUID_STR ":%04hx:%02hhx:%s",
3179                                 value_handle, properties, uuid_str);
3180
3181         } else
3182                 sprintf(value, GATT_CHARAC_UUID_STR ":%04hx:%02hhx:%s",
3183                                 value_handle, properties, uuid_str);
3184
3185         g_key_file_set_string(key_file, "Attributes", handle, value);
3186
3187         gatt_db_service_foreach_desc(attr, store_desc, saver);
3188 }
3189
3190 static void store_incl(struct gatt_db_attribute *attr, void *user_data)
3191 {
3192         struct gatt_saver *saver = user_data;
3193         GKeyFile *key_file = saver->key_file;
3194         struct gatt_db_attribute *service;
3195         char handle[6], value[100], uuid_str[MAX_LEN_UUID_STR];
3196         uint16_t handle_num, start, end;
3197         bt_uuid_t uuid;
3198
3199         if (!gatt_db_attribute_get_incl_data(attr, &handle_num, &start, &end)) {
3200                 warn("Error storing included service - can't get data");
3201                 return;
3202         }
3203
3204         service = gatt_db_get_attribute(saver->device->db, start);
3205         if (!service) {
3206                 warn("Error storing included service - can't find it");
3207                 return;
3208         }
3209
3210         sprintf(handle, "%04hx", handle_num);
3211
3212         gatt_db_attribute_get_service_uuid(service, &uuid);
3213         bt_uuid_to_string(&uuid, uuid_str, sizeof(uuid_str));
3214         sprintf(value, GATT_INCLUDE_UUID_STR ":%04hx:%04hx:%s", start,
3215                                                                 end, uuid_str);
3216
3217         g_key_file_set_string(key_file, "Attributes", handle, value);
3218 }
3219
3220 static void store_service(struct gatt_db_attribute *attr, void *user_data)
3221 {
3222         struct gatt_saver *saver = user_data;
3223         GKeyFile *key_file = saver->key_file;
3224         char uuid_str[MAX_LEN_UUID_STR], handle[6], value[256];
3225         uint16_t start, end;
3226         bt_uuid_t uuid;
3227         bool primary;
3228         char *type;
3229
3230         if (!gatt_db_attribute_get_service_data(attr, &start, &end, &primary,
3231                                                                 &uuid)) {
3232                 warn("Error storing service - can't get data");
3233                 return;
3234         }
3235
3236         sprintf(handle, "%04hx", start);
3237
3238         bt_uuid_to_string(&uuid, uuid_str, sizeof(uuid_str));
3239
3240         if (primary)
3241                 type = GATT_PRIM_SVC_UUID_STR;
3242         else
3243                 type = GATT_SND_SVC_UUID_STR;
3244
3245         sprintf(value, "%s:%04hx:%s", type, end, uuid_str);
3246
3247         g_key_file_set_string(key_file, "Attributes", handle, value);
3248
3249         gatt_db_service_foreach_incl(attr, store_incl, saver);
3250         gatt_db_service_foreach_char(attr, store_chrc, saver);
3251 }
3252
3253 static void store_gatt_db(struct btd_device *device)
3254 {
3255         char filename[PATH_MAX];
3256         char dst_addr[18];
3257         GKeyFile *key_file;
3258         GError *gerr = NULL;
3259         char *data;
3260         gsize length = 0;
3261         struct gatt_saver saver;
3262
3263         if (device_address_is_private(device)) {
3264                 DBG("Can't store GATT db for private addressed device %s",
3265                                                                 device->path);
3266                 return;
3267         }
3268
3269         if (!gatt_cache_is_enabled(device))
3270                 return;
3271
3272         ba2str(&device->bdaddr, dst_addr);
3273
3274         snprintf(filename, PATH_MAX, STORAGEDIR "/%s/cache/%s",
3275                                 btd_adapter_get_storage_dir(device->adapter),
3276                                 dst_addr);
3277         create_file(filename, 0600);
3278
3279         key_file = g_key_file_new();
3280         if (!g_key_file_load_from_file(key_file, filename, 0, &gerr)) {
3281                 error("Unable to load key file from %s: (%s)", filename,
3282                                                                 gerr->message);
3283                 g_error_free(gerr);
3284         }
3285
3286         /* Remove current attributes since it might have changed */
3287         g_key_file_remove_group(key_file, "Attributes", NULL);
3288
3289         saver.key_file = key_file;
3290         saver.device = device;
3291
3292         gatt_db_foreach_service(device->db, NULL, store_service, &saver);
3293
3294         data = g_key_file_to_data(key_file, &length, NULL);
3295         if (!g_file_set_contents(filename, data, length, &gerr)) {
3296                 error("Unable set contents for %s: (%s)", filename,
3297                                                                 gerr->message);
3298                 g_error_free(gerr);
3299         }
3300
3301         g_free(data);
3302         g_key_file_free(key_file);
3303 }
3304
3305
3306 static void browse_request_complete(struct browse_req *req, uint8_t type,
3307                                                 uint8_t bdaddr_type, int err)
3308 {
3309         struct btd_device *dev = req->device;
3310         DBusMessage *reply = NULL;
3311         DBusMessage *msg;
3312
3313         if (req->type != type)
3314                 return;
3315
3316         if (!req->msg)
3317                 goto done;
3318
3319         if (dbus_message_is_method_call(req->msg, DEVICE_INTERFACE, "Pair")) {
3320                 if (!device_is_paired(dev, bdaddr_type)) {
3321                         reply = btd_error_failed(req->msg, "Not paired");
3322                         goto done;
3323                 }
3324
3325                 if (dev->pending_paired) {
3326                         g_dbus_emit_property_changed(dbus_conn, dev->path,
3327                                                 DEVICE_INTERFACE, "Paired");
3328                         dev->pending_paired = false;
3329                 }
3330
3331                 /* Disregard browse errors in case of Pair */
3332                 reply = g_dbus_create_reply(req->msg, DBUS_TYPE_INVALID);
3333                 goto done;
3334         }
3335
3336         if (err) {
3337                 /* Fallback to LE bearer if supported */
3338                 if (err == -EHOSTDOWN && bdaddr_type == BDADDR_BREDR &&
3339                                 dev->le && !dev->le_state.connected) {
3340                         err = device_connect_le(dev);
3341                         if (err == 0)
3342                                 goto done;
3343                 }
3344                 reply = btd_error_failed(req->msg,
3345                                 bdaddr_type == BDADDR_BREDR ?
3346                                 btd_error_bredr_conn_from_errno(err) :
3347                                 btd_error_le_conn_from_errno(err));
3348                 goto done;
3349         }
3350
3351         /* if successfully resolved services we need to free browsing request
3352          * before passing message back to connect functions, otherwise
3353          * device->browse is set and "InProgress" error is returned instead
3354          * of actually connecting services
3355          */
3356         msg = dbus_message_ref(req->msg);
3357         browse_request_free(req);
3358         req = NULL;
3359
3360         if (dbus_message_is_method_call(msg, DEVICE_INTERFACE, "Connect"))
3361                 reply = dev_connect(dbus_conn, msg, dev);
3362         else if (dbus_message_is_method_call(msg, DEVICE_INTERFACE,
3363                                                         "ConnectProfile"))
3364                 reply = connect_profile(dbus_conn, msg, dev);
3365         else
3366                 reply = g_dbus_create_reply(msg, DBUS_TYPE_INVALID);
3367
3368         dbus_message_unref(msg);
3369
3370 done:
3371         if (reply)
3372                 g_dbus_send_message(dbus_conn, reply);
3373
3374         if (req)
3375                 browse_request_free(req);
3376 }
3377
3378 void device_set_refresh_discovery(struct btd_device *dev, bool refresh)
3379 {
3380         dev->refresh_discovery = refresh;
3381 }
3382
3383 static void device_set_svc_refreshed(struct btd_device *device, bool value)
3384 {
3385         if (device->svc_refreshed == value)
3386                 return;
3387
3388         device->svc_refreshed = value;
3389
3390         g_dbus_emit_property_changed(dbus_conn, device->path,
3391                                         DEVICE_INTERFACE, "ServicesResolved");
3392 }
3393
3394 static void device_svc_resolved(struct btd_device *dev, uint8_t browse_type,
3395                                                 uint8_t bdaddr_type, int err)
3396 {
3397         struct bearer_state *state = get_state(dev, bdaddr_type);
3398         struct browse_req *req = dev->browse;
3399
3400 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
3401         DBG("%s bdaddr_type %d err %d", dev->path, bdaddr_type, err);
3402 #else
3403         DBG("%s err %d", dev->path, err);
3404 #endif
3405
3406 #ifndef TIZEN_FEATURE_BLUEZ_MODIFY
3407         state->svc_resolved = true;
3408 #else
3409         if (err == 0)
3410                 state->svc_resolved = true;
3411 #endif
3412
3413         /* Disconnection notification can happen before this function
3414          * gets called, so don't set svc_refreshed for a disconnected
3415          * device.
3416          */
3417         if (state->connected)
3418                 device_set_svc_refreshed(dev, true);
3419
3420         g_slist_free_full(dev->eir_uuids, g_free);
3421         dev->eir_uuids = NULL;
3422
3423         if (dev->pending_paired) {
3424                 g_dbus_emit_property_changed(dbus_conn, dev->path,
3425                                                 DEVICE_INTERFACE, "Paired");
3426                 dev->pending_paired = false;
3427         }
3428
3429         if (!dev->temporary) {
3430                 store_device_info(dev);
3431
3432                 if (bdaddr_type != BDADDR_BREDR && err == 0)
3433                         store_services(dev);
3434         }
3435
3436 #ifndef TIZEN_FEATURE_BLUEZ_MODIFY
3437         if (req)
3438                 browse_request_complete(req, browse_type, bdaddr_type, err);
3439 #endif
3440
3441         while (dev->svc_callbacks) {
3442                 struct svc_callback *cb = dev->svc_callbacks->data;
3443
3444                 if (cb->idle_id > 0)
3445                         g_source_remove(cb->idle_id);
3446
3447                 cb->func(dev, err, cb->user_data);
3448
3449                 dev->svc_callbacks = g_slist_delete_link(dev->svc_callbacks,
3450                                                         dev->svc_callbacks);
3451                 g_free(cb);
3452         }
3453
3454 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
3455         if (!req) 
3456                 return;
3457
3458         /* If bdaddr_type is LE but req is for SDP, don't complete browse req. */
3459         if (bdaddr_type != BDADDR_BREDR && req->search_uuid) {
3460                 DBG("Discover comp. is for LE but browse req. is for SDP.");
3461                 return;
3462         }
3463
3464         browse_request_complete(req, browse_type, bdaddr_type, err);
3465 #endif
3466         btd_device_update_allowed_services(dev);
3467         device_resolved_drivers(dev->adapter, dev);
3468 }
3469
3470 static struct bonding_req *bonding_request_new(DBusMessage *msg,
3471                                                 struct btd_device *device,
3472                                                 uint8_t bdaddr_type,
3473                                                 struct agent *agent)
3474 {
3475         struct bonding_req *bonding;
3476         char addr[18];
3477
3478         ba2str(&device->bdaddr, addr);
3479         DBG("Requesting bonding for %s", addr);
3480
3481         bonding = g_new0(struct bonding_req, 1);
3482
3483         bonding->msg = dbus_message_ref(msg);
3484         bonding->bdaddr_type = bdaddr_type;
3485
3486         bonding->cb_iter = btd_adapter_pin_cb_iter_new(device->adapter);
3487
3488         /* Marks the bonding start time for the first attempt on request
3489          * construction. The following attempts will be updated on
3490          * device_bonding_retry. */
3491         clock_gettime(CLOCK_MONOTONIC, &bonding->attempt_start_time);
3492
3493         if (agent)
3494                 bonding->agent = agent_ref(agent);
3495
3496         return bonding;
3497 }
3498
3499 void device_bonding_restart_timer(struct btd_device *device)
3500 {
3501         if (!device || !device->bonding)
3502                 return;
3503
3504         clock_gettime(CLOCK_MONOTONIC, &device->bonding->attempt_start_time);
3505 }
3506
3507 static void bonding_request_stop_timer(struct bonding_req *bonding)
3508 {
3509         struct timespec current;
3510
3511         clock_gettime(CLOCK_MONOTONIC, &current);
3512
3513         /* Compute the time difference in ms. */
3514         bonding->last_attempt_duration_ms =
3515                 (current.tv_sec - bonding->attempt_start_time.tv_sec) * 1000L +
3516                 (current.tv_nsec - bonding->attempt_start_time.tv_nsec)
3517                                                                 / 1000000L;
3518 }
3519
3520 /* Returns the duration of the last bonding attempt in milliseconds. The
3521  * duration is measured starting from the latest of the following three
3522  * events and finishing when the Command complete event is received for the
3523  * authentication request:
3524  *  - MGMT_OP_PAIR_DEVICE is sent,
3525  *  - MGMT_OP_PIN_CODE_REPLY is sent and
3526  *  - Command complete event is received for the sent MGMT_OP_PIN_CODE_REPLY.
3527  */
3528 long device_bonding_last_duration(struct btd_device *device)
3529 {
3530         struct bonding_req *bonding = device->bonding;
3531
3532         if (!bonding)
3533                 return 0;
3534
3535         return bonding->last_attempt_duration_ms;
3536 }
3537
3538 static void create_bond_req_exit(DBusConnection *conn, void *user_data)
3539 {
3540         struct btd_device *device = user_data;
3541         char addr[18];
3542
3543         ba2str(&device->bdaddr, addr);
3544         DBG("%s: requestor exited before bonding was completed", addr);
3545
3546         if (device->authr)
3547                 device_cancel_authentication(device, FALSE);
3548
3549         if (device->bonding) {
3550                 device->bonding->listener_id = 0;
3551                 device_request_disconnect(device, NULL);
3552         }
3553 }
3554
3555 static void bonding_request_free(struct bonding_req *bonding)
3556 {
3557         if (!bonding)
3558                 return;
3559
3560         if (bonding->listener_id)
3561                 g_dbus_remove_watch(dbus_conn, bonding->listener_id);
3562
3563         if (bonding->msg)
3564                 dbus_message_unref(bonding->msg);
3565
3566         if (bonding->cb_iter)
3567                 g_free(bonding->cb_iter);
3568
3569         if (bonding->agent) {
3570                 agent_cancel(bonding->agent);
3571                 agent_unref(bonding->agent);
3572                 bonding->agent = NULL;
3573         }
3574
3575         if (bonding->retry_timer)
3576                 g_source_remove(bonding->retry_timer);
3577
3578         if (bonding->device)
3579                 bonding->device->bonding = NULL;
3580
3581         g_free(bonding);
3582 }
3583
3584 static DBusMessage *pair_device(DBusConnection *conn, DBusMessage *msg,
3585                                                                 void *data)
3586 {
3587         struct btd_device *device = data;
3588         struct btd_adapter *adapter = device->adapter;
3589 #ifndef TIZEN_FEATURE_BLUEZ_MODIFY
3590         struct bearer_state *state;
3591 #endif
3592         uint8_t bdaddr_type;
3593         const char *sender;
3594         struct agent *agent;
3595         struct bonding_req *bonding;
3596         uint8_t io_cap;
3597 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
3598         uint8_t conn_type;
3599         bool connect_le = FALSE;
3600         uint8_t link_type = DEV_CONNECTED_NONE;
3601 #endif
3602         int err;
3603
3604         btd_device_set_temporary(device, false);
3605
3606 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
3607         if (dbus_message_get_args(msg, NULL, DBUS_TYPE_BYTE, &conn_type,
3608                                         DBUS_TYPE_INVALID) == FALSE)
3609 #else
3610         if (!dbus_message_get_args(msg, NULL, DBUS_TYPE_INVALID))
3611 #endif
3612                 return btd_error_invalid_args(msg);
3613
3614         if (device->bonding)
3615                 return btd_error_in_progress(msg);
3616
3617 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
3618         if (conn_type == DEV_CONN_DEFAULT) {
3619                 link_type = device_get_connected_state(device);
3620
3621                 if (link_type == DEV_CONNECTED_BREDR) {
3622                         if (device_is_bonded(device, DEV_CONN_BREDR))
3623                                 return btd_error_already_exists(msg);
3624                         conn_type = DEV_CONN_BREDR;
3625                 } else if (link_type == DEV_CONNECTED_LE) {
3626                          if (device_is_bonded(device, DEV_CONN_LE))
3627                                 return btd_error_already_exists(msg);
3628                          conn_type = DEV_CONN_LE;
3629                 } else {
3630                         if (device_is_bonded(device, DEV_CONN_BREDR))
3631                                 return btd_error_already_exists(msg);
3632                         else if (device_is_bonded(device, DEV_CONN_LE))
3633                                 return btd_error_already_exists(msg);
3634
3635                         if (device->bredr)
3636                                 conn_type = DEV_CONN_BREDR;
3637                         else if (device->le)
3638                                 conn_type = DEV_CONN_LE;
3639                         else
3640                                 conn_type = DEV_CONN_BREDR;
3641                 }
3642         } else {
3643                 if (device_is_bonded(device, conn_type))
3644                         return btd_error_already_exists(msg);
3645         }
3646         bdaddr_type = device->bdaddr_type;
3647 #else
3648         if (device->bredr_state.bonded)
3649                 bdaddr_type = device->bdaddr_type;
3650         else if (device->le_state.bonded)
3651                 bdaddr_type = BDADDR_BREDR;
3652         else
3653                 bdaddr_type = select_conn_bearer(device);
3654
3655         state = get_state(device, bdaddr_type);
3656
3657         if (state->bonded)
3658                 return btd_error_already_exists(msg);
3659 #endif
3660
3661 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
3662         DBG("conn_type %d, link_type %d, bdaddr_type %d, device->bredr %d",
3663                         conn_type, link_type, bdaddr_type, device->bredr);
3664         if (conn_type == DEV_CONN_LE &&
3665             (device_is_bredrle(device) || bdaddr_type != BDADDR_BREDR)) {
3666                 DBG("LE Connect request");
3667                 connect_le = TRUE;
3668         }
3669 #endif
3670
3671         sender = dbus_message_get_sender(msg);
3672
3673         agent = agent_get(sender);
3674         if (agent)
3675                 io_cap = agent_get_io_capability(agent);
3676         else
3677                 io_cap = IO_CAPABILITY_NOINPUTNOOUTPUT;
3678
3679 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
3680         if ((conn_type == DEV_CONN_LE && bdaddr_type != BDADDR_BREDR) ||
3681                         connect_le)
3682                 bonding = bonding_request_new(msg, device, bdaddr_type, agent);
3683         else
3684                 bonding = bonding_request_new(msg, device, BDADDR_BREDR, agent);
3685 #else
3686         bonding = bonding_request_new(msg, device, bdaddr_type, agent);
3687 #endif
3688
3689         if (agent)
3690                 agent_unref(agent);
3691
3692         bonding->listener_id = g_dbus_add_disconnect_watch(dbus_conn,
3693                                                 sender, create_bond_req_exit,
3694                                                 device, NULL);
3695
3696         device->bonding = bonding;
3697         bonding->device = device;
3698
3699         /* Due to a bug in the kernel we might loose out on ATT commands
3700          * that arrive during the SMP procedure, so connect the ATT
3701          * channel first and only then start pairing (there's code for
3702          * this in the ATT connect callback)
3703          */
3704 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
3705         if (((conn_type == DEV_CONN_LE && bdaddr_type != BDADDR_BREDR) ||
3706                 (connect_le)) && !device->le_state.connected)
3707                 err = device_connect_le(device);
3708         else if (connect_le) /* Send bonding request if LE is already connected*/
3709                 err = adapter_create_bonding(adapter, &device->bdaddr,
3710                                                         bdaddr_type, io_cap);
3711         else
3712                 err = adapter_create_bonding(adapter, &device->bdaddr,
3713                                                         BDADDR_BREDR, io_cap);
3714 #else
3715         if (bdaddr_type != BDADDR_BREDR) {
3716                 if (!state->connected && btd_le_connect_before_pairing())
3717                         err = device_connect_le(device);
3718                 else
3719                         err = adapter_create_bonding(adapter, &device->bdaddr,
3720                                                         device->bdaddr_type,
3721                                                         io_cap);
3722         } else {
3723                 err = adapter_create_bonding(adapter, &device->bdaddr,
3724                                                         BDADDR_BREDR, io_cap);
3725         }
3726 #endif
3727
3728         if (err < 0) {
3729                 bonding_request_free(device->bonding);
3730                 return btd_error_failed(msg, strerror(-err));
3731         }
3732
3733         return NULL;
3734 }
3735
3736 static DBusMessage *new_authentication_return(DBusMessage *msg, uint8_t status)
3737 {
3738         switch (status) {
3739         case MGMT_STATUS_SUCCESS:
3740                 return dbus_message_new_method_return(msg);
3741
3742         case MGMT_STATUS_CONNECT_FAILED:
3743                 return dbus_message_new_error(msg,
3744                                 ERROR_INTERFACE ".ConnectionAttemptFailed",
3745                                 "Page Timeout");
3746         case MGMT_STATUS_TIMEOUT:
3747                 return dbus_message_new_error(msg,
3748                                 ERROR_INTERFACE ".AuthenticationTimeout",
3749                                 "Authentication Timeout");
3750         case MGMT_STATUS_BUSY:
3751         case MGMT_STATUS_REJECTED:
3752                 return dbus_message_new_error(msg,
3753                                 ERROR_INTERFACE ".AuthenticationRejected",
3754                                 "Authentication Rejected");
3755         case MGMT_STATUS_CANCELLED:
3756         case MGMT_STATUS_NO_RESOURCES:
3757 #ifndef TIZEN_FEATURE_BLUEZ_MODIFY
3758         case MGMT_STATUS_DISCONNECTED:
3759 #endif
3760                 return dbus_message_new_error(msg,
3761                                 ERROR_INTERFACE ".AuthenticationCanceled",
3762                                 "Authentication Canceled");
3763         case MGMT_STATUS_ALREADY_PAIRED:
3764                 return dbus_message_new_error(msg,
3765                                 ERROR_INTERFACE ".AlreadyExists",
3766                                 "Already Paired");
3767         default:
3768                 return dbus_message_new_error(msg,
3769                                 ERROR_INTERFACE ".AuthenticationFailed",
3770                                 "Authentication Failed");
3771         }
3772 }
3773
3774 static void device_cancel_bonding(struct btd_device *device, uint8_t status)
3775 {
3776         struct bonding_req *bonding = device->bonding;
3777         DBusMessage *reply;
3778         char addr[18];
3779
3780         if (!bonding)
3781                 return;
3782
3783         ba2str(&device->bdaddr, addr);
3784         DBG("Canceling bonding request for %s", addr);
3785
3786         if (device->authr)
3787                 device_cancel_authentication(device, FALSE);
3788
3789         reply = new_authentication_return(bonding->msg, status);
3790         g_dbus_send_message(dbus_conn, reply);
3791
3792         bonding_request_cancel(bonding);
3793         bonding_request_free(bonding);
3794 }
3795
3796 static DBusMessage *cancel_pairing(DBusConnection *conn, DBusMessage *msg,
3797                                                                 void *data)
3798 {
3799         struct btd_device *device = data;
3800         struct bonding_req *req = device->bonding;
3801
3802         DBG("");
3803
3804         if (!req)
3805                 return btd_error_does_not_exist(msg);
3806
3807         device_cancel_bonding(device, MGMT_STATUS_CANCELLED);
3808
3809         return dbus_message_new_method_return(msg);
3810 }
3811
3812 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
3813 static DBusMessage *discover_services(DBusConnection *conn,
3814                                         DBusMessage *msg, void *user_data)
3815 {
3816         struct btd_device *device = user_data;
3817         const char *pattern;
3818         int err;
3819
3820         if (device->browse)
3821                 return btd_error_in_progress(msg);
3822
3823         if (dbus_message_get_args(msg, NULL, DBUS_TYPE_STRING, &pattern,
3824                                                 DBUS_TYPE_INVALID) == FALSE)
3825                 return btd_error_invalid_args(msg);
3826
3827         err = device_browse_sdp(device, msg);
3828         if (err < 0)
3829                 goto fail;
3830
3831         return NULL;
3832
3833 fail:
3834         return btd_error_failed(msg,
3835                         "Unable to search the SDP services");
3836 }
3837
3838 static const char *browse_request_get_requestor(struct browse_req *req)
3839 {
3840         if (!req->msg)
3841                 return NULL;
3842
3843         return dbus_message_get_sender(req->msg);
3844 }
3845
3846 static void iter_append_record(DBusMessageIter *dict, uint32_t handle,
3847                                                         const char *record)
3848 {
3849         DBusMessageIter entry;
3850
3851         dbus_message_iter_open_container(dict, DBUS_TYPE_DICT_ENTRY,
3852                                                         NULL, &entry);
3853
3854         dbus_message_iter_append_basic(&entry, DBUS_TYPE_UINT32, &handle);
3855
3856         dbus_message_iter_append_basic(&entry, DBUS_TYPE_STRING, &record);
3857
3858         dbus_message_iter_close_container(dict, &entry);
3859 }
3860
3861 static void discover_services_reply(struct browse_req *req, int err,
3862                                                         sdp_list_t *recs)
3863 {
3864         DBusMessage *reply;
3865         DBusMessageIter iter, dict;
3866         sdp_list_t *seq;
3867
3868         if (!req->msg)
3869                 return;
3870
3871         if (err) {
3872                 const char *err_if;
3873
3874                 if (err == -EHOSTDOWN)
3875                         err_if = ERROR_INTERFACE ".ConnectionAttemptFailed";
3876                 else
3877                         err_if = ERROR_INTERFACE ".Failed";
3878
3879                 reply = dbus_message_new_error(req->msg, err_if,
3880                                                         strerror(-err));
3881                 g_dbus_send_message(dbus_conn, reply);
3882                 return;
3883         }
3884
3885         reply = dbus_message_new_method_return(req->msg);
3886         if (!reply)
3887                 return;
3888
3889         dbus_message_iter_init_append(reply, &iter);
3890
3891         dbus_message_iter_open_container(&iter, DBUS_TYPE_ARRAY,
3892                         DBUS_DICT_ENTRY_BEGIN_CHAR_AS_STRING
3893                         DBUS_TYPE_UINT32_AS_STRING DBUS_TYPE_STRING_AS_STRING
3894                         DBUS_DICT_ENTRY_END_CHAR_AS_STRING, &dict);
3895
3896         for (seq = recs; seq; seq = seq->next) {
3897                 sdp_record_t *rec = (sdp_record_t *) seq->data;
3898                 GString *result;
3899
3900                 if (!rec)
3901                         break;
3902
3903                 result = g_string_new(NULL);
3904
3905                 convert_sdp_record_to_xml(rec, result,
3906                                 (void *) g_string_append);
3907
3908                 if (result->len) {
3909                         if (!g_utf8_validate(result->str, -1, NULL)) {
3910                                 gchar *ptr = NULL;
3911
3912                                 DBG("UTF8 invalid string, make valid");
3913                                 ptr = g_utf8_make_valid(result->str, -1);
3914                                 iter_append_record(&dict, rec->handle, ptr);
3915                                 g_free(ptr);
3916                         } else {
3917                                 iter_append_record(&dict, rec->handle, result->str);
3918                         }
3919                 }
3920
3921                 g_string_free(result, TRUE);
3922         }
3923
3924         dbus_message_iter_close_container(&iter, &dict);
3925
3926         g_dbus_send_message(dbus_conn, reply);
3927 }
3928
3929 static DBusMessage *cancel_discover(DBusConnection *conn,
3930                                         DBusMessage *msg, void *user_data)
3931 {
3932         struct btd_device *device = user_data;
3933         const char *sender = dbus_message_get_sender(msg);
3934         const char *requestor;
3935
3936         if (!device->browse)
3937                 return btd_error_does_not_exist(msg);
3938
3939         if (!dbus_message_is_method_call(device->browse->msg, DEVICE_INTERFACE,
3940                                         "DiscoverServices"))
3941                 return btd_error_not_authorized(msg);
3942
3943         requestor = browse_request_get_requestor(device->browse);
3944
3945         /* only the discover requestor can cancel the inquiry process */
3946         if (!requestor || !g_str_equal(requestor, sender))
3947                 return btd_error_not_authorized(msg);
3948
3949         discover_services_reply(device->browse, -ECANCELED, NULL);
3950
3951         if (device->browse)
3952                 browse_request_cancel(device->browse);
3953
3954         return dbus_message_new_method_return(msg);
3955 }
3956
3957 void device_set_gatt_connected(struct btd_device *device, gboolean connected)
3958 {
3959         if (device == NULL) {
3960                 error("device is NULL");
3961                 return;
3962         }
3963
3964         if (device->gatt_connected == connected) {
3965                 error("same state change for gatt_connected : %d", connected);
3966                 return;
3967         }
3968         DBG("GattConnected %d", connected);
3969
3970         device->gatt_connected = connected;
3971         g_dbus_emit_property_changed(dbus_conn, device->path,
3972                         DEVICE_INTERFACE, "GattConnected");
3973 }
3974
3975 static DBusMessage *connect_le(DBusConnection *conn, DBusMessage *msg,
3976                                                         void *user_data)
3977 {
3978         struct btd_device *dev = user_data;
3979         dbus_bool_t auto_connect = FALSE;
3980         int err;
3981
3982         if (!dev->le) {
3983                 /*
3984                  * If a LE connection is requested without device discovery,
3985                  * we try to get device object. Here, technology can be updated
3986                  * if there is matched device object. Or, a new device object
3987                  * will be created.
3988                  */
3989                 dev = btd_adapter_get_device(dev->adapter, &dev->bdaddr,
3990                                 BDADDR_LE_PUBLIC);
3991                 if (dev == NULL) {
3992                         error("Unable to get device object");
3993                         return btd_error_not_supported(msg);
3994                 }
3995         }
3996
3997         if (dev->le_state.connected)
3998                 return dbus_message_new_method_return(msg);
3999
4000         if (!dbus_message_get_args(msg, NULL, DBUS_TYPE_BOOLEAN, &auto_connect,
4001                                 DBUS_TYPE_INVALID))
4002                 return btd_error_invalid_args(msg);
4003
4004         btd_device_set_temporary(dev, false);
4005
4006         if (auto_connect) {
4007                 DBG("Start BLE auto connection");
4008                 dev->disable_auto_connect = FALSE;
4009                 device_set_auto_connect(dev, TRUE);
4010
4011                 return dbus_message_new_method_return(msg);
4012         }
4013
4014         err = device_connect_le(dev);
4015         if (err < 0)
4016                 return btd_error_failed(msg, strerror(-err));
4017
4018         dev->connect = dbus_message_ref(msg);
4019
4020         return NULL;
4021 }
4022
4023 static DBusMessage *disconnect_le(DBusConnection *conn, DBusMessage *msg,
4024                                                         void *user_data)
4025 {
4026         struct btd_device *dev = user_data;
4027
4028         if (!dev->le)
4029                 return btd_error_not_supported(msg);
4030
4031         /*
4032          * Disable connections through passive sccanning
4033          */
4034         if (dev->auto_connect) {
4035                 DBG("Stop BLE auto connection");
4036                 dev->disable_auto_connect = FALSE;
4037                 device_set_auto_connect(dev, FALSE);
4038
4039                 if (!dev->le_state.connected) {
4040                         g_dbus_send_reply(dbus_conn, msg, DBUS_TYPE_INVALID);
4041                         return NULL;
4042                 }
4043         }
4044
4045         device_request_disconnect(dev, msg);
4046
4047         return NULL;
4048 }
4049
4050 static DBusMessage *connect_ipsp(DBusConnection *conn, DBusMessage *msg,
4051                                                         void *user_data)
4052 {
4053         struct btd_device *device = user_data;
4054
4055         DBG("bdaddr_type  %d", device->bdaddr_type);
4056
4057         if (device->bdaddr_type == BDADDR_BREDR) {
4058                 if(device->le)
4059                         device->bdaddr_type = BDADDR_LE_PUBLIC;
4060                 else {
4061                         device = btd_adapter_get_device(device->adapter,
4062                                         &device->bdaddr, BDADDR_LE_PUBLIC);
4063                         if (device == NULL)
4064                                 return btd_error_no_such_adapter(msg);
4065                 }
4066         }
4067
4068         if (device->ipsp_connected)
4069                 return btd_error_already_connected(msg);
4070
4071         /* Initiate Connection for 6Lowan*/
4072         if (btd_adapter_connect_ipsp(device->adapter, &device->bdaddr,
4073                                         device->bdaddr_type) != 0)
4074                 return btd_error_failed(msg, "ConnectFailed");
4075
4076         return dbus_message_new_method_return(msg);;
4077 }
4078
4079 static DBusMessage *disconnect_ipsp(DBusConnection *conn, DBusMessage *msg,
4080                                                         void *user_data)
4081 {
4082         struct btd_device *device = user_data;
4083         DBG("bdaddr_type  %d", device->bdaddr_type);
4084
4085         if (device->bdaddr_type == BDADDR_BREDR)
4086                 return btd_error_not_supported(msg);
4087
4088         if (!device->ipsp_connected)
4089                 return btd_error_not_connected(msg);
4090
4091         /* Disconnect the 6Lowpan connection */
4092         if (btd_adapter_disconnect_ipsp(device->adapter, &device->bdaddr,
4093                                         device->bdaddr_type) != 0)
4094                 return btd_error_failed(msg, "DisconnectFailed");
4095
4096         /* TODO: Handle disconnection of GATT connection, If the connection
4097          * is established as part of IPSP connection. */
4098
4099         return dbus_message_new_method_return(msg);;
4100 }
4101
4102 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
4103 static GSList *find_otc_conn_info(GSList *list, const char *path)
4104 {
4105         GSList *l;
4106
4107         for (l = list; l != NULL; l = g_slist_next(l)) {
4108                 struct otc_conn_info *info = l->data;
4109
4110                 if (g_strcmp0(info->dev_path, path) == 0)
4111                         return l;
4112         }
4113
4114         return NULL;
4115 }
4116
4117 static gboolean otc_disconnected_cb(GIOChannel *chan, GIOCondition cond,
4118                                                         gpointer user_data)
4119 {
4120         struct otc_conn_info *conn_info;
4121         const char *dev_path = (const char *) user_data;
4122         GSList *l;
4123
4124         DBG("OTC Disconnected");
4125
4126         l = find_otc_conn_info(otc_connection_list, dev_path);
4127         if (!l)
4128                 return FALSE;
4129
4130         conn_info = l->data;
4131         conn_info->otc_connected = false;
4132
4133         g_dbus_emit_signal(dbus_conn, dev_path,
4134                                 DEVICE_INTERFACE, "OtcDisconnected",
4135                                 DBUS_TYPE_INVALID);
4136
4137         if (conn_info->io) {
4138                 g_io_channel_shutdown(conn_info->io, TRUE, NULL);
4139                 g_io_channel_unref(conn_info->io);
4140         }
4141
4142         otc_connection_list = g_slist_remove(otc_connection_list, conn_info);
4143         g_free(conn_info);
4144
4145         return FALSE;
4146 }
4147
4148 static void otc_connect_cb(GIOChannel *chan, GError *gerr,
4149                                                 gpointer user_data)
4150 {
4151         const char *dev_path;
4152         GSList *l;
4153         struct otc_conn_info *conn_info = NULL;
4154         DBusMessage *msg = NULL;
4155         DBusMessageIter iter;
4156         int fd;
4157
4158         if (gerr)
4159                 return;
4160
4161         dev_path = (const char *) user_data;
4162         l = find_otc_conn_info(otc_connection_list, dev_path);
4163
4164         if (!l)
4165                 return;
4166
4167         conn_info = l->data;
4168         conn_info->otc_connected = true;
4169
4170         fd = g_io_channel_unix_get_fd(chan);
4171
4172         DBG("OTC Connected fd [%d], role [%s]",
4173                         fd, conn_info->role ? "server" : "client");
4174         DBG("dev_path [%s]", dev_path);
4175
4176         g_io_add_watch(chan, G_IO_HUP | G_IO_ERR | G_IO_NVAL,
4177                         otc_disconnected_cb, (gpointer) dev_path);
4178
4179         if (conn_info->role == BT_OTP_CLIENT_ROLE) {
4180                 msg = dbus_message_new_method_call(BT_OTC_SERVICE_NAME,
4181                                                         BT_OTC_OBJECT_PATH,
4182                                                         BT_OTC_INTERFACE_NAME,
4183                                                         "NewConnection");
4184         } else if (conn_info->role == BT_OTP_SERVER_ROLE) {
4185                 msg = dbus_message_new_method_call(BT_OTS_SERVICE_NAME,
4186                                                         BT_OTS_OBJECT_PATH,
4187                                                         BT_OTS_INTERFACE_NAME,
4188                                                         "NewConnection");
4189         }
4190
4191         if (!msg) {
4192                 error("Unable to create NewConnection call");
4193                 return;
4194         }
4195
4196         dbus_message_iter_init_append(msg, &iter);
4197
4198         dbus_message_iter_append_basic(&iter, DBUS_TYPE_OBJECT_PATH, &dev_path);
4199
4200         dbus_message_iter_append_basic(&iter, DBUS_TYPE_UNIX_FD, &fd);
4201
4202         if (!g_dbus_send_message(dbus_conn, msg)) {
4203                 error("sending NewConnection failed");
4204                 dbus_message_unref(msg);
4205         }
4206 }
4207
4208 int btd_adapter_connect_otc(struct btd_device *device)
4209 {
4210         struct btd_adapter *adapter = device_get_adapter(device);
4211         const bdaddr_t *src = btd_adapter_get_address(adapter);
4212         uint8_t src_type = btd_adapter_get_le_address_type(adapter);
4213         const bdaddr_t *dest = device_get_address(device);
4214         uint8_t dest_type = device->bdaddr_type;
4215         struct otc_conn_info *conn_info = NULL;
4216         const char *dev_path = device_get_path(device);
4217         GError *gerr = NULL;
4218
4219         conn_info = g_malloc0(sizeof(struct otc_conn_info));
4220
4221         conn_info->io = bt_io_connect(otc_connect_cb,
4222                                         (gpointer) dev_path, NULL, &gerr,
4223                                         BT_IO_OPT_SOURCE_BDADDR, src,
4224                                         BT_IO_OPT_SOURCE_TYPE, src_type,
4225                                         BT_IO_OPT_DEST_BDADDR, dest,
4226                                         BT_IO_OPT_DEST_TYPE, dest_type,
4227                                         BT_IO_OPT_PSM, OTP_PSM,
4228                                         BT_IO_OPT_SEC_LEVEL, BT_IO_SEC_LOW,
4229                                         BT_IO_OPT_INVALID);
4230
4231         if (!conn_info->io) {
4232                 error("OTC Connect failed : %s", gerr->message);
4233                 g_error_free(gerr);
4234                 g_free(conn_info);
4235                 return -EIO;
4236         }
4237
4238         conn_info->dev_path = dev_path;
4239         conn_info->role = BT_OTP_CLIENT_ROLE;
4240         conn_info->otc_connected = false;
4241         g_io_channel_set_close_on_unref(conn_info->io, FALSE);
4242
4243         otc_connection_list = g_slist_append(otc_connection_list, conn_info);
4244         return 0;
4245 }
4246
4247 static DBusMessage *connect_otc(DBusConnection *conn, DBusMessage *msg,
4248                                                         void *user_data)
4249 {
4250         struct btd_device *device = user_data;
4251         GSList *l;
4252
4253         if (device == NULL)
4254                 return btd_error_invalid_args(msg);
4255
4256         l = find_otc_conn_info(otc_connection_list, device_get_path(device));
4257
4258         if (l) {
4259                 struct otc_conn_info *info = l->data;
4260                 if (info->otc_connected)
4261                         return btd_error_already_connected(msg);
4262                 else
4263                         return btd_error_busy(msg);
4264         }
4265
4266         if (btd_adapter_connect_otc(device) != 0)
4267                 return btd_error_failed(msg, "ConnectFailed");
4268
4269         return dbus_message_new_method_return(msg);
4270 }
4271
4272 static DBusMessage *disconnect_otc(DBusConnection *conn, DBusMessage *msg,
4273                                                         void *user_data)
4274 {
4275         struct btd_device *device = user_data;
4276         struct otc_conn_info *info = NULL;
4277         GSList *l;
4278         int sock;
4279
4280         l = find_otc_conn_info(otc_connection_list, device_get_path(device));
4281
4282         if (!l)
4283                 return btd_error_does_not_exist(msg);
4284
4285         info = l->data;
4286
4287         if (!info->otc_connected)
4288                 return btd_error_not_connected(msg);
4289
4290         sock = g_io_channel_unix_get_fd(info->io);
4291
4292         shutdown(sock, SHUT_RDWR);
4293
4294         g_io_channel_shutdown(info->io, FALSE, NULL);
4295
4296         g_io_channel_unref(info->io);
4297         info->io = NULL;
4298
4299         return dbus_message_new_method_return(msg);
4300 }
4301
4302 int btd_adapter_listen_otc(struct btd_device *device)
4303 {
4304         struct btd_adapter *adapter = device_get_adapter(device);
4305         const bdaddr_t *src = btd_adapter_get_address(adapter);
4306         uint8_t type = btd_adapter_get_le_address_type(adapter);
4307         struct otc_conn_info *conn_info = NULL;
4308         const char *dev_path = device_get_path(device);
4309         GError *gerr = NULL;
4310
4311         conn_info = g_malloc0(sizeof(struct otc_conn_info));
4312
4313         conn_info->io = bt_io_listen(otc_connect_cb, NULL, (gpointer) dev_path,
4314                                 NULL, &gerr,
4315                                 BT_IO_OPT_SOURCE_BDADDR, src,
4316                                 BT_IO_OPT_SOURCE_TYPE, type,
4317                                 BT_IO_OPT_PSM, OTP_PSM,
4318                                 BT_IO_OPT_SEC_LEVEL, BT_IO_SEC_LOW,
4319                                 BT_IO_OPT_INVALID);
4320
4321         if (!conn_info->io) {
4322                 error("OTC Listen failed : %s", gerr->message);
4323                 g_error_free(gerr);
4324                 g_free(conn_info);
4325                 return -EIO;
4326         }
4327
4328         conn_info->dev_path = dev_path;
4329         conn_info->otc_connected = false;
4330         conn_info->role = BT_OTP_SERVER_ROLE;
4331         g_io_channel_set_close_on_unref(conn_info->io, FALSE);
4332
4333         otc_connection_list = g_slist_append(otc_connection_list, conn_info);
4334         return 0;
4335 }
4336
4337 static DBusMessage *listen_otc(DBusConnection *conn, DBusMessage *msg,
4338                                                         void *user_data)
4339 {
4340         struct btd_device *device = user_data;
4341         GSList *l;
4342
4343         if (device == NULL)
4344                 return btd_error_invalid_args(msg);
4345
4346         l = find_otc_conn_info(otc_connection_list, device_get_path(device));
4347
4348         if (l) {
4349                 struct otc_conn_info *info = l->data;
4350                 if (info->otc_connected)
4351                         return btd_error_already_connected(msg);
4352                 else
4353                         return btd_error_busy(msg);
4354         }
4355
4356         if (btd_adapter_listen_otc(device) != 0)
4357                 return btd_error_failed(msg, "ListenFailed");
4358
4359         return dbus_message_new_method_return(msg);
4360 }
4361 #endif
4362
4363 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
4364 /********************* L2CAP LE SOCKET IMPLEMENTATION *************************/
4365 static GSList *find_l2cap_le_profile_info(GSList *list, const char *owner,
4366                                                 const char *path)
4367 {
4368         GSList *l;
4369         for (l = list; l != NULL; l = g_slist_next(l)) {
4370                 struct l2cap_le_profile_info *info = l->data;
4371
4372                 if (!info)
4373                         continue;
4374
4375                 if (g_strcmp0(info->owner, owner))
4376                         continue;
4377
4378                 if (!g_strcmp0(info->path, path))
4379                         return l;
4380         }
4381
4382         return NULL;
4383 }
4384
4385 static int parse_l2cap_le_opt(struct l2cap_le_profile_info *info,
4386                                                 const char *key, DBusMessageIter *value)
4387 {
4388         int type = dbus_message_iter_get_arg_type(value);
4389         dbus_bool_t b;
4390
4391         if (strcasecmp(key, "RequireAuthentication") == 0) {
4392                 if (type != DBUS_TYPE_BOOLEAN)
4393                         return -EINVAL;
4394
4395                 dbus_message_iter_get_basic(value, &b);
4396
4397                 if (b)
4398                         info->sec_level = BT_IO_SEC_MEDIUM;
4399                 else
4400                         info->sec_level = BT_IO_SEC_LOW;
4401         } else if (strcasecmp(key, "RequireAuthorization") == 0) {
4402                 if (type != DBUS_TYPE_BOOLEAN)
4403                         return -EINVAL;
4404                 dbus_message_iter_get_basic(value, &b);
4405                 info->authorize = b;
4406         }
4407
4408         return 0;
4409 }
4410
4411 static struct l2cap_le_profile_info *create_l2cap_le_socket(const char *owner,
4412                                                 const char *path, int psm, DBusMessageIter *opts)
4413 {
4414         struct l2cap_le_profile_info *info = NULL;
4415
4416         if (psm < 0 || psm > BTD_L2CAP_LE_PSM_MAX)
4417                 return NULL;
4418
4419         info = g_malloc0(sizeof(struct l2cap_le_profile_info));
4420
4421         info->owner = g_strdup(owner);
4422         info->path = g_strdup(path);
4423         info->psm = psm;
4424
4425         while (dbus_message_iter_get_arg_type(opts) == DBUS_TYPE_DICT_ENTRY) {
4426                 DBusMessageIter value, entry;
4427                 const char *key;
4428
4429                 dbus_message_iter_recurse(opts, &entry);
4430                 dbus_message_iter_get_basic(&entry, &key);
4431
4432                 dbus_message_iter_next(&entry);
4433                 dbus_message_iter_recurse(&entry, &value);
4434
4435                 if (parse_l2cap_le_opt(info, key, &value) < 0)
4436                         error("Invalid value for l2cap_le_socket option %s", key);
4437
4438                 dbus_message_iter_next(opts);
4439         }
4440
4441         if (!info->name)
4442                 info->name = g_strdup_printf("%s%s/%d", owner, path, psm);
4443
4444         return info;
4445 }
4446
4447 static void l2cap_le_io_destroy(gpointer p)
4448 {
4449         struct l2cap_le_conn_info *conn = p;
4450
4451         if (conn->io_id > 0)
4452                 g_source_remove(conn->io_id);
4453
4454         if (conn->io) {
4455                 g_io_channel_shutdown(conn->io, FALSE, NULL);
4456                 g_io_channel_unref(conn->io);
4457         }
4458
4459         if (conn->auth_id != 0)
4460                 btd_cancel_authorization(conn->auth_id);
4461
4462         if (conn->auth_uuid)
4463                 free(conn->auth_uuid);
4464
4465         g_free(conn);
4466 }
4467
4468 static gboolean l2cap_le_disconnected_cb(GIOChannel *chan,
4469                                                 GIOCondition cond, gpointer user_data)
4470 {
4471         struct l2cap_le_conn_info *conn = user_data;
4472         struct l2cap_le_profile_info *info = conn->profile_info;
4473
4474         DBG(" L2CAP LE socket disconnected role [%s] ",
4475                         info->role == BT_L2CAP_LE_SERVER_ROLE ? "server" : "client");
4476
4477         g_dbus_emit_signal(dbus_conn, conn->dev_path,
4478                         DEVICE_INTERFACE, "L2CAPLEDisconnected",
4479                         DBUS_TYPE_INVALID);
4480
4481         conn->connected = false;
4482
4483         info->conn = g_slist_remove(info->conn, conn);
4484         l2cap_le_io_destroy(conn);
4485         return FALSE;
4486 }
4487
4488 static void l2cap_le_connect_cb(GIOChannel *chan, GError *gerr,
4489                                                 gpointer user_data)
4490 {
4491         struct l2cap_le_conn_info *conn = (struct l2cap_le_conn_info *) user_data;
4492         struct l2cap_le_profile_info *info = conn->profile_info;
4493         DBusMessage *msg = NULL;
4494         DBusMessageIter iter;
4495         const char *dev_path;
4496         int fd;
4497         GError *io_err = NULL;
4498         char addr[18];
4499
4500         if (!bt_io_get(chan, &io_err,
4501                                 BT_IO_OPT_DEST, addr,
4502                                 BT_IO_OPT_INVALID)) {
4503                 if (gerr) {
4504                         error("%s failed %s", info->name, gerr->message);
4505                         g_error_free(io_err);
4506                         io_err = NULL;
4507                 } else {
4508                         error("Unable to get connect data for %s: %s",
4509                                 info->name, io_err->message);
4510                         gerr = io_err;
4511                 }
4512                 goto drop;
4513         }
4514
4515         if (gerr != NULL) {
4516                 error("%s failed to connect to %s: %s", info->name, addr,
4517                                                                 gerr->message);
4518                 goto drop;
4519         }
4520
4521         conn->connected = true;
4522
4523         fd = g_io_channel_unix_get_fd(chan);
4524
4525         if (conn->io_id == 0)
4526                 conn->io_id = g_io_add_watch(chan, G_IO_HUP | G_IO_ERR | G_IO_NVAL,
4527                         l2cap_le_disconnected_cb, conn);
4528
4529         msg = dbus_message_new_method_call(info->owner,
4530                                                         info->path,
4531                                                         BT_L2CAP_LE_INTERFACE_NAME,
4532                                                         "NewConnection");
4533
4534         if (!msg) {
4535                 error("Unable to create NewConnection call");
4536                 goto drop;
4537         }
4538
4539         dev_path = conn->dev_path;
4540
4541         dbus_message_iter_init_append(msg, &iter);
4542
4543         dbus_message_iter_append_basic(&iter, DBUS_TYPE_OBJECT_PATH, &dev_path);
4544
4545         dbus_message_iter_append_basic(&iter, DBUS_TYPE_UNIX_FD, &fd);
4546
4547         if (!g_dbus_send_message(dbus_conn, msg)) {
4548                 error("sending NewConnection failed");
4549                 dbus_message_unref(msg);
4550                 goto drop;
4551         }
4552
4553         DBG("L2CAP_LE Connected fd [%d] addr [%s], role [%s]",fd, addr,
4554                         info->role == BT_L2CAP_LE_SERVER_ROLE ? "server" : "client");
4555         return;
4556
4557 drop:
4558         if (io_err)
4559                 g_error_free(io_err);
4560
4561         info->conn = g_slist_remove(info->conn, conn);
4562         l2cap_le_io_destroy(conn);
4563 }
4564
4565 static struct l2cap_le_conn_info *create_l2cap_le_conn(
4566                                                 struct l2cap_le_conn_info *server, GIOChannel *io,
4567                                                 bdaddr_t *src, bdaddr_t *dst, uint8_t dst_type)
4568 {
4569         struct l2cap_le_conn_info *conn;
4570         GIOCondition cond;
4571         struct btd_device *device;
4572         struct btd_adapter *adapter = adapter_find(src);
4573
4574         if (!adapter) {
4575                 error("could not find adapter");
4576                 return NULL;
4577         }
4578
4579         device = btd_adapter_get_device(adapter, dst, dst_type);
4580         if (!device) {
4581                 error("could not find Device");
4582                 return NULL;
4583         }
4584
4585         conn = g_new0(struct l2cap_le_conn_info, 1);
4586         conn->io = g_io_channel_ref(io);
4587         conn->profile_info = server->profile_info;
4588         conn->dev_path = device_get_path(device);
4589
4590         cond = G_IO_HUP | G_IO_ERR | G_IO_NVAL;
4591         conn->io_id = g_io_add_watch(io, cond, l2cap_le_disconnected_cb, conn);
4592
4593         return conn;
4594 }
4595
4596 static void l2cap_le_auth(DBusError *err, void *user_data)
4597 {
4598         struct l2cap_le_conn_info *conn = user_data;
4599         struct l2cap_le_profile_info *info = conn->profile_info;
4600         GError *gerr = NULL;
4601         char addr[18];
4602
4603         conn->auth_id = 0;
4604
4605         bt_io_get(conn->io, &gerr, BT_IO_OPT_DEST, addr, BT_IO_OPT_INVALID);
4606         if (gerr != NULL) {
4607                 error("Unable to get connect data for %s: %s",
4608                                                 info->name, gerr->message);
4609                 g_error_free(gerr);
4610                 goto drop;
4611         }
4612
4613         if (err && dbus_error_is_set(err)) {
4614                 error("%s rejected %s: %s", info->name, addr, err->message);
4615                 goto drop;
4616         }
4617
4618         if (!bt_io_accept(conn->io, l2cap_le_connect_cb, conn, NULL, &gerr)) {
4619                 error("bt_io_accept: %s", gerr->message);
4620                 g_error_free(gerr);
4621                 goto drop;
4622         }
4623
4624         DBG("%s authorized to connect to %s", addr, info->name);
4625         return;
4626
4627 drop:
4628         info->conn = g_slist_remove(info->conn, conn);
4629         l2cap_le_io_destroy(conn);
4630 }
4631
4632 static void l2cap_le_confirm(GIOChannel *io, gpointer user_data)
4633 {
4634         struct l2cap_le_conn_info *server = user_data;
4635         struct l2cap_le_profile_info *info = server->profile_info;
4636         struct l2cap_le_conn_info *conn;
4637         GError *gerr = NULL;
4638         uint8_t dst_type;
4639         bdaddr_t src, dst;
4640         char addr[18];
4641         char *uuid = g_malloc0(UUID_LEN * sizeof(char));
4642
4643         bt_io_get(io, &gerr,
4644                         BT_IO_OPT_SOURCE_BDADDR, &src,
4645                         BT_IO_OPT_DEST_BDADDR, &dst,
4646                         BT_IO_OPT_DEST_TYPE, &dst_type,
4647                         BT_IO_OPT_DEST, addr,
4648                         BT_IO_OPT_INVALID);
4649         if (gerr != NULL) {
4650                 error("%s failed to get connect data: %s", info->name,
4651                                                         gerr->message);
4652                 g_error_free(gerr);
4653                 return;
4654         }
4655
4656         DBG("incoming connect from %s for authorization", addr);
4657
4658         conn = create_l2cap_le_conn(server, io, &src, &dst, dst_type);
4659         if (conn == NULL)
4660                 return;
4661
4662         /* Use custom uuid of the form "FFFFFFFF-FFFF-FFFF-FFFF-<psm in 12 digits>"
4663         *  for authorizing l2cap_le socket using existing flow.
4664         *  This custom uuid will be used in the BT-OAL layer to identify the
4665         *  l2cap_le socket authorization and extracting psm from it.
4666         */
4667         snprintf(uuid, UUID_LEN, "%s%012d", L2CAP_LE_UUID_SUBSTR, server->psm);
4668         conn->auth_uuid = uuid;
4669
4670         conn->auth_id = btd_request_authorization(&src, &dst,
4671                                         (const char *)conn->auth_uuid, l2cap_le_auth, conn);
4672         if (conn->auth_id == 0) {
4673                 error("%s authorization failure", info->name);
4674                 l2cap_le_io_destroy(conn);
4675                 return;
4676         }
4677
4678         info->conn = g_slist_append(info->conn, conn);
4679
4680         DBG("%s authorizing connection from %s", info->name, addr);
4681 }
4682
4683 static void l2cap_le_direct_connect(GIOChannel *io, GError *err,
4684                                                 gpointer user_data)
4685 {
4686         struct l2cap_le_conn_info *server = user_data;
4687         struct l2cap_le_profile_info *info = server->profile_info;
4688         struct l2cap_le_conn_info *conn;
4689         GError *gerr = NULL;
4690         uint8_t dst_type;
4691         bdaddr_t src, dst;
4692
4693         bt_io_get(io, &gerr,
4694                         BT_IO_OPT_SOURCE_BDADDR, &src,
4695                         BT_IO_OPT_DEST_BDADDR, &dst,
4696                         BT_IO_OPT_DEST_TYPE, &dst_type,
4697                         BT_IO_OPT_INVALID);
4698         if (gerr != NULL) {
4699                 error("%s failed to get connect data: %s", info->name,
4700                                                                 gerr->message);
4701                 g_error_free(gerr);
4702                 return;
4703         }
4704
4705         conn = create_l2cap_le_conn(server, io, &src, &dst, dst_type);
4706         if (conn == NULL)
4707                 return;
4708
4709         info->conn = g_slist_append(info->conn, conn);
4710
4711         l2cap_le_connect_cb(io, err, conn);
4712 }
4713
4714 static void _remove_l2cap_le_socket(struct l2cap_le_profile_info *info)
4715 {
4716         l2cap_le_socket_list = g_slist_remove(l2cap_le_socket_list, info);
4717
4718         DBG("Removed \"%s\"", info->name);
4719
4720         if (info->server)
4721                 l2cap_le_io_destroy((gpointer)info->server);
4722         g_slist_free_full(info->conn, l2cap_le_io_destroy);
4723
4724         g_free(info->name);
4725         g_free(info->owner);
4726         g_free(info->path);
4727
4728         g_free(info);
4729 }
4730
4731 static void l2cap_le_socket_exited(DBusConnection *conn, void *user_data)
4732 {
4733         struct l2cap_le_profile_info *info = user_data;
4734
4735         DBG("l2cap le server \"%s\" exited", info->name);
4736
4737         _remove_l2cap_le_socket(info);
4738 }
4739
4740 static int _connect_l2cap_le(struct btd_device *device,
4741                                                 struct l2cap_le_profile_info *info)
4742 {
4743         struct btd_adapter *adapter = device_get_adapter(device);
4744         const bdaddr_t *src = btd_adapter_get_address(adapter);
4745         uint8_t src_type = btd_adapter_get_le_address_type(adapter);
4746         const bdaddr_t *dest = device_get_address(device);
4747         uint8_t dest_type = device->bdaddr_type;
4748         const char *dev_path = device_get_path(device);
4749         GError *gerr = NULL;
4750         struct l2cap_le_conn_info *conn = NULL;
4751
4752         conn = g_malloc0(sizeof(struct l2cap_le_conn_info));
4753         info->conn = g_slist_append(info->conn, conn);
4754
4755         conn->io = bt_io_connect(l2cap_le_connect_cb,
4756                                         conn, NULL, &gerr,
4757                                         BT_IO_OPT_SOURCE_BDADDR, src,
4758                                         BT_IO_OPT_SOURCE_TYPE, src_type,
4759                                         BT_IO_OPT_DEST_BDADDR, dest,
4760                                         BT_IO_OPT_DEST_TYPE, dest_type,
4761                                         BT_IO_OPT_PSM, info->psm,
4762                                         BT_IO_OPT_SEC_LEVEL, info->sec_level,
4763                                         BT_IO_OPT_INVALID);
4764
4765         if (!conn->io) {
4766                 error("L2CAP_LE Connect failed : %s", gerr->message);
4767                 g_error_free(gerr);
4768                 _remove_l2cap_le_socket(info);
4769                 return -EIO;
4770         }
4771
4772         info->role = BT_L2CAP_LE_CLIENT_ROLE;
4773         conn->dev_path = dev_path;
4774         conn->profile_info = info;
4775         conn->connected = false;
4776         g_io_channel_set_close_on_unref(conn->io, FALSE);
4777
4778         l2cap_le_socket_list = g_slist_append(l2cap_le_socket_list, info);
4779         return 0;
4780 }
4781
4782 static int _listen_l2cap_le(struct btd_adapter *adapter,
4783                                                 struct l2cap_le_profile_info *info)
4784 {
4785         const bdaddr_t *src = btd_adapter_get_address(adapter);
4786         uint8_t type = btd_adapter_get_le_address_type(adapter);
4787         GError *gerr = NULL;
4788         struct l2cap_le_conn_info *conn = NULL;
4789         BtIOConfirm confirm;
4790         BtIOConnect connect;
4791         int psm = 0;
4792
4793         if (info->authorize) {
4794                 confirm = l2cap_le_confirm;
4795                 connect = NULL;
4796         } else {
4797                 confirm = NULL;
4798                 connect = l2cap_le_direct_connect;
4799         }
4800
4801         conn = g_malloc0(sizeof(struct l2cap_le_conn_info));
4802         info->server = conn;
4803
4804         conn->io = bt_io_listen(connect, confirm, (gpointer)conn,
4805                                                         NULL, &gerr,
4806                                                         BT_IO_OPT_SOURCE_BDADDR, src,
4807                                                         BT_IO_OPT_SOURCE_TYPE, type,
4808                                                         BT_IO_OPT_PSM, info->psm,
4809                                                         BT_IO_OPT_SEC_LEVEL, info->sec_level,
4810                                                         BT_IO_OPT_INVALID);
4811
4812     if (!conn->io) {
4813                 error("L2cap_LE Listen failed : %s", gerr->message);
4814                 g_error_free(gerr);
4815                 _remove_l2cap_le_socket(info);
4816                 return -EIO;
4817     }
4818
4819         bt_io_get(conn->io, &gerr, BT_IO_OPT_PSM, &psm, BT_IO_OPT_INVALID);
4820
4821         DBG("L2CAP LE Socket listen to PSM %d successful", psm);
4822
4823         conn->connected = false;
4824         info->role = BT_L2CAP_LE_SERVER_ROLE;
4825         conn->psm = psm;
4826         conn->profile_info = info;
4827         g_io_channel_set_close_on_unref(conn->io, FALSE);
4828
4829         l2cap_le_socket_list = g_slist_append(l2cap_le_socket_list, info);
4830
4831         return 0;
4832 }
4833
4834 static DBusMessage *connect_l2cap_le_socket(DBusConnection *conn,
4835                                                 DBusMessage *msg, void *user_data)
4836 {
4837         struct btd_device *device = user_data;
4838         GSList *l;
4839         const char *path, *sender;
4840         dbus_int32_t psm;
4841         DBusMessageIter args, opts;
4842         struct l2cap_le_profile_info *info = NULL;
4843
4844         if (device == NULL)
4845                 return btd_error_invalid_args(msg);
4846
4847         sender = dbus_message_get_sender(msg);
4848
4849         dbus_message_iter_init(msg, &args);
4850         dbus_message_iter_get_basic(&args, &path);
4851         dbus_message_iter_next(&args);
4852
4853         dbus_message_iter_get_basic(&args, &psm);
4854         dbus_message_iter_next(&args);
4855
4856         l = find_l2cap_le_profile_info(l2cap_le_socket_list,  sender, path);
4857
4858         if (l) {
4859                 struct l2cap_le_profile_info *info = l->data;
4860                 if (info->conn) {
4861                         struct l2cap_le_conn_info *conn_info = info->conn->data;
4862                         if (conn_info && conn_info->connected)
4863                                 return btd_error_already_connected(msg);
4864                         else
4865                                 return btd_error_busy(msg);
4866                 } else {
4867                         error("Something is wrong!!!");
4868                         return btd_error_failed(msg, "ConnectFailed due to some internal error");
4869                 }
4870         }
4871
4872         if (dbus_message_iter_get_arg_type(&args) != DBUS_TYPE_ARRAY)
4873                 return btd_error_invalid_args(msg);
4874
4875         dbus_message_iter_recurse(&args, &opts);
4876
4877         info = create_l2cap_le_socket(sender, path, psm, &opts);
4878         if (!info)
4879                 return btd_error_invalid_args(msg);
4880
4881         info->role = BT_L2CAP_LE_CLIENT_ROLE;
4882
4883         DBG("connect l2cap l2 socket channel %d", (int)psm);
4884
4885         if (_connect_l2cap_le(device, info) != 0)
4886                 return btd_error_failed(msg, "ConnectFailed");
4887
4888         info->id = g_dbus_add_disconnect_watch(conn, sender, l2cap_le_socket_exited,
4889                                                         info, NULL);
4890
4891         return dbus_message_new_method_return(msg);
4892 }
4893
4894 DBusMessage *listen_l2cap_le_socket(DBusConnection *conn, DBusMessage *msg,
4895                                                 void *user_data)
4896 {
4897         struct btd_adapter *adapter = user_data;
4898         GSList *l;
4899         const char *path, *sender;
4900         dbus_int32_t psm;
4901         DBusMessageIter args, opts;
4902         struct l2cap_le_profile_info *info = NULL;
4903
4904         sender = dbus_message_get_sender(msg);
4905
4906         dbus_message_iter_init(msg, &args);
4907         dbus_message_iter_get_basic(&args, &path);
4908         dbus_message_iter_next(&args);
4909
4910         dbus_message_iter_get_basic(&args, &psm);
4911         dbus_message_iter_next(&args);
4912
4913         l = find_l2cap_le_profile_info(l2cap_le_socket_list, sender, path);
4914
4915         if (l)
4916                 return btd_error_already_exists(msg);
4917
4918         if (dbus_message_iter_get_arg_type(&args) != DBUS_TYPE_ARRAY)
4919                 return btd_error_invalid_args(msg);
4920
4921         dbus_message_iter_recurse(&args, &opts);
4922
4923         info = create_l2cap_le_socket(sender, path, psm, &opts);
4924         if (!info)
4925                 return btd_error_invalid_args(msg);
4926
4927         info->role = BT_L2CAP_LE_SERVER_ROLE;
4928
4929         DBG("listen l2cap_le socket to psm %d", (int)psm);
4930
4931         if (_listen_l2cap_le(adapter, info) != 0)
4932                 return btd_error_failed(msg, "ListenFailed");
4933
4934         info->id = g_dbus_add_disconnect_watch(conn, sender, l2cap_le_socket_exited,
4935                                                         info, NULL);
4936
4937         return dbus_message_new_method_return(msg);
4938 }
4939
4940 DBusMessage *get_psm_l2cap_le(DBusConnection *conn, DBusMessage *msg)
4941 {
4942         const char *path, *sender;
4943         int psm;
4944         GSList *l;
4945         DBusMessage *reply;
4946         DBusMessageIter args;
4947         struct l2cap_le_profile_info *info;
4948
4949         sender = dbus_message_get_sender(msg);
4950
4951         DBG("sender %s", sender);
4952
4953         dbus_message_iter_init(msg, &args);
4954
4955         dbus_message_iter_get_basic(&args, &path);
4956         dbus_message_iter_next(&args);
4957
4958         l = find_l2cap_le_profile_info(l2cap_le_socket_list, sender, path);
4959
4960         if (!l) {
4961                 DBG("L2cap LE socket not exist");
4962                 return btd_error_does_not_exist(msg);
4963         }
4964
4965         info = l->data;
4966
4967         if(info->server)
4968                 psm = info->server->psm;
4969         else
4970                 return btd_error_does_not_exist(msg);
4971
4972         reply = dbus_message_new_method_return(msg);
4973         if (!reply)
4974                 return btd_error_failed(msg,
4975                                         "Failed to create reply.");
4976
4977         dbus_message_append_args(reply,
4978                         DBUS_TYPE_UINT32, &psm,
4979                         DBUS_TYPE_INVALID);
4980
4981         return reply;
4982 }
4983
4984 DBusMessage *remove_l2cap_le_socket(DBusConnection *conn, DBusMessage *msg)
4985 {
4986         const char *path, *sender;
4987         struct l2cap_le_profile_info *info = NULL;
4988         GSList *l;
4989
4990         sender = dbus_message_get_sender(msg);
4991
4992         if (!dbus_message_get_args(msg, NULL, DBUS_TYPE_OBJECT_PATH, &path,
4993                                                         DBUS_TYPE_INVALID))
4994                 return btd_error_invalid_args(msg);
4995
4996         DBG("remove socket sender %s path %s", sender, path);
4997
4998         l = find_l2cap_le_profile_info(l2cap_le_socket_list, sender, path);
4999
5000         if (!l) {
5001                 DBG("L2cap LE socket not exist");
5002                 return btd_error_does_not_exist(msg);
5003         }
5004
5005         info = l->data;
5006
5007         g_dbus_remove_watch(conn, info->id);
5008         _remove_l2cap_le_socket(info);
5009
5010         return dbus_message_new_method_return(msg);
5011 }
5012 #endif
5013
5014 static DBusMessage *le_set_data_length(
5015                         DBusConnection *conn, DBusMessage *msg,
5016                         void *user_data)
5017 {
5018         dbus_uint16_t max_tx_octets;
5019         dbus_uint16_t max_tx_time;
5020         struct btd_device *device = user_data;
5021         int status;
5022         char addr[18];
5023
5024         if (!dbus_message_get_args(msg, NULL,
5025                                 DBUS_TYPE_UINT16, &max_tx_octets,
5026                                 DBUS_TYPE_UINT16, &max_tx_time,
5027                                 DBUS_TYPE_INVALID)) {
5028                 DBG("error in retrieving values");
5029                 return btd_error_invalid_args(msg);
5030         }
5031
5032         if (device->bdaddr_type == BDADDR_BREDR)
5033                 return btd_error_not_supported(msg);
5034
5035         ba2str(&device->bdaddr, addr);
5036
5037         DBG("Remote device address: %s", addr);
5038         DBG("Max tx octets: %u, Max tx time: %u",
5039                                 max_tx_octets, max_tx_time);
5040
5041         status = btd_adapter_le_set_data_length(device->adapter,
5042                                 &device->bdaddr, max_tx_octets,
5043                                 max_tx_time);
5044
5045         if (status != 0)
5046                 return btd_error_failed(msg, "Unable to set le data length values");
5047         else
5048                 return dbus_message_new_method_return(msg);
5049 }
5050
5051 static DBusMessage *set_trusted_profile(DBusConnection *conn,
5052                                                 DBusMessage *msg, void *data)
5053 {
5054         struct btd_device *dev = data;
5055         dbus_bool_t profile_trusted;
5056         const char *pattern;
5057         char *uuid;
5058         uint32_t pbap = dev->trusted_profiles.pbap;
5059         uint32_t map = dev->trusted_profiles.map;
5060         uint32_t sap = dev->trusted_profiles.sap;
5061         uint32_t hfp_hs = dev->trusted_profiles.hfp_hs;
5062         uint32_t a2dp = dev->trusted_profiles.a2dp;
5063
5064         if (!dbus_message_get_args(msg, NULL,
5065                                 DBUS_TYPE_STRING, &pattern,
5066                                 DBUS_TYPE_BOOLEAN, &profile_trusted,
5067                                 DBUS_TYPE_INVALID))
5068                 return btd_error_invalid_args(msg);
5069
5070         DBG("Pattern : %s", pattern);
5071         uuid = bt_name2string(pattern);
5072         DBG("UUID : %s", uuid);
5073         DBG("profile Trusted : %d %d %d", dev->trusted_profiles.pbap,
5074                         dev->trusted_profiles.map, dev->trusted_profiles.sap);
5075         DBG("profile Restricted : %d %d", dev->trusted_profiles.hfp_hs,
5076                         dev->trusted_profiles.a2dp);
5077         if (g_strcmp0(uuid, OBEX_PBAP_UUID) == 0) {
5078                 if (profile_trusted)
5079                         pbap = SUPPORTED_TRUSTED;
5080                 else
5081                         pbap = SUPPORTED_BLOCKED;
5082         } else if (g_strcmp0(uuid, OBEX_MAP_UUID) == 0) {
5083                 if (profile_trusted)
5084                         map = SUPPORTED_TRUSTED;
5085                 else
5086                         map = SUPPORTED_BLOCKED;
5087         } else if (g_strcmp0(uuid, SAP_UUID) == 0) {
5088                 if (profile_trusted)
5089                         sap = SUPPORTED_TRUSTED;
5090                 else
5091                         sap = SUPPORTED_BLOCKED;
5092         } else  if (g_strcmp0(uuid, HFP_HS_UUID) == 0) {
5093                 if (profile_trusted)
5094                         hfp_hs = SUPPORTED_TRUSTED;
5095                 else
5096                         hfp_hs = SUPPORTED_BLOCKED;
5097         } else if (g_strcmp0(uuid, A2DP_SINK_UUID) == 0) {
5098                 if (profile_trusted)
5099                         a2dp = SUPPORTED_TRUSTED;
5100                 else
5101                         a2dp = SUPPORTED_BLOCKED;
5102         } else {
5103                 free(uuid);
5104                 return btd_error_invalid_args(msg);
5105         }
5106
5107         free(uuid);
5108         btd_device_set_trusted_profiles(dev, pbap, map, sap, hfp_hs, a2dp);
5109         return dbus_message_new_method_return(msg);
5110 }
5111
5112 static DBusMessage *is_connected_profile(DBusConnection *conn, DBusMessage *msg,
5113                                                                         void *user_data)
5114 {
5115         struct btd_device *dev = user_data;
5116         struct btd_service *service;
5117         btd_service_state_t state;
5118         const char *pattern;
5119         char *uuid;
5120         DBusMessage *reply;
5121         dbus_bool_t val;
5122
5123         if (!dbus_message_get_args(msg, NULL, DBUS_TYPE_STRING, &pattern,
5124                                                         DBUS_TYPE_INVALID))
5125                 return btd_error_invalid_args(msg);
5126
5127         reply = dbus_message_new_method_return(msg);
5128         if (!reply)
5129                 return btd_error_invalid_args(reply);
5130
5131         uuid = bt_name2string(pattern);
5132         DBG("is_connected_profile_uuid : %s", uuid);
5133         service = btd_device_get_service(dev, uuid);
5134
5135         if ((service == NULL) && (g_strcmp0(uuid, HFP_HS_UUID) == 0)) {
5136                 DBG("HFP  service is not found check for HSP service");
5137                 service = btd_device_get_service(dev, HSP_HS_UUID);
5138         }
5139         if (uuid)
5140                 free(uuid);
5141
5142         if (!service)
5143                 return btd_error_not_connected(msg);
5144
5145         state = btd_service_get_state(service);
5146         DBG("Connected State : %d", state);
5147
5148         if (state == BTD_SERVICE_STATE_CONNECTED)
5149                 val = TRUE;
5150         else
5151                 val = FALSE;
5152
5153         dbus_message_append_args(reply,
5154                         DBUS_TYPE_BOOLEAN, &val,
5155                         DBUS_TYPE_INVALID);
5156
5157         return reply;
5158 }
5159
5160 static DBusMessage *update_le_conn_parm(DBusConnection *conn, DBusMessage *msg,
5161                                         void *user_data)
5162 {
5163         struct btd_device *device = user_data;
5164         GIOChannel *io;
5165         int fd;
5166         struct le_conn_param param = {0, 0, 0, 0};
5167         uint32_t min, max, latency, to_multiplier;
5168
5169         DBG("");
5170
5171         if (device == NULL) {
5172                 error("device is NULL");
5173                 return btd_error_invalid_args(msg);
5174         }
5175
5176         if (!device->le) {
5177                 error("le is not supported");
5178                 return btd_error_not_supported(msg);
5179         }
5180
5181         if (!device->gatt_connected || !device->attrib)
5182                 return btd_error_not_connected(msg);
5183
5184         io = g_attrib_get_channel(device->attrib);
5185         if (!io)
5186                 return btd_error_not_connected(msg);
5187
5188         fd = g_io_channel_unix_get_fd(io);
5189         if (fd < 0)
5190                 return btd_error_not_connected(msg);
5191
5192         if (device_get_conn_update_state(device))
5193                 return btd_error_in_progress(msg);
5194         else
5195                 device_set_conn_update_state(device, true);
5196
5197         if (!dbus_message_get_args(msg, NULL, DBUS_TYPE_UINT32, &min,
5198                                         DBUS_TYPE_UINT32, &max,
5199                                         DBUS_TYPE_UINT32, &latency,
5200                                         DBUS_TYPE_UINT32, &to_multiplier,
5201                                         DBUS_TYPE_INVALID)) {
5202                 error("Invalid args");
5203                 return btd_error_invalid_args(msg);
5204         }
5205
5206         if (min > UINT16_MAX || max > UINT16_MAX ||
5207                         latency > UINT16_MAX || to_multiplier > UINT16_MAX) {
5208                 error("Invalid args");
5209                 return btd_error_invalid_args(msg);
5210         }
5211         param.min = (uint16_t)min;
5212         param.max = (uint16_t)max;
5213         param.latency = (uint16_t)latency;
5214         param.to_multiplier = (uint16_t)to_multiplier;
5215
5216         if (setsockopt(fd, SOL_BLUETOOTH, BT_LE_CONN_PARAM,
5217                                 &param, sizeof(param)) < 0) {
5218                 error("Can't Update LE conn param : %s (%d)",
5219                                 strerror(errno), errno);
5220                 return btd_error_failed(msg, strerror(errno));
5221         }
5222
5223         return dbus_message_new_method_return(msg);
5224 }
5225
5226 static void device_request_att_mtu_reponse_cb(bool success, uint8_t att_ecode,
5227                                         void *user_data)
5228 {
5229         struct btd_device *device = user_data;
5230         DBusMessage *reply;
5231         DBusMessageIter iter;
5232         uint16_t mtu;
5233
5234         if (!device->req_att_mtu)
5235                 return;
5236
5237         mtu = bt_gatt_client_get_mtu(device->client);
5238
5239         if (!success) {
5240                 const char *err_if;
5241                 err_if = ERROR_INTERFACE ".Failed";
5242
5243                 reply = dbus_message_new_error(device->req_att_mtu, err_if,
5244                                                         "Request Att MTU failed");
5245                 g_dbus_send_message(dbus_conn, reply);
5246                 return;
5247         }
5248
5249         DBG("MTU exchange complete, with MTU: %u", mtu);
5250
5251         reply = dbus_message_new_method_return(device->req_att_mtu);
5252         if (!reply)
5253                 return;
5254
5255         dbus_message_iter_init_append(reply, &iter);
5256
5257         dbus_message_iter_append_basic(&iter, DBUS_TYPE_UINT16,
5258                                                         &mtu);
5259         dbus_message_iter_append_basic(&iter, DBUS_TYPE_BYTE,
5260                                                         &att_ecode);
5261         g_dbus_send_message(dbus_conn, reply);
5262
5263         dbus_message_unref(device->req_att_mtu);
5264         device->req_att_mtu = NULL;
5265 }
5266
5267 static DBusMessage *request_att_mtu(DBusConnection *conn, DBusMessage *msg,
5268                                         void *user_data)
5269 {
5270         struct btd_device *device = user_data;
5271         uint16_t mtu;
5272
5273         DBG("");
5274
5275         if (device == NULL) {
5276                 error("device is NULL");
5277                 return btd_error_invalid_args(msg);
5278         }
5279
5280         if (!device->le) {
5281                 error("le is not supported");
5282                 return btd_error_not_supported(msg);
5283         }
5284
5285         if (!device->gatt_connected || !device->attrib)
5286                 return btd_error_not_connected(msg);
5287
5288         if (!dbus_message_get_args(msg, NULL,
5289                                                 DBUS_TYPE_UINT16, &mtu,
5290                                                 DBUS_TYPE_INVALID)) {
5291                 error("Invalid args");
5292                 return btd_error_invalid_args(msg);
5293         }
5294
5295         DBG("MTU %d", mtu);
5296
5297         if (!bt_gatt_request_att_mtu(device->client, mtu,
5298                                 device_request_att_mtu_reponse_cb, device))
5299                 return btd_error_failed(msg, "Unable to Request MTU");
5300
5301         device->req_att_mtu = dbus_message_ref(msg);
5302         return NULL;
5303 }
5304
5305 static DBusMessage *device_get_ida(DBusConnection *conn, DBusMessage *msg,
5306                                                         void *user_data)
5307 {
5308         struct btd_device *device = user_data;
5309         char device_idaddr[18] = { 0 };
5310         DBusMessage *reply;
5311         const gchar *id_address = device_idaddr;
5312
5313         DBG("");
5314
5315         if (device == NULL)
5316                 return btd_error_invalid_args(msg);
5317
5318         if (!device->le) {
5319                 error("It doesn't support LE");
5320                 return btd_error_not_supported(msg);
5321         }
5322
5323         if (device->rpa) {
5324                 // There is the first RPA. So it's paired device.
5325                 if (device->bredr)
5326                         ba2str(device->rpa, device_idaddr);
5327                 else
5328                         ba2str(&device->bdaddr, device_idaddr);
5329         } else if (device->bdaddr_type != BDADDR_LE_RANDOM) {
5330                 // device->bdaddr is identity address.
5331                 ba2str(&device->bdaddr, device_idaddr);
5332         } else if ((device->bdaddr.b[5] >> 6) == 0x01) {
5333                 // RPA but it's not paired
5334                 return btd_error_does_not_exist(msg);
5335         } else if ((device->bdaddr.b[5] >> 6) == 0x03) {
5336                 // Static Random address
5337                 ba2str(&device->bdaddr, device_idaddr);
5338         } else {
5339                 // Non-RPA case
5340                 return btd_error_not_supported(msg);
5341         }
5342
5343         reply = dbus_message_new_method_return(msg);
5344         if (!reply)
5345                 return NULL;
5346
5347         dbus_message_append_args(reply, DBUS_TYPE_STRING, &id_address,
5348                                                         DBUS_TYPE_INVALID);
5349
5350         return reply;
5351 }
5352
5353 void device_set_conn_update_state(struct btd_device *device, bool state)
5354 {
5355         if (!device)
5356                 return;
5357
5358         device->pending_conn_update = state;
5359 }
5360
5361 bool device_get_conn_update_state(struct btd_device *device)
5362 {
5363         return device->pending_conn_update;
5364 }
5365 #endif
5366
5367 static const GDBusMethodTable device_methods[] = {
5368         { GDBUS_ASYNC_METHOD("Disconnect", NULL, NULL, dev_disconnect) },
5369         { GDBUS_ASYNC_METHOD("Connect", NULL, NULL, dev_connect) },
5370         { GDBUS_ASYNC_METHOD("ConnectProfile", GDBUS_ARGS({ "UUID", "s" }),
5371                                                 NULL, connect_profile) },
5372         { GDBUS_ASYNC_METHOD("DisconnectProfile", GDBUS_ARGS({ "UUID", "s" }),
5373                                                 NULL, disconnect_profile) },
5374 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
5375         { GDBUS_ASYNC_METHOD("DisconnectExtProfile",
5376                                         GDBUS_ARGS({ "profile", "o" }), NULL,
5377                                         disconnect_ext_profile) },
5378         { GDBUS_ASYNC_METHOD("Pair", GDBUS_ARGS({ "conn_type", "y" }), NULL,
5379                         pair_device) },
5380 #else
5381         { GDBUS_ASYNC_METHOD("Pair", NULL, NULL, pair_device) },
5382 #endif
5383         { GDBUS_METHOD("CancelPairing", NULL, NULL, cancel_pairing) },
5384 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
5385         { GDBUS_ASYNC_METHOD("ConnectLE", GDBUS_ARGS({ "auto_connect", "b"}),
5386                                                 NULL, connect_le) },
5387         { GDBUS_ASYNC_METHOD("DisconnectLE", NULL, NULL, disconnect_le) },
5388         { GDBUS_METHOD("IsConnectedProfile", GDBUS_ARGS({ "UUID", "s" }),
5389                         GDBUS_ARGS({ "IsConnected", "b" }),
5390                         is_connected_profile)},
5391         { GDBUS_METHOD("LeConnUpdate", GDBUS_ARGS({ "interval_min", "u" },
5392                                 { "interval_max", "u" }, { "latency", "u" },
5393                                 { "time_out", "u" }), NULL,
5394                         update_le_conn_parm) },
5395         { GDBUS_ASYNC_METHOD("DiscoverServices", GDBUS_ARGS({ "pattern", "s" }),
5396                         NULL, discover_services) },
5397         { GDBUS_METHOD("CancelDiscovery", NULL, NULL, cancel_discover) },
5398         { GDBUS_ASYNC_METHOD("ConnectIpsp", NULL, NULL, connect_ipsp) },
5399         { GDBUS_ASYNC_METHOD("DisconnectIpsp", NULL, NULL, disconnect_ipsp) },
5400 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
5401         { GDBUS_METHOD("ConnectOtc", NULL, NULL, connect_otc) },
5402         { GDBUS_METHOD("DisconnectOtc", NULL, NULL, disconnect_otc) },
5403         { GDBUS_METHOD("ListenOtc", NULL, NULL, listen_otc) },
5404         { GDBUS_ASYNC_METHOD("ConnectL2capLESocket",
5405                         GDBUS_ARGS({ "path", "o"}, { "psm", "i" }, { "options", "a{sv}" }),
5406                                                 NULL, connect_l2cap_le_socket) },
5407 #endif
5408         { GDBUS_ASYNC_METHOD("LESetDataLength",
5409                         GDBUS_ARGS({"max_tx_octets", "q" },
5410                         { "max_tx_time", "q" }), NULL,
5411                         le_set_data_length)},
5412         { GDBUS_ASYNC_METHOD("RequestAttMtu", GDBUS_ARGS({ "mtu", "q" }),
5413                         GDBUS_ARGS({ "mtu", "q" }, { "status", "y"}),
5414                         request_att_mtu) },
5415         { GDBUS_METHOD("GetIDAddress", NULL, GDBUS_ARGS({ "IDAdress", "s" }),
5416                         device_get_ida) },
5417         { GDBUS_METHOD("SetTrustedProfile",
5418                         GDBUS_ARGS({ "uuid", "s"}, { "trusted", "b"}), NULL,
5419                         set_trusted_profile) },
5420 #endif
5421         { }
5422 };
5423
5424 static const GDBusPropertyTable device_properties[] = {
5425         { "Address", "s", dev_property_get_address },
5426         { "AddressType", "s", property_get_address_type },
5427         { "Name", "s", dev_property_get_name, NULL, dev_property_exists_name },
5428         { "Alias", "s", dev_property_get_alias, dev_property_set_alias },
5429         { "Class", "u", dev_property_get_class, NULL,
5430                                         dev_property_exists_class },
5431         { "Appearance", "q", dev_property_get_appearance, NULL,
5432                                         dev_property_exists_appearance },
5433         { "Icon", "s", dev_property_get_icon, NULL,
5434                                         dev_property_exists_icon },
5435         { "Paired", "b", dev_property_get_paired },
5436         { "Trusted", "b", dev_property_get_trusted, dev_property_set_trusted },
5437         { "Blocked", "b", dev_property_get_blocked, dev_property_set_blocked },
5438         { "LegacyPairing", "b", dev_property_get_legacy },
5439         { "RSSI", "n", dev_property_get_rssi, NULL, dev_property_exists_rssi },
5440 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
5441         {"IsAliasSet", "b", dev_property_get_alias_set },
5442         { "Connected", "y", dev_property_get_connected },
5443 #else
5444         { "Connected", "b", dev_property_get_connected },
5445 #endif
5446         { "UUIDs", "as", dev_property_get_uuids },
5447         { "Modalias", "s", dev_property_get_modalias, NULL,
5448                                                 dev_property_exists_modalias },
5449         { "Adapter", "o", dev_property_get_adapter },
5450 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
5451          /* To handle Failed Legacy Pairing when initiated from Remote device*/
5452         { "LegacyPaired", "b", dev_property_get_paired },
5453         { "LegacyManufacturerDataLen", "q", property_get_manufacturer_data_len },
5454         { "LegacyManufacturerData", "ay", property_get_manufacturer_data },
5455         { "GattConnected", "b", dev_property_get_gatt_connected },
5456         { "PayloadTimeout", "q", dev_property_get_payload},
5457         { "LastAddrType", "y", dev_property_get_last_addr_type},
5458         { "IpspConnected", "b", dev_property_get_ipsp_conn_state },
5459         { "IpspBtInterfaceInfo", "s", dev_property_get_ipsp_conn_bt_iface_name },
5460         { "AttMtu", "q", dev_property_get_att_mtu },
5461         { "TrustedProfiles", "u", dev_property_get_trusted_profiles},
5462 #endif
5463         { "ManufacturerData", "a{qv}", dev_property_get_manufacturer_data,
5464                                 NULL, dev_property_manufacturer_data_exist },
5465         { "ServiceData", "a{sv}", dev_property_get_service_data,
5466                                 NULL, dev_property_service_data_exist },
5467         { "TxPower", "n", dev_property_get_tx_power, NULL,
5468                                         dev_property_exists_tx_power },
5469         { "ServicesResolved", "b", dev_property_get_svc_resolved, NULL, NULL },
5470         { "AdvertisingFlags", "ay", dev_property_get_flags, NULL,
5471                                         dev_property_flags_exist,
5472                                         G_DBUS_PROPERTY_FLAG_EXPERIMENTAL},
5473         { "AdvertisingData", "a{yv}", dev_property_get_advertising_data,
5474                                 NULL, dev_property_advertising_data_exist,
5475                                 G_DBUS_PROPERTY_FLAG_EXPERIMENTAL },
5476         { "WakeAllowed", "b", dev_property_get_wake_allowed,
5477                                 dev_property_set_wake_allowed,
5478                                 dev_property_wake_allowed_exist },
5479         { }
5480 };
5481
5482 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
5483 static const GDBusSignalTable device_signals[] = {
5484         { GDBUS_SIGNAL("Disconnected",
5485                         GDBUS_ARGS({ "bdaddr_type", "y" }, { "reason", "y" },
5486                                 { "name", "s" })) },
5487         { GDBUS_SIGNAL("DeviceConnected", GDBUS_ARGS({ "bdaddr_type", "y"})) },
5488         { GDBUS_SIGNAL("ProfileStateChanged",
5489                         GDBUS_ARGS({ "profile", "s"}, {"state", "i"})) },
5490         { GDBUS_SIGNAL("AdvReport",
5491                         GDBUS_ARGS({"Address","s"}, { "Address Type", "y" },
5492                                 { "Adv Type", "y"}, { "RSSI", "i"},
5493                                 { "AdvDataLen", "i"}, { "AdvData", "ay"})) },
5494         { GDBUS_SIGNAL("LEDataLengthChanged",
5495                         GDBUS_ARGS({"max_tx_octets","q"},
5496                                 { "max_tx_time", "q" },
5497                                 { "max_rx_octets", "q"},
5498                                 { "max_rx_time", "q"}))},
5499         { GDBUS_SIGNAL("IpspStateChanged",
5500                         GDBUS_ARGS({"connected","b"}, {"if_name","s"}))},
5501         { GDBUS_SIGNAL("OtcDisconnected", NULL)},
5502         { GDBUS_SIGNAL("AttMtuChanged",
5503                         GDBUS_ARGS({"mtu", "q"})) },
5504         { }
5505 };
5506 #endif
5507
5508 uint8_t btd_device_get_bdaddr_type(struct btd_device *dev)
5509 {
5510         return dev->bdaddr_type;
5511 }
5512
5513 bool btd_device_is_connected(struct btd_device *dev)
5514 {
5515         return dev->bredr_state.connected || dev->le_state.connected;
5516 }
5517
5518 static void clear_temporary_timer(struct btd_device *dev)
5519 {
5520         if (dev->temporary_timer) {
5521                 timeout_remove(dev->temporary_timer);
5522                 dev->temporary_timer = 0;
5523         }
5524 }
5525
5526 void device_add_connection(struct btd_device *dev, uint8_t bdaddr_type)
5527 {
5528         struct bearer_state *state = get_state(dev, bdaddr_type);
5529
5530         device_update_last_seen(dev, bdaddr_type);
5531
5532         if (state->connected) {
5533                 char addr[18];
5534                 ba2str(&dev->bdaddr, addr);
5535                 error("Device %s is already connected", addr);
5536                 return;
5537         }
5538
5539         bacpy(&dev->conn_bdaddr, &dev->bdaddr);
5540         dev->conn_bdaddr_type = dev->bdaddr_type;
5541
5542         /* If this is the first connection over this bearer */
5543         if (bdaddr_type == BDADDR_BREDR)
5544                 device_set_bredr_support(dev);
5545         else
5546                 device_set_le_support(dev, bdaddr_type);
5547
5548         state->connected = true;
5549
5550 #ifndef TIZEN_FEATURE_BLUEZ_MODIFY
5551         if (dev->le_state.connected && dev->bredr_state.connected)
5552                 return;
5553
5554         /* Remove temporary timer while connected */
5555         clear_temporary_timer(dev);
5556
5557         g_dbus_emit_property_changed(dbus_conn, dev->path, DEVICE_INTERFACE,
5558                                                                 "Connected");
5559 #else
5560 #ifdef TIZEN_FEATURE_BLUEZ_BATTERY_WATCH
5561         if (bdaddr_type == BDADDR_BREDR &&
5562             get_charging_state(dev->adapter) == WIRELESS_CHARGING) {
5563                 int br_pkt_type = ACL_PTYPE_MASK |
5564                         HCI_2DH1 | HCI_2DH3 | HCI_2DH5 |
5565                         HCI_3DH1 | HCI_3DH3 | HCI_3DH5;
5566
5567                 DBG("During wireless charging... Change packet type");
5568                 device_change_pkt_type(dev, (gpointer)br_pkt_type);
5569         }
5570 #endif  /* TIZEN_FEATURE_BLUEZ_BATTERY_WATCH */
5571
5572         g_dbus_emit_signal(dbus_conn, dev->path,
5573                 DEVICE_INTERFACE, "DeviceConnected",
5574                 DBUS_TYPE_BYTE, &bdaddr_type,
5575                 DBUS_TYPE_INVALID);
5576 #endif
5577 }
5578
5579 void device_remove_connection(struct btd_device *device, uint8_t bdaddr_type)
5580 {
5581         struct bearer_state *state = get_state(device, bdaddr_type);
5582         DBusMessage *reply;
5583 #ifndef TIZEN_FEATURE_BLUEZ_MODIFY
5584         bool remove_device = false;
5585 #endif
5586         bool paired_status_updated = false;
5587 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
5588         char *dev_name = device->name;
5589 #endif
5590
5591         if (!state->connected)
5592                 return;
5593
5594         state->connected = false;
5595         device->general_connect = FALSE;
5596
5597         device_set_svc_refreshed(device, false);
5598
5599         if (device->disconn_timer > 0) {
5600                 timeout_remove(device->disconn_timer);
5601                 device->disconn_timer = 0;
5602         }
5603
5604 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
5605         if (device->browse) {
5606                 struct browse_req *req = device->browse;
5607
5608                 if ((bdaddr_type == BDADDR_BREDR && req->search_uuid != 0) ||
5609                     (bdaddr_type != BDADDR_BREDR && req->search_uuid == 0))
5610                         device->browse = NULL;
5611                 else
5612                         DBG("device->browse is for other link");
5613         }
5614 #endif
5615
5616         /* This could be executed while the client is waiting for Connect() but
5617          * att_connect_cb has not been invoked.
5618          * In that case reply the client that the connection failed.
5619          */
5620         if (device->connect) {
5621                 DBG("connection removed while Connect() is waiting reply");
5622                 reply = btd_error_failed(device->connect,
5623                                                 ERR_BREDR_CONN_CANCELED);
5624                 g_dbus_send_message(dbus_conn, reply);
5625                 dbus_message_unref(device->connect);
5626                 device->connect = NULL;
5627         }
5628
5629         while (device->disconnects) {
5630                 DBusMessage *msg = device->disconnects->data;
5631
5632 #ifndef TIZEN_FEATURE_BLUEZ_MODIFY
5633                 if (dbus_message_is_method_call(msg, ADAPTER_INTERFACE,
5634                                                                 "RemoveDevice"))
5635                         remove_device = true;
5636 #endif
5637                 g_dbus_send_reply(dbus_conn, msg, DBUS_TYPE_INVALID);
5638                 device->disconnects = g_slist_remove(device->disconnects, msg);
5639                 dbus_message_unref(msg);
5640         }
5641
5642         /* Check paired status of both bearers since it's possible to be
5643          * paired but not connected via link key to LTK conversion.
5644          */
5645         if (!device->bredr_state.connected && device->bredr_state.paired &&
5646                                                 !device->bredr_state.bonded) {
5647                 btd_adapter_remove_bonding(device->adapter,
5648                                                 &device->bdaddr,
5649                                                 BDADDR_BREDR);
5650                 device->bredr_state.paired = false;
5651                 paired_status_updated = true;
5652         }
5653
5654         if (!device->le_state.connected && device->le_state.paired &&
5655                                                 !device->le_state.bonded) {
5656                 btd_adapter_remove_bonding(device->adapter,
5657                                                 &device->bdaddr,
5658                                                 device->bdaddr_type);
5659                 device->le_state.paired = false;
5660                 paired_status_updated = true;
5661         }
5662
5663         /* report change only if both bearers are unpaired */
5664         if (!device->bredr_state.paired && !device->le_state.paired &&
5665                                                         paired_status_updated)
5666                 g_dbus_emit_property_changed(dbus_conn, device->path,
5667                                                 DEVICE_INTERFACE,
5668                                                 "Paired");
5669
5670
5671 #ifndef TIZEN_FEATURE_BLUEZ_MODIFY
5672         if (device->bredr_state.connected || device->le_state.connected)
5673                 return;
5674
5675         device_update_last_seen(device, bdaddr_type);
5676
5677         g_slist_free_full(device->eir_uuids, g_free);
5678         device->eir_uuids = NULL;
5679
5680         g_dbus_emit_property_changed(dbus_conn, device->path,
5681                                                 DEVICE_INTERFACE, "Connected");
5682
5683         if (remove_device)
5684                 btd_adapter_remove_device(device->adapter, device);
5685 #else
5686         g_dbus_emit_signal(dbus_conn, device->path,
5687                 DEVICE_INTERFACE, "Disconnected",
5688                 DBUS_TYPE_BYTE, &bdaddr_type,
5689                 DBUS_TYPE_BYTE, &device->disc_reason,
5690                 DBUS_TYPE_STRING, &dev_name,
5691                 DBUS_TYPE_INVALID);
5692 #endif
5693 }
5694
5695 guint device_add_disconnect_watch(struct btd_device *device,
5696                                 disconnect_watch watch, void *user_data,
5697                                 GDestroyNotify destroy)
5698 {
5699         struct btd_disconnect_data *data;
5700         static guint id = 0;
5701
5702         data = g_new0(struct btd_disconnect_data, 1);
5703         data->id = ++id;
5704         data->watch = watch;
5705         data->user_data = user_data;
5706         data->destroy = destroy;
5707
5708         device->watches = g_slist_append(device->watches, data);
5709
5710         return data->id;
5711 }
5712
5713 void device_remove_disconnect_watch(struct btd_device *device, guint id)
5714 {
5715         GSList *l;
5716
5717         for (l = device->watches; l; l = l->next) {
5718                 struct btd_disconnect_data *data = l->data;
5719
5720                 if (data->id == id) {
5721                         device->watches = g_slist_remove(device->watches,
5722                                                         data);
5723                         if (data->destroy)
5724                                 data->destroy(data->user_data);
5725                         g_free(data);
5726                         return;
5727                 }
5728         }
5729 }
5730
5731 static char *load_cached_name(struct btd_device *device, const char *local,
5732                                 const char *peer)
5733 {
5734         char filename[PATH_MAX];
5735         GKeyFile *key_file;
5736         char *str = NULL;
5737         int len;
5738
5739         if (device_address_is_private(device))
5740                 return NULL;
5741
5742         snprintf(filename, PATH_MAX, STORAGEDIR "/%s/cache/%s", local, peer);
5743
5744         key_file = g_key_file_new();
5745
5746         if (!g_key_file_load_from_file(key_file, filename, 0, NULL))
5747                 goto failed;
5748
5749         str = g_key_file_get_string(key_file, "General", "Name", NULL);
5750         if (str) {
5751                 len = strlen(str);
5752                 if (len > HCI_MAX_NAME_LENGTH)
5753                         str[HCI_MAX_NAME_LENGTH] = '\0';
5754         }
5755
5756 failed:
5757         g_key_file_free(key_file);
5758
5759         return str;
5760 }
5761
5762 static struct csrk_info *load_csrk(GKeyFile *key_file, const char *group)
5763 {
5764         struct csrk_info *csrk;
5765         char *str;
5766         int i;
5767
5768         str = g_key_file_get_string(key_file, group, "Key", NULL);
5769         if (!str)
5770                 return NULL;
5771
5772         csrk = g_new0(struct csrk_info, 1);
5773
5774         for (i = 0; i < 16; i++) {
5775                 if (sscanf(str + (i * 2), "%2hhx", &csrk->key[i]) != 1)
5776                         goto fail;
5777         }
5778
5779         /*
5780          * In case of older storage this will return 0 which is fine since it
5781          * didn't support signing at that point the counter should never have
5782          * been used.
5783          */
5784         csrk->counter = g_key_file_get_integer(key_file, group, "Counter",
5785                                                                         NULL);
5786         g_free(str);
5787
5788         return csrk;
5789
5790 fail:
5791         g_free(str);
5792         g_free(csrk);
5793         return NULL;
5794 }
5795
5796 static void load_services(struct btd_device *device, char **uuids)
5797 {
5798         char **uuid;
5799
5800         for (uuid = uuids; *uuid; uuid++) {
5801                 if (g_slist_find_custom(device->uuids, *uuid, bt_uuid_strcmp))
5802                         continue;
5803
5804                 device->uuids = g_slist_insert_sorted(device->uuids,
5805                                                         g_strdup(*uuid),
5806                                                         bt_uuid_strcmp);
5807         }
5808
5809         g_strfreev(uuids);
5810 }
5811
5812 static void convert_info(struct btd_device *device, GKeyFile *key_file)
5813 {
5814         char filename[PATH_MAX];
5815         char adapter_addr[18];
5816         char device_addr[18];
5817         char **uuids;
5818         char *str;
5819         gsize length = 0;
5820         GError *gerr = NULL;
5821
5822         /* Load device profile list from legacy properties */
5823         uuids = g_key_file_get_string_list(key_file, "General", "SDPServices",
5824                                                                 NULL, NULL);
5825         if (uuids)
5826                 load_services(device, uuids);
5827
5828         uuids = g_key_file_get_string_list(key_file, "General", "GATTServices",
5829                                                                 NULL, NULL);
5830         if (uuids)
5831                 load_services(device, uuids);
5832
5833         if (!device->uuids)
5834                 return;
5835
5836         /* Remove old entries so they are not loaded again */
5837         g_key_file_remove_key(key_file, "General", "SDPServices", NULL);
5838         g_key_file_remove_key(key_file, "General", "GATTServices", NULL);
5839
5840         ba2str(btd_adapter_get_address(device->adapter), adapter_addr);
5841         ba2str(&device->bdaddr, device_addr);
5842         snprintf(filename, PATH_MAX, STORAGEDIR "/%s/%s/info", adapter_addr,
5843                         device_addr);
5844
5845         str = g_key_file_to_data(key_file, &length, NULL);
5846         if (!g_file_set_contents(filename, str, length, &gerr)) {
5847                 error("Unable set contents for %s: (%s)", filename,
5848                                                                 gerr->message);
5849                 g_error_free(gerr);
5850         }
5851         g_free(str);
5852
5853         store_device_info(device);
5854 }
5855
5856 static void load_info(struct btd_device *device, const char *local,
5857                         const char *peer, GKeyFile *key_file)
5858 {
5859         GError *gerr = NULL;
5860         char *str;
5861         gboolean store_needed = FALSE;
5862         gboolean blocked;
5863         gboolean wake_allowed;
5864         char **uuids;
5865         int source, vendor, product, version;
5866         char **techno, **t;
5867 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
5868         gboolean svc_change_regd;
5869         char buf[DEV_MAX_MANUFACTURER_DATA_LEN] = { 0, };
5870 #endif
5871         /* Load device name from storage info file, if that fails fall back to
5872          * the cache.
5873          */
5874         str = g_key_file_get_string(key_file, "General", "Name", NULL);
5875         if (str == NULL) {
5876                 str = load_cached_name(device, local, peer);
5877                 if (str)
5878                         store_needed = TRUE;
5879         }
5880
5881         if (str) {
5882                 strcpy(device->name, str);
5883                 g_free(str);
5884         }
5885
5886         /* Load alias */
5887         device->alias = g_key_file_get_string(key_file, "General", "Alias",
5888                                                                         NULL);
5889
5890         /* Load class */
5891         str = g_key_file_get_string(key_file, "General", "Class", NULL);
5892         if (str) {
5893                 uint32_t class;
5894
5895                 if (sscanf(str, "%x", &class) == 1)
5896                         device->class = class;
5897                 g_free(str);
5898         }
5899
5900         /* Load appearance */
5901         str = g_key_file_get_string(key_file, "General", "Appearance", NULL);
5902         if (str) {
5903                 device->appearance = strtol(str, NULL, 16);
5904                 g_free(str);
5905         }
5906
5907 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
5908         /* Load RPA Resolution Support value */
5909         device->rpa_res_support = g_key_file_get_integer(key_file,
5910                                                         "General", "RPAResSupport", NULL);
5911
5912         str = g_key_file_get_string(key_file, "General", "LegacyManufacturerDataLen", NULL);
5913         if (str) {
5914                 device->manufacturer_data_len = strtol(str, NULL, 10);
5915                 g_free(str);
5916
5917                 if (0 > device->manufacturer_data_len) {
5918                         error("Invalid manufacturer_data_len: %d",
5919                                         device->manufacturer_data_len);
5920                         device->manufacturer_data_len = 0;
5921                 }
5922
5923                 str = g_key_file_get_string(key_file, "General", "LegacyManufacturerData", NULL);
5924                 if (str) {
5925                         if (device->manufacturer_data_len < DEV_MAX_MANUFACTURER_DATA_LEN) {
5926                                 load_manufacturer_data_2digit(str,
5927                                                         device->manufacturer_data_len,  buf);
5928                                 device->manufacturer_data = g_memdup(buf,
5929                                                         device->manufacturer_data_len);
5930                         }
5931                         g_free(str);
5932                 }
5933         }
5934
5935         str = g_key_file_get_string(key_file, "General", "IdentityAddress",
5936                                                                 NULL);
5937
5938         if (str) {
5939                 device->rpa = g_malloc0(sizeof(bdaddr_t));
5940                 bacpy(device->rpa, &device->bdaddr);
5941                 str2ba(str, &device->bdaddr);
5942                 g_free(str);
5943         }
5944 #endif
5945
5946         /* Load device technology */
5947         techno = g_key_file_get_string_list(key_file, "General",
5948                                         "SupportedTechnologies", NULL, NULL);
5949         if (!techno)
5950                 goto next;
5951
5952         for (t = techno; *t; t++) {
5953                 if (g_str_equal(*t, "BR/EDR"))
5954                         device->bredr = true;
5955                 else if (g_str_equal(*t, "LE"))
5956                         device->le = true;
5957                 else
5958                         error("Unknown device technology");
5959         }
5960
5961         if (!device->le) {
5962                 device->bdaddr_type = BDADDR_BREDR;
5963         } else {
5964                 str = g_key_file_get_string(key_file, "General",
5965                                                 "AddressType", NULL);
5966
5967                 if (str && g_str_equal(str, "public"))
5968                         device->bdaddr_type = BDADDR_LE_PUBLIC;
5969                 else if (str && g_str_equal(str, "static"))
5970                         device->bdaddr_type = BDADDR_LE_RANDOM;
5971                 else
5972                         error("Unknown LE device technology");
5973
5974                 g_free(str);
5975
5976                 device->local_csrk = load_csrk(key_file, "LocalSignatureKey");
5977                 device->remote_csrk = load_csrk(key_file, "RemoteSignatureKey");
5978         }
5979
5980         g_strfreev(techno);
5981
5982 next:
5983         /* Load trust */
5984         device->trusted = g_key_file_get_boolean(key_file, "General",
5985                                                         "Trusted", NULL);
5986
5987 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
5988         /* Load Trusted Profiles*/
5989         int trusted_profiles = g_key_file_get_integer(key_file, "General",
5990                                                         "TrustedProfiles", NULL);
5991         DBG("Loading TrustedProfiles %d", trusted_profiles);
5992         device->trusted_profiles.pbap = ((trusted_profiles &
5993                         (PROFILE_SUPPORTED << PBAP_SHIFT_OFFSET)) >> PBAP_SHIFT_OFFSET);
5994         device->trusted_profiles.map = ((trusted_profiles &
5995                         (PROFILE_SUPPORTED << MAP_SHIFT_OFFSET)) >> MAP_SHIFT_OFFSET);
5996         device->trusted_profiles.sap = ((trusted_profiles &
5997                         (PROFILE_SUPPORTED << SAP_SHIFT_OFFSET)) >> SAP_SHIFT_OFFSET);
5998         device->trusted_profiles.hfp_hs = ((trusted_profiles &
5999                         (PROFILE_SUPPORTED << HFP_HS_SHIFT_OFFSET)) >> HFP_HS_SHIFT_OFFSET);
6000         device->trusted_profiles.a2dp = ((trusted_profiles &
6001                         (PROFILE_SUPPORTED << A2DP_SHIFT_OFFSET)) >> A2DP_SHIFT_OFFSET);
6002
6003 #endif
6004
6005         /* Load device blocked */
6006         blocked = g_key_file_get_boolean(key_file, "General", "Blocked", NULL);
6007         if (blocked)
6008                 device_block(device, FALSE);
6009
6010         /* Load device profile list */
6011         uuids = g_key_file_get_string_list(key_file, "General", "Services",
6012                                                 NULL, NULL);
6013         if (uuids) {
6014                 load_services(device, uuids);
6015
6016                 /* Discovered services restored from storage */
6017                 device->bredr_state.svc_resolved = true;
6018         }
6019
6020         /* Load device id */
6021         source = g_key_file_get_integer(key_file, "DeviceID", "Source", NULL);
6022         if (source) {
6023                 vendor = g_key_file_get_integer(key_file, "DeviceID",
6024                                                         "Vendor", NULL);
6025
6026                 product = g_key_file_get_integer(key_file, "DeviceID",
6027                                                         "Product", NULL);
6028
6029                 version = g_key_file_get_integer(key_file, "DeviceID",
6030                                                         "Version", NULL);
6031
6032                 btd_device_set_pnpid(device, source, vendor, product, version);
6033         }
6034
6035         /* Wake allowed is only configured and stored if user changed it.
6036          * Otherwise, we enable if profile supports it.
6037          */
6038         wake_allowed = g_key_file_get_boolean(key_file, "General",
6039                                               "WakeAllowed", &gerr);
6040         if (!gerr) {
6041                 device_set_wake_override(device, wake_allowed);
6042         } else {
6043                 g_error_free(gerr);
6044                 gerr = NULL;
6045         }
6046
6047 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
6048         /* Load Service changed Registered flag */
6049         svc_change_regd = g_key_file_get_boolean(key_file, "Att",
6050                                                 "SvcChangeRegd", NULL);
6051
6052         bt_att_set_svc_changed_indication_registered(device->att,
6053                                                 svc_change_regd);
6054 #endif
6055
6056         if (store_needed)
6057                 store_device_info(device);
6058 }
6059
6060 static void load_att_info(struct btd_device *device, const char *local,
6061                                 const char *peer)
6062 {
6063         char filename[PATH_MAX];
6064         GKeyFile *key_file;
6065         GError *gerr = NULL;
6066         char *prim_uuid, *str;
6067         char **groups, **handle, *service_uuid;
6068         struct gatt_primary *prim;
6069         uuid_t uuid;
6070         char tmp[3];
6071         int i;
6072
6073         sdp_uuid16_create(&uuid, GATT_PRIM_SVC_UUID);
6074         prim_uuid = bt_uuid2string(&uuid);
6075
6076         snprintf(filename, PATH_MAX, STORAGEDIR "/%s/%s/attributes", local,
6077                         peer);
6078
6079         key_file = g_key_file_new();
6080         if (!g_key_file_load_from_file(key_file, filename, 0, &gerr)) {
6081                 error("Unable to load key file from %s: (%s)", filename,
6082                                                                 gerr->message);
6083                 g_error_free(gerr);
6084         }
6085         groups = g_key_file_get_groups(key_file, NULL);
6086
6087         for (handle = groups; *handle; handle++) {
6088                 gboolean uuid_ok;
6089                 int end;
6090
6091                 str = g_key_file_get_string(key_file, *handle, "UUID", NULL);
6092                 if (!str)
6093                         continue;
6094
6095                 uuid_ok = g_str_equal(str, prim_uuid);
6096                 g_free(str);
6097
6098                 if (!uuid_ok)
6099                         continue;
6100
6101                 str = g_key_file_get_string(key_file, *handle, "Value", NULL);
6102                 if (!str)
6103                         continue;
6104
6105                 end = g_key_file_get_integer(key_file, *handle,
6106                                                 "EndGroupHandle", NULL);
6107                 if (end == 0) {
6108                         g_free(str);
6109                         continue;
6110                 }
6111
6112                 prim = g_new0(struct gatt_primary, 1);
6113                 prim->range.start = atoi(*handle);
6114                 prim->range.end = end;
6115
6116                 switch (strlen(str)) {
6117                 case 4:
6118                         uuid.type = SDP_UUID16;
6119                         sscanf(str, "%04hx", &uuid.value.uuid16);
6120                 break;
6121                 case 8:
6122                         uuid.type = SDP_UUID32;
6123                         sscanf(str, "%08x", &uuid.value.uuid32);
6124                         break;
6125                 case 32:
6126                         uuid.type = SDP_UUID128;
6127                         memset(tmp, 0, sizeof(tmp));
6128                         for (i = 0; i < 16; i++) {
6129                                 memcpy(tmp, str + (i * 2), 2);
6130                                 uuid.value.uuid128.data[i] =
6131                                                 (uint8_t) strtol(tmp, NULL, 16);
6132                         }
6133                         break;
6134                 default:
6135                         g_free(str);
6136                         g_free(prim);
6137                         continue;
6138                 }
6139
6140                 service_uuid = bt_uuid2string(&uuid);
6141                 memcpy(prim->uuid, service_uuid, MAX_LEN_UUID_STR);
6142                 free(service_uuid);
6143                 g_free(str);
6144
6145                 device->primaries = g_slist_append(device->primaries, prim);
6146         }
6147
6148         g_strfreev(groups);
6149         g_key_file_free(key_file);
6150         free(prim_uuid);
6151 }
6152
6153 static void device_register_primaries(struct btd_device *device,
6154                                                 GSList *prim_list, int psm)
6155 {
6156         device->primaries = g_slist_concat(device->primaries, prim_list);
6157 }
6158
6159 static void add_primary(struct gatt_db_attribute *attr, void *user_data)
6160 {
6161         GSList **new_services = user_data;
6162         struct gatt_primary *prim;
6163         bt_uuid_t uuid;
6164
6165         prim = g_new0(struct gatt_primary, 1);
6166         if (!prim) {
6167                 DBG("Failed to allocate gatt_primary structure");
6168                 return;
6169         }
6170
6171         gatt_db_attribute_get_service_handles(attr, &prim->range.start,
6172                                                         &prim->range.end);
6173         gatt_db_attribute_get_service_uuid(attr, &uuid);
6174         bt_uuid_to_string(&uuid, prim->uuid, sizeof(prim->uuid));
6175
6176         *new_services = g_slist_append(*new_services, prim);
6177 }
6178
6179 static void load_desc_value(struct gatt_db_attribute *attrib,
6180                                                 int err, void *user_data)
6181 {
6182         if (err)
6183                 warn("loading descriptor value to db failed");
6184 }
6185
6186 static ssize_t str2val(const char *str, uint8_t *val, size_t len)
6187 {
6188         const char *pos = str;
6189         size_t i;
6190
6191         for (i = 0; i < len; i++) {
6192                 if (sscanf(pos, "%2hhx", &val[i]) != 1)
6193                         break;
6194                 pos += 2;
6195         }
6196
6197         return i;
6198 }
6199
6200 static int load_desc(char *handle, char *value,
6201                                         struct gatt_db_attribute *service)
6202 {
6203         char uuid_str[MAX_LEN_UUID_STR];
6204         struct gatt_db_attribute *att;
6205         uint16_t handle_int;
6206         uint16_t val;
6207         bt_uuid_t uuid, ext_uuid;
6208
6209         if (sscanf(handle, "%04hx", &handle_int) != 1)
6210                 return -EIO;
6211
6212         /* Check if there is any value stored, otherwise it is just the UUID */
6213         if (sscanf(value, "%04hx:%s", &val, uuid_str) != 2) {
6214                 if (sscanf(value, "%s", uuid_str) != 1)
6215                         return -EIO;
6216                 val = 0;
6217         }
6218
6219         DBG("loading descriptor handle: 0x%04x, value: 0x%04x, value uuid: %s",
6220                                 handle_int, val, uuid_str);
6221
6222         bt_string_to_uuid(&uuid, uuid_str);
6223         bt_uuid16_create(&ext_uuid, GATT_CHARAC_EXT_PROPER_UUID);
6224
6225         /* If it is CEP then it must contain the value */
6226         if (!bt_uuid_cmp(&uuid, &ext_uuid) && !val) {
6227                 warn("cannot load CEP descriptor without value");
6228                 return -EIO;
6229         }
6230
6231         att = gatt_db_service_insert_descriptor(service, handle_int, &uuid,
6232                                                         0, NULL, NULL, NULL);
6233         if (!att || gatt_db_attribute_get_handle(att) != handle_int) {
6234                 warn("loading descriptor to db failed");
6235                 return -EIO;
6236         }
6237
6238         if (val) {
6239                 if (!gatt_db_attribute_write(att, 0, (uint8_t *)&val,
6240                                                 sizeof(val), 0, NULL,
6241                                                 load_desc_value, NULL))
6242                         return -EIO;
6243         }
6244
6245         return 0;
6246 }
6247
6248 static int load_chrc(char *handle, char *value,
6249                                         struct gatt_db_attribute *service)
6250 {
6251         uint16_t properties, value_handle, handle_int;
6252         char uuid_str[MAX_LEN_UUID_STR];
6253         struct gatt_db_attribute *att;
6254         char val_str[32];
6255         uint8_t val[16];
6256         size_t val_len;
6257         bt_uuid_t uuid;
6258
6259         if (sscanf(handle, "%04hx", &handle_int) != 1)
6260                 return -EIO;
6261
6262         /* Check if there is any value stored */
6263         if (sscanf(value, GATT_CHARAC_UUID_STR ":%04hx:%02hx:%32s:%s",
6264                         &value_handle, &properties, val_str, uuid_str) != 4) {
6265                 if (sscanf(value, GATT_CHARAC_UUID_STR ":%04hx:%02hx:%s",
6266                                 &value_handle, &properties, uuid_str) != 3)
6267                         return -EIO;
6268                 val_len = 0;
6269         } else
6270                 val_len = str2val(val_str, val, sizeof(val));
6271
6272         bt_string_to_uuid(&uuid, uuid_str);
6273
6274         /* Log debug message. */
6275         DBG("loading characteristic handle: 0x%04x, value handle: 0x%04x,"
6276                                 " properties 0x%04x value: %s uuid: %s",
6277                                 handle_int, value_handle, properties,
6278                                 val_len ? val_str : "", uuid_str);
6279
6280         att = gatt_db_service_insert_characteristic(service, value_handle,
6281                                                         &uuid, 0, properties,
6282                                                         NULL, NULL, NULL);
6283         if (!att || gatt_db_attribute_get_handle(att) != value_handle) {
6284                 warn("loading characteristic to db failed");
6285                 return -EIO;
6286         }
6287
6288         if (val_len) {
6289                 if (!gatt_db_attribute_write(att, 0, val, val_len, 0, NULL,
6290                                                 load_desc_value, NULL))
6291                         return -EIO;
6292         }
6293
6294         return 0;
6295 }
6296
6297 static int load_incl(struct gatt_db *db, char *handle, char *value,
6298                                         struct gatt_db_attribute *service)
6299 {
6300         char uuid_str[MAX_LEN_UUID_STR];
6301         struct gatt_db_attribute *att;
6302         uint16_t start, end;
6303
6304         if (sscanf(handle, "%04hx", &start) != 1)
6305                 return -EIO;
6306
6307         if (sscanf(value, GATT_INCLUDE_UUID_STR ":%04hx:%04hx:%s", &start, &end,
6308                                                                 uuid_str) != 3)
6309                 return -EIO;
6310
6311         /* Log debug message. */
6312         DBG("loading included service: 0x%04x, end: 0x%04x, uuid: %s", start,
6313                                                                 end, uuid_str);
6314
6315         att = gatt_db_get_attribute(db, start);
6316         if (!att) {
6317                 warn("loading included service to db failed - no such service");
6318                 return -EIO;
6319         }
6320
6321         att = gatt_db_service_add_included(service, att);
6322         if (!att) {
6323                 warn("loading included service to db failed");
6324                 return -EIO;
6325         }
6326
6327         return 0;
6328 }
6329
6330 static int load_service(struct gatt_db *db, char *handle, char *value)
6331 {
6332         struct gatt_db_attribute *att;
6333         uint16_t start, end;
6334         char type[MAX_LEN_UUID_STR], uuid_str[MAX_LEN_UUID_STR];
6335         bt_uuid_t uuid;
6336         bool primary;
6337
6338         if (sscanf(handle, "%04hx", &start) != 1)
6339                 return -EIO;
6340
6341         if (sscanf(value, "%[^:]:%04hx:%s", type, &end, uuid_str) != 3)
6342                 return -EIO;
6343
6344         if (g_str_equal(type, GATT_PRIM_SVC_UUID_STR))
6345                 primary = true;
6346         else if (g_str_equal(type, GATT_SND_SVC_UUID_STR))
6347                 primary = false;
6348         else
6349                 return -EIO;
6350
6351         bt_string_to_uuid(&uuid, uuid_str);
6352
6353         /* Log debug message. */
6354         DBG("loading service: 0x%04x, end: 0x%04x, uuid: %s",
6355                                                         start, end, uuid_str);
6356
6357         att = gatt_db_insert_service(db, start, &uuid, primary,
6358                                                         end - start + 1);
6359         if (!att) {
6360                 error("Unable load service into db!");
6361                 return -EIO;
6362         }
6363
6364         return 0;
6365 }
6366
6367 static int load_gatt_db_impl(GKeyFile *key_file, char **keys,
6368                                                         struct gatt_db *db)
6369 {
6370         struct gatt_db_attribute *current_service;
6371         char **handle, *value, type[MAX_LEN_UUID_STR];
6372         int ret;
6373
6374         /* first load service definitions */
6375         for (handle = keys; *handle; handle++) {
6376                 value = g_key_file_get_string(key_file, "Attributes", *handle,
6377                                                                         NULL);
6378
6379                 if (sscanf(value, "%[^:]:", type) != 1) {
6380                         warn("Missing Type in attribute definition");
6381                         g_free(value);
6382                         return -EIO;
6383                 }
6384
6385                 if (g_str_equal(type, GATT_PRIM_SVC_UUID_STR) ||
6386                                 g_str_equal(type, GATT_SND_SVC_UUID_STR)) {
6387                         ret = load_service(db, *handle, value);
6388                         if (ret) {
6389                                 g_free(value);
6390                                 return ret;
6391                         }
6392                 }
6393
6394                 g_free(value);
6395         }
6396
6397         current_service = NULL;
6398         /* then fill them with data*/
6399         for (handle = keys; *handle; handle++) {
6400                 value = g_key_file_get_string(key_file, "Attributes", *handle,
6401                                                                         NULL);
6402
6403                 if (sscanf(value, "%[^:]:", type) != 1) {
6404                         warn("Missing Type in attribute definition");
6405                         g_free(value);
6406                         return -EIO;
6407                 }
6408
6409                 if (g_str_equal(type, GATT_PRIM_SVC_UUID_STR) ||
6410                                 g_str_equal(type, GATT_SND_SVC_UUID_STR)) {
6411                         uint16_t tmp;
6412                         uint16_t start, end;
6413                         bool primary;
6414                         bt_uuid_t uuid;
6415                         char uuid_str[MAX_LEN_UUID_STR];
6416
6417                         if (sscanf(*handle, "%04hx", &tmp) != 1) {
6418                                 warn("Unable to parse attribute handle");
6419                                 g_free(value);
6420                                 return -EIO;
6421                         }
6422
6423                         if (current_service)
6424                                 gatt_db_service_set_active(current_service,
6425                                                                         true);
6426
6427                         current_service = gatt_db_get_attribute(db, tmp);
6428
6429                         gatt_db_attribute_get_service_data(current_service,
6430                                                         &start, &end,
6431                                                         &primary, &uuid);
6432
6433                         bt_uuid_to_string(&uuid, uuid_str, sizeof(uuid_str));
6434                 } else if (g_str_equal(type, GATT_INCLUDE_UUID_STR)) {
6435                         ret = load_incl(db, *handle, value, current_service);
6436                 } else if (g_str_equal(type, GATT_CHARAC_UUID_STR)) {
6437                         ret = load_chrc(*handle, value, current_service);
6438                 } else {
6439                         ret = load_desc(*handle, value, current_service);
6440                 }
6441
6442                 g_free(value);
6443                 if (ret) {
6444                         gatt_db_clear(db);
6445                         return ret;
6446                 }
6447         }
6448
6449         if (current_service)
6450                 gatt_db_service_set_active(current_service, true);
6451
6452         return 0;
6453 }
6454
6455 static void load_gatt_db(struct btd_device *device, const char *local,
6456                                                         const char *peer)
6457 {
6458         char **keys, filename[PATH_MAX];
6459         GKeyFile *key_file;
6460         GError *gerr = NULL;
6461
6462         if (!gatt_cache_is_enabled(device))
6463                 return;
6464
6465         DBG("Restoring %s gatt database from file", peer);
6466
6467         snprintf(filename, PATH_MAX, STORAGEDIR "/%s/cache/%s", local, peer);
6468
6469         key_file = g_key_file_new();
6470         if (!g_key_file_load_from_file(key_file, filename, 0, &gerr)) {
6471                 error("Unable to load key file from %s: (%s)", filename,
6472                                                                 gerr->message);
6473                 g_error_free(gerr);
6474         }
6475         keys = g_key_file_get_keys(key_file, "Attributes", NULL, NULL);
6476
6477         if (!keys) {
6478                 warn("No cache for %s", peer);
6479                 g_key_file_free(key_file);
6480                 return;
6481         }
6482
6483         if (load_gatt_db_impl(key_file, keys, device->db))
6484                 warn("Unable to load gatt db from file for %s", peer);
6485
6486         g_strfreev(keys);
6487         g_key_file_free(key_file);
6488
6489         g_slist_free_full(device->primaries, g_free);
6490         device->primaries = NULL;
6491         gatt_db_foreach_service(device->db, NULL, add_primary,
6492                                                         &device->primaries);
6493 }
6494
6495 static void device_add_uuids(struct btd_device *device, GSList *uuids)
6496 {
6497         GSList *l;
6498         bool changed = false;
6499
6500         for (l = uuids; l != NULL; l = g_slist_next(l)) {
6501                 GSList *match = g_slist_find_custom(device->uuids, l->data,
6502                                                         bt_uuid_strcmp);
6503                 if (match)
6504                         continue;
6505
6506                 changed = true;
6507                 device->uuids = g_slist_insert_sorted(device->uuids,
6508                                                 g_strdup(l->data),
6509                                                 bt_uuid_strcmp);
6510         }
6511
6512         if (changed)
6513                 g_dbus_emit_property_changed(dbus_conn, device->path,
6514                                                 DEVICE_INTERFACE, "UUIDs");
6515 }
6516
6517 static bool device_match_profile(struct btd_device *device,
6518                                         struct btd_profile *profile,
6519                                         GSList *uuids)
6520 {
6521         if (profile->remote_uuid == NULL)
6522                 return false;
6523
6524         if (g_slist_find_custom(uuids, profile->remote_uuid,
6525                                                         bt_uuid_strcmp) == NULL) {
6526 #ifdef TIZEN_BT_HID_DEVICE_ENABLE
6527                 if (strcmp(profile->name, "hid-device") == 0)
6528                         return true;
6529 #endif
6530                 return false;
6531         }
6532
6533         return true;
6534 }
6535
6536 static void add_gatt_service(struct gatt_db_attribute *attr, void *user_data)
6537 {
6538         struct btd_device *device = user_data;
6539         struct btd_service *service;
6540         struct btd_profile *profile;
6541         bt_uuid_t uuid;
6542         char uuid_str[MAX_LEN_UUID_STR];
6543         GSList *l;
6544
6545         gatt_db_attribute_get_service_uuid(attr, &uuid);
6546         bt_uuid_to_string(&uuid, uuid_str, sizeof(uuid_str));
6547
6548         /* Check if service was already probed */
6549         l = find_service_with_uuid(device->services, uuid_str);
6550         if (l)
6551                 goto done;
6552
6553         /* Add UUID and probe service */
6554         btd_device_add_uuid(device, uuid_str);
6555
6556         /* Check if service was probed */
6557         l = find_service_with_uuid(device->services, uuid_str);
6558         if (!l)
6559                 return;
6560
6561 done:
6562         /* Mark service as active to skip discovering it again */
6563         gatt_db_service_set_active(attr, true);
6564
6565         service = l->data;
6566         profile = btd_service_get_profile(service);
6567
6568         /* Claim attributes of internal profiles */
6569         if (!profile->external) {
6570                 /* Mark the service as claimed by the existing profile. */
6571                 gatt_db_service_set_claimed(attr, true);
6572         }
6573
6574         /* Notify driver about the new connection */
6575         service_accept(service);
6576 }
6577
6578 static void device_add_gatt_services(struct btd_device *device)
6579 {
6580         char addr[18];
6581
6582         ba2str(&device->bdaddr, addr);
6583
6584         if (device->blocked) {
6585                 DBG("Skipping profiles for blocked device %s", addr);
6586                 return;
6587         }
6588
6589         gatt_db_foreach_service(device->db, NULL, add_gatt_service, device);
6590 }
6591
6592 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
6593 static void accept_gatt_service(struct gatt_db_attribute *attr, void *user_data)
6594 {
6595         struct btd_device *device = user_data;
6596         GSList *l;
6597         bt_uuid_t uuid;
6598         char uuid_str[MAX_LEN_UUID_STR];
6599
6600         gatt_db_attribute_get_service_uuid(attr, &uuid);
6601         bt_uuid_to_string(&uuid, uuid_str, sizeof(uuid_str));
6602
6603         l = find_service_with_uuid(device->services, uuid_str);
6604         if (!l)
6605                 return;
6606
6607         service_accept(l->data);
6608 }
6609 #endif
6610
6611 static void device_accept_gatt_profiles(struct btd_device *device)
6612 {
6613 #ifndef TIZEN_FEATURE_BLUEZ_MODIFY
6614         GSList *l;
6615
6616         for (l = device->services; l != NULL; l = g_slist_next(l))
6617                 service_accept(l->data);
6618 #else
6619         gatt_db_foreach_service(device->db, NULL, accept_gatt_service, device);
6620 #endif
6621 }
6622
6623 static void device_remove_gatt_service(struct btd_device *device,
6624                                                 struct gatt_db_attribute *attr)
6625 {
6626         struct btd_service *service;
6627         bt_uuid_t uuid;
6628         char uuid_str[MAX_LEN_UUID_STR];
6629         GSList *l;
6630
6631         gatt_db_attribute_get_service_uuid(attr, &uuid);
6632         bt_uuid_to_string(&uuid, uuid_str, sizeof(uuid_str));
6633
6634         l = find_service_with_uuid(device->services, uuid_str);
6635         if (!l)
6636                 return;
6637
6638         service = l->data;
6639         device->services = g_slist_delete_link(device->services, l);
6640         device->pending = g_slist_remove(device->pending, service);
6641         service_remove(service);
6642 }
6643
6644 static gboolean gatt_services_changed(gpointer user_data)
6645 {
6646         struct btd_device *device = user_data;
6647
6648         store_gatt_db(device);
6649
6650         return FALSE;
6651 }
6652
6653 static void gatt_service_added(struct gatt_db_attribute *attr, void *user_data)
6654 {
6655         struct btd_device *device = user_data;
6656         GSList *new_service = NULL;
6657         uint16_t start, end;
6658
6659         if (!bt_gatt_client_is_ready(device->client))
6660                 return;
6661
6662         gatt_db_attribute_get_service_data(attr, &start, &end, NULL, NULL);
6663
6664         DBG("start: 0x%04x, end: 0x%04x", start, end);
6665
6666         /*
6667          * TODO: Remove the primaries list entirely once all profiles use
6668          * shared/gatt.
6669          */
6670         add_primary(attr, &new_service);
6671         if (!new_service)
6672                 return;
6673
6674         device_register_primaries(device, new_service, -1);
6675
6676         add_gatt_service(attr, device);
6677
6678         btd_gatt_client_service_added(device->client_dbus, attr);
6679
6680         gatt_services_changed(device);
6681 }
6682
6683 static gint prim_attr_cmp(gconstpointer a, gconstpointer b)
6684 {
6685         const struct gatt_primary *prim = a;
6686         const struct gatt_db_attribute *attr = b;
6687         uint16_t start, end;
6688
6689         gatt_db_attribute_get_service_handles(attr, &start, &end);
6690
6691         return !(prim->range.start == start && prim->range.end == end);
6692 }
6693
6694 static gint prim_uuid_cmp(gconstpointer a, gconstpointer b)
6695 {
6696         const struct gatt_primary *prim = a;
6697         const char *uuid = b;
6698
6699         return bt_uuid_strcmp(prim->uuid, uuid);
6700 }
6701
6702 static void gatt_service_removed(struct gatt_db_attribute *attr,
6703                                                                 void *user_data)
6704 {
6705         struct btd_device *device = user_data;
6706         GSList *l;
6707         struct gatt_primary *prim;
6708         uint16_t start, end;
6709
6710         /*
6711          * NOTE: shared/gatt-client clears the database in case of failure. This
6712          * triggers the service_removed callback for all affected services.
6713          * Hence, this function will be called in the following cases:
6714          *
6715          *    1. When a GATT service gets removed due to "Service Changed".
6716          *
6717          *    2. When a GATT service gets removed when the database get cleared
6718          *       upon disconnection with a non-bonded device.
6719          *
6720          *    3. When a GATT service gets removed when the database get cleared
6721          *       by shared/gatt-client when its initialization procedure fails,
6722          *       e.g. due to an ATT protocol error or an unexpected disconnect.
6723          *       In this case the gatt-client will not be ready.
6724          */
6725
6726         gatt_db_attribute_get_service_handles(attr, &start, &end);
6727
6728         DBG("start: 0x%04x, end: 0x%04x", start, end);
6729
6730         /* Remove the corresponding gatt_primary */
6731         l = g_slist_find_custom(device->primaries, attr, prim_attr_cmp);
6732         if (!l)
6733                 return;
6734
6735         prim = l->data;
6736         device->primaries = g_slist_delete_link(device->primaries, l);
6737
6738         /*
6739          * Remove the corresponding UUIDs entry and profile, only if this is
6740          * the last service with this UUID.
6741          */
6742         l = g_slist_find_custom(device->uuids, prim->uuid, bt_uuid_strcmp);
6743
6744         if (l && !g_slist_find_custom(device->primaries, prim->uuid,
6745                                                         prim_uuid_cmp)) {
6746                 /*
6747                  * If this happend since the db was cleared for a non-bonded
6748                  * device, then don't remove the btd_service just yet. We do
6749                  * this so that we can avoid re-probing the profile if the same
6750                  * GATT service is found on the device on re-connection.
6751                  * However, if the device is marked as temporary, then we
6752                  * remove it anyway.
6753                  */
6754                 if (device->client || device->temporary == TRUE)
6755                         device_remove_gatt_service(device, attr);
6756
6757                 g_free(l->data);
6758                 device->uuids = g_slist_delete_link(device->uuids, l);
6759                 g_dbus_emit_property_changed(dbus_conn, device->path,
6760                                                 DEVICE_INTERFACE, "UUIDs");
6761         }
6762
6763         g_free(prim);
6764
6765         store_device_info(device);
6766
6767         btd_gatt_client_service_removed(device->client_dbus, attr);
6768
6769         gatt_services_changed(device);
6770 }
6771
6772 static struct btd_device *device_new(struct btd_adapter *adapter,
6773                                 const char *address)
6774 {
6775         char *address_up;
6776         struct btd_device *device;
6777         const char *adapter_path = adapter_get_path(adapter);
6778
6779 #ifndef TIZEN_FEATURE_BLUEZ_MODIFY
6780         DBG("address %s", address);
6781 #endif
6782
6783         device = g_try_malloc0(sizeof(struct btd_device));
6784         if (device == NULL)
6785                 return NULL;
6786
6787         device->tx_power = 127;
6788
6789         device->db = gatt_db_new();
6790         if (!device->db) {
6791                 g_free(device);
6792                 return NULL;
6793         }
6794
6795         memset(device->ad_flags, INVALID_FLAGS, sizeof(device->ad_flags));
6796
6797         device->ad = bt_ad_new();
6798         if (!device->ad) {
6799                 device_free(device);
6800                 return NULL;
6801         }
6802
6803         address_up = g_ascii_strup(address, -1);
6804         device->path = g_strdup_printf("%s/dev_%s", adapter_path, address_up);
6805         g_strdelimit(device->path, ":", '_');
6806         g_free(address_up);
6807
6808         str2ba(address, &device->bdaddr);
6809
6810         device->client_dbus = btd_gatt_client_new(device);
6811         if (!device->client_dbus) {
6812                 error("Failed to create btd_gatt_client");
6813                 device_free(device);
6814                 return NULL;
6815         }
6816
6817         DBG("Creating device %s", device->path);
6818
6819         if (g_dbus_register_interface(dbus_conn,
6820                                         device->path, DEVICE_INTERFACE,
6821 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
6822                                         device_methods, device_signals,
6823 #else
6824                                         device_methods, NULL,
6825 #endif
6826                                         device_properties, device,
6827                                         device_free) == FALSE) {
6828                 error("Unable to register device interface for %s", address);
6829                 device_free(device);
6830                 return NULL;
6831         }
6832
6833         device->adapter = adapter;
6834         device->temporary = true;
6835
6836         device->db_id = gatt_db_register(device->db, gatt_service_added,
6837                                         gatt_service_removed, device, NULL);
6838
6839         device->refresh_discovery = btd_opts.refresh_discovery;
6840
6841         return btd_device_ref(device);
6842 }
6843
6844 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
6845 void device_print_addr(struct btd_device *dev)
6846 {
6847         char ida[18];
6848         char rpa[18];
6849
6850         ba2str(&dev->bdaddr, ida);
6851
6852         if (dev->rpa) {
6853                 ba2str(dev->rpa, rpa);
6854
6855                 DBG("IDA %s [%d] : RPA [%s], BREDR [%d], LE [%d]",
6856                                 ida, dev->bdaddr_type, rpa,
6857                                 dev->bredr ? 1 : 0, dev->le ? 1 : 0);
6858         } else {
6859                 DBG("ADDR %s [%d] : BREDR [%d], LE [%d]",
6860                                 ida, dev->bdaddr_type,
6861                                 dev->bredr ? 1 : 0, dev->le ? 1 : 0);
6862         }
6863 }
6864 #endif
6865
6866 struct btd_device *device_create_from_storage(struct btd_adapter *adapter,
6867                                 const char *address, GKeyFile *key_file)
6868 {
6869         struct btd_device *device;
6870         const char *src_dir;
6871
6872         DBG("address %s", address);
6873
6874         device = device_new(adapter, address);
6875         if (device == NULL)
6876                 return NULL;
6877
6878         convert_info(device, key_file);
6879
6880         src_dir = btd_adapter_get_storage_dir(adapter);
6881
6882         load_info(device, src_dir, address, key_file);
6883         load_att_info(device, src_dir, address);
6884
6885         return device;
6886 }
6887
6888 struct btd_device *device_create(struct btd_adapter *adapter,
6889                                 const bdaddr_t *bdaddr, uint8_t bdaddr_type)
6890 {
6891         struct btd_device *device;
6892         char dst[18];
6893         char *str;
6894
6895         ba2str(bdaddr, dst);
6896         DBG("dst %s", dst);
6897
6898         device = device_new(adapter, dst);
6899         if (device == NULL)
6900                 return NULL;
6901
6902         device->bdaddr_type = bdaddr_type;
6903
6904         if (bdaddr_type == BDADDR_BREDR)
6905                 device->bredr = true;
6906         else
6907                 device->le = true;
6908
6909         str = load_cached_name(device, btd_adapter_get_storage_dir(adapter),
6910                                                                         dst);
6911         if (str) {
6912                 strcpy(device->name, str);
6913                 g_free(str);
6914         }
6915
6916         return device;
6917 }
6918
6919 char *btd_device_get_storage_path(struct btd_device *device,
6920                                 const char *filename)
6921 {
6922         char dstaddr[18];
6923
6924         if (device_address_is_private(device)) {
6925                 warn("Refusing storage path for private addressed device %s",
6926                                                                 device->path);
6927                 return NULL;
6928         }
6929
6930         ba2str(&device->bdaddr, dstaddr);
6931
6932 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
6933         if (device->rpa)
6934                 ba2str(device->rpa, dstaddr);
6935 #endif
6936
6937         if (!filename)
6938                 return g_strdup_printf(STORAGEDIR "/%s/%s",
6939                                 btd_adapter_get_storage_dir(device->adapter),
6940                                 dstaddr);
6941
6942         return g_strdup_printf(STORAGEDIR "/%s/%s/%s",
6943                                 btd_adapter_get_storage_dir(device->adapter),
6944                                 dstaddr, filename);
6945 }
6946
6947 void btd_device_device_set_name(struct btd_device *device, const char *name)
6948 {
6949         if (strncmp(name, device->name, MAX_NAME_LENGTH) == 0)
6950                 return;
6951
6952         DBG("%s %s", device->path, name);
6953
6954         strncpy(device->name, name, MAX_NAME_LENGTH);
6955
6956         store_device_info(device);
6957
6958         g_dbus_emit_property_changed(dbus_conn, device->path,
6959                                                 DEVICE_INTERFACE, "Name");
6960
6961         if (device->alias != NULL)
6962                 return;
6963
6964         g_dbus_emit_property_changed(dbus_conn, device->path,
6965                                                 DEVICE_INTERFACE, "Alias");
6966 }
6967
6968 void device_get_name(struct btd_device *device, char *name, size_t len)
6969 {
6970         if (name != NULL && len > 0) {
6971                 strncpy(name, device->name, len - 1);
6972                 name[len - 1] = '\0';
6973         }
6974 }
6975
6976 bool device_name_known(struct btd_device *device)
6977 {
6978         return device->name[0] != '\0';
6979 }
6980
6981 bool device_is_name_resolve_allowed(struct btd_device *device)
6982 {
6983         struct timespec now;
6984
6985         if (!device)
6986                 return false;
6987
6988         clock_gettime(CLOCK_MONOTONIC, &now);
6989         return now.tv_sec >= device->name_resolve_failed_time +
6990                                                 NAME_RESOLVE_RETRY_DELAY;
6991 }
6992
6993 void device_name_resolve_fail(struct btd_device *device)
6994 {
6995         struct timespec now;
6996
6997         if (!device)
6998                 return;
6999
7000         clock_gettime(CLOCK_MONOTONIC, &now);
7001         device->name_resolve_failed_time = now.tv_sec;
7002 }
7003
7004 void device_set_class(struct btd_device *device, uint32_t class)
7005 {
7006         if (device->class == class)
7007                 return;
7008
7009         DBG("%s 0x%06X", device->path, class);
7010
7011         device->class = class;
7012
7013         store_device_info(device);
7014
7015         g_dbus_emit_property_changed(dbus_conn, device->path,
7016                                                 DEVICE_INTERFACE, "Class");
7017         g_dbus_emit_property_changed(dbus_conn, device->path,
7018                                                 DEVICE_INTERFACE, "Icon");
7019 }
7020
7021 void device_update_addr(struct btd_device *device, const bdaddr_t *bdaddr,
7022                                                         uint8_t bdaddr_type)
7023 {
7024         bool auto_connect = device->auto_connect;
7025
7026         if (!bacmp(bdaddr, &device->bdaddr) &&
7027                                         bdaddr_type == device->bdaddr_type)
7028                 return;
7029
7030         /* Since this function is only used for LE SMP Identity
7031          * Resolving purposes we can now assume LE is supported.
7032          */
7033         device->le = true;
7034
7035         /* Remove old address from accept/auto-connect list since its address
7036          * will be changed.
7037          */
7038         if (auto_connect)
7039                 device_set_auto_connect(device, FALSE);
7040
7041         bacpy(&device->bdaddr, bdaddr);
7042         device->bdaddr_type = bdaddr_type;
7043
7044         store_device_info(device);
7045
7046         g_dbus_emit_property_changed(dbus_conn, device->path,
7047                                                 DEVICE_INTERFACE, "Address");
7048         g_dbus_emit_property_changed(dbus_conn, device->path,
7049                                         DEVICE_INTERFACE, "AddressType");
7050
7051         if (auto_connect)
7052                 device_set_auto_connect(device, TRUE);
7053 }
7054
7055 void device_set_bredr_support(struct btd_device *device)
7056 {
7057 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
7058         char addr_str[18];
7059
7060         if (device->rpa) {
7061                 ba2str(device->rpa, addr_str);
7062                 error("Cannot set bredr support to RPA device [%s]", addr_str);
7063                 return;
7064         }
7065
7066         if (device->bdaddr_type == BDADDR_LE_RANDOM) {
7067                 ba2str(&device->bdaddr, addr_str);
7068                 error("Cannot set bredr support to LE random device [%s]",
7069                                                                 addr_str);
7070                 return;
7071         }
7072 #endif
7073
7074         if (device->bredr)
7075                 return;
7076
7077         device->bredr = true;
7078         store_device_info(device);
7079 }
7080
7081 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
7082 void device_set_rpa(struct btd_device *device, const bdaddr_t *rpa)
7083 {
7084         if (device->rpa == NULL) {
7085                 device->rpa = g_malloc0(sizeof(bdaddr_t));
7086                 bacpy(device->rpa, rpa);
7087         } else
7088                 error("RPA is already set");
7089 }
7090
7091 void device_set_irk_value(struct btd_device *device, const uint8_t *val)
7092 {
7093         memcpy(&device->irk_val, val, sizeof(device->irk_val));
7094 }
7095 #endif
7096
7097 void device_set_le_support(struct btd_device *device, uint8_t bdaddr_type)
7098 {
7099         if (device->le)
7100                 return;
7101
7102         device->le = true;
7103         device->bdaddr_type = bdaddr_type;
7104
7105         store_device_info(device);
7106 }
7107
7108 static bool device_disappeared(gpointer user_data)
7109 {
7110         struct btd_device *dev = user_data;
7111
7112 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
7113         if (dev->le_state.connected) {
7114                 DBG("GATT connection exists, don't remove the device");
7115                 return FALSE;
7116         }
7117 #endif
7118
7119         dev->temporary_timer = 0;
7120
7121         btd_adapter_remove_device(dev->adapter, dev);
7122
7123         return FALSE;
7124 }
7125
7126 static void set_temporary_timer(struct btd_device *dev, unsigned int timeout)
7127 {
7128         clear_temporary_timer(dev);
7129
7130         if (!timeout)
7131                 return;
7132
7133         dev->temporary_timer = timeout_add_seconds(timeout, device_disappeared,
7134                                                                 dev, NULL);
7135 }
7136
7137 void device_update_last_seen(struct btd_device *device, uint8_t bdaddr_type)
7138 {
7139         if (bdaddr_type == BDADDR_BREDR)
7140                 device->bredr_seen = time(NULL);
7141         else
7142                 device->le_seen = time(NULL);
7143
7144         if (!device_is_temporary(device))
7145                 return;
7146
7147         /* Restart temporary timer */
7148         set_temporary_timer(device, btd_opts.tmpto);
7149 }
7150
7151 /* It is possible that we have two device objects for the same device in
7152  * case it has first been discovered over BR/EDR and has a private
7153  * address when discovered over LE for the first time. In such a case we
7154  * need to inherit critical values from the duplicate so that we don't
7155  * ovewrite them when writing to storage. The next time bluetoothd
7156  * starts the device will show up as a single instance.
7157  */
7158 void device_merge_duplicate(struct btd_device *dev, struct btd_device *dup)
7159 {
7160         GSList *l;
7161
7162         DBG("");
7163
7164         dev->bredr = dup->bredr;
7165
7166         dev->trusted = dup->trusted;
7167         dev->blocked = dup->blocked;
7168
7169         for (l = dup->uuids; l; l = g_slist_next(l))
7170                 dev->uuids = g_slist_append(dev->uuids, g_strdup(l->data));
7171
7172         if (dev->name[0] == '\0')
7173                 strcpy(dev->name, dup->name);
7174
7175         if (!dev->alias)
7176                 dev->alias = g_strdup(dup->alias);
7177
7178         dev->class = dup->class;
7179
7180         dev->vendor_src = dup->vendor_src;
7181         dev->vendor = dup->vendor;
7182         dev->product = dup->product;
7183         dev->version = dup->version;
7184 }
7185
7186 uint32_t btd_device_get_class(struct btd_device *device)
7187 {
7188         return device->class;
7189 }
7190
7191 uint16_t btd_device_get_vendor(struct btd_device *device)
7192 {
7193         return device->vendor;
7194 }
7195
7196 uint16_t btd_device_get_vendor_src(struct btd_device *device)
7197 {
7198         return device->vendor_src;
7199 }
7200
7201 uint16_t btd_device_get_product(struct btd_device *device)
7202 {
7203         return device->product;
7204 }
7205
7206 uint16_t btd_device_get_version(struct btd_device *device)
7207 {
7208         return device->version;
7209 }
7210
7211 static void delete_folder_tree(const char *dirname)
7212 {
7213         DIR *dir;
7214         struct dirent *entry;
7215         char filename[PATH_MAX];
7216
7217         dir = opendir(dirname);
7218         if (dir == NULL)
7219                 return;
7220
7221         while ((entry = readdir(dir)) != NULL) {
7222                 if (g_str_equal(entry->d_name, ".") ||
7223                                 g_str_equal(entry->d_name, ".."))
7224                         continue;
7225
7226                 if (entry->d_type == DT_UNKNOWN)
7227                         entry->d_type = util_get_dt(dirname, entry->d_name);
7228
7229                 snprintf(filename, PATH_MAX, "%s/%s", dirname, entry->d_name);
7230
7231                 if (entry->d_type == DT_DIR)
7232                         delete_folder_tree(filename);
7233                 else
7234                         unlink(filename);
7235         }
7236         closedir(dir);
7237
7238         rmdir(dirname);
7239 }
7240
7241 void device_remove_bonding(struct btd_device *device, uint8_t bdaddr_type)
7242 {
7243         if (bdaddr_type == BDADDR_BREDR)
7244                 device->bredr_state.bonded = false;
7245         else
7246                 device->le_state.bonded = false;
7247
7248         if (!device->bredr_state.bonded && !device->le_state.bonded)
7249                 btd_device_set_temporary(device, true);
7250
7251         btd_adapter_remove_bonding(device->adapter, &device->bdaddr,
7252                                                         bdaddr_type);
7253 }
7254
7255 static void device_remove_stored(struct btd_device *device)
7256 {
7257         char device_addr[18];
7258         char filename[PATH_MAX];
7259         GKeyFile *key_file;
7260         GError *gerr = NULL;
7261         char *data;
7262         gsize length = 0;
7263
7264         if (device->bredr_state.bonded)
7265                 device_remove_bonding(device, BDADDR_BREDR);
7266
7267         if (device->le_state.bonded)
7268                 device_remove_bonding(device, device->bdaddr_type);
7269
7270         device->bredr_state.paired = false;
7271         device->le_state.paired = false;
7272
7273         if (device->blocked)
7274                 device_unblock(device, TRUE, FALSE);
7275
7276         ba2str(&device->bdaddr, device_addr);
7277
7278 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
7279         if (device->rpa)
7280                 ba2str(device->rpa, device_addr);
7281 #endif
7282
7283         snprintf(filename, PATH_MAX, STORAGEDIR "/%s/%s",
7284                                 btd_adapter_get_storage_dir(device->adapter),
7285                                 device_addr);
7286         delete_folder_tree(filename);
7287
7288         snprintf(filename, PATH_MAX, STORAGEDIR "/%s/cache/%s",
7289                                 btd_adapter_get_storage_dir(device->adapter),
7290                                 device_addr);
7291
7292         key_file = g_key_file_new();
7293         if (!g_key_file_load_from_file(key_file, filename, 0, &gerr)) {
7294                 g_error_free(gerr);
7295                 g_key_file_free(key_file);
7296                 return;
7297         }
7298         g_key_file_remove_group(key_file, "ServiceRecords", NULL);
7299         g_key_file_remove_group(key_file, "Attributes", NULL);
7300
7301         data = g_key_file_to_data(key_file, &length, NULL);
7302         if (length > 0) {
7303                 create_file(filename, 0600);
7304                 if (!g_file_set_contents(filename, data, length, &gerr)) {
7305                         error("Unable set contents for %s: (%s)", filename,
7306                                                                 gerr->message);
7307                         g_error_free(gerr);
7308                 }
7309         }
7310
7311         g_free(data);
7312         g_key_file_free(key_file);
7313 }
7314
7315 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
7316 void device_unpair(struct btd_device *device, gboolean remove_stored)
7317 {
7318         DBG("+");
7319         DBG("Unpairing device %s", device->path);
7320
7321         if (device->bonding) {
7322                 uint8_t status;
7323
7324                 if (device->bredr_state.connected)
7325                         status = MGMT_STATUS_DISCONNECTED;
7326                 else
7327                         status = MGMT_STATUS_CONNECT_FAILED;
7328
7329                 device_cancel_bonding(device, status);
7330         }
7331
7332         if (device->browse)
7333                 browse_request_cancel(device->browse);
7334
7335
7336         //      while (device->services != NULL) {
7337         //              struct btd_service *service = device->services->data;
7338         //
7339         //              device->services = g_slist_remove(device->services, service);
7340         //              service_remove(service);
7341         //      }
7342
7343         g_slist_free(device->pending);
7344         device->pending = NULL;
7345
7346         if (btd_device_is_connected(device))
7347                 disconnect_all(device);
7348
7349         if (device->store_id > 0) {
7350                 g_source_remove(device->store_id);
7351                 device->store_id = 0;
7352
7353                 if (!remove_stored)
7354                         store_device_info_cb(device);
7355         }
7356
7357         if (remove_stored)
7358                 device_remove_stored(device);
7359
7360         gatt_db_clear(device->db);
7361
7362         if (device->rpa) {
7363                 bacpy(&device->bdaddr, device->rpa);
7364                 device->bdaddr_type = BDADDR_LE_RANDOM;
7365
7366                 g_free(device->rpa);
7367                 device->rpa = NULL;
7368         }
7369
7370         device->bredr_state.paired = 0;
7371         device->le_state.paired = 0;
7372         device->bredr_state.svc_resolved = false;
7373         device->trusted = false;
7374         device->trusted_profiles.pbap = SHOW_AUTHORIZATION;
7375         device->trusted_profiles.map = SHOW_AUTHORIZATION;
7376         device->trusted_profiles.sap = SHOW_AUTHORIZATION;
7377         device->trusted_profiles.hfp_hs = SUPPORTED_TRUSTED;
7378         device->trusted_profiles.a2dp = SUPPORTED_TRUSTED;
7379         if (device->alias != NULL) {
7380                 /* Remove alias name because
7381                  * In UG if we rename and then unpair device and
7382                  * initiates connection without scanning then paired
7383                  * list will have alias name as first preference is
7384                  * given to alias name.
7385                  */
7386                 DBG("Freeing device alias name");
7387                 g_free(device->alias);
7388                 device->alias = NULL;
7389         }
7390         g_dbus_emit_property_changed(dbus_conn, device->path,
7391                         DEVICE_INTERFACE, "Paired");
7392         //      btd_device_unref(device);
7393         DBG("-");
7394 }
7395
7396 void device_remove_stored_folder(struct btd_device *device)
7397 {
7398         const bdaddr_t *src = btd_adapter_get_address(device->adapter);
7399         char adapter_addr[18];
7400         char device_addr[18];
7401         char filename[PATH_MAX];
7402
7403         ba2str(src, adapter_addr);
7404         ba2str(&device->bdaddr, device_addr);
7405
7406         snprintf(filename, PATH_MAX, STORAGEDIR "/%s/%s", adapter_addr,
7407                         device_addr);
7408
7409         delete_folder_tree(filename);
7410 }
7411 #endif
7412
7413 void device_remove(struct btd_device *device, gboolean remove_stored)
7414 {
7415         DBG("Removing device %s", device->path);
7416
7417         if (device->auto_connect) {
7418                 device->disable_auto_connect = TRUE;
7419                 device_set_auto_connect(device, FALSE);
7420         }
7421
7422         if (device->bonding) {
7423                 uint8_t status;
7424
7425                 if (device->bredr_state.connected)
7426                         status = MGMT_STATUS_DISCONNECTED;
7427                 else
7428                         status = MGMT_STATUS_CONNECT_FAILED;
7429
7430                 device_cancel_bonding(device, status);
7431         }
7432
7433         if (device->browse)
7434                 browse_request_cancel(device->browse);
7435
7436         while (device->services != NULL) {
7437                 struct btd_service *service = device->services->data;
7438
7439                 device->services = g_slist_remove(device->services, service);
7440                 service_remove(service);
7441         }
7442
7443         g_slist_free(device->pending);
7444         device->pending = NULL;
7445
7446         if (btd_device_is_connected(device)) {
7447                 if (device->disconn_timer > 0)
7448                         timeout_remove(device->disconn_timer);
7449                 disconnect_all(device);
7450         }
7451
7452         clear_temporary_timer(device);
7453
7454         if (device->store_id > 0) {
7455                 g_source_remove(device->store_id);
7456                 device->store_id = 0;
7457
7458                 if (!remove_stored)
7459                         store_device_info_cb(device);
7460         }
7461
7462         if (remove_stored)
7463                 device_remove_stored(device);
7464
7465         btd_device_unref(device);
7466 }
7467
7468 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
7469 int device_rpa_cmp(gconstpointer a, gconstpointer b)
7470 {
7471         const struct btd_device *device = a;
7472         const char *address = b;
7473         char addr[18];
7474
7475         if (!device->rpa)
7476                 return -1;
7477
7478         ba2str(device->rpa, addr);
7479
7480         return strcasecmp(addr, address);
7481 }
7482
7483 int device_addr_cmp(gconstpointer a, gconstpointer b)
7484 {
7485         const struct btd_device *device = a;
7486         const bdaddr_t *bdaddr = b;
7487
7488         return bacmp(&device->bdaddr, bdaddr);
7489 }
7490
7491 int device_rpa_ida_cmp(gconstpointer a, gconstpointer b)
7492 {
7493         const struct btd_device *device = a;
7494         const char *address = b;
7495         char addr[18];
7496
7497         if (!device->rpa || device->le == false)
7498                 return -1;
7499
7500         ba2str(&device->bdaddr, addr);
7501         return strcasecmp(addr, address);
7502 }
7503 #endif
7504
7505 int device_address_cmp(gconstpointer a, gconstpointer b)
7506 {
7507         const struct btd_device *device = a;
7508         const char *address = b;
7509         char addr[18];
7510
7511         ba2str(&device->bdaddr, addr);
7512         return strcasecmp(addr, address);
7513 }
7514
7515 int device_bdaddr_cmp(gconstpointer a, gconstpointer b)
7516 {
7517         const struct btd_device *device = a;
7518         const bdaddr_t *bdaddr = b;
7519
7520         return bacmp(&device->bdaddr, bdaddr);
7521 }
7522
7523 static bool addr_is_public(uint8_t addr_type)
7524 {
7525         if (addr_type == BDADDR_BREDR || addr_type == BDADDR_LE_PUBLIC)
7526                 return true;
7527
7528         return false;
7529 }
7530
7531 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
7532 int device_addr_type_strict_cmp(gconstpointer a, gconstpointer b)
7533 {
7534         const struct btd_device *dev = a;
7535         const struct device_addr_type *addr = b;
7536         int cmp;
7537
7538         cmp = bacmp(&dev->bdaddr, &addr->bdaddr);
7539
7540         if (addr->bdaddr_type == BDADDR_BREDR) {
7541                 if (!dev->bredr)
7542                         return -1;
7543
7544                 return cmp;
7545         }
7546
7547         if (!dev->le)
7548                 return -1;
7549
7550         if (cmp && dev->rpa && addr->bdaddr_type == BDADDR_LE_RANDOM &&
7551                         (addr->bdaddr.b[5] >> 6) == 0x01)
7552                 return bacmp(dev->rpa, &addr->bdaddr);
7553
7554         if (addr->bdaddr_type != dev->bdaddr_type)
7555                 return -1;
7556
7557         return cmp;
7558 }
7559 #endif
7560
7561 int device_addr_type_cmp(gconstpointer a, gconstpointer b)
7562 {
7563         const struct btd_device *dev = a;
7564         const struct device_addr_type *addr = b;
7565         int cmp;
7566
7567         cmp = bacmp(&dev->bdaddr, &addr->bdaddr);
7568
7569         /*
7570          * Address matches and both old and new are public addresses
7571          * (doesn't matter whether LE or BR/EDR, then consider this a
7572          * match.
7573          */
7574         if (!cmp && addr_is_public(addr->bdaddr_type) &&
7575                                         addr_is_public(dev->bdaddr_type))
7576 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
7577         {
7578                 if (dev->rpa && addr->bdaddr_type == BDADDR_BREDR) {
7579                         char addr_str[18];
7580
7581                         ba2str(&dev->bdaddr, addr_str);
7582                         DBG("Don't match. LE Only device [%s]", addr_str);
7583                         return -1;
7584                 }
7585                 return 0;
7586         }
7587 #else
7588                 return 0;
7589 #endif
7590
7591         if (addr->bdaddr_type == BDADDR_BREDR) {
7592                 if (!dev->bredr)
7593                         return -1;
7594
7595                 return cmp;
7596         }
7597
7598         if (!dev->le)
7599                 return -1;
7600
7601         if (addr->bdaddr_type != dev->bdaddr_type) {
7602                 if (addr->bdaddr_type == dev->conn_bdaddr_type)
7603                         return bacmp(&dev->conn_bdaddr, &addr->bdaddr);
7604                 return -1;
7605         }
7606
7607         return cmp;
7608 }
7609
7610 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
7611 #ifdef TIZEN_FEATURE_BLUEZ_BATTERY_WATCH
7612 void device_change_pkt_type(gpointer data, gpointer user_data)
7613 {
7614         int pkt_type = (int)user_data;
7615         struct btd_device *device = data;
7616         struct hci_conn_info_req *cr;
7617         set_conn_ptype_cp cp;
7618         char addr[18];
7619         int hdev = 0;
7620         int err = 0;
7621
7622         /* Change a packet type only for Phone device */
7623         if ((device->class & 0x00001F00) >> 8 != 0x02)
7624                 return;
7625
7626         if (!device->bredr_state.connected)
7627                 return;
7628
7629         hdev = hci_open_dev(0);
7630         if (hdev < 0) {
7631                 error("Cannot open hdev");
7632                 return;
7633         }
7634
7635         cr = g_malloc0(sizeof(*cr) + sizeof(struct hci_conn_info));
7636         if (cr == NULL) {
7637                 error("Out of memory");
7638                 return;
7639         }
7640         cr->type = ACL_LINK;
7641         bacpy(&cr->bdaddr, &device->bdaddr);
7642
7643         err = ioctl(hdev, HCIGETCONNINFO, cr);
7644         if (err < 0) {
7645                 error("Fail to get HCIGETCOINFO");
7646                 g_free(cr);
7647                 hci_close_dev(hdev);
7648                 return;
7649         }
7650
7651         cp.handle = cr->conn_info->handle;
7652         g_free(cr);
7653         cp.pkt_type = cpu_to_le16((uint16_t)pkt_type);
7654
7655         ba2str(&device->bdaddr, addr);
7656         DBG("Handle %d, Addr %s", cp.handle, addr);
7657         DBG("Send Change pkt type request : 0x%X", pkt_type);
7658
7659         if (hci_send_cmd(hdev, OGF_LINK_CTL, OCF_SET_CONN_PTYPE,
7660                                 SET_CONN_PTYPE_CP_SIZE, &cp) < 0) {
7661                 error("hci_send_cmd is failed");
7662                 hci_close_dev(hdev);
7663                 return;
7664         }
7665
7666         hci_close_dev(hdev);
7667         return;
7668 }
7669 #endif  /* TIZEN_FEATURE_BLUEZ_BATTERY_WATCH */
7670 #endif
7671
7672 static gboolean record_has_uuid(const sdp_record_t *rec,
7673                                 const char *profile_uuid)
7674 {
7675         sdp_list_t *pat;
7676
7677         for (pat = rec->pattern; pat != NULL; pat = pat->next) {
7678                 char *uuid;
7679                 int ret;
7680
7681                 uuid = bt_uuid2string(pat->data);
7682                 if (!uuid)
7683                         continue;
7684
7685                 ret = strcasecmp(uuid, profile_uuid);
7686
7687                 free(uuid);
7688
7689                 if (ret == 0)
7690                         return TRUE;
7691         }
7692
7693         return FALSE;
7694 }
7695
7696 GSList *btd_device_get_uuids(struct btd_device *device)
7697 {
7698         return device->uuids;
7699 }
7700
7701 struct probe_data {
7702         struct btd_device *dev;
7703         GSList *uuids;
7704 };
7705
7706 static struct btd_service *probe_service(struct btd_device *device,
7707                                                 struct btd_profile *profile,
7708                                                 GSList *uuids)
7709 {
7710         GSList *l;
7711         struct btd_service *service;
7712
7713         if (profile->device_probe == NULL)
7714                 return NULL;
7715
7716         if (!device_match_profile(device, profile, uuids))
7717                 return NULL;
7718
7719         l = find_service_with_profile(device->services, profile);
7720         /* If the service already exists, return NULL so that it won't be added
7721          * to the device->services.
7722          */
7723         if (l)
7724                 return NULL;
7725
7726         service = service_create(device, profile);
7727
7728         if (service_probe(service)) {
7729                 btd_service_unref(service);
7730                 return NULL;
7731         }
7732
7733         /* Only set auto connect if profile has set the flag and can really
7734          * accept connections.
7735          */
7736 #ifndef TIZEN_FEATURE_BLUEZ_MODIFY
7737         if (profile->auto_connect && profile->accept)
7738                 device_set_auto_connect(device, TRUE);
7739 #endif
7740
7741         return service;
7742 }
7743
7744 static void dev_probe(struct btd_profile *p, void *user_data)
7745 {
7746         struct probe_data *d = user_data;
7747         struct btd_service *service;
7748
7749 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
7750         if (find_service_with_profile(d->dev->services, p)) {
7751                 DBG("%s is already probed.(UUID:%s)", p->name, p->remote_uuid);
7752                 return;
7753         }
7754 #endif
7755
7756         service = probe_service(d->dev, p, d->uuids);
7757         if (!service)
7758                 return;
7759
7760         d->dev->services = g_slist_append(d->dev->services, service);
7761 }
7762
7763 void device_probe_profile(gpointer a, gpointer b)
7764 {
7765         struct btd_device *device = a;
7766         struct btd_profile *profile = b;
7767         struct btd_service *service;
7768
7769         service = probe_service(device, profile, device->uuids);
7770         if (!service)
7771                 return;
7772
7773         device->services = g_slist_append(device->services, service);
7774
7775         if (!profile->auto_connect || !device->general_connect)
7776                 return;
7777
7778         device->pending = g_slist_append(device->pending, service);
7779
7780         if (g_slist_length(device->pending) == 1)
7781                 connect_next(device);
7782 }
7783
7784 void device_remove_profile(gpointer a, gpointer b)
7785 {
7786         struct btd_device *device = a;
7787         struct btd_profile *profile = b;
7788         struct btd_service *service;
7789         GSList *l;
7790
7791         l = find_service_with_profile(device->services, profile);
7792 #ifdef TIZEN_BT_HID_DEVICE_ENABLE
7793         if (l == NULL) {
7794                 if (g_strcmp0(profile->local_uuid , HID_DEVICE_UUID) == 0) {
7795                         l = find_service_with_uuid(device->services,
7796                                         HID_DEVICE_UUID);
7797                         if (l == NULL)
7798                                 return;
7799
7800                         service = l->data;
7801
7802                         if (btd_service_get_state(service) ==
7803                                 BTD_SERVICE_STATE_CONNECTED) {
7804                                 int err;
7805                                 err = btd_service_disconnect(service);
7806                                 if (err)
7807                                         error("error: %s", strerror(-err));
7808                         }
7809                 }
7810                 return;
7811         }
7812 #else
7813         if (l == NULL)
7814                 return;
7815 #endif
7816
7817         service = l->data;
7818         device->services = g_slist_delete_link(device->services, l);
7819         device->pending = g_slist_remove(device->pending, service);
7820         service_remove(service);
7821 }
7822
7823 void device_probe_profiles(struct btd_device *device, GSList *uuids)
7824 {
7825         struct probe_data d = { device, uuids };
7826         char addr[18];
7827
7828         ba2str(&device->bdaddr, addr);
7829
7830         if (device->blocked) {
7831                 DBG("Skipping profiles for blocked device %s", addr);
7832                 goto add_uuids;
7833         }
7834
7835         DBG("Probing profiles for device %s", addr);
7836
7837         btd_profile_foreach(dev_probe, &d);
7838
7839 add_uuids:
7840         device_add_uuids(device, uuids);
7841 }
7842
7843 static void store_sdp_record(GKeyFile *key_file, sdp_record_t *rec)
7844 {
7845         char handle_str[11];
7846         sdp_buf_t buf;
7847         int size, i;
7848         char *str;
7849
7850         sprintf(handle_str, "0x%8.8X", rec->handle);
7851
7852         if (sdp_gen_record_pdu(rec, &buf) < 0)
7853                 return;
7854
7855         size = buf.data_size;
7856
7857         str = g_malloc0(size*2+1);
7858
7859         for (i = 0; i < size; i++)
7860                 sprintf(str + (i * 2), "%02X", buf.data[i]);
7861
7862         g_key_file_set_string(key_file, "ServiceRecords", handle_str, str);
7863
7864         free(buf.data);
7865         g_free(str);
7866 }
7867
7868 static void store_primaries_from_sdp_record(GKeyFile *key_file,
7869                                                 sdp_record_t *rec)
7870 {
7871         uuid_t uuid;
7872         char *att_uuid, *prim_uuid;
7873         uint16_t start = 0, end = 0, psm = 0;
7874         char handle[6], uuid_str[33];
7875         int i;
7876
7877         sdp_uuid16_create(&uuid, ATT_UUID);
7878         att_uuid = bt_uuid2string(&uuid);
7879
7880         sdp_uuid16_create(&uuid, GATT_PRIM_SVC_UUID);
7881         prim_uuid = bt_uuid2string(&uuid);
7882
7883         if (!record_has_uuid(rec, att_uuid))
7884                 goto done;
7885
7886         if (!gatt_parse_record(rec, &uuid, &psm, &start, &end))
7887                 goto done;
7888
7889         sprintf(handle, "%hu", start);
7890         switch (uuid.type) {
7891         case SDP_UUID16:
7892                 sprintf(uuid_str, "%4.4X", uuid.value.uuid16);
7893                 break;
7894         case SDP_UUID32:
7895                 sprintf(uuid_str, "%8.8X", uuid.value.uuid32);
7896                 break;
7897         case SDP_UUID128:
7898                 for (i = 0; i < 16; i++)
7899                         sprintf(uuid_str + (i * 2), "%2.2X",
7900                                         uuid.value.uuid128.data[i]);
7901                 break;
7902         default:
7903                 uuid_str[0] = '\0';
7904         }
7905
7906         g_key_file_set_string(key_file, handle, "UUID", prim_uuid);
7907         g_key_file_set_string(key_file, handle, "Value", uuid_str);
7908         g_key_file_set_integer(key_file, handle, "EndGroupHandle", end);
7909
7910 done:
7911         free(prim_uuid);
7912         free(att_uuid);
7913 }
7914
7915 static int rec_cmp(const void *a, const void *b)
7916 {
7917         const sdp_record_t *r1 = a;
7918         const sdp_record_t *r2 = b;
7919
7920         return r1->handle - r2->handle;
7921 }
7922
7923 static int update_record(struct browse_req *req, const char *uuid,
7924                                                         sdp_record_t *rec)
7925 {
7926         GSList *l;
7927
7928         /* Check for duplicates */
7929         if (sdp_list_find(req->records, rec, rec_cmp))
7930                 return -EALREADY;
7931
7932         /* Copy record */
7933         req->records = sdp_list_append(req->records, sdp_copy_record(rec));
7934
7935         /* Check if UUID is duplicated */
7936         l = g_slist_find_custom(req->device->uuids, uuid, bt_uuid_strcmp);
7937         if (l == NULL) {
7938                 l = g_slist_find_custom(req->profiles_added, uuid,
7939                                                         bt_uuid_strcmp);
7940                 if (l != NULL)
7941                         return 0;
7942                 req->profiles_added = g_slist_append(req->profiles_added,
7943                                                         g_strdup(uuid));
7944         }
7945
7946         return 0;
7947 }
7948
7949 static void update_bredr_services(struct browse_req *req, sdp_list_t *recs)
7950 {
7951         struct btd_device *device = req->device;
7952         sdp_list_t *seq;
7953         char srcaddr[18], dstaddr[18];
7954         char sdp_file[PATH_MAX];
7955         char att_file[PATH_MAX];
7956         GKeyFile *sdp_key_file;
7957         GKeyFile *att_key_file;
7958         GError *gerr = NULL;
7959
7960         char *data;
7961         gsize length = 0;
7962
7963         ba2str(btd_adapter_get_address(device->adapter), srcaddr);
7964         ba2str(&device->bdaddr, dstaddr);
7965
7966         snprintf(sdp_file, PATH_MAX, STORAGEDIR "/%s/cache/%s", srcaddr,
7967                                                                 dstaddr);
7968         create_file(sdp_file, 0600);
7969
7970         sdp_key_file = g_key_file_new();
7971         if (!g_key_file_load_from_file(sdp_key_file, sdp_file, 0, &gerr)) {
7972                 error("Unable to load key file from %s: (%s)", sdp_file,
7973                                                                 gerr->message);
7974                 g_clear_error(&gerr);
7975                 g_key_file_free(sdp_key_file);
7976                 sdp_key_file = NULL;
7977         }
7978
7979         snprintf(att_file, PATH_MAX, STORAGEDIR "/%s/%s/attributes", srcaddr,
7980                                                                 dstaddr);
7981         create_file(att_file, 0600);
7982
7983         att_key_file = g_key_file_new();
7984         if (!g_key_file_load_from_file(att_key_file, att_file, 0, &gerr)) {
7985                 error("Unable to load key file from %s: (%s)", att_file,
7986                                                                 gerr->message);
7987                 g_clear_error(&gerr);
7988                 g_key_file_free(att_key_file);
7989                 att_key_file = NULL;
7990         }
7991
7992         for (seq = recs; seq; seq = seq->next) {
7993                 sdp_record_t *rec = (sdp_record_t *) seq->data;
7994                 char *profile_uuid;
7995
7996                 if (!rec)
7997                         break;
7998
7999                 /* If service class attribute is missing, svclass will be all
8000                  * zero and the resulting uuid string will be NULL.
8001                  */
8002                 profile_uuid = bt_uuid2string(&rec->svclass);
8003
8004                 if (!profile_uuid)
8005                         continue;
8006
8007                 if (bt_uuid_strcmp(profile_uuid, PNP_UUID) == 0) {
8008                         uint16_t source, vendor, product, version;
8009                         sdp_data_t *pdlist;
8010
8011                         pdlist = sdp_data_get(rec, SDP_ATTR_VENDOR_ID_SOURCE);
8012                         source = pdlist ? pdlist->val.uint16 : 0x0000;
8013
8014                         pdlist = sdp_data_get(rec, SDP_ATTR_VENDOR_ID);
8015                         vendor = pdlist ? pdlist->val.uint16 : 0x0000;
8016
8017                         pdlist = sdp_data_get(rec, SDP_ATTR_PRODUCT_ID);
8018                         product = pdlist ? pdlist->val.uint16 : 0x0000;
8019
8020                         pdlist = sdp_data_get(rec, SDP_ATTR_VERSION);
8021                         version = pdlist ? pdlist->val.uint16 : 0x0000;
8022
8023                         if (source || vendor || product || version)
8024                                 btd_device_set_pnpid(device, source, vendor,
8025                                                         product, version);
8026                 }
8027
8028                 if (update_record(req, profile_uuid, rec) < 0)
8029                         goto next;
8030
8031                 if (sdp_key_file)
8032                         store_sdp_record(sdp_key_file, rec);
8033
8034                 if (att_key_file)
8035                         store_primaries_from_sdp_record(att_key_file, rec);
8036
8037 next:
8038                 free(profile_uuid);
8039         }
8040
8041         if (sdp_key_file) {
8042                 data = g_key_file_to_data(sdp_key_file, &length, NULL);
8043                 if (length > 0) {
8044                         if (!g_file_set_contents(sdp_file, data, length,
8045                                                                 &gerr)) {
8046                                 error("Unable set contents for %s: (%s)",
8047                                                 sdp_file, gerr->message);
8048                                 g_clear_error(&gerr);
8049                         }
8050                 }
8051
8052                 g_free(data);
8053                 g_key_file_free(sdp_key_file);
8054         }
8055
8056         if (att_key_file) {
8057                 data = g_key_file_to_data(att_key_file, &length, NULL);
8058                 if (length > 0) {
8059                         if (!g_file_set_contents(att_file, data, length,
8060                                                                 &gerr)) {
8061                                 error("Unable set contents for %s: (%s)",
8062                                                 att_file, gerr->message);
8063                                 g_clear_error(&gerr);
8064                         }
8065                 }
8066
8067                 g_free(data);
8068                 g_key_file_free(att_key_file);
8069         }
8070 }
8071
8072 static int primary_cmp(gconstpointer a, gconstpointer b)
8073 {
8074         return memcmp(a, b, sizeof(struct gatt_primary));
8075 }
8076
8077 static void update_gatt_uuids(struct browse_req *req, GSList *current,
8078                                                                 GSList *found)
8079 {
8080         GSList *l, *lmatch;
8081
8082         /* Added Profiles */
8083         for (l = found; l; l = g_slist_next(l)) {
8084                 struct gatt_primary *prim = l->data;
8085
8086                 /* Entry found ? */
8087                 lmatch = g_slist_find_custom(current, prim, primary_cmp);
8088                 if (lmatch)
8089                         continue;
8090
8091                 /* New entry */
8092                 req->profiles_added = g_slist_append(req->profiles_added,
8093                                                         g_strdup(prim->uuid));
8094
8095                 DBG("UUID Added: %s", prim->uuid);
8096         }
8097 }
8098
8099 static GSList *device_services_from_record(struct btd_device *device,
8100                                                         GSList *profiles)
8101 {
8102         GSList *l, *prim_list = NULL;
8103         char *att_uuid;
8104         uuid_t proto_uuid;
8105
8106         sdp_uuid16_create(&proto_uuid, ATT_UUID);
8107         att_uuid = bt_uuid2string(&proto_uuid);
8108
8109         for (l = profiles; l; l = l->next) {
8110                 const char *profile_uuid = l->data;
8111                 const sdp_record_t *rec;
8112                 struct gatt_primary *prim;
8113                 uint16_t start = 0, end = 0, psm = 0;
8114                 uuid_t prim_uuid;
8115
8116                 rec = btd_device_get_record(device, profile_uuid);
8117                 if (!rec)
8118                         continue;
8119
8120                 if (!record_has_uuid(rec, att_uuid))
8121                         continue;
8122
8123                 if (!gatt_parse_record(rec, &prim_uuid, &psm, &start, &end))
8124                         continue;
8125
8126                 prim = g_new0(struct gatt_primary, 1);
8127                 prim->range.start = start;
8128                 prim->range.end = end;
8129                 sdp_uuid2strn(&prim_uuid, prim->uuid, sizeof(prim->uuid));
8130
8131                 prim_list = g_slist_append(prim_list, prim);
8132         }
8133
8134         free(att_uuid);
8135
8136         return prim_list;
8137 }
8138
8139 static void search_cb(sdp_list_t *recs, int err, gpointer user_data)
8140 {
8141         struct browse_req *req = user_data;
8142         struct btd_device *device = req->device;
8143         DBusMessage *reply;
8144         GSList *primaries;
8145         char addr[18];
8146
8147         ba2str(&device->bdaddr, addr);
8148
8149         if (err < 0) {
8150                 error("%s: error updating services: %s (%d)",
8151                                 addr, strerror(-err), -err);
8152                 goto send_reply;
8153         }
8154
8155         update_bredr_services(req, recs);
8156
8157         if (device->tmp_records)
8158                 sdp_list_free(device->tmp_records,
8159                                         (sdp_free_func_t) sdp_record_free);
8160
8161         device->tmp_records = req->records;
8162         req->records = NULL;
8163
8164         if (!req->profiles_added) {
8165                 DBG("%s: No service update", addr);
8166                 goto send_reply;
8167         }
8168
8169         primaries = device_services_from_record(device, req->profiles_added);
8170         if (primaries)
8171                 device_register_primaries(device, primaries, ATT_PSM);
8172
8173         /*
8174          * TODO: The btd_service instances for GATT services need to be
8175          * initialized with the service handles. Eventually this code should
8176          * perform ATT protocol service discovery over the ATT PSM to obtain
8177          * the full list of services and populate a client-role gatt_db over
8178          * BR/EDR.
8179          */
8180         device_probe_profiles(device, req->profiles_added);
8181
8182         /* Propagate services changes */
8183         g_dbus_emit_property_changed(dbus_conn, req->device->path,
8184                                                 DEVICE_INTERFACE, "UUIDs");
8185
8186 send_reply:
8187 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
8188         if (!req->msg)
8189                 goto done;
8190
8191         /* since no new services are found, UUID signal is not emitted,
8192         ** so send a reply to the framework with the existing services */
8193         if (dbus_message_is_method_call(req->msg, DEVICE_INTERFACE,
8194                                 "DiscoverServices"))
8195                 discover_services_reply(req, err, device->tmp_records);
8196
8197 done:
8198 #endif
8199         /* If SDP search failed during an ongoing connection request, we should
8200          * reply to D-Bus method call.
8201          */
8202         if (err < 0 && device->connect) {
8203                 DBG("SDP failed during connection");
8204                 reply = btd_error_failed(device->connect, strerror(-err));
8205                 g_dbus_send_message(dbus_conn, reply);
8206                 dbus_message_unref(device->connect);
8207                 device->connect = NULL;
8208         }
8209
8210         device_svc_resolved(device, BROWSE_SDP, BDADDR_BREDR, err);
8211 }
8212
8213 static void browse_cb(sdp_list_t *recs, int err, gpointer user_data)
8214 {
8215         struct browse_req *req = user_data;
8216         struct btd_device *device = req->device;
8217         struct btd_adapter *adapter = device->adapter;
8218         uuid_t uuid;
8219
8220         /* If we have a valid response and req->search_uuid == 2, then L2CAP
8221          * UUID & PNP searching was successful -- we are done */
8222         if (err < 0 || (req->search_uuid == 2 && req->records)) {
8223                 if (err == -ECONNRESET && req->reconnect_attempt < 1) {
8224                         req->search_uuid--;
8225                         req->reconnect_attempt++;
8226                 } else
8227                         goto done;
8228         }
8229
8230         update_bredr_services(req, recs);
8231
8232         /* Search for mandatory uuids */
8233         if (uuid_list[req->search_uuid]) {
8234                 sdp_uuid16_create(&uuid, uuid_list[req->search_uuid++]);
8235                 bt_search_service(btd_adapter_get_address(adapter),
8236                                                 &device->bdaddr, &uuid,
8237                                                 browse_cb, user_data, NULL,
8238                                                 req->sdp_flags);
8239                 return;
8240         }
8241
8242 done:
8243         search_cb(recs, err, user_data);
8244 }
8245
8246 static bool device_get_auto_connect(struct btd_device *device)
8247 {
8248         if (device->disable_auto_connect)
8249                 return false;
8250
8251         return device->auto_connect;
8252 }
8253
8254 static void disconnect_gatt_service(gpointer data, gpointer user_data)
8255 {
8256         struct btd_service *service = data;
8257         struct btd_profile *profile = btd_service_get_profile(service);
8258
8259         /* Ignore if profile cannot accept connections */
8260         if (!profile->accept)
8261                 return;
8262
8263         btd_service_disconnect(service);
8264 }
8265
8266 static void att_disconnected_cb(int err, void *user_data)
8267 {
8268         struct btd_device *device = user_data;
8269
8270         DBG("");
8271
8272         if (device->browse)
8273                 goto done;
8274
8275         DBG("%s (%d)", strerror(err), err);
8276
8277         g_slist_foreach(device->services, disconnect_gatt_service, NULL);
8278
8279         btd_gatt_client_disconnected(device->client_dbus);
8280
8281         if (!device_get_auto_connect(device)) {
8282                 DBG("Automatic connection disabled");
8283                 goto done;
8284         }
8285
8286         /*
8287          * Keep scanning/re-connection active if disconnection reason
8288          * is connection timeout, remote user terminated connection or local
8289          * initiated disconnection.
8290          */
8291         if (err == ETIMEDOUT || err == ECONNRESET || err == ECONNABORTED)
8292                 adapter_connect_list_add(device->adapter, device);
8293
8294 done:
8295 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
8296         device_set_gatt_connected(device, FALSE);
8297 #endif
8298         attio_cleanup(device);
8299 }
8300
8301 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
8302 static void att_mtu_changed(uint16_t mtu, void *user_data)
8303 {
8304         struct btd_device *device = user_data;
8305
8306         DBG("att mtu changed %d", mtu);
8307
8308         g_dbus_emit_signal(dbus_conn, device->path,
8309                 DEVICE_INTERFACE, "AttMtuChanged",
8310                 DBUS_TYPE_UINT16, &mtu,
8311                 DBUS_TYPE_INVALID);
8312 }
8313 #endif
8314
8315 static void register_gatt_services(struct btd_device *device)
8316 {
8317         struct browse_req *req = device->browse;
8318         GSList *services = NULL;
8319
8320         if (!bt_gatt_client_is_ready(device->client))
8321                 return;
8322
8323         /*
8324          * TODO: Remove the primaries list entirely once all profiles use
8325          * shared/gatt.
8326          */
8327         gatt_db_foreach_service(device->db, NULL, add_primary, &services);
8328
8329         btd_device_set_temporary(device, false);
8330
8331 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
8332         if (req) {
8333                 if (req->search_uuid)
8334                         DBG("browse req. is for SDP. Ignore it.");
8335                 else
8336                         update_gatt_uuids(req, device->primaries, services);
8337         }
8338 #else
8339         if (req)
8340                 update_gatt_uuids(req, device->primaries, services);
8341 #endif
8342
8343 #ifndef TIZEN_FEATURE_BLUEZ_MODIFY
8344         /* do not delete existing primary list,
8345          * just append the new primary uuids,
8346          * the list will be modifed when service changed
8347          * indication is received during connection */
8348         g_slist_free_full(device->primaries, g_free);
8349         device->primaries = NULL;
8350 #endif
8351
8352         device_register_primaries(device, services, -1);
8353
8354         device_add_gatt_services(device);
8355 }
8356
8357 static void gatt_client_init(struct btd_device *device);
8358
8359 static void gatt_client_ready_cb(bool success, uint8_t att_ecode,
8360                                                                 void *user_data)
8361 {
8362         struct btd_device *device = user_data;
8363
8364         DBG("status: %s, error: %u", success ? "success" : "failed", att_ecode);
8365
8366         if (!success) {
8367                 device_svc_resolved(device, BROWSE_GATT, device->bdaddr_type,
8368                                                                         -EIO);
8369                 return;
8370         }
8371
8372 #ifndef TIZEN_FEATURE_BLUEZ_MODIFY
8373         /* Register the services after setting the client is ready
8374          * and exporting all the services and characteristics paths.
8375          */
8376         register_gatt_services(device);
8377 #endif
8378
8379         btd_gatt_client_ready(device->client_dbus);
8380 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
8381         register_gatt_services(device);
8382 #endif
8383
8384         device_svc_resolved(device, BROWSE_GATT, device->bdaddr_type, 0);
8385
8386         store_gatt_db(device);
8387
8388 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
8389         if (device->name[0] == '\0') {
8390                 char *name = NULL;
8391                 name = bt_gatt_client_get_gap_device_name(device->client);
8392                 if (name)
8393                         strncpy(device->name, name, MAX_NAME_LENGTH);
8394         }
8395 #endif
8396 }
8397
8398 static void gatt_client_service_changed(uint16_t start_handle,
8399                                                         uint16_t end_handle,
8400                                                         void *user_data)
8401 {
8402         DBG("start 0x%04x, end: 0x%04x", start_handle, end_handle);
8403 }
8404
8405 static void gatt_debug(const char *str, void *user_data)
8406 {
8407         DBG("%s", str);
8408 }
8409
8410 static void gatt_client_init(struct btd_device *device)
8411 {
8412         gatt_client_cleanup(device);
8413
8414         if (!device->connect && !btd_opts.reverse_discovery) {
8415                 DBG("Reverse service discovery disabled: skipping GATT client");
8416                 return;
8417         }
8418
8419         device->client = bt_gatt_client_new(device->db, device->att,
8420                                                         device->att_mtu, 0);
8421         if (!device->client) {
8422                 DBG("Failed to initialize");
8423                 return;
8424         }
8425
8426         bt_gatt_client_set_debug(device->client, gatt_debug, NULL, NULL);
8427
8428         /*
8429          * Notify notify existing service about the new connection so they can
8430          * react to notifications while discovering services
8431          */
8432         device_accept_gatt_profiles(device);
8433
8434         device->gatt_ready_id = bt_gatt_client_ready_register(device->client,
8435                                                         gatt_client_ready_cb,
8436                                                         device, NULL);
8437         if (!device->gatt_ready_id) {
8438                 DBG("Failed to register GATT ready callback");
8439                 gatt_client_cleanup(device);
8440                 return;
8441         }
8442
8443         if (!bt_gatt_client_set_service_changed(device->client,
8444                                                 gatt_client_service_changed,
8445                                                 device, NULL)) {
8446                 DBG("Failed to set service changed handler");
8447                 gatt_client_cleanup(device);
8448                 return;
8449         }
8450
8451         btd_gatt_client_connected(device->client_dbus);
8452
8453         /* Only initiate EATT connection when acting as initiator, as acceptor
8454          * it shall be triggered only when ready to avoid possible clashes where
8455          * both sides attempt to connection at same time.
8456          */
8457         if (device->connect)
8458                 btd_gatt_client_eatt_connect(device->client_dbus);
8459 }
8460
8461 static void gatt_server_init(struct btd_device *device,
8462                                 struct btd_gatt_database *database)
8463 {
8464         struct gatt_db *db = btd_gatt_database_get_db(database);
8465
8466         if (!db) {
8467                 error("No local GATT database exists for this adapter");
8468                 return;
8469         }
8470
8471         gatt_server_cleanup(device);
8472
8473         device->server = bt_gatt_server_new(db, device->att, device->att_mtu,
8474                                                 btd_opts.key_size);
8475         if (!device->server) {
8476                 error("Failed to initialize bt_gatt_server");
8477                 return;
8478         }
8479  
8480         bt_att_set_enc_key_size(device->att, device->ltk_enc_size);
8481
8482         bt_gatt_server_set_debug(device->server, gatt_debug, NULL, NULL);
8483
8484 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
8485         if (!bt_gatt_server_set_mtu_changed(device->server,
8486                                                 att_mtu_changed,
8487                                                 device, NULL)) {
8488                 DBG("Failed to set mtu changed handler");
8489                 return;
8490         }
8491 #endif
8492 }
8493
8494 static bool local_counter(uint32_t *sign_cnt, void *user_data)
8495 {
8496         struct btd_device *dev = user_data;
8497
8498         if (!dev->local_csrk)
8499                 return false;
8500
8501         *sign_cnt = dev->local_csrk->counter++;
8502
8503         store_device_info(dev);
8504
8505         return true;
8506 }
8507
8508 static bool remote_counter(uint32_t *sign_cnt, void *user_data)
8509 {
8510         struct btd_device *dev = user_data;
8511
8512         if (!dev->remote_csrk || *sign_cnt < dev->remote_csrk->counter)
8513                 return false;
8514
8515         dev->remote_csrk->counter = *sign_cnt;
8516
8517         store_device_info(dev);
8518
8519         return true;
8520 }
8521
8522 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
8523 static bool load_svc_change_indication_status(struct btd_device *device, const char *local,
8524                                 const char *peer)
8525 {
8526         char filename[PATH_MAX];
8527         GKeyFile *key_file;
8528         gboolean svc_change_regd = false;
8529         snprintf(filename, PATH_MAX, STORAGEDIR "/%s/%s/info", local, peer);
8530
8531         key_file = g_key_file_new();
8532         if (!g_key_file_load_from_file(key_file, filename, 0, NULL))
8533                 goto failed;
8534
8535         /* Load Service changed Registered flag */
8536         svc_change_regd = g_key_file_get_boolean(key_file, "Att",
8537                                                 "SvcChangeRegd", NULL);
8538         bt_att_set_svc_changed_indication_registered(device->att,
8539                                                 svc_change_regd);
8540
8541
8542 failed:
8543         g_key_file_free(key_file);
8544
8545         return svc_change_regd;
8546 }
8547 #endif
8548
8549 bool device_attach_att(struct btd_device *dev, GIOChannel *io)
8550 {
8551         GError *gerr = NULL;
8552         GAttrib *attrib;
8553         BtIOSecLevel sec_level;
8554         uint16_t mtu;
8555         uint16_t cid;
8556         struct btd_gatt_database *database;
8557         const bdaddr_t *dst;
8558         char dstaddr[18];
8559 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
8560         uint8_t dst_type = BDADDR_BREDR;
8561         char srcaddr[18];
8562         const bdaddr_t *src;
8563 #endif
8564
8565         bt_io_get(io, &gerr, BT_IO_OPT_SEC_LEVEL, &sec_level,
8566                                                 BT_IO_OPT_IMTU, &mtu,
8567                                                 BT_IO_OPT_CID, &cid,
8568 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
8569                                                 BT_IO_OPT_DEST_TYPE, &dst_type,
8570 #endif
8571                                                 BT_IO_OPT_INVALID);
8572
8573         if (gerr) {
8574                 error("bt_io_get: %s", gerr->message);
8575                 g_error_free(gerr);
8576                 return false;
8577         }
8578
8579         if (dev->att) {
8580                 if (btd_opts.gatt_channels == bt_att_get_channels(dev->att)) {
8581                         DBG("EATT channel limit reached");
8582                         return false;
8583                 }
8584
8585                 if (!bt_att_attach_fd(dev->att, g_io_channel_unix_get_fd(io))) {
8586                         DBG("EATT channel connected");
8587                         g_io_channel_set_close_on_unref(io, FALSE);
8588                         return true;
8589                 }
8590
8591                 error("Failed to attach EATT channel");
8592                 return false;
8593         }
8594
8595 #ifndef TIZEN_FEATURE_BLUEZ_MODIFY
8596         if (sec_level == BT_IO_SEC_LOW && dev->le_state.paired) {
8597                 DBG("Elevating security level since LTK is available");
8598
8599                 sec_level = BT_IO_SEC_MEDIUM;
8600                 bt_io_set(io, &gerr, BT_IO_OPT_SEC_LEVEL, sec_level,
8601                                                         BT_IO_OPT_INVALID);
8602                 if (gerr) {
8603                         error("bt_io_set: %s", gerr->message);
8604                         g_error_free(gerr);
8605                         return false;
8606                 }
8607         }
8608 #endif
8609
8610         dev->att_mtu = MIN(mtu, btd_opts.gatt_mtu);
8611         attrib = g_attrib_new(io,
8612                         cid == ATT_CID ? BT_ATT_DEFAULT_LE_MTU : dev->att_mtu,
8613                         false);
8614         if (!attrib) {
8615                 error("Unable to create new GAttrib instance");
8616                 return false;
8617         }
8618
8619         dev->attrib = attrib;
8620         dev->att = g_attrib_get_att(attrib);
8621
8622         bt_att_ref(dev->att);
8623
8624         bt_att_set_debug(dev->att, BT_ATT_DEBUG, gatt_debug, NULL, NULL);
8625
8626         dev->att_disconn_id = bt_att_register_disconnect(dev->att,
8627                                                 att_disconnected_cb, dev, NULL);
8628         bt_att_set_close_on_unref(dev->att, true);
8629
8630         if (dev->local_csrk)
8631                 bt_att_set_local_key(dev->att, dev->local_csrk->key,
8632                                                         local_counter, dev);
8633
8634         if (dev->remote_csrk)
8635                 bt_att_set_remote_key(dev->att, dev->remote_csrk->key,
8636                                                         remote_counter, dev);
8637
8638 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
8639         if (dst_type != BDADDR_BREDR && device_get_rpa_exist(dev) == true) {
8640                 bt_att_set_remote_addr(dev->att,
8641                                         device_get_rpa(dev), BDADDR_LE_RANDOM);
8642         } else {
8643                 bt_att_set_remote_addr(dev->att,
8644                                         &dev->bdaddr, dev->bdaddr_type);
8645         }
8646 #endif
8647
8648         database = btd_adapter_get_database(dev->adapter);
8649
8650         dst = device_get_address(dev);
8651         ba2str(dst, dstaddr);
8652
8653         if (gatt_db_isempty(dev->db))
8654                 load_gatt_db(dev, btd_adapter_get_storage_dir(dev->adapter),
8655                                                                 dstaddr);
8656
8657         gatt_client_init(dev);
8658         gatt_server_init(dev, database);
8659
8660         /*
8661          * Remove the device from the connect_list and give the passive
8662          * scanning another chance to be restarted in case there are
8663          * other devices in the connect_list.
8664          */
8665         adapter_connect_list_remove(dev->adapter, dev);
8666
8667 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
8668         src = btd_adapter_get_address(dev->adapter);
8669         ba2str(src, srcaddr);
8670
8671         /* load the service changed indication status on connection */
8672         load_svc_change_indication_status(dev, srcaddr, dstaddr);
8673 #endif
8674
8675         return true;
8676 }
8677
8678 static void att_connect_cb(GIOChannel *io, GError *gerr, gpointer user_data)
8679 {
8680         struct btd_device *device = user_data;
8681         DBusMessage *reply;
8682         uint8_t io_cap;
8683         int err = 0;
8684
8685         g_io_channel_unref(device->att_io);
8686         device->att_io = NULL;
8687
8688         if (gerr) {
8689                 DBG("%s", gerr->message);
8690
8691                 if (g_error_matches(gerr, BT_IO_ERROR, ECONNABORTED))
8692                         goto done;
8693
8694                 if (device_get_auto_connect(device)) {
8695                         DBG("Enabling automatic connections");
8696                         adapter_connect_list_add(device->adapter, device);
8697                 }
8698
8699                 if (device->browse)
8700                         browse_request_complete(device->browse,
8701                                                 BROWSE_GATT,
8702                                                 device->bdaddr_type,
8703                                                 -ECONNABORTED);
8704
8705                 err = -ECONNABORTED;
8706                 goto done;
8707         }
8708
8709         if (!device_attach_att(device, io))
8710                 goto done;
8711
8712         if (!device->bonding)
8713                 goto done;
8714
8715         if (device->bonding->agent)
8716                 io_cap = agent_get_io_capability(device->bonding->agent);
8717         else
8718                 io_cap = IO_CAPABILITY_NOINPUTNOOUTPUT;
8719
8720         err = adapter_create_bonding(device->adapter, &device->bdaddr,
8721                                         device->bdaddr_type, io_cap);
8722 done:
8723         if (device->bonding && err < 0) {
8724                 reply = btd_error_failed(device->bonding->msg, strerror(-err));
8725                 g_dbus_send_message(dbus_conn, reply);
8726                 bonding_request_cancel(device->bonding);
8727                 bonding_request_free(device->bonding);
8728         }
8729
8730         if (!err)
8731                 device_browse_gatt(device, NULL);
8732
8733         if (device->connect) {
8734                 if (err < 0)
8735                         reply = btd_error_failed(device->connect,
8736                                         btd_error_le_conn_from_errno(err));
8737                 else
8738                         reply = dbus_message_new_method_return(device->connect);
8739
8740                 g_dbus_send_message(dbus_conn, reply);
8741                 dbus_message_unref(device->connect);
8742                 device->connect = NULL;
8743         }
8744 }
8745
8746 int device_connect_le(struct btd_device *dev)
8747 {
8748         struct btd_adapter *adapter = dev->adapter;
8749         BtIOSecLevel sec_level;
8750         GIOChannel *io;
8751         GError *gerr = NULL;
8752         char addr[18];
8753
8754         /* There is one connection attempt going on */
8755         if (dev->att_io)
8756                 return -EALREADY;
8757
8758         ba2str(&dev->bdaddr, addr);
8759
8760         DBG("Connection attempt to: %s", addr);
8761
8762         if (dev->le_state.paired)
8763                 sec_level = BT_IO_SEC_MEDIUM;
8764         else
8765                 sec_level = BT_IO_SEC_LOW;
8766
8767         /*
8768          * This connection will help us catch any PDUs that comes before
8769          * pairing finishes
8770          */
8771         io = bt_io_connect(att_connect_cb, dev, NULL, &gerr,
8772                         BT_IO_OPT_SOURCE_BDADDR,
8773                         btd_adapter_get_address(adapter),
8774                         BT_IO_OPT_SOURCE_TYPE,
8775                         btd_adapter_get_address_type(adapter),
8776                         BT_IO_OPT_DEST_BDADDR, &dev->bdaddr,
8777                         BT_IO_OPT_DEST_TYPE, dev->bdaddr_type,
8778                         BT_IO_OPT_CID, ATT_CID,
8779                         BT_IO_OPT_SEC_LEVEL, sec_level,
8780                         BT_IO_OPT_INVALID);
8781
8782         if (io == NULL) {
8783                 if (dev->bonding) {
8784                         DBusMessage *reply = btd_error_failed(
8785                                         dev->bonding->msg, gerr->message);
8786
8787                         g_dbus_send_message(dbus_conn, reply);
8788                         bonding_request_cancel(dev->bonding);
8789                         bonding_request_free(dev->bonding);
8790                 }
8791
8792                 error("ATT bt_io_connect(%s): %s", addr, gerr->message);
8793                 g_error_free(gerr);
8794                 return -EIO;
8795         }
8796
8797         /* Keep this, so we can cancel the connection */
8798         dev->att_io = io;
8799
8800         return 0;
8801 }
8802
8803 static struct browse_req *browse_request_new(struct btd_device *device,
8804                                                         uint8_t type,
8805                                                         DBusMessage *msg)
8806 {
8807         struct browse_req *req;
8808
8809         if (device->browse)
8810                 return NULL;
8811
8812         req = g_new0(struct browse_req, 1);
8813         req->device = device;
8814         req->type = type;
8815
8816         device->browse = req;
8817
8818         if (!msg)
8819                 return req;
8820
8821         req->msg = dbus_message_ref(msg);
8822
8823         /*
8824          * Track the request owner to cancel it automatically if the owner
8825          * exits
8826          */
8827         req->listener_id = g_dbus_add_disconnect_watch(dbus_conn,
8828                                                 dbus_message_get_sender(msg),
8829                                                 browse_request_exit,
8830                                                 req, NULL);
8831
8832         return req;
8833 }
8834
8835 static int device_browse_gatt(struct btd_device *device, DBusMessage *msg)
8836 {
8837         struct btd_adapter *adapter = device->adapter;
8838         struct browse_req *req;
8839
8840 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
8841         DBG("");
8842 #endif
8843         req = browse_request_new(device, BROWSE_GATT, msg);
8844         if (!req)
8845                 return -EBUSY;
8846
8847         if (device->client) {
8848                 /*
8849                  * If discovery has not yet completed, then wait for gatt-client
8850                  * to become ready.
8851                  */
8852                 if (!bt_gatt_client_is_ready(device->client))
8853                         return 0;
8854
8855                 /*
8856                  * Services have already been discovered, so signal this browse
8857                  * request as resolved.
8858                  */
8859                 device_svc_resolved(device, BROWSE_GATT, device->bdaddr_type,
8860                                                                         0);
8861                 return 0;
8862         }
8863
8864         device->att_io = bt_io_connect(att_connect_cb,
8865                                 device, NULL, NULL,
8866                                 BT_IO_OPT_SOURCE_BDADDR,
8867                                 btd_adapter_get_address(adapter),
8868                                 BT_IO_OPT_SOURCE_TYPE,
8869                                 btd_adapter_get_address_type(adapter),
8870                                 BT_IO_OPT_DEST_BDADDR, &device->bdaddr,
8871                                 BT_IO_OPT_DEST_TYPE, device->bdaddr_type,
8872                                 BT_IO_OPT_CID, ATT_CID,
8873                                 BT_IO_OPT_SEC_LEVEL, BT_IO_SEC_LOW,
8874                                 BT_IO_OPT_INVALID);
8875
8876         if (device->att_io == NULL) {
8877                 browse_request_free(req);
8878                 return -EIO;
8879         }
8880
8881         return 0;
8882 }
8883
8884 static uint16_t get_sdp_flags(struct btd_device *device)
8885 {
8886         uint16_t vid, pid;
8887
8888         vid = btd_device_get_vendor(device);
8889         pid = btd_device_get_product(device);
8890
8891         /* Sony DualShock 4 is not respecting negotiated L2CAP MTU. This might
8892          * results in SDP response being dropped by kernel. Workaround this by
8893          * forcing SDP code to use bigger MTU while connecting.
8894          */
8895         if (vid == 0x054c && pid == 0x05c4)
8896                 return SDP_LARGE_MTU;
8897
8898         if (btd_adapter_ssp_enabled(device->adapter))
8899                 return 0;
8900
8901         /* if no EIR try matching Sony DualShock 4 with name and class */
8902         if (!strncmp(device->name, "Wireless Controller", MAX_NAME_LENGTH) &&
8903                         device->class == 0x2508)
8904                 return SDP_LARGE_MTU;
8905
8906         return 0;
8907 }
8908
8909 static int device_browse_sdp(struct btd_device *device, DBusMessage *msg)
8910 {
8911         struct btd_adapter *adapter = device->adapter;
8912         struct browse_req *req;
8913         uuid_t uuid;
8914         int err;
8915
8916 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
8917         DBG("");
8918 #endif
8919         req = browse_request_new(device, BROWSE_SDP, msg);
8920         if (!req)
8921                 return -EBUSY;
8922
8923         sdp_uuid16_create(&uuid, uuid_list[req->search_uuid++]);
8924
8925         req->sdp_flags = get_sdp_flags(device);
8926
8927         err = bt_search(btd_adapter_get_address(adapter),
8928                         &device->bdaddr, &uuid, browse_cb, req, NULL,
8929                         req->sdp_flags);
8930         if (err < 0) {
8931 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
8932                 device->browse = NULL;
8933 #endif
8934                 browse_request_free(req);
8935                 return err;
8936         }
8937
8938         return err;
8939 }
8940
8941 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
8942 void device_set_last_addr_type(struct btd_device *device, uint8_t type)
8943 {
8944         if (!device)
8945                 return;
8946
8947         //DBG("Last addr type %d", type);
8948
8949         device->last_bdaddr_type = type;
8950 }
8951
8952 gboolean device_is_ipsp_connected(struct btd_device * device)
8953 {
8954         return device->ipsp_connected;
8955 }
8956
8957 void device_set_ipsp_connected(struct btd_device *device, gboolean connected,
8958                                         const unsigned char *ifname)
8959 {
8960         char *iface_name = NULL;
8961
8962         if (device == NULL) {
8963                 error("device is NULL");
8964                 return;
8965         }
8966
8967         if (device->ipsp_connected == connected)
8968                 return;
8969
8970         device->ipsp_connected = connected;
8971
8972         memset(device->if_name, 0, sizeof(device->if_name));
8973         memcpy(device->if_name, ifname, 16);
8974         iface_name = device->if_name;
8975
8976         DBG("ipsp_connected %d", connected);
8977         DBG("ipsp_iface: %s is Up !", iface_name);
8978
8979         g_dbus_emit_signal(dbus_conn, device->path,
8980                         DEVICE_INTERFACE, "IpspStateChanged",
8981                         DBUS_TYPE_BOOLEAN, &connected,
8982                         DBUS_TYPE_STRING, &iface_name,
8983                         DBUS_TYPE_INVALID);
8984 }
8985 void device_le_data_length_changed(struct btd_device *device, uint16_t max_tx_octets,
8986                 uint16_t max_tx_time, uint16_t max_rx_octets, uint16_t max_rx_time)
8987 {
8988         if (device == NULL) {
8989                 error("device is NULL");
8990                 return;
8991         }
8992
8993         device->max_tx_octets = max_tx_octets;
8994         device->max_tx_time = max_tx_time;
8995         device->max_rx_octets = max_rx_octets;
8996         device->max_rx_time = max_rx_time;
8997
8998         DBG("data length changed values :max_tx_octets: %d  max_tx_time: %d  max_rx_octets: %d  max_rx_time: %d",
8999                 max_tx_octets, max_tx_time, max_rx_octets, max_rx_time);
9000
9001         g_dbus_emit_signal(dbus_conn, device->path,
9002                 DEVICE_INTERFACE, "LEDataLengthChanged",
9003                 DBUS_TYPE_UINT16, &max_tx_octets,
9004                 DBUS_TYPE_UINT16, &max_tx_time,
9005                 DBUS_TYPE_UINT16, &max_rx_octets,
9006                 DBUS_TYPE_UINT16, &max_rx_time,
9007                 DBUS_TYPE_INVALID);
9008 }
9009
9010 const bdaddr_t *device_get_rpa(struct btd_device *device)
9011 {
9012         return device->rpa;
9013 }
9014
9015 const uint8_t *device_get_irk_value(struct btd_device *device)
9016 {
9017         return device->irk_val;
9018 }
9019
9020 bool device_get_rpa_exist(struct btd_device *device)
9021 {
9022         return device->rpa ? true : false;
9023 }
9024
9025 void device_set_auth_addr_type(struct btd_device *device, uint8_t type)
9026 {
9027         if (!device)
9028                 return;
9029
9030         DBG("Auth addr type %d", type);
9031
9032         device->auth_bdaddr_type = type;
9033 }
9034
9035 void device_get_tizen_addr(struct btd_device *device, uint8_t type,
9036                            struct device_addr_type *addr)
9037 {
9038         if (!device || !addr)
9039                 return;
9040
9041         if (type == BDADDR_BREDR) {
9042                 bacpy(&addr->bdaddr, &device->bdaddr);
9043                 addr->bdaddr_type = BDADDR_BREDR;
9044                 return;
9045         }
9046
9047         if (device->rpa) {
9048                 bacpy(&addr->bdaddr, device->rpa);
9049                 addr->bdaddr_type = BDADDR_LE_RANDOM;
9050                 return;
9051         }
9052
9053         bacpy(&addr->bdaddr, &device->bdaddr);
9054         addr->bdaddr_type = device->bdaddr_type;
9055 }
9056 #endif
9057
9058 int device_discover_services(struct btd_device *device)
9059 {
9060         int err;
9061
9062         if (device->bredr)
9063                 err = device_browse_sdp(device, NULL);
9064         else
9065                 err = device_browse_gatt(device, NULL);
9066
9067         if (err == 0 && device->discov_timer) {
9068                 timeout_remove(device->discov_timer);
9069                 device->discov_timer = 0;
9070         }
9071
9072         return err;
9073 }
9074
9075 struct btd_adapter *device_get_adapter(struct btd_device *device)
9076 {
9077         if (!device)
9078                 return NULL;
9079
9080         return device->adapter;
9081 }
9082
9083 const bdaddr_t *device_get_address(struct btd_device *device)
9084 {
9085         return &device->bdaddr;
9086 }
9087 uint8_t device_get_le_address_type(struct btd_device *device)
9088 {
9089         return device->bdaddr_type;
9090 }
9091
9092 const char *device_get_path(const struct btd_device *device)
9093 {
9094         if (!device)
9095                 return NULL;
9096
9097         return device->path;
9098 }
9099
9100 gboolean device_is_temporary(struct btd_device *device)
9101 {
9102         return device->temporary;
9103 }
9104
9105 void btd_device_set_temporary(struct btd_device *device, bool temporary)
9106 {
9107         if (!device)
9108                 return;
9109
9110         if (device->temporary == temporary)
9111                 return;
9112
9113         if (device_address_is_private(device))
9114                 return;
9115
9116         DBG("temporary %d", temporary);
9117
9118         device->temporary = temporary;
9119
9120         if (temporary) {
9121                 if (device->bredr)
9122                         adapter_accept_list_remove(device->adapter, device);
9123                 adapter_connect_list_remove(device->adapter, device);
9124                 if (device->auto_connect) {
9125                         device->disable_auto_connect = TRUE;
9126                         device_set_auto_connect(device, FALSE);
9127                 }
9128                 set_temporary_timer(device, btd_opts.tmpto);
9129                 return;
9130         } else
9131                 clear_temporary_timer(device);
9132
9133         if (device->bredr)
9134                 adapter_accept_list_add(device->adapter, device);
9135
9136         store_device_info(device);
9137
9138         /* attributes were not stored when resolved if device was temporary */
9139         if (device->bdaddr_type != BDADDR_BREDR &&
9140                         device->le_state.svc_resolved &&
9141                         g_slist_length(device->primaries) != 0)
9142                 store_services(device);
9143 }
9144
9145 void btd_device_set_trusted(struct btd_device *device, gboolean trusted)
9146 {
9147         if (!device)
9148                 return;
9149
9150         if (device->trusted == trusted)
9151                 return;
9152
9153         DBG("trusted %d", trusted);
9154
9155         device->trusted = trusted;
9156
9157         store_device_info(device);
9158
9159         g_dbus_emit_property_changed(dbus_conn, device->path,
9160                                         DEVICE_INTERFACE, "Trusted");
9161 }
9162
9163 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
9164 void device_disconnect_blocked(struct btd_device *device, char *uuid)
9165 {
9166         struct btd_service *service;
9167         GSList *l;
9168
9169         if (!device || !uuid)
9170                 return;
9171
9172         l = find_service_with_uuid(device->services, uuid);
9173         if (l == NULL)
9174                 return;
9175
9176         service = l->data;
9177         if (btd_service_get_state(service) ==
9178                         BTD_SERVICE_STATE_CONNECTED) {
9179                 int err;
9180                 err = btd_service_disconnect(service);
9181                 if (err)
9182                         error("error: %s", strerror(-err));
9183         }
9184 }
9185
9186 void btd_device_set_trusted_profiles(struct btd_device *device,
9187                 uint32_t pbap, uint32_t map, uint32_t sap,
9188                 uint32_t hfp_hs, uint32_t a2dp)
9189 {
9190         if (!device)
9191                 return;
9192
9193         DBG("TrustedProfiles Parameters: [PBAP %d] [MAP %d] [SAP %d] [HFP %d] [A2DP %d]",
9194                         pbap, map, sap, hfp_hs, a2dp);
9195
9196         if (device->trusted_profiles.pbap == pbap &&
9197                         device->trusted_profiles.map == map &&
9198                         device->trusted_profiles.sap == sap &&
9199                         device->trusted_profiles.hfp_hs == hfp_hs &&
9200                         device->trusted_profiles.a2dp == a2dp)
9201                 return;
9202
9203         /* Disconnect OBEX based profiles if connected */
9204         if (device->trusted_profiles.pbap != pbap) {
9205                 device->trusted_profiles.pbap = pbap;
9206                 if (pbap == SUPPORTED_BLOCKED)
9207                         device_disconnect_blocked(device, OBEX_PSE_UUID);
9208         } else if (device->trusted_profiles.map != map) {
9209                 device->trusted_profiles.map = map;
9210                 if (map == SUPPORTED_BLOCKED)
9211                         device_disconnect_blocked(device, OBEX_MAP_UUID);
9212         } else if (device->trusted_profiles.sap != sap) {
9213                 device->trusted_profiles.sap = sap;
9214                 if (sap == SUPPORTED_BLOCKED)
9215                         device_disconnect_blocked(device, SAP_UUID);
9216         } else if (device->trusted_profiles.hfp_hs != hfp_hs) {
9217                 device->trusted_profiles.hfp_hs = hfp_hs;
9218         } else if (device->trusted_profiles.a2dp != a2dp) {
9219                 device->trusted_profiles.a2dp = a2dp;
9220         }
9221
9222         store_device_info(device);
9223         g_dbus_emit_property_changed(dbus_conn, device->path,
9224                                         DEVICE_INTERFACE, "TrustedProfiles");
9225 }
9226 #endif
9227
9228 void device_set_bonded(struct btd_device *device, uint8_t bdaddr_type)
9229 {
9230         if (!device)
9231                 return;
9232
9233         DBG("");
9234
9235         if (bdaddr_type == BDADDR_BREDR)
9236                 device->bredr_state.bonded = true;
9237         else
9238                 device->le_state.bonded = true;
9239
9240         btd_device_set_temporary(device, false);
9241 }
9242
9243 void device_set_legacy(struct btd_device *device, bool legacy)
9244 {
9245         if (!device)
9246                 return;
9247
9248         DBG("legacy %d", legacy);
9249
9250         if (device->legacy == legacy)
9251                 return;
9252
9253         device->legacy = legacy;
9254
9255         g_dbus_emit_property_changed(dbus_conn, device->path,
9256                                         DEVICE_INTERFACE, "LegacyPairing");
9257 }
9258
9259 void device_store_svc_chng_ccc(struct btd_device *device, uint8_t bdaddr_type,
9260                                                                 uint16_t value)
9261 {
9262         char filename[PATH_MAX];
9263         char device_addr[18];
9264         GKeyFile *key_file;
9265         GError *gerr = NULL;
9266         uint16_t old_value;
9267         gsize length = 0;
9268         char *str;
9269
9270         ba2str(&device->bdaddr, device_addr);
9271         snprintf(filename, PATH_MAX, STORAGEDIR "/%s/%s/info",
9272                                 btd_adapter_get_storage_dir(device->adapter),
9273                                 device_addr);
9274
9275         key_file = g_key_file_new();
9276         if (!g_key_file_load_from_file(key_file, filename, 0, &gerr)) {
9277                 error("Unable to load key file from %s: (%s)", filename,
9278                                                                 gerr->message);
9279                 g_error_free(gerr);
9280         }
9281
9282         /* for bonded devices this is done on every connection so limit writes
9283          * to storage if no change needed
9284          */
9285         if (bdaddr_type == BDADDR_BREDR) {
9286                 old_value = g_key_file_get_integer(key_file, "ServiceChanged",
9287                                                         "CCC_BR/EDR", NULL);
9288                 if (old_value == value)
9289                         goto done;
9290
9291                 g_key_file_set_integer(key_file, "ServiceChanged", "CCC_BR/EDR",
9292                                                                         value);
9293         } else {
9294                 old_value = g_key_file_get_integer(key_file, "ServiceChanged",
9295                                                         "CCC_LE", NULL);
9296                 if (old_value == value)
9297                         goto done;
9298
9299                 g_key_file_set_integer(key_file, "ServiceChanged", "CCC_LE",
9300                                                                         value);
9301         }
9302
9303         create_file(filename, 0600);
9304
9305         str = g_key_file_to_data(key_file, &length, NULL);
9306         if (!g_file_set_contents(filename, str, length, &gerr)) {
9307                 error("Unable set contents for %s: (%s)", filename,
9308                                                                 gerr->message);
9309                 g_error_free(gerr);
9310         }
9311         g_free(str);
9312
9313 done:
9314         g_key_file_free(key_file);
9315 }
9316 void device_load_svc_chng_ccc(struct btd_device *device, uint16_t *ccc_le,
9317                                                         uint16_t *ccc_bredr)
9318 {
9319         char filename[PATH_MAX];
9320         char device_addr[18];
9321         GKeyFile *key_file;
9322         GError *gerr = NULL;
9323
9324         ba2str(&device->bdaddr, device_addr);
9325         snprintf(filename, PATH_MAX, STORAGEDIR "/%s/%s/info",
9326                                 btd_adapter_get_storage_dir(device->adapter),
9327                                 device_addr);
9328
9329         key_file = g_key_file_new();
9330         if (!g_key_file_load_from_file(key_file, filename, 0, &gerr)) {
9331                 error("Unable to load key file from %s: (%s)", filename,
9332                                                                 gerr->message);
9333                 g_error_free(gerr);
9334         }
9335
9336         if (!g_key_file_has_group(key_file, "ServiceChanged")) {
9337                 if (ccc_le)
9338                         *ccc_le = 0x0000;
9339                 if (ccc_bredr)
9340                         *ccc_bredr = 0x0000;
9341                 g_key_file_free(key_file);
9342                 return;
9343         }
9344
9345         if (ccc_le)
9346                 *ccc_le = g_key_file_get_integer(key_file, "ServiceChanged",
9347                                                         "CCC_LE", NULL);
9348
9349         if (ccc_bredr)
9350                 *ccc_bredr = g_key_file_get_integer(key_file, "ServiceChanged",
9351                                                         "CCC_BR/EDR", NULL);
9352
9353         g_key_file_free(key_file);
9354 }
9355
9356 void device_set_rssi_with_delta(struct btd_device *device, int8_t rssi,
9357                                                         int8_t delta_threshold)
9358 {
9359         if (!device)
9360                 return;
9361
9362 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
9363         if (rssi == 0 || device->rssi == 0) {
9364                 if (device->rssi == rssi)
9365                         return;
9366         }
9367
9368         device->rssi = rssi;
9369         DBG("rssi %d", rssi);
9370 #else
9371         if (rssi == 0 || device->rssi == 0) {
9372                 if (device->rssi == rssi)
9373                         return;
9374
9375                 DBG("rssi %d", rssi);
9376
9377                 device->rssi = rssi;
9378         } else {
9379                 int delta;
9380
9381                 if (device->rssi > rssi)
9382                         delta = device->rssi - rssi;
9383                 else
9384                         delta = rssi - device->rssi;
9385
9386                 /* only report changes of delta_threshold dBm or more */
9387                 if (delta < delta_threshold)
9388                         return;
9389
9390                 DBG("rssi %d delta %d", rssi, delta);
9391
9392                 device->rssi = rssi;
9393         }
9394 #endif
9395
9396         g_dbus_emit_property_changed(dbus_conn, device->path,
9397                                                 DEVICE_INTERFACE, "RSSI");
9398 }
9399
9400 void device_set_rssi(struct btd_device *device, int8_t rssi)
9401 {
9402         device_set_rssi_with_delta(device, rssi, RSSI_THRESHOLD);
9403 }
9404
9405 void device_set_tx_power(struct btd_device *device, int8_t tx_power)
9406 {
9407         if (!device)
9408                 return;
9409
9410         if (device->tx_power == tx_power)
9411                 return;
9412
9413         DBG("tx_power %d", tx_power);
9414
9415         device->tx_power = tx_power;
9416
9417         g_dbus_emit_property_changed(dbus_conn, device->path,
9418                                                 DEVICE_INTERFACE, "TxPower");
9419 }
9420
9421 void device_set_flags(struct btd_device *device, uint8_t flags)
9422 {
9423         if (!device)
9424                 return;
9425
9426 #ifndef TIZEN_FEATURE_BLUEZ_MODIFY
9427         DBG("flags %d", flags);
9428 #endif
9429
9430         if (device->ad_flags[0] == flags)
9431                 return;
9432
9433         device->ad_flags[0] = flags;
9434
9435         g_dbus_emit_property_changed(dbus_conn, device->path,
9436                                         DEVICE_INTERFACE, "AdvertisingFlags");
9437 }
9438
9439 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
9440 void device_set_le_connectable(struct btd_device *device, uint8_t adv_type)
9441 {
9442         if (!device)
9443                 return;
9444
9445         if (device->le_connectable)
9446                 return;
9447
9448         if (adv_type == ADV_TYPE_IND || adv_type == ADV_TYPE_DIRECT_IND)
9449                 device->le_connectable = true;
9450 }
9451 #endif
9452
9453 bool device_is_connectable(struct btd_device *device)
9454 {
9455         if (!device)
9456                 return false;
9457
9458         if (device->bredr)
9459                 return true;
9460
9461 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
9462         /* Check the ADV type. Some beacon device can be connectable regardless adv flags  */
9463         return device->le_connectable;
9464 #else
9465         /* Check if either Limited or General discoverable are set */
9466         return (device->ad_flags[0] & 0x03);
9467 #endif
9468 }
9469
9470 static bool start_discovery(gpointer user_data)
9471 {
9472         struct btd_device *device = user_data;
9473
9474         if (device->bredr)
9475                 device_browse_sdp(device, NULL);
9476         else
9477                 device_browse_gatt(device, NULL);
9478
9479         device->discov_timer = 0;
9480
9481         return FALSE;
9482 }
9483
9484 void device_set_paired(struct btd_device *dev, uint8_t bdaddr_type)
9485 {
9486         struct bearer_state *state = get_state(dev, bdaddr_type);
9487
9488         if (state->paired)
9489                 return;
9490
9491         state->paired = true;
9492
9493         /* If the other bearer state was already true we don't need to
9494          * send any property signals.
9495          */
9496         if (dev->bredr_state.paired == dev->le_state.paired)
9497                 return;
9498
9499         if (!state->svc_resolved) {
9500                 dev->pending_paired = true;
9501                 return;
9502         }
9503
9504 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
9505         if (dev->bonding == NULL)
9506 #endif
9507                 g_dbus_emit_property_changed(dbus_conn, dev->path,
9508                                                 DEVICE_INTERFACE, "Paired");
9509 }
9510
9511 void device_set_unpaired(struct btd_device *dev, uint8_t bdaddr_type)
9512 {
9513         struct bearer_state *state = get_state(dev, bdaddr_type);
9514
9515         if (!state->paired)
9516                 return;
9517
9518         state->paired = false;
9519
9520         /*
9521          * If the other bearer state is still true we don't need to
9522          * send any property signals or remove device.
9523          */
9524         if (dev->bredr_state.paired != dev->le_state.paired) {
9525                 /* TODO disconnect only unpaired bearer */
9526                 if (state->connected)
9527                         device_request_disconnect(dev, NULL);
9528
9529                 return;
9530         }
9531
9532         g_dbus_emit_property_changed(dbus_conn, dev->path,
9533                                                 DEVICE_INTERFACE, "Paired");
9534
9535         btd_device_set_temporary(dev, true);
9536
9537         if (btd_device_is_connected(dev))
9538                 device_request_disconnect(dev, NULL);
9539         else
9540                 btd_adapter_remove_device(dev->adapter, dev);
9541 }
9542
9543 static void device_auth_req_free(struct btd_device *device)
9544 {
9545         struct authentication_req *authr = device->authr;
9546
9547         if (!authr)
9548                 return;
9549
9550         if (authr->agent)
9551                 agent_unref(authr->agent);
9552
9553         g_free(authr->pincode);
9554         g_free(authr);
9555
9556         device->authr = NULL;
9557 }
9558
9559 bool device_is_retrying(struct btd_device *device)
9560 {
9561         struct bonding_req *bonding = device->bonding;
9562
9563         return bonding && bonding->retry_timer > 0;
9564 }
9565
9566 void device_bonding_complete(struct btd_device *device, uint8_t bdaddr_type,
9567                                                                 uint8_t status)
9568 {
9569         struct bonding_req *bonding = device->bonding;
9570         struct authentication_req *auth = device->authr;
9571         struct bearer_state *state = get_state(device, bdaddr_type);
9572
9573         DBG("bonding %p status 0x%02x", bonding, status);
9574
9575         if (auth && auth->agent)
9576                 agent_cancel(auth->agent);
9577
9578         if (status) {
9579                 device_cancel_authentication(device, TRUE);
9580
9581                 /* Put the device back to the temporary state so that it will be
9582                  * treated as a newly discovered device.
9583                  */
9584                 if (!device_is_paired(device, bdaddr_type) &&
9585                                 !device_is_trusted(device))
9586                         btd_device_set_temporary(device, true);
9587
9588                 device_bonding_failed(device, status);
9589 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
9590                 device->legacy_pairing = false;
9591 #endif
9592                 return;
9593         }
9594 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
9595                 device->legacy_pairing = false;
9596 #endif
9597         device_auth_req_free(device);
9598
9599         /* If we're already paired nothing more is needed */
9600         if (state->paired) {
9601 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
9602                 if (bdaddr_type == BDADDR_BREDR && state->svc_resolved) {
9603                         DBG("Link key has been changed. Report it");
9604                         if (!device->rpa)
9605                                 g_dbus_emit_property_changed(dbus_conn,
9606                                                 device->path, DEVICE_INTERFACE,
9607                                                 "Paired");
9608                         else
9609                                 DBG("Just overwrite Link key");
9610                 } else if (bdaddr_type == BDADDR_LE_RANDOM ||
9611                            bdaddr_type == BDADDR_LE_PUBLIC) {
9612                         DBG("Long Term Key has been changed. Report it");
9613                         g_dbus_emit_property_changed(dbus_conn, device->path,
9614                                         DEVICE_INTERFACE, "Paired");
9615                 }
9616 #endif  /* TIZEN_FEATURE_BLUEZ_MODIFY */
9617                 return;
9618         }
9619
9620         device_set_paired(device, bdaddr_type);
9621
9622         /* If services are already resolved just reply to the pairing
9623          * request
9624          */
9625         if (state->svc_resolved && bonding) {
9626                 /* Attept to store services for this device failed because it
9627                  * was not paired. Now that we're paired retry. */
9628                 store_gatt_db(device);
9629
9630                 g_dbus_send_reply(dbus_conn, bonding->msg, DBUS_TYPE_INVALID);
9631                 bonding_request_free(bonding);
9632                 return;
9633         }
9634
9635         /* If we were initiators start service discovery immediately.
9636          * However if the other end was the initator wait a few seconds
9637          * before SDP. This is due to potential IOP issues if the other
9638          * end starts doing SDP at the same time as us */
9639         if (bonding) {
9640                 DBG("Proceeding with service discovery");
9641                 /* If we are initiators remove any discovery timer and just
9642                  * start discovering services directly */
9643                 if (device->discov_timer) {
9644                         timeout_remove(device->discov_timer);
9645                         device->discov_timer = 0;
9646                 }
9647
9648                 if (bdaddr_type == BDADDR_BREDR)
9649                         device_browse_sdp(device, bonding->msg);
9650                 else
9651                         device_browse_gatt(device, bonding->msg);
9652
9653                 bonding_request_free(bonding);
9654         } else if (!state->svc_resolved) {
9655                 if (!device->browse && !device->discov_timer &&
9656                                 btd_opts.reverse_discovery) {
9657                         /* If we are not initiators and there is no currently
9658                          * active discovery or discovery timer, set discovery
9659                          * timer */
9660                         DBG("setting timer for reverse service discovery");
9661                         device->discov_timer = timeout_add_seconds(
9662                                                         DISCOVERY_TIMER,
9663                                                         start_discovery,
9664                                                         device, NULL);
9665                 }
9666         }
9667 }
9668
9669 static gboolean svc_idle_cb(gpointer user_data)
9670 {
9671         struct svc_callback *cb = user_data;
9672         struct btd_device *dev = cb->dev;
9673
9674         dev->svc_callbacks = g_slist_remove(dev->svc_callbacks, cb);
9675
9676         cb->func(cb->dev, 0, cb->user_data);
9677
9678         g_free(cb);
9679
9680         return FALSE;
9681 }
9682
9683 unsigned int device_wait_for_svc_complete(struct btd_device *dev,
9684                                                         device_svc_cb_t func,
9685                                                         void *user_data)
9686 {
9687         /* This API is only used for BR/EDR (for now) */
9688         struct bearer_state *state = &dev->bredr_state;
9689         static unsigned int id = 0;
9690         struct svc_callback *cb;
9691
9692         cb = g_new0(struct svc_callback, 1);
9693         cb->func = func;
9694         cb->user_data = user_data;
9695         cb->dev = dev;
9696         cb->id = ++id;
9697
9698         dev->svc_callbacks = g_slist_prepend(dev->svc_callbacks, cb);
9699
9700         if (state->svc_resolved || !btd_opts.reverse_discovery)
9701                 cb->idle_id = g_idle_add(svc_idle_cb, cb);
9702         else if (dev->discov_timer >0) {
9703                 timeout_remove(dev->discov_timer);
9704                 dev->discov_timer = timeout_add_seconds(
9705                                                 0,
9706                                                 start_discovery,
9707                                                 dev, NULL);
9708         }
9709 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
9710         else if (!dev->browse) {
9711                 DBG("Service is not going on. Start discovery");
9712                 dev->discov_timer = timeout_add_seconds(
9713                                                 0,
9714                                                 start_discovery,
9715                                                 dev, NULL);
9716         } else
9717                 DBG("Wait for service discovery");
9718 #endif
9719
9720         return cb->id;
9721 }
9722
9723 bool device_remove_svc_complete_callback(struct btd_device *dev,
9724                                                         unsigned int id)
9725 {
9726         GSList *l;
9727
9728         for (l = dev->svc_callbacks; l != NULL; l = g_slist_next(l)) {
9729                 struct svc_callback *cb = l->data;
9730
9731                 if (cb->id != id)
9732                         continue;
9733
9734                 if (cb->idle_id > 0)
9735                         g_source_remove(cb->idle_id);
9736
9737                 dev->svc_callbacks = g_slist_remove(dev->svc_callbacks, cb);
9738                 g_free(cb);
9739
9740                 return true;
9741         }
9742
9743         return false;
9744 }
9745
9746 gboolean device_is_bonding(struct btd_device *device, const char *sender)
9747 {
9748         struct bonding_req *bonding = device->bonding;
9749
9750         if (!device->bonding)
9751                 return FALSE;
9752
9753         if (!sender)
9754                 return TRUE;
9755
9756         return g_str_equal(sender, dbus_message_get_sender(bonding->msg));
9757 }
9758
9759 static gboolean device_bonding_retry(gpointer data)
9760 {
9761         struct btd_device *device = data;
9762         struct btd_adapter *adapter = device_get_adapter(device);
9763         struct bonding_req *bonding = device->bonding;
9764         uint8_t io_cap;
9765         int err;
9766
9767         if (!bonding)
9768                 return FALSE;
9769
9770         DBG("retrying bonding");
9771         bonding->retry_timer = 0;
9772
9773         /* Restart the bonding timer to the begining of the pairing. If not
9774          * pincode request/reply occurs during this retry,
9775          * device_bonding_last_duration() will return a consistent value from
9776          * this point. */
9777         device_bonding_restart_timer(device);
9778
9779         if (bonding->agent)
9780                 io_cap = agent_get_io_capability(bonding->agent);
9781         else
9782                 io_cap = IO_CAPABILITY_NOINPUTNOOUTPUT;
9783
9784         err = adapter_bonding_attempt(adapter, &device->bdaddr,
9785                                 device->bdaddr_type, io_cap);
9786         if (err < 0)
9787                 device_bonding_complete(device, bonding->bdaddr_type,
9788                                                         bonding->status);
9789
9790         return FALSE;
9791 }
9792
9793 int device_bonding_attempt_retry(struct btd_device *device)
9794 {
9795         struct bonding_req *bonding = device->bonding;
9796
9797         /* Ignore other failure events while retrying */
9798         if (device_is_retrying(device))
9799                 return 0;
9800
9801         if (!bonding)
9802                 return -EINVAL;
9803
9804         /* Mark the end of a bonding attempt to compute the delta for the
9805          * retry. */
9806         bonding_request_stop_timer(bonding);
9807
9808         if (btd_adapter_pin_cb_iter_end(bonding->cb_iter))
9809                 return -EINVAL;
9810
9811         DBG("scheduling retry");
9812         bonding->retry_timer = g_timeout_add(3000,
9813                                                 device_bonding_retry, device);
9814         return 0;
9815 }
9816
9817 void device_bonding_failed(struct btd_device *device, uint8_t status)
9818 {
9819         struct bonding_req *bonding = device->bonding;
9820         DBusMessage *reply;
9821
9822         DBG("status %u", status);
9823
9824         if (!bonding) {
9825 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
9826                 if (device->legacy_pairing) {
9827                         DBG("Emit LegacyPaired");
9828                         g_dbus_emit_property_changed(dbus_conn, device->path,
9829                                         DEVICE_INTERFACE, "LegacyPaired");
9830                 }
9831 #endif
9832                 return;
9833         }
9834 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
9835         btd_device_set_temporary(device, TRUE);
9836 #endif
9837
9838         if (device->authr)
9839                 device_cancel_authentication(device, FALSE);
9840
9841         reply = new_authentication_return(bonding->msg, status);
9842         g_dbus_send_message(dbus_conn, reply);
9843
9844         bonding_request_free(bonding);
9845 }
9846
9847 struct btd_adapter_pin_cb_iter *device_bonding_iter(struct btd_device *device)
9848 {
9849         if (device->bonding == NULL)
9850                 return NULL;
9851
9852         return device->bonding->cb_iter;
9853 }
9854
9855 static void pincode_cb(struct agent *agent, DBusError *err, const char *pin,
9856                                                                 void *data)
9857 {
9858         struct authentication_req *auth = data;
9859         struct btd_device *device = auth->device;
9860
9861         /* No need to reply anything if the authentication already failed */
9862         if (auth->agent == NULL)
9863                 return;
9864
9865         btd_adapter_pincode_reply(device->adapter, &device->bdaddr,
9866                                                 pin, pin ? strlen(pin) : 0);
9867
9868         agent_unref(device->authr->agent);
9869         device->authr->agent = NULL;
9870 }
9871
9872 static void confirm_cb(struct agent *agent, DBusError *err, void *data)
9873 {
9874         struct authentication_req *auth = data;
9875         struct btd_device *device = auth->device;
9876
9877         /* No need to reply anything if the authentication already failed */
9878         if (auth->agent == NULL)
9879                 return;
9880
9881 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
9882         btd_adapter_confirm_reply(device->adapter, &device->bdaddr,
9883                                                 auth->addr_type,
9884                                                 err ? FALSE : TRUE);
9885         device_set_auth_addr_type(device, BDADDR_BREDR);
9886 #else
9887         btd_adapter_confirm_reply(device->adapter, &device->bdaddr,
9888                                                         auth->addr_type,
9889                                                         err ? FALSE : TRUE);
9890 #endif
9891
9892         agent_unref(device->authr->agent);
9893         device->authr->agent = NULL;
9894 }
9895
9896 static void passkey_cb(struct agent *agent, DBusError *err,
9897                                                 uint32_t passkey, void *data)
9898 {
9899         struct authentication_req *auth = data;
9900         struct btd_device *device = auth->device;
9901
9902         /* No need to reply anything if the authentication already failed */
9903         if (auth->agent == NULL)
9904                 return;
9905
9906         if (err)
9907                 passkey = INVALID_PASSKEY;
9908
9909 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
9910         btd_adapter_passkey_reply(device->adapter, &device->bdaddr,
9911                                         auth->addr_type, passkey);
9912         device_set_auth_addr_type(device, BDADDR_BREDR);
9913 #else
9914         btd_adapter_passkey_reply(device->adapter, &device->bdaddr,
9915                                                 auth->addr_type, passkey);
9916 #endif
9917
9918         agent_unref(device->authr->agent);
9919         device->authr->agent = NULL;
9920 }
9921
9922 static void display_pincode_cb(struct agent *agent, DBusError *err, void *data)
9923 {
9924         struct authentication_req *auth = data;
9925         struct btd_device *device = auth->device;
9926
9927         pincode_cb(agent, err, auth->pincode, auth);
9928
9929         g_free(device->authr->pincode);
9930         device->authr->pincode = NULL;
9931 }
9932
9933 static struct authentication_req *new_auth(struct btd_device *device,
9934                                                 uint8_t addr_type,
9935                                                 auth_type_t type,
9936                                                 gboolean secure)
9937 {
9938         struct authentication_req *auth;
9939         struct agent *agent;
9940         char addr[18];
9941
9942         ba2str(&device->bdaddr, addr);
9943         DBG("Requesting agent authentication for %s", addr);
9944
9945         if (device->authr) {
9946                 error("Authentication already requested for %s", addr);
9947                 return NULL;
9948         }
9949
9950         if (device->bonding && device->bonding->agent)
9951                 agent = agent_ref(device->bonding->agent);
9952         else
9953                 agent = agent_get(NULL);
9954
9955         if (!agent) {
9956                 error("No agent available for request type %d", type);
9957                 return NULL;
9958         }
9959
9960         auth = g_new0(struct authentication_req, 1);
9961         auth->agent = agent;
9962         auth->device = device;
9963         auth->type = type;
9964         auth->addr_type = addr_type;
9965         auth->secure = secure;
9966         device->authr = auth;
9967
9968         return auth;
9969 }
9970
9971 int device_request_pincode(struct btd_device *device, gboolean secure)
9972 {
9973         struct authentication_req *auth;
9974         int err;
9975
9976         auth = new_auth(device, BDADDR_BREDR, AUTH_TYPE_PINCODE, secure);
9977         if (!auth)
9978                 return -EPERM;
9979
9980         err = agent_request_pincode(auth->agent, device, pincode_cb, secure,
9981                                                                 auth, NULL);
9982         if (err < 0) {
9983                 error("Failed requesting authentication");
9984                 device_auth_req_free(device);
9985         }
9986
9987         return err;
9988 }
9989
9990 int device_request_passkey(struct btd_device *device, uint8_t type)
9991 {
9992         struct authentication_req *auth;
9993         int err;
9994
9995         auth = new_auth(device, type, AUTH_TYPE_PASSKEY, FALSE);
9996         if (!auth)
9997                 return -EPERM;
9998
9999         err = agent_request_passkey(auth->agent, device, passkey_cb, auth,
10000                                                                         NULL);
10001         if (err < 0) {
10002                 error("Failed requesting authentication");
10003                 device_auth_req_free(device);
10004         }
10005
10006         return err;
10007 }
10008
10009 int device_confirm_passkey(struct btd_device *device, uint8_t type,
10010                                         int32_t passkey, uint8_t confirm_hint)
10011 {
10012         struct authentication_req *auth;
10013         int err;
10014
10015         /* Just-Works repairing policy */
10016         if (confirm_hint && device_is_paired(device, type)) {
10017                 if (btd_opts.jw_repairing == JW_REPAIRING_NEVER) {
10018                         btd_adapter_confirm_reply(device->adapter,
10019                                                   &device->bdaddr,
10020                                                   type, FALSE);
10021                         return 0;
10022                 } else if (btd_opts.jw_repairing == JW_REPAIRING_ALWAYS) {
10023                         btd_adapter_confirm_reply(device->adapter,
10024                                                   &device->bdaddr,
10025                                                   type, TRUE);
10026                         return 0;
10027                 }
10028         }
10029
10030         auth = new_auth(device, type, AUTH_TYPE_CONFIRM, FALSE);
10031         if (!auth)
10032                 return -EPERM;
10033
10034         auth->passkey = passkey;
10035
10036 #ifndef TIZEN_FEATURE_BLUEZ_CONFIRM_ONLY
10037         if (confirm_hint) {
10038                 if (device->bonding != NULL) {
10039                         /* We know the client has indicated the intent to pair
10040                          * with the peer device, so we can auto-accept.
10041                          */
10042                         btd_adapter_confirm_reply(device->adapter,
10043                                                   &device->bdaddr,
10044                                                   type, TRUE);
10045                         return 0;
10046                 }
10047
10048                 err = agent_request_authorization(auth->agent, device,
10049                                                 confirm_cb, auth, NULL);
10050         } else
10051 #endif
10052                 err = agent_request_confirmation(auth->agent, device, passkey,
10053                                                 confirm_cb, auth, NULL);
10054
10055         if (err < 0) {
10056                 if (err == -EINPROGRESS) {
10057                         /* Already in progress */
10058                         confirm_cb(auth->agent, NULL, auth);
10059                         return 0;
10060                 }
10061
10062                 error("Failed requesting authentication");
10063                 device_auth_req_free(device);
10064         }
10065
10066         return err;
10067 }
10068
10069 int device_notify_passkey(struct btd_device *device, uint8_t type,
10070                                         uint32_t passkey, uint8_t entered)
10071 {
10072         struct authentication_req *auth;
10073         int err;
10074
10075         if (device->authr) {
10076                 auth = device->authr;
10077                 if (auth->type != AUTH_TYPE_NOTIFY_PASSKEY)
10078                         return -EPERM;
10079         } else {
10080                 auth = new_auth(device, type, AUTH_TYPE_NOTIFY_PASSKEY, FALSE);
10081                 if (!auth)
10082                         return -EPERM;
10083         }
10084
10085         err = agent_display_passkey(auth->agent, device, passkey, entered);
10086         if (err < 0) {
10087                 error("Failed requesting authentication");
10088                 device_auth_req_free(device);
10089         }
10090
10091         return err;
10092 }
10093
10094 int device_notify_pincode(struct btd_device *device, gboolean secure,
10095                                                         const char *pincode)
10096 {
10097         struct authentication_req *auth;
10098         int err;
10099
10100         auth = new_auth(device, BDADDR_BREDR, AUTH_TYPE_NOTIFY_PINCODE, secure);
10101         if (!auth)
10102                 return -EPERM;
10103
10104         auth->pincode = g_strdup(pincode);
10105
10106         err = agent_display_pincode(auth->agent, device, pincode,
10107                                         display_pincode_cb, auth, NULL);
10108         if (err < 0) {
10109                 if (err == -EINPROGRESS) {
10110                         /* Already in progress */
10111                         display_pincode_cb(auth->agent, NULL, auth);
10112                         return 0;
10113                 }
10114
10115                 error("Failed requesting authentication");
10116                 device_auth_req_free(device);
10117         }
10118
10119         return err;
10120 }
10121
10122 static void cancel_authentication(struct authentication_req *auth)
10123 {
10124         struct agent *agent;
10125         DBusError err;
10126
10127         if (!auth || !auth->agent)
10128                 return;
10129
10130         agent = auth->agent;
10131         auth->agent = NULL;
10132
10133         dbus_error_init(&err);
10134         dbus_set_error_const(&err, ERROR_INTERFACE ".Canceled", NULL);
10135
10136         switch (auth->type) {
10137         case AUTH_TYPE_PINCODE:
10138                 pincode_cb(agent, &err, NULL, auth);
10139                 break;
10140         case AUTH_TYPE_CONFIRM:
10141                 confirm_cb(agent, &err, auth);
10142                 break;
10143         case AUTH_TYPE_PASSKEY:
10144                 passkey_cb(agent, &err, 0, auth);
10145                 break;
10146         case AUTH_TYPE_NOTIFY_PASSKEY:
10147                 /* User Notify doesn't require any reply */
10148                 break;
10149         case AUTH_TYPE_NOTIFY_PINCODE:
10150                 pincode_cb(agent, &err, NULL, auth);
10151                 break;
10152         }
10153
10154         dbus_error_free(&err);
10155 }
10156
10157 void device_cancel_authentication(struct btd_device *device, gboolean aborted)
10158 {
10159         struct authentication_req *auth = device->authr;
10160         char addr[18];
10161
10162         if (!auth)
10163                 return;
10164
10165         ba2str(&device->bdaddr, addr);
10166         DBG("Canceling authentication request for %s", addr);
10167
10168         if (auth->agent)
10169                 agent_cancel(auth->agent);
10170
10171         if (!aborted)
10172                 cancel_authentication(auth);
10173
10174         device_auth_req_free(device);
10175
10176 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
10177         device_set_auth_addr_type(device, BDADDR_BREDR);
10178 #endif
10179 }
10180
10181 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
10182 gboolean device_is_authenticating(struct btd_device *dev, uint8_t bdaddr_type)
10183 {
10184         return (dev->auth_bdaddr_type == bdaddr_type && dev->authr != NULL);
10185 }
10186 #else
10187 gboolean device_is_authenticating(struct btd_device *device)
10188 {
10189         return (device->authr != NULL);
10190 }
10191 #endif
10192
10193 struct gatt_primary *btd_device_get_primary(struct btd_device *device,
10194                                                         const char *uuid)
10195 {
10196         GSList *match;
10197
10198         match = g_slist_find_custom(device->primaries, uuid, bt_uuid_strcmp);
10199         if (match)
10200                 return match->data;
10201
10202         return NULL;
10203 }
10204
10205 GSList *btd_device_get_primaries(struct btd_device *device)
10206 {
10207         return device->primaries;
10208 }
10209
10210 struct gatt_db *btd_device_get_gatt_db(struct btd_device *device)
10211 {
10212         if (!device)
10213                 return NULL;
10214
10215         return device->db;
10216 }
10217
10218 struct bt_gatt_client *btd_device_get_gatt_client(struct btd_device *device)
10219 {
10220         if (!device)
10221                 return NULL;
10222
10223         return device->client;
10224 }
10225
10226 void *btd_device_get_attrib(struct btd_device *device)
10227 {
10228         if (!device)
10229                 return NULL;
10230
10231         return device->attrib;
10232 }
10233
10234 struct bt_gatt_server *btd_device_get_gatt_server(struct btd_device *device)
10235 {
10236         if (!device)
10237                 return NULL;
10238
10239         return device->server;
10240 }
10241
10242 void btd_device_gatt_set_service_changed(struct btd_device *device,
10243                                                 uint16_t start, uint16_t end)
10244 {
10245         /*
10246          * TODO: Remove this function and handle service changed via
10247          * gatt-client.
10248          */
10249 }
10250
10251 void btd_device_add_uuid(struct btd_device *device, const char *uuid)
10252 {
10253         GSList *uuid_list;
10254         char *new_uuid;
10255
10256         if (g_slist_find_custom(device->uuids, uuid, bt_uuid_strcmp))
10257                 return;
10258
10259         new_uuid = g_strdup(uuid);
10260         uuid_list = g_slist_append(NULL, new_uuid);
10261
10262         device_probe_profiles(device, uuid_list);
10263
10264         g_free(new_uuid);
10265         g_slist_free(uuid_list);
10266
10267         store_device_info(device);
10268
10269         g_dbus_emit_property_changed(dbus_conn, device->path,
10270                                                 DEVICE_INTERFACE, "UUIDs");
10271 }
10272
10273 static sdp_list_t *read_device_records(struct btd_device *device)
10274 {
10275         char local[18], peer[18];
10276         char filename[PATH_MAX];
10277         GKeyFile *key_file;
10278         GError *gerr = NULL;
10279         char **keys, **handle;
10280         char *str;
10281         sdp_list_t *recs = NULL;
10282         sdp_record_t *rec;
10283
10284         ba2str(btd_adapter_get_address(device->adapter), local);
10285         ba2str(&device->bdaddr, peer);
10286
10287 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
10288         if (device->rpa)
10289                 ba2str(device->rpa, peer);
10290 #endif
10291
10292         snprintf(filename, PATH_MAX, STORAGEDIR "/%s/cache/%s", local, peer);
10293
10294         key_file = g_key_file_new();
10295         if (!g_key_file_load_from_file(key_file, filename, 0, &gerr)) {
10296                 error("Unable to load key file from %s: (%s)", filename,
10297                                                                 gerr->message);
10298                 g_error_free(gerr);
10299         }
10300         keys = g_key_file_get_keys(key_file, "ServiceRecords", NULL, NULL);
10301
10302         for (handle = keys; handle && *handle; handle++) {
10303                 str = g_key_file_get_string(key_file, "ServiceRecords",
10304                                                 *handle, NULL);
10305                 if (!str)
10306                         continue;
10307
10308                 rec = record_from_string(str);
10309                 recs = sdp_list_append(recs, rec);
10310                 g_free(str);
10311         }
10312
10313         g_strfreev(keys);
10314         g_key_file_free(key_file);
10315
10316         return recs;
10317 }
10318
10319 void btd_device_set_record(struct btd_device *device, const char *uuid,
10320                                                         const char *record)
10321 {
10322         /* This API is only used for BR/EDR */
10323         struct bearer_state *state = &device->bredr_state;
10324         struct browse_req *req;
10325         sdp_list_t *recs = NULL;
10326         sdp_record_t *rec;
10327
10328         if (!record)
10329                 return;
10330
10331         req = browse_request_new(device, BROWSE_SDP, NULL);
10332         if (!req)
10333                 return;
10334
10335         rec = record_from_string(record);
10336         recs = sdp_list_append(recs, rec);
10337         update_bredr_services(req, recs);
10338         sdp_list_free(recs, NULL);
10339
10340         device->svc_refreshed = true;
10341         state->svc_resolved = true;
10342
10343         device_probe_profiles(device, req->profiles_added);
10344
10345         /* Propagate services changes */
10346         g_dbus_emit_property_changed(dbus_conn, req->device->path,
10347                                                 DEVICE_INTERFACE, "UUIDs");
10348
10349         device_svc_resolved(device, BROWSE_SDP, device->bdaddr_type, 0);
10350 }
10351
10352 const sdp_record_t *btd_device_get_record(struct btd_device *device,
10353                                                         const char *uuid)
10354 {
10355         /* Load records from storage if there is nothing in cache */
10356         if (!device->tmp_records) {
10357                 device->tmp_records = read_device_records(device);
10358                 if (!device->tmp_records)
10359                         return NULL;
10360         }
10361
10362         return find_record_in_list(device->tmp_records, uuid);
10363 }
10364
10365 struct btd_device *btd_device_ref(struct btd_device *device)
10366 {
10367         __sync_fetch_and_add(&device->ref_count, 1);
10368
10369         return device;
10370 }
10371
10372 void btd_device_unref(struct btd_device *device)
10373 {
10374         if (__sync_sub_and_fetch(&device->ref_count, 1))
10375                 return;
10376
10377         if (!device->path) {
10378                 error("freeing device without an object path");
10379                 return;
10380         }
10381
10382         DBG("Freeing device %s", device->path);
10383
10384         g_dbus_unregister_interface(dbus_conn, device->path, DEVICE_INTERFACE);
10385 }
10386
10387 int device_get_appearance(struct btd_device *device, uint16_t *value)
10388 {
10389         if (device->appearance == 0)
10390                 return -1;
10391
10392         if (value)
10393                 *value = device->appearance;
10394
10395         return 0;
10396 }
10397
10398 void device_set_appearance(struct btd_device *device, uint16_t value)
10399 {
10400         const char *icon = gap_appearance_to_icon(value);
10401
10402         if (device->appearance == value)
10403                 return;
10404
10405         g_dbus_emit_property_changed(dbus_conn, device->path,
10406                                         DEVICE_INTERFACE, "Appearance");
10407
10408         if (icon)
10409                 g_dbus_emit_property_changed(dbus_conn, device->path,
10410                                                 DEVICE_INTERFACE, "Icon");
10411
10412         device->appearance = value;
10413         store_device_info(device);
10414 }
10415
10416 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
10417 int device_get_rpa_res_char_value(struct btd_device *device)
10418 {
10419         return device->rpa_res_support;
10420 }
10421
10422 /* Store the RPA Resolution Characteristic Value of remote device.
10423  * This value would be checked before start directed advertising using RPA.
10424  */
10425 void device_set_rpa_res_char_value(struct btd_device *device, uint8_t value)
10426 {
10427         if (device->rpa_res_support == value)
10428                 return;
10429
10430         device->rpa_res_support = value;
10431         store_device_info(device);
10432 }
10433
10434 void device_set_manufacturer_info(struct btd_device *device, struct eir_data *eir)
10435 {
10436         if (!device)
10437                 return;
10438
10439         if (eir->manufacturer_data_len == 0)
10440                 return;
10441
10442         device->manufacturer_data = g_memdup(eir->manufacturer_data,
10443                                                                 eir->manufacturer_data_len);
10444         device->manufacturer_data_len = eir->manufacturer_data_len;
10445
10446         store_device_info(device);
10447
10448         g_dbus_emit_property_changed(dbus_conn, device->path,
10449                                         DEVICE_INTERFACE, "LegacyManufacturerDataLen");
10450
10451         g_dbus_emit_property_changed(dbus_conn, device->path,
10452                                         DEVICE_INTERFACE, "LegacyManufacturerData");
10453 }
10454
10455
10456 void device_set_adv_report_info(struct btd_device *device, void *data, uint8_t data_len,
10457                                 uint8_t adv_type, int8_t rssi)
10458 {
10459         if (!device)
10460                 return;
10461
10462         char peer_addr[18];
10463         const char *paddr = peer_addr;
10464         dbus_int32_t rssi_val = rssi;
10465         int adv_len = data_len;
10466         uint8_t addr_type;
10467
10468         ba2str(&device->bdaddr, peer_addr);
10469
10470         /* Replace address type for paired RPA device since IDA passed from controller */
10471         if (device->rpa) {
10472                 ba2str(device->rpa, peer_addr);
10473                 addr_type = BDADDR_LE_RANDOM;
10474         } else
10475                 addr_type = device->bdaddr_type;
10476
10477         g_dbus_emit_signal(dbus_conn, device->path,
10478                 DEVICE_INTERFACE, "AdvReport",
10479                 DBUS_TYPE_STRING, &paddr,
10480                 DBUS_TYPE_BYTE, &addr_type,
10481                 DBUS_TYPE_BYTE, &adv_type,
10482                 DBUS_TYPE_INT32, &rssi_val,
10483                 DBUS_TYPE_INT32, &adv_len,
10484                 DBUS_TYPE_ARRAY, DBUS_TYPE_BYTE, &data, data_len,
10485                 DBUS_TYPE_INVALID);
10486 }
10487
10488 void device_set_payload_timeout(struct btd_device *device,
10489                         uint16_t payload_timeout)
10490 {
10491         if (!device)
10492                 return;
10493         if (device->auth_payload_timeout == payload_timeout)
10494                 return;
10495
10496         DBG("Payload timeout %d", payload_timeout);
10497
10498         device->auth_payload_timeout = payload_timeout;
10499         g_dbus_emit_property_changed(dbus_conn, device->path,
10500                                 DEVICE_INTERFACE, "PayloadTimeout");
10501 }
10502
10503 void device_set_disconnect_reason(struct btd_device *device, uint8_t reason)
10504 {
10505         device->disc_reason = reason;
10506 }
10507
10508 void btd_device_disconnect(struct btd_device *device)
10509 {
10510         char dst[18];
10511         struct btd_service *service;
10512         btd_service_state_t state;
10513
10514         ba2str(&device->bdaddr, dst);
10515
10516         DBG("");
10517         if (device->bredr_state.connected == false)
10518                 return;
10519
10520         service = btd_device_get_service(device, HFP_HS_UUID);
10521         if (!service)
10522                 return;
10523
10524         state = btd_service_get_state(service);
10525         DBG("Connected State : %d", state);
10526
10527         if (state == BTD_SERVICE_STATE_DISCONNECTED) {
10528                 btd_adapter_disconnect_device(device->adapter, &device->bdaddr,
10529                                                                 BDADDR_BREDR);
10530         }
10531
10532         return;
10533 }
10534
10535 #endif
10536
10537 void btd_device_set_pnpid(struct btd_device *device, uint16_t source,
10538                         uint16_t vendor, uint16_t product, uint16_t version)
10539 {
10540         if (device->vendor_src == source && device->version == version &&
10541                         device->vendor == vendor && device->product == product)
10542                 return;
10543
10544         device->vendor_src = source;
10545         device->vendor = vendor;
10546         device->product = product;
10547         device->version = version;
10548
10549         free(device->modalias);
10550         device->modalias = bt_modalias(source, vendor, product, version);
10551
10552         g_dbus_emit_property_changed(dbus_conn, device->path,
10553                                                 DEVICE_INTERFACE, "Modalias");
10554
10555         store_device_info(device);
10556 }
10557
10558 uint32_t btd_device_get_current_flags(struct btd_device *dev)
10559 {
10560         return dev->current_flags;
10561 }
10562
10563 /* This event is sent immediately after add device on all mgmt sockets.
10564  * Afterwards, it is only sent to mgmt sockets other than the one which called
10565  * set_device_flags.
10566  */
10567 void btd_device_flags_changed(struct btd_device *dev, uint32_t supported_flags,
10568                               uint32_t current_flags)
10569 {
10570         const uint32_t changed_flags = dev->current_flags ^ current_flags;
10571         bool flag_value;
10572
10573         dev->supported_flags = supported_flags;
10574         dev->current_flags = current_flags;
10575
10576         if (!changed_flags)
10577                 return;
10578
10579         if (changed_flags & DEVICE_FLAG_REMOTE_WAKEUP) {
10580                 flag_value = !!(current_flags & DEVICE_FLAG_REMOTE_WAKEUP);
10581                 dev->pending_wake_allowed = flag_value;
10582
10583                 /* If an override exists and doesn't match the current state,
10584                  * apply it. This logic will run after Add Device only and will
10585                  * enable wake for previously paired devices.
10586                  */
10587                 if (dev->wake_override != WAKE_FLAG_DEFAULT) {
10588                         bool wake_allowed =
10589                                 dev->wake_override == WAKE_FLAG_ENABLED;
10590                         if (flag_value != wake_allowed)
10591                                 device_set_wake_allowed(dev, wake_allowed, -1U);
10592                         else
10593                                 device_set_wake_allowed_complete(dev);
10594                 } else {
10595                         device_set_wake_allowed_complete(dev);
10596                 }
10597         }
10598 }
10599
10600 static void service_state_changed(struct btd_service *service,
10601                                                 btd_service_state_t old_state,
10602                                                 btd_service_state_t new_state,
10603                                                 void *user_data)
10604 {
10605         struct btd_profile *profile = btd_service_get_profile(service);
10606         struct btd_device *device = btd_service_get_device(service);
10607         int err = btd_service_get_error(service);
10608
10609 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
10610         if (!err) {
10611                 if (old_state == BTD_SERVICE_STATE_UNAVAILABLE ||
10612                                         new_state == BTD_SERVICE_STATE_UNAVAILABLE)
10613                         DBG("Skip status updating ([%d] -> [%d])", old_state, new_state);
10614                 else
10615                         g_dbus_emit_signal(dbus_conn, device->path,
10616                                 DEVICE_INTERFACE, "ProfileStateChanged",
10617                                 DBUS_TYPE_STRING, &profile->remote_uuid,
10618                                 DBUS_TYPE_INT32, &new_state,
10619                                 DBUS_TYPE_INVALID);
10620         }
10621
10622         if (new_state == BTD_SERVICE_STATE_CONNECTING ||
10623                         new_state == BTD_SERVICE_STATE_DISCONNECTING ||
10624                         new_state == BTD_SERVICE_STATE_UNAVAILABLE)
10625 #else
10626         if (new_state == BTD_SERVICE_STATE_CONNECTING ||
10627                                 new_state == BTD_SERVICE_STATE_DISCONNECTING)
10628 #endif
10629                 return;
10630
10631         if (old_state == BTD_SERVICE_STATE_CONNECTING)
10632                 device_profile_connected(device, profile, err);
10633         else if (old_state == BTD_SERVICE_STATE_DISCONNECTING)
10634                 device_profile_disconnected(device, profile, err);
10635 }
10636
10637 struct btd_service *btd_device_get_service(struct btd_device *dev,
10638                                                 const char *remote_uuid)
10639 {
10640         GSList *l;
10641
10642         for (l = dev->services; l != NULL; l = g_slist_next(l)) {
10643                 struct btd_service *service = l->data;
10644                 struct btd_profile *p = btd_service_get_profile(service);
10645
10646                 if (g_str_equal(p->remote_uuid, remote_uuid))
10647                         return service;
10648
10649 #ifdef TIZEN_BT_HID_DEVICE_ENABLE
10650                 if (g_str_equal(HID_UUID, remote_uuid)) {
10651                         if (strcmp(p->name, "hid-device") == 0)
10652                                 return service;
10653                 }
10654 #endif
10655         }
10656
10657         return NULL;
10658 }
10659
10660 void btd_device_init(void)
10661 {
10662         dbus_conn = btd_get_dbus_connection();
10663         service_state_cb_id = btd_service_add_state_cb(
10664                                                 service_state_changed, NULL);
10665 }
10666
10667 void btd_device_cleanup(void)
10668 {
10669         btd_service_remove_state_cb(service_state_cb_id);
10670 }
10671
10672 #ifdef TIZEN_FEATURE_BLUEZ_MODIFY
10673 void btd_device_set_legacy_pairing(struct btd_device *dev, bool legacy_pairing)
10674 {
10675         dev->legacy_pairing = legacy_pairing;
10676 }
10677
10678 void btd_device_set_svc_changed_indication(struct btd_device *dev, bool value)
10679 {
10680         bt_att_set_svc_changed_indication_registered(dev->att, value);
10681         store_device_info(dev);
10682 }
10683
10684 bool btd_device_get_svc_changed_indication(struct btd_device *dev)
10685 {
10686         return bt_att_get_svc_changed_indication_registered(dev->att);
10687 }
10688 #endif