device.c revision a4145c63530b4c3575b7da5f117c0df352f939fc
1dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann/* 2dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann * 3dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann * BlueZ - Bluetooth protocol stack for Linux 4dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann * 5f1659f19cfb3ef0c0c09b5f5b7e2b06d90d079abMarcel Holtmann * Copyright (C) 2006-2007 Nokia Corporation 6e823c15e43a6f924779e466d434c51157002d9eeMarcel Holtmann * Copyright (C) 2004-2008 Marcel Holtmann <marcel@holtmann.org> 7dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann * 8dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann * 9dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann * This program is free software; you can redistribute it and/or modify 10dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann * it under the terms of the GNU General Public License as published by 11dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann * the Free Software Foundation; either version 2 of the License, or 12dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann * (at your option) any later version. 13dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann * 14dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann * This program is distributed in the hope that it will be useful, 15dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann * but WITHOUT ANY WARRANTY; without even the implied warranty of 16dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann * GNU General Public License for more details. 18dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann * 19dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann * You should have received a copy of the GNU General Public License 20dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann * along with this program; if not, write to the Free Software 21dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA 22dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann * 23dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann */ 24dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann 25dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann#ifdef HAVE_CONFIG_H 26dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann#include <config.h> 27dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann#endif 28dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann 29dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann#include <stdio.h> 30dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann#include <stdlib.h> 315d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi#include <unistd.h> 326a3ea0f9f9aa9dd550f9f2af4a36639961846643Marcel Holtmann#include <sys/stat.h> 331af86fb9d1717a27b3a776fc0fb62c96045ccb9aJohan Hedberg#include <errno.h> 34dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann 35dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann#include <bluetooth/bluetooth.h> 36dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann#include <bluetooth/hci.h> 37dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann#include <bluetooth/hci_lib.h> 385d5d89bb2dbc295443900d59d8a7172dc2f279c7Claudio Takahasi#include <bluetooth/sdp.h> 395d5d89bb2dbc295443900d59d8a7172dc2f279c7Claudio Takahasi#include <bluetooth/sdp_lib.h> 40dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann 4186892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann#include <glib.h> 4286892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann#include <dbus/dbus.h> 4315ea15b3a752f0487bc50d0ea04925f1b9d33dcbMarcel Holtmann#include <gdbus.h> 4486892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann 4586892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann#include "logging.h" 466a3ea0f9f9aa9dd550f9f2af4a36639961846643Marcel Holtmann#include "textfile.h" 47dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann 48506c95298346d318304aa7e2211dfba5dbe6e3e0Claudio Takahasi#include "hcid.h" 492c1effee41e974f97b21aec1bdd1a232ba48056aVinicius Costa Gomes#include "adapter.h" 5086892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann#include "device.h" 51da0e7105811dc046d13d0365404efc1189ee4a8cClaudio Takahasi#include "dbus-common.h" 524e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz#include "dbus-hci.h" 537fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz#include "error.h" 543d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz#include "glib-helper.h" 55fb27732e05fb7b69c3b784ed8a6aaed2d9d939aeCidorvan Leite#include "agent.h" 563d3cdef8da6b3e1b14c3cdccda8c099cbad4f3aeMarcel Holtmann#include "sdp-xml.h" 57506c95298346d318304aa7e2211dfba5dbe6e3e0Claudio Takahasi#include "storage.h" 5886892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann 59c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz#define DEFAULT_XML_BUF_SIZE 1024 605d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi#define DISCONNECT_TIMER 2 61013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg#define DISCOVERY_TIMER 2000 62dfc20857eb381b464b8fd6efdaac59e4a15f5d6dMarcel Holtmann 63e3afaa0b7ff373d89fd3fa257110a34df7495df7Luiz Augusto von Dentzstruct btd_driver_data { 64b76fbc7d29f28a95a9ea25aae1f6f2d9c10adb19Alok Barsode struct btd_device_driver *driver; 65b76fbc7d29f28a95a9ea25aae1f6f2d9c10adb19Alok Barsode void *priv; 66b76fbc7d29f28a95a9ea25aae1f6f2d9c10adb19Alok Barsode}; 67b76fbc7d29f28a95a9ea25aae1f6f2d9c10adb19Alok Barsode 68555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsodestruct btd_device { 69cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode bdaddr_t bdaddr; 70ea245383ac6650cbf34c327ed095d956b84ac5fbAlok Barsode gchar *path; 7118614bd2b008cb9f3879990883c569c37b72f195Alok Barsode struct btd_adapter *adapter; 72ea245383ac6650cbf34c327ed095d956b84ac5fbAlok Barsode GSList *uuids; 73b76fbc7d29f28a95a9ea25aae1f6f2d9c10adb19Alok Barsode GSList *drivers; /* List of driver_data */ 74ea245383ac6650cbf34c327ed095d956b84ac5fbAlok Barsode gboolean temporary; 75ea245383ac6650cbf34c327ed095d956b84ac5fbAlok Barsode struct agent *agent; 76ea245383ac6650cbf34c327ed095d956b84ac5fbAlok Barsode guint disconn_timer; 77ea245383ac6650cbf34c327ed095d956b84ac5fbAlok Barsode int discov_active; /* Service discovery active */ 78ea245383ac6650cbf34c327ed095d956b84ac5fbAlok Barsode char *discov_requestor; /* discovery requestor unique name */ 79ea245383ac6650cbf34c327ed095d956b84ac5fbAlok Barsode guint discov_listener; 80013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg guint discov_timer; 81ea245383ac6650cbf34c327ed095d956b84ac5fbAlok Barsode 82ea245383ac6650cbf34c327ed095d956b84ac5fbAlok Barsode /* For Secure Simple Pairing */ 83ea245383ac6650cbf34c327ed095d956b84ac5fbAlok Barsode uint8_t cap; 84ea245383ac6650cbf34c327ed095d956b84ac5fbAlok Barsode uint8_t auth; 85e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg 86e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg gboolean connected; 87e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg 88e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg /* Whether were creating a security mode 3 connection */ 89e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg gboolean secmode3; 90ea245383ac6650cbf34c327ed095d956b84ac5fbAlok Barsode}; 91ea245383ac6650cbf34c327ed095d956b84ac5fbAlok Barsode 923d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentzstruct browse_req { 933d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz DBusConnection *conn; 943d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz DBusMessage *msg; 95555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsode struct btd_device *device; 9658d8ea3c3a8ea69e652d8a39649a19426f31933bLuiz Augusto von Dentz GSList *uuids; 9736dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz GSList *uuids_added; 9836dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz GSList *uuids_removed; 99681e50c618d246483728bca6628a18c1c44c5b36Luiz Augusto von Dentz sdp_list_t *records; 100d69e08eb0d567b61106ca37e0546402f4ae0c34eMarcel Holtmann int search_uuid; 1013d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz}; 1023d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz 103d69e08eb0d567b61106ca37e0546402f4ae0c34eMarcel Holtmannstatic uint16_t uuid_list[] = { 104d69e08eb0d567b61106ca37e0546402f4ae0c34eMarcel Holtmann PUBLIC_BROWSE_GROUP, 1051c284b3ba427638179d936286f4c4866fff99e28Luiz Augusto von Dentz PNP_INFO_SVCLASS_ID, 106f22b20c3d40bd7571944af6a4946f756dc39f812Marcel Holtmann HID_SVCLASS_ID, 107d69e08eb0d567b61106ca37e0546402f4ae0c34eMarcel Holtmann GENERIC_AUDIO_SVCLASS_ID, 108d69e08eb0d567b61106ca37e0546402f4ae0c34eMarcel Holtmann ADVANCED_AUDIO_SVCLASS_ID, 109d69e08eb0d567b61106ca37e0546402f4ae0c34eMarcel Holtmann AV_REMOTE_SVCLASS_ID, 1101c284b3ba427638179d936286f4c4866fff99e28Luiz Augusto von Dentz PANU_SVCLASS_ID, 1111c284b3ba427638179d936286f4c4866fff99e28Luiz Augusto von Dentz GN_SVCLASS_ID, 1121c284b3ba427638179d936286f4c4866fff99e28Luiz Augusto von Dentz NAP_SVCLASS_ID, 1131c284b3ba427638179d936286f4c4866fff99e28Luiz Augusto von Dentz SERIAL_PORT_SVCLASS_ID, 114d69e08eb0d567b61106ca37e0546402f4ae0c34eMarcel Holtmann 0 115d69e08eb0d567b61106ca37e0546402f4ae0c34eMarcel Holtmann}; 116d69e08eb0d567b61106ca37e0546402f4ae0c34eMarcel Holtmann 117c560d02ccf1dd156f068b1da8a3e7d75d2319dfdLuiz Augusto von Dentzstatic GSList *device_drivers = NULL; 118c560d02ccf1dd156f068b1da8a3e7d75d2319dfdLuiz Augusto von Dentz 119e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasistatic void device_free(gpointer user_data) 12086892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann{ 121555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsode struct btd_device *device = user_data; 1222f9fbeeb5931cda983aa72ed9a53b1f22d0aa85dLuiz Augusto von Dentz struct btd_adapter *adapter = device->adapter; 1232f9fbeeb5931cda983aa72ed9a53b1f22d0aa85dLuiz Augusto von Dentz struct agent *agent = adapter_get_agent(adapter); 124e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi 125fb27732e05fb7b69c3b784ed8a6aaed2d9d939aeCidorvan Leite if (device->agent) 126fb27732e05fb7b69c3b784ed8a6aaed2d9d939aeCidorvan Leite agent_destroy(device->agent, FALSE); 127f62f8d892b5d5cc5aedef83779671c1ed54a35daMarcel Holtmann 1282f9fbeeb5931cda983aa72ed9a53b1f22d0aa85dLuiz Augusto von Dentz if (agent && agent_is_busy(agent, device)) 1292f9fbeeb5931cda983aa72ed9a53b1f22d0aa85dLuiz Augusto von Dentz agent_cancel(agent); 1302f9fbeeb5931cda983aa72ed9a53b1f22d0aa85dLuiz Augusto von Dentz 131ea00a446dbacead62040dd2bd7e663774c205c04Claudio Takahasi g_slist_foreach(device->uuids, (GFunc) g_free, NULL); 132ea00a446dbacead62040dd2bd7e663774c205c04Claudio Takahasi g_slist_free(device->uuids); 133f62f8d892b5d5cc5aedef83779671c1ed54a35daMarcel Holtmann 1345d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi if (device->disconn_timer) 1355d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi g_source_remove(device->disconn_timer); 1365d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi 137401374312bdc966bf386a1d89bf6cd0f74a4314cLuiz Augusto von Dentz if (device->discov_timer) 138401374312bdc966bf386a1d89bf6cd0f74a4314cLuiz Augusto von Dentz g_source_remove(device->discov_timer); 139401374312bdc966bf386a1d89bf6cd0f74a4314cLuiz Augusto von Dentz 14086892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann g_free(device->path); 14186892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann g_free(device); 14286892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann} 14386892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann 144555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsodestatic gboolean device_is_paired(struct btd_device *device) 145769c4b021665a26c9a6c20457ef9b7ded54c8ad6Luiz Augusto von Dentz{ 14618614bd2b008cb9f3879990883c569c37b72f195Alok Barsode struct btd_adapter *adapter = device->adapter; 147cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode char filename[PATH_MAX + 1], *str; 148cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode char srcaddr[18], dstaddr[18]; 149769c4b021665a26c9a6c20457ef9b7ded54c8ad6Luiz Augusto von Dentz gboolean ret; 150cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode bdaddr_t src; 1512a8fb41c4c57b24a22f3adaab472b416faae122eAlok Barsode 152cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode adapter_get_address(adapter, &src); 153cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode ba2str(&src, srcaddr); 154cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode ba2str(&device->bdaddr, dstaddr); 155769c4b021665a26c9a6c20457ef9b7ded54c8ad6Luiz Augusto von Dentz 156769c4b021665a26c9a6c20457ef9b7ded54c8ad6Luiz Augusto von Dentz create_name(filename, PATH_MAX, STORAGEDIR, 157cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode srcaddr, "linkkeys"); 158cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode str = textfile_caseget(filename, dstaddr); 159769c4b021665a26c9a6c20457ef9b7ded54c8ad6Luiz Augusto von Dentz ret = str ? TRUE : FALSE; 160769c4b021665a26c9a6c20457ef9b7ded54c8ad6Luiz Augusto von Dentz g_free(str); 161769c4b021665a26c9a6c20457ef9b7ded54c8ad6Luiz Augusto von Dentz 162769c4b021665a26c9a6c20457ef9b7ded54c8ad6Luiz Augusto von Dentz return ret; 163769c4b021665a26c9a6c20457ef9b7ded54c8ad6Luiz Augusto von Dentz} 164769c4b021665a26c9a6c20457ef9b7ded54c8ad6Luiz Augusto von Dentz 165e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasistatic DBusMessage *get_properties(DBusConnection *conn, 166e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi DBusMessage *msg, void *user_data) 1672c1effee41e974f97b21aec1bdd1a232ba48056aVinicius Costa Gomes{ 168555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsode struct btd_device *device = user_data; 16918614bd2b008cb9f3879990883c569c37b72f195Alok Barsode struct btd_adapter *adapter = device->adapter; 1704e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz DBusMessage *reply; 1714e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz DBusMessageIter iter; 1724e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz DBusMessageIter dict; 173cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode bdaddr_t src; 174cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode char name[248], srcaddr[18], dstaddr[18]; 1758a68b5fe931db5a432f924b0de22ed3acee024baClaudio Takahasi char **uuids; 1762a8fb41c4c57b24a22f3adaab472b416faae122eAlok Barsode const char *ptr; 1774e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz dbus_bool_t boolean; 1784e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz uint32_t class; 179769c4b021665a26c9a6c20457ef9b7ded54c8ad6Luiz Augusto von Dentz int i; 180769c4b021665a26c9a6c20457ef9b7ded54c8ad6Luiz Augusto von Dentz GSList *l; 181bcb5f7e4d5e570c1acfd5364547d36e970408394Alok Barsode struct active_conn_info *dev; 1824e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz 183cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode ba2str(&device->bdaddr, dstaddr); 184cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode 1854e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz reply = dbus_message_new_method_return(msg); 1864e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz if (!reply) 187e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi return NULL; 1884e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz 1894e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz dbus_message_iter_init_append(reply, &iter); 1904e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz 1914e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz dbus_message_iter_open_container(&iter, DBUS_TYPE_ARRAY, 1924e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz DBUS_DICT_ENTRY_BEGIN_CHAR_AS_STRING 1934e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz DBUS_TYPE_STRING_AS_STRING DBUS_TYPE_VARIANT_AS_STRING 1944e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz DBUS_DICT_ENTRY_END_CHAR_AS_STRING, &dict); 1954e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz 1964e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz /* Address */ 197cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode ptr = dstaddr; 198afda5bee3495e4fe070cf59e2f240127c341faf4Marcel Holtmann dbus_message_iter_append_dict_entry(&dict, "Address", 199afda5bee3495e4fe070cf59e2f240127c341faf4Marcel Holtmann DBUS_TYPE_STRING, &ptr); 2004e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz 2014e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz /* Name */ 202506c95298346d318304aa7e2211dfba5dbe6e3e0Claudio Takahasi ptr = NULL; 203506c95298346d318304aa7e2211dfba5dbe6e3e0Claudio Takahasi memset(name, 0, sizeof(name)); 2042a8fb41c4c57b24a22f3adaab472b416faae122eAlok Barsode adapter_get_address(adapter, &src); 205cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode ba2str(&src, srcaddr); 2068a68b5fe931db5a432f924b0de22ed3acee024baClaudio Takahasi 207cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode if (read_device_name(srcaddr, dstaddr, name) == 0) { 208506c95298346d318304aa7e2211dfba5dbe6e3e0Claudio Takahasi ptr = name; 2094e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz dbus_message_iter_append_dict_entry(&dict, "Name", 210e1a6c133d7a7fd2acf6d3462d200f47ff6124c1bMarcel Holtmann DBUS_TYPE_STRING, &ptr); 2114e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz } 2124e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz 213afda5bee3495e4fe070cf59e2f240127c341faf4Marcel Holtmann /* Alias (fallback to name or address) */ 214afda5bee3495e4fe070cf59e2f240127c341faf4Marcel Holtmann if (read_device_alias(srcaddr, dstaddr, name, sizeof(name)) < 1) { 215afda5bee3495e4fe070cf59e2f240127c341faf4Marcel Holtmann if (!ptr) { 216afda5bee3495e4fe070cf59e2f240127c341faf4Marcel Holtmann g_strdelimit(dstaddr, ":", '-'); 217afda5bee3495e4fe070cf59e2f240127c341faf4Marcel Holtmann ptr = dstaddr; 218afda5bee3495e4fe070cf59e2f240127c341faf4Marcel Holtmann } 219afda5bee3495e4fe070cf59e2f240127c341faf4Marcel Holtmann } else 220506c95298346d318304aa7e2211dfba5dbe6e3e0Claudio Takahasi ptr = name; 221506c95298346d318304aa7e2211dfba5dbe6e3e0Claudio Takahasi 222506c95298346d318304aa7e2211dfba5dbe6e3e0Claudio Takahasi if (ptr) 223506c95298346d318304aa7e2211dfba5dbe6e3e0Claudio Takahasi dbus_message_iter_append_dict_entry(&dict, "Alias", 224e1a6c133d7a7fd2acf6d3462d200f47ff6124c1bMarcel Holtmann DBUS_TYPE_STRING, &ptr); 225506c95298346d318304aa7e2211dfba5dbe6e3e0Claudio Takahasi 2264e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz /* Class */ 227cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode if (read_remote_class(&src, &device->bdaddr, &class) == 0) { 228e1a6c133d7a7fd2acf6d3462d200f47ff6124c1bMarcel Holtmann const char *icon = class_to_icon(class); 229e1a6c133d7a7fd2acf6d3462d200f47ff6124c1bMarcel Holtmann 2304e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz dbus_message_iter_append_dict_entry(&dict, "Class", 231e1a6c133d7a7fd2acf6d3462d200f47ff6124c1bMarcel Holtmann DBUS_TYPE_UINT32, &class); 232e1a6c133d7a7fd2acf6d3462d200f47ff6124c1bMarcel Holtmann 233e1a6c133d7a7fd2acf6d3462d200f47ff6124c1bMarcel Holtmann if (icon) 234e1a6c133d7a7fd2acf6d3462d200f47ff6124c1bMarcel Holtmann dbus_message_iter_append_dict_entry(&dict, "Icon", 235e1a6c133d7a7fd2acf6d3462d200f47ff6124c1bMarcel Holtmann DBUS_TYPE_STRING, &icon); 2364e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz } 2374e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz 2384e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz /* Paired */ 239769c4b021665a26c9a6c20457ef9b7ded54c8ad6Luiz Augusto von Dentz boolean = device_is_paired(device); 2404e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz dbus_message_iter_append_dict_entry(&dict, "Paired", 241e1a6c133d7a7fd2acf6d3462d200f47ff6124c1bMarcel Holtmann DBUS_TYPE_BOOLEAN, &boolean); 2424e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz 2434e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz /* Trusted */ 244cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode boolean = read_trust(&src, dstaddr, GLOBAL_TRUST); 2454e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz dbus_message_iter_append_dict_entry(&dict, "Trusted", 246e1a6c133d7a7fd2acf6d3462d200f47ff6124c1bMarcel Holtmann DBUS_TYPE_BOOLEAN, &boolean); 2474e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz 2484e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz /* Connected */ 249cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode dev = adapter_search_active_conn_by_bdaddr(adapter, &device->bdaddr); 250bcb5f7e4d5e570c1acfd5364547d36e970408394Alok Barsode if (dev) 2514e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz boolean = TRUE; 2524e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz else 2534e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz boolean = FALSE; 2544e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz 2554e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz dbus_message_iter_append_dict_entry(&dict, "Connected", 256e1a6c133d7a7fd2acf6d3462d200f47ff6124c1bMarcel Holtmann DBUS_TYPE_BOOLEAN, &boolean); 2574e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz 258ba93fb91ea81a35be0834ac395650e020a6b3fd3Claudio Takahasi /* UUIDs */ 259769c4b021665a26c9a6c20457ef9b7ded54c8ad6Luiz Augusto von Dentz uuids = g_new0(char *, g_slist_length(device->uuids) + 1); 260769c4b021665a26c9a6c20457ef9b7ded54c8ad6Luiz Augusto von Dentz for (i = 0, l = device->uuids; l; l = l->next, i++) 261769c4b021665a26c9a6c20457ef9b7ded54c8ad6Luiz Augusto von Dentz uuids[i] = l->data; 2628afa46e246f1598ebfac26725606823cee2dd0ecLuiz Augusto von Dentz dbus_message_iter_append_dict_entry(&dict, "UUIDs", 263e1a6c133d7a7fd2acf6d3462d200f47ff6124c1bMarcel Holtmann DBUS_TYPE_ARRAY, &uuids); 264769c4b021665a26c9a6c20457ef9b7ded54c8ad6Luiz Augusto von Dentz g_free(uuids); 2654e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz 26674fdac28eafca963c8081ea39dcf057459cf491aLuiz Augusto von Dentz /* Adapter */ 2678a68b5fe931db5a432f924b0de22ed3acee024baClaudio Takahasi ptr = adapter_get_path(adapter); 26874fdac28eafca963c8081ea39dcf057459cf491aLuiz Augusto von Dentz dbus_message_iter_append_dict_entry(&dict, "Adapter", 269e1a6c133d7a7fd2acf6d3462d200f47ff6124c1bMarcel Holtmann DBUS_TYPE_OBJECT_PATH, &ptr); 27074fdac28eafca963c8081ea39dcf057459cf491aLuiz Augusto von Dentz 2714e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz dbus_message_iter_close_container(&iter, &dict); 2724e6726e8029f20be3e08b44760c56fc7a419090bLuiz Augusto von Dentz 273e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi return reply; 2742c1effee41e974f97b21aec1bdd1a232ba48056aVinicius Costa Gomes} 2752c1effee41e974f97b21aec1bdd1a232ba48056aVinicius Costa Gomes 276e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasistatic DBusMessage *set_alias(DBusConnection *conn, DBusMessage *msg, 2777fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz const char *alias, void *data) 2787fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz{ 279555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsode struct btd_device *device = data; 28018614bd2b008cb9f3879990883c569c37b72f195Alok Barsode struct btd_adapter *adapter = device->adapter; 281cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode char srcaddr[18], dstaddr[18]; 282cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode bdaddr_t src; 283506c95298346d318304aa7e2211dfba5dbe6e3e0Claudio Takahasi int err; 2847fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz 285cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode adapter_get_address(adapter, &src); 286cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode ba2str(&src, srcaddr); 287cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode ba2str(&device->bdaddr, dstaddr); 2882a8fb41c4c57b24a22f3adaab472b416faae122eAlok Barsode 289cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode /* Remove alias if empty string */ 290cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode err = write_device_alias(srcaddr, dstaddr, 291506c95298346d318304aa7e2211dfba5dbe6e3e0Claudio Takahasi g_str_equal(alias, "") ? NULL : alias); 292506c95298346d318304aa7e2211dfba5dbe6e3e0Claudio Takahasi if (err < 0) 293e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi return g_dbus_create_error(msg, 294e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi ERROR_INTERFACE ".Failed", 295506c95298346d318304aa7e2211dfba5dbe6e3e0Claudio Takahasi strerror(-err)); 2967fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz 2977fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz dbus_connection_emit_property_changed(conn, dbus_message_get_path(msg), 2987fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz DEVICE_INTERFACE, "Alias", 299506c95298346d318304aa7e2211dfba5dbe6e3e0Claudio Takahasi DBUS_TYPE_STRING, &alias); 3007fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz 301e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi return dbus_message_new_method_return(msg); 3027fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz} 3037fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz 304e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasistatic DBusMessage *set_trust(DBusConnection *conn, DBusMessage *msg, 3057fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz dbus_bool_t value, void *data) 3067fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz{ 307555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsode struct btd_device *device = data; 30818614bd2b008cb9f3879990883c569c37b72f195Alok Barsode struct btd_adapter *adapter = device->adapter; 309cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode char srcaddr[18], dstaddr[18]; 310cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode bdaddr_t src; 3112a8fb41c4c57b24a22f3adaab472b416faae122eAlok Barsode 3127fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz 313cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode adapter_get_address(adapter, &src); 314cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode ba2str(&src, srcaddr); 315cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode ba2str(&device->bdaddr, dstaddr); 3162a8fb41c4c57b24a22f3adaab472b416faae122eAlok Barsode 317cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode write_trust(srcaddr, dstaddr, GLOBAL_TRUST, value); 3187fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz 3197fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz dbus_connection_emit_property_changed(conn, dbus_message_get_path(msg), 3207fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz DEVICE_INTERFACE, "Trusted", 3217fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz DBUS_TYPE_BOOLEAN, &value); 3227fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz 323e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi return dbus_message_new_method_return(msg); 3247fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz} 3257fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz 326e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasistatic inline DBusMessage *invalid_args(DBusMessage *msg) 327e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi{ 328e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi return g_dbus_create_error(msg, 329e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi ERROR_INTERFACE ".InvalidArguments", 330e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi "Invalid arguments in method call"); 331e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi} 332e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi 333e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasistatic DBusMessage *set_property(DBusConnection *conn, 334e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi DBusMessage *msg, void *data) 3352c1effee41e974f97b21aec1bdd1a232ba48056aVinicius Costa Gomes{ 3367fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz DBusMessageIter iter; 3377fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz DBusMessageIter sub; 3387fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz const char *property; 3397fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz 3407fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz if (!dbus_message_iter_init(msg, &iter)) 341e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi return invalid_args(msg); 3427fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz 3437fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_STRING) 344e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi return invalid_args(msg); 3457fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz 3467fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz dbus_message_iter_get_basic(&iter, &property); 3477fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz dbus_message_iter_next(&iter); 3487fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz 3497fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz if (dbus_message_iter_get_arg_type(&iter) != DBUS_TYPE_VARIANT) 350e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi return invalid_args(msg); 3517fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz dbus_message_iter_recurse(&iter, &sub); 3527fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz 3537fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz if (g_str_equal("Trusted", property)) { 3547fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz dbus_bool_t value; 3557fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz 3567fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz if (dbus_message_iter_get_arg_type(&sub) != DBUS_TYPE_BOOLEAN) 357e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi return invalid_args(msg); 3587fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz dbus_message_iter_get_basic(&sub, &value); 3597fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz 3607fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz return set_trust(conn, msg, value, data); 3617fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz } else if (g_str_equal("Alias", property)) { 362506c95298346d318304aa7e2211dfba5dbe6e3e0Claudio Takahasi const char *alias; 3637fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz 3647fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz if (dbus_message_iter_get_arg_type(&sub) != DBUS_TYPE_STRING) 365e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi return invalid_args(msg); 3667fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz dbus_message_iter_get_basic(&sub, &alias); 3677fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz 3687fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz return set_alias(conn, msg, alias, data); 3697fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz } 3707fe6ac58638e86d11494f5a785bcf1d074ca2c37Luiz Augusto von Dentz 371e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi return invalid_args(msg); 3722c1effee41e974f97b21aec1bdd1a232ba48056aVinicius Costa Gomes} 3732c1effee41e974f97b21aec1bdd1a232ba48056aVinicius Costa Gomes 374342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentzstatic void discover_services_req_exit(void *user_data) 375342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz{ 376555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsode struct btd_device *device = user_data; 37718614bd2b008cb9f3879990883c569c37b72f195Alok Barsode struct btd_adapter *adapter = device->adapter; 378cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode bdaddr_t src; 3792a8fb41c4c57b24a22f3adaab472b416faae122eAlok Barsode 3802a8fb41c4c57b24a22f3adaab472b416faae122eAlok Barsode adapter_get_address(adapter, &src); 381342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz 382342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz debug("DiscoverDevices requestor exited"); 383342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz 384cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode bt_cancel_discovery(&src, &device->bdaddr); 385342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz} 386342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz 38794c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmannstatic DBusMessage *discover_services(DBusConnection *conn, 38894c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann DBusMessage *msg, void *user_data) 38994c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann{ 390555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsode struct btd_device *device = user_data; 39194c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann const char *pattern; 392342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz int err; 393342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz 394342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz if (device->discov_active) 395342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz return g_dbus_create_error(msg, ERROR_INTERFACE ".InProgress", 396342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz "Discover in progress"); 39794c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann 39894c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann if (dbus_message_get_args(msg, NULL, DBUS_TYPE_STRING, &pattern, 39994c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann DBUS_TYPE_INVALID) == FALSE) 400342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz goto fail; 40194c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann 402a6f07d2bf12942854072c37c3c42d7447921beeeMarcel Holtmann if (strlen(pattern) == 0) { 403040728e5019fce4eba5790939329fae0aa9104ffClaudio Takahasi err = device_browse(device, conn, msg, NULL); 404342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz if (err < 0) 405342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz goto fail; 406342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz } else { 407040728e5019fce4eba5790939329fae0aa9104ffClaudio Takahasi uuid_t uuid; 408040728e5019fce4eba5790939329fae0aa9104ffClaudio Takahasi 409040728e5019fce4eba5790939329fae0aa9104ffClaudio Takahasi if (bt_string2uuid(&uuid, pattern) < 0) 410342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz return invalid_args(msg); 411a6f07d2bf12942854072c37c3c42d7447921beeeMarcel Holtmann 412040728e5019fce4eba5790939329fae0aa9104ffClaudio Takahasi err = device_browse(device, conn, msg, &uuid); 413342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz if (err < 0) 414342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz goto fail; 415342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz } 41694c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann 41794c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann return NULL; 418342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz 419342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentzfail: 420342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz return g_dbus_create_error(msg, ERROR_INTERFACE ".Failed", 421342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz "Discovery Failed"); 42294c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann} 42394c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann 42494c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmannstatic DBusMessage *cancel_discover(DBusConnection *conn, 42594c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann DBusMessage *msg, void *user_data) 42694c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann{ 427555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsode struct btd_device *device = user_data; 42818614bd2b008cb9f3879990883c569c37b72f195Alok Barsode struct btd_adapter *adapter = device->adapter; 429cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode bdaddr_t src; 4302a8fb41c4c57b24a22f3adaab472b416faae122eAlok Barsode 4312a8fb41c4c57b24a22f3adaab472b416faae122eAlok Barsode adapter_get_address(adapter, &src); 43219b4c8b0e51a20a1b95ede34b092ebc56e1183aeMarcel Holtmann 433342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz if (!device->discov_active) 434342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz return g_dbus_create_error(msg, 435342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz ERROR_INTERFACE ".Failed", 436342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz "No pending discovery"); 437342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz 438342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz /* only the discover requestor can cancel the inquiry process */ 439342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz if (!device->discov_requestor || 440342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz strcmp(device->discov_requestor, dbus_message_get_sender(msg))) 441342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz return g_dbus_create_error(msg, 442342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz ERROR_INTERFACE ".NotAuthorized", 443342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz "Not Authorized"); 444342293a80657406a02003452e3a23d097dd9c73eLuiz Augusto von Dentz 445cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode if (bt_cancel_discovery(&src, &device->bdaddr) < 0) 446289e29c6c4a073569c7e7aa3c8fc51ed5c46993fLuiz Augusto von Dentz return g_dbus_create_error(msg, 447289e29c6c4a073569c7e7aa3c8fc51ed5c46993fLuiz Augusto von Dentz ERROR_INTERFACE ".Failed", 448289e29c6c4a073569c7e7aa3c8fc51ed5c46993fLuiz Augusto von Dentz "No pending discover"); 44994c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann 45094c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann return dbus_message_new_method_return(msg); 45194c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann} 45294c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann 4535d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasistatic gboolean disconnect_timeout(gpointer user_data) 4545d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi{ 455555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsode struct btd_device *device = user_data; 4565d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi struct active_conn_info *ci; 4575d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi disconnect_cp cp; 4585d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi int dd; 459661a10565362c5ae0aad6a2ebf6513390cba868eAlok Barsode uint16_t dev_id = adapter_get_dev_id(device->adapter); 4605d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi 4615d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi device->disconn_timer = 0; 4625d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi 463cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode ci = adapter_search_active_conn_by_bdaddr(device->adapter, 464cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode &device->bdaddr); 465bcb5f7e4d5e570c1acfd5364547d36e970408394Alok Barsode 466bcb5f7e4d5e570c1acfd5364547d36e970408394Alok Barsode if (!ci) 4675d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi return FALSE; 4685d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi 469661a10565362c5ae0aad6a2ebf6513390cba868eAlok Barsode dd = hci_open_dev(dev_id); 4705d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi if (dd < 0) 4715d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi goto fail; 4725d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi 4735d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi memset(&cp, 0, sizeof(cp)); 4745d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi cp.handle = htobs(ci->handle); 4755d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi cp.reason = HCI_OE_USER_ENDED_CONNECTION; 4765d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi 4775d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi hci_send_cmd(dd, OGF_LINK_CTL, OCF_DISCONNECT, 4785d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi DISCONNECT_CP_SIZE, &cp); 4795d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi 4805d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi close(dd); 4815d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi 4825d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasifail: 4835d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi return FALSE; 4845d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi} 4855d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi 48694c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmannstatic DBusMessage *disconnect(DBusConnection *conn, 48794c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann DBusMessage *msg, void *user_data) 48894c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann{ 489555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsode struct btd_device *device = user_data; 490bcb5f7e4d5e570c1acfd5364547d36e970408394Alok Barsode struct active_conn_info *dev; 4915d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi 492cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode dev = adapter_search_active_conn_by_bdaddr(device->adapter, 493cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode &device->bdaddr); 494bcb5f7e4d5e570c1acfd5364547d36e970408394Alok Barsode 495bcb5f7e4d5e570c1acfd5364547d36e970408394Alok Barsode if (!dev) 4965d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi return g_dbus_create_error(msg, 4975d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi ERROR_INTERFACE ".NotConnected", 4985d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi "Device is not connected"); 4995d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi 5005d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi g_dbus_emit_signal(conn, device->path, 5015d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi DEVICE_INTERFACE, "DisconnectRequested", 5025d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi DBUS_TYPE_INVALID); 5035d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi 5045d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi device->disconn_timer = g_timeout_add_seconds(DISCONNECT_TIMER, 5055d49d848060b0809a25acb9a20b176600f52e66dClaudio Takahasi disconnect_timeout, device); 50694c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann 50794c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann return dbus_message_new_method_return(msg); 50894c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann} 50994c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann 510e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasistatic GDBusMethodTable device_methods[] = { 511e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi { "GetProperties", "", "a{sv}", get_properties }, 512e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi { "SetProperty", "sv", "", set_property }, 513e0d13d6da4b527ee02838af6b9dd7d53615e4896Marcel Holtmann { "DiscoverServices", "s", "a{us}", discover_services, 51494c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann G_DBUS_METHOD_FLAG_ASYNC}, 51594c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann { "CancelDiscovery", "", "", cancel_discover }, 516e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi { "Disconnect", "", "", disconnect }, 51794c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann { } 5182c1effee41e974f97b21aec1bdd1a232ba48056aVinicius Costa Gomes}; 5192c1effee41e974f97b21aec1bdd1a232ba48056aVinicius Costa Gomes 520e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasistatic GDBusSignalTable device_signals[] = { 52194c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann { "PropertyChanged", "sv" }, 52294c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann { "DisconnectRequested", "" }, 52394c199911b1dc1395a8025647f0686f58e6bf4f6Marcel Holtmann { } 5242c1effee41e974f97b21aec1bdd1a232ba48056aVinicius Costa Gomes}; 5252c1effee41e974f97b21aec1bdd1a232ba48056aVinicius Costa Gomes 526e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberggboolean device_get_connected(struct btd_device *device) 527e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg{ 528e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg return device->connected; 529e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg} 530e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg 531013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedbergvoid device_set_connected(DBusConnection *conn, struct btd_device *device, 532013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg gboolean connected) 533013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg{ 534e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg device->connected = connected; 535e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg 536013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg if (!connected && device->discov_timer) { 537013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg g_source_remove(device->discov_timer); 538013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg device->discov_timer = 0; 539013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg } 540013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg 541013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg dbus_connection_emit_property_changed(conn, device->path, 542013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg DEVICE_INTERFACE, 543013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg "Connected", DBUS_TYPE_BOOLEAN, 544013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg &connected); 545e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg 546e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg if (connected && device->secmode3) { 547e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg struct btd_adapter *adapter = device_get_adapter(device); 548e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg bdaddr_t sba; 549e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg 550e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg adapter_get_address(adapter, &sba); 551e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg 552e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg device->secmode3 = FALSE; 553e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg 554e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg hcid_dbus_bonding_process_complete(&sba, &device->bdaddr, 0); 555e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg } 556e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg} 557e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg 558e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedbergvoid device_set_secmode3_conn(struct btd_device *device, gboolean enable) 559e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg{ 560e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg device->secmode3 = enable; 561013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg} 562013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg 56318614bd2b008cb9f3879990883c569c37b72f195Alok Barsodestruct btd_device *device_create(DBusConnection *conn, struct btd_adapter *adapter, 56436dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz const gchar *address) 56586892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann{ 566ecbcc749831ab86da7ed8d15c36f1bd1fb380be8Cidorvan Leite gchar *address_up; 567555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsode struct btd_device *device; 568661a10565362c5ae0aad6a2ebf6513390cba868eAlok Barsode uint16_t dev_id = adapter_get_dev_id(adapter); 56986892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann 570555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsode device = g_try_malloc0(sizeof(struct btd_device)); 57186892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann if (device == NULL) 57286892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann return NULL; 57386892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann 574ecbcc749831ab86da7ed8d15c36f1bd1fb380be8Cidorvan Leite address_up = g_ascii_strup(address, -1); 57593fbf4400a81f68cd3642084bd6d2aa51a173250Marcel Holtmann device->path = g_strdup_printf("%s/hci%d/dev_%s", "/org/bluez", 57693fbf4400a81f68cd3642084bd6d2aa51a173250Marcel Holtmann dev_id, address_up); 57786892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann g_strdelimit(device->path, ":", '_'); 578ecbcc749831ab86da7ed8d15c36f1bd1fb380be8Cidorvan Leite g_free(address_up); 57986892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann 58086892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann debug("Creating device %s", device->path); 58186892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann 582e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi if (g_dbus_register_interface(conn, device->path, DEVICE_INTERFACE, 583e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi device_methods, device_signals, NULL, 584e2731d4c2e3ef7d1677a73aca5fa58f044075980Claudio Takahasi device, device_free) == FALSE) { 58586892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann device_free(device); 58686892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann return NULL; 58786892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann } 588da0e7105811dc046d13d0365404efc1189ee4a8cClaudio Takahasi 589cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode str2ba(address, &device->bdaddr); 590da0e7105811dc046d13d0365404efc1189ee4a8cClaudio Takahasi device->adapter = adapter; 591da0e7105811dc046d13d0365404efc1189ee4a8cClaudio Takahasi 5926bfa88d706cc57a0c975c980dabec5d8ed67dcc0Claudio Takahasi return device; 59386892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann} 59486892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann 595555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsodevoid device_remove(DBusConnection *conn, struct btd_device *device) 59675add5651e5dbc49c9c144acceac7e2c32d9bd16Claudio Takahasi{ 5976061f1a889c90d4d408ca12b63b2db6235c73baeMarcel Holtmann GSList *list; 5986061f1a889c90d4d408ca12b63b2db6235c73baeMarcel Holtmann struct btd_device_driver *driver; 599f62f8d892b5d5cc5aedef83779671c1ed54a35daMarcel Holtmann gchar *path = g_strdup(device->path); 600f62f8d892b5d5cc5aedef83779671c1ed54a35daMarcel Holtmann 601f62f8d892b5d5cc5aedef83779671c1ed54a35daMarcel Holtmann debug("Removing device %s", path); 602f62f8d892b5d5cc5aedef83779671c1ed54a35daMarcel Holtmann 6036061f1a889c90d4d408ca12b63b2db6235c73baeMarcel Holtmann for (list = device->drivers; list; list = list->next) { 604b76fbc7d29f28a95a9ea25aae1f6f2d9c10adb19Alok Barsode struct btd_driver_data *driver_data = list->data; 605b76fbc7d29f28a95a9ea25aae1f6f2d9c10adb19Alok Barsode driver = driver_data->driver; 6066061f1a889c90d4d408ca12b63b2db6235c73baeMarcel Holtmann 607e780c7bd8ec0527723db3c19f28365063bbe7d93Luiz Augusto von Dentz driver->remove(device); 608b76fbc7d29f28a95a9ea25aae1f6f2d9c10adb19Alok Barsode g_free(driver_data); 6096061f1a889c90d4d408ca12b63b2db6235c73baeMarcel Holtmann } 6106061f1a889c90d4d408ca12b63b2db6235c73baeMarcel Holtmann 611f62f8d892b5d5cc5aedef83779671c1ed54a35daMarcel Holtmann g_dbus_unregister_interface(conn, path, DEVICE_INTERFACE); 61275add5651e5dbc49c9c144acceac7e2c32d9bd16Claudio Takahasi 613f62f8d892b5d5cc5aedef83779671c1ed54a35daMarcel Holtmann g_free(path); 61486892be8d38960096f9b9c5613ba28fc9003d288Marcel Holtmann} 615ff296428a08dee619db1cc702146faefa91087faCidorvan Leite 616555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsodegint device_address_cmp(struct btd_device *device, const gchar *address) 617ff296428a08dee619db1cc702146faefa91087faCidorvan Leite{ 618cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode char addr[18]; 619cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode 620cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode ba2str(&device->bdaddr, addr); 621cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode return strcasecmp(addr, address); 622ff296428a08dee619db1cc702146faefa91087faCidorvan Leite} 6233d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz 6244b0ab7e43f4fa555641902b07f2f7ab3821f2b75Alok Barsodevoid device_probe_drivers(struct btd_device *device, GSList *uuids, sdp_list_t *recs) 625f4eb9e2dea643f41e261bb9e2bff33fc03bd9eccMarcel Holtmann{ 626c560d02ccf1dd156f068b1da8a3e7d75d2319dfdLuiz Augusto von Dentz GSList *list; 6276061f1a889c90d4d408ca12b63b2db6235c73baeMarcel Holtmann const char **uuid; 628f4eb9e2dea643f41e261bb9e2bff33fc03bd9eccMarcel Holtmann int err; 629f4eb9e2dea643f41e261bb9e2bff33fc03bd9eccMarcel Holtmann 630f4eb9e2dea643f41e261bb9e2bff33fc03bd9eccMarcel Holtmann debug("Probe drivers for %s", device->path); 631f4eb9e2dea643f41e261bb9e2bff33fc03bd9eccMarcel Holtmann 632c560d02ccf1dd156f068b1da8a3e7d75d2319dfdLuiz Augusto von Dentz for (list = device_drivers; list; list = list->next) { 633e0863545e6239ac338fa7fbe9647a5748a60b436Marcel Holtmann struct btd_device_driver *driver = list->data; 6344b0ab7e43f4fa555641902b07f2f7ab3821f2b75Alok Barsode GSList *records = NULL; 635f4eb9e2dea643f41e261bb9e2bff33fc03bd9eccMarcel Holtmann 6366061f1a889c90d4d408ca12b63b2db6235c73baeMarcel Holtmann for (uuid = driver->uuids; *uuid; uuid++) { 637081d9d1df3cde11e3e3833201f4cadac6f355da0Luiz Augusto von Dentz sdp_record_t *rec; 6384b0ab7e43f4fa555641902b07f2f7ab3821f2b75Alok Barsode 639081d9d1df3cde11e3e3833201f4cadac6f355da0Luiz Augusto von Dentz if (!g_slist_find_custom(uuids, *uuid, 640081d9d1df3cde11e3e3833201f4cadac6f355da0Luiz Augusto von Dentz (GCompareFunc) strcasecmp)) 641081d9d1df3cde11e3e3833201f4cadac6f355da0Luiz Augusto von Dentz continue; 642081d9d1df3cde11e3e3833201f4cadac6f355da0Luiz Augusto von Dentz 64360af857dbc8a258eb91ef3fb6de06c17c8fb4ec2David Woodhouse rec = find_record_in_list(recs, *uuid); 644081d9d1df3cde11e3e3833201f4cadac6f355da0Luiz Augusto von Dentz if (!rec) 645081d9d1df3cde11e3e3833201f4cadac6f355da0Luiz Augusto von Dentz continue; 646081d9d1df3cde11e3e3833201f4cadac6f355da0Luiz Augusto von Dentz 647081d9d1df3cde11e3e3833201f4cadac6f355da0Luiz Augusto von Dentz records = g_slist_append(records, rec); 648f4eb9e2dea643f41e261bb9e2bff33fc03bd9eccMarcel Holtmann } 649f4eb9e2dea643f41e261bb9e2bff33fc03bd9eccMarcel Holtmann 6504b0ab7e43f4fa555641902b07f2f7ab3821f2b75Alok Barsode if (records) { 651b76fbc7d29f28a95a9ea25aae1f6f2d9c10adb19Alok Barsode struct btd_driver_data *driver_data = g_new0(struct btd_driver_data, 1); 652b76fbc7d29f28a95a9ea25aae1f6f2d9c10adb19Alok Barsode 653e780c7bd8ec0527723db3c19f28365063bbe7d93Luiz Augusto von Dentz err = driver->probe(device, records); 654fad3b8ad7a07de0c96c34b9d624ec174c2754817Marcel Holtmann if (err < 0) { 655f4eb9e2dea643f41e261bb9e2bff33fc03bd9eccMarcel Holtmann error("probe failed for driver %s", 656f4eb9e2dea643f41e261bb9e2bff33fc03bd9eccMarcel Holtmann driver->name); 657b76fbc7d29f28a95a9ea25aae1f6f2d9c10adb19Alok Barsode 658b76fbc7d29f28a95a9ea25aae1f6f2d9c10adb19Alok Barsode g_free(driver_data); 659fad3b8ad7a07de0c96c34b9d624ec174c2754817Marcel Holtmann continue; 660fad3b8ad7a07de0c96c34b9d624ec174c2754817Marcel Holtmann } 661fad3b8ad7a07de0c96c34b9d624ec174c2754817Marcel Holtmann 662b76fbc7d29f28a95a9ea25aae1f6f2d9c10adb19Alok Barsode driver_data->driver = driver; 663fad3b8ad7a07de0c96c34b9d624ec174c2754817Marcel Holtmann device->drivers = g_slist_append(device->drivers, 664b76fbc7d29f28a95a9ea25aae1f6f2d9c10adb19Alok Barsode driver_data); 665f4eb9e2dea643f41e261bb9e2bff33fc03bd9eccMarcel Holtmann } 666f4eb9e2dea643f41e261bb9e2bff33fc03bd9eccMarcel Holtmann } 66736dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz 668c4c130d3922dedc992e00fbf94bde64a180306c2Marcel Holtmann for (list = uuids; list; list = list->next) { 669c4c130d3922dedc992e00fbf94bde64a180306c2Marcel Holtmann GSList *l = g_slist_find_custom(device->uuids, list->data, 670c4c130d3922dedc992e00fbf94bde64a180306c2Marcel Holtmann (GCompareFunc) strcmp); 671c4c130d3922dedc992e00fbf94bde64a180306c2Marcel Holtmann if (l) 672c4c130d3922dedc992e00fbf94bde64a180306c2Marcel Holtmann continue; 673c4c130d3922dedc992e00fbf94bde64a180306c2Marcel Holtmann 67436dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz device->uuids = g_slist_insert_sorted(device->uuids, 675c4c130d3922dedc992e00fbf94bde64a180306c2Marcel Holtmann list->data, (GCompareFunc) strcmp); 676c4c130d3922dedc992e00fbf94bde64a180306c2Marcel Holtmann } 67736dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz} 67836dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz 6794b0ab7e43f4fa555641902b07f2f7ab3821f2b75Alok Barsodevoid device_remove_drivers(struct btd_device *device, GSList *uuids, sdp_list_t *recs) 68036dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz{ 68118614bd2b008cb9f3879990883c569c37b72f195Alok Barsode struct btd_adapter *adapter = device_get_adapter(device); 682352a65d3de4fdf6e1e507f958685097f33e3b899Johan Hedberg GSList *list, *next; 683cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode char srcaddr[18], dstaddr[18]; 6842a8fb41c4c57b24a22f3adaab472b416faae122eAlok Barsode bdaddr_t src; 6852a8fb41c4c57b24a22f3adaab472b416faae122eAlok Barsode 6862a8fb41c4c57b24a22f3adaab472b416faae122eAlok Barsode adapter_get_address(adapter, &src); 687cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode ba2str(&src, srcaddr); 688cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode ba2str(&device->bdaddr, dstaddr); 68936dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz 69036dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz debug("Remove drivers for %s", device->path); 69136dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz 692352a65d3de4fdf6e1e507f958685097f33e3b899Johan Hedberg for (list = device->drivers; list; list = next) { 693b76fbc7d29f28a95a9ea25aae1f6f2d9c10adb19Alok Barsode struct btd_driver_data *driver_data = list->data; 694b76fbc7d29f28a95a9ea25aae1f6f2d9c10adb19Alok Barsode struct btd_device_driver *driver = driver_data->driver; 69536dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz const char **uuid; 69636dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz 697352a65d3de4fdf6e1e507f958685097f33e3b899Johan Hedberg next = list->next; 698352a65d3de4fdf6e1e507f958685097f33e3b899Johan Hedberg 69936dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz for (uuid = driver->uuids; *uuid; uuid++) { 7009b4bfa74d25e360932402994a32305bf2145eb34Luiz Augusto von Dentz sdp_record_t *rec; 70136dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz 7029b4bfa74d25e360932402994a32305bf2145eb34Luiz Augusto von Dentz if (!g_slist_find_custom(uuids, *uuid, 7039b4bfa74d25e360932402994a32305bf2145eb34Luiz Augusto von Dentz (GCompareFunc) strcasecmp)) 70436dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz continue; 70536dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz 706e780c7bd8ec0527723db3c19f28365063bbe7d93Luiz Augusto von Dentz driver->remove(device); 70736dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz device->drivers = g_slist_remove(device->drivers, 708b76fbc7d29f28a95a9ea25aae1f6f2d9c10adb19Alok Barsode driver_data); 709b76fbc7d29f28a95a9ea25aae1f6f2d9c10adb19Alok Barsode 710b76fbc7d29f28a95a9ea25aae1f6f2d9c10adb19Alok Barsode g_free(driver_data); 711b76fbc7d29f28a95a9ea25aae1f6f2d9c10adb19Alok Barsode 71260af857dbc8a258eb91ef3fb6de06c17c8fb4ec2David Woodhouse rec = find_record_in_list(recs, *uuid); 7139b4bfa74d25e360932402994a32305bf2145eb34Luiz Augusto von Dentz if (!rec) 7149b4bfa74d25e360932402994a32305bf2145eb34Luiz Augusto von Dentz continue; 7159b4bfa74d25e360932402994a32305bf2145eb34Luiz Augusto von Dentz 716cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode delete_record(srcaddr, dstaddr, rec->handle); 71736dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz } 71836dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz } 71936dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz 72036dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz for (list = uuids; list; list = list->next) 72136dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz device->uuids = g_slist_remove(device->uuids, list->data); 722f4eb9e2dea643f41e261bb9e2bff33fc03bd9eccMarcel Holtmann} 723f4eb9e2dea643f41e261bb9e2bff33fc03bd9eccMarcel Holtmann 724bbe56de7715cf62e37026711a6eb3f1c5be6d1cdMarcel Holtmannstatic void iter_append_record(DBusMessageIter *dict, uint32_t handle, 725bbe56de7715cf62e37026711a6eb3f1c5be6d1cdMarcel Holtmann const char *record) 726bbe56de7715cf62e37026711a6eb3f1c5be6d1cdMarcel Holtmann{ 727bbe56de7715cf62e37026711a6eb3f1c5be6d1cdMarcel Holtmann DBusMessageIter entry; 728bbe56de7715cf62e37026711a6eb3f1c5be6d1cdMarcel Holtmann 729bbe56de7715cf62e37026711a6eb3f1c5be6d1cdMarcel Holtmann dbus_message_iter_open_container(dict, DBUS_TYPE_DICT_ENTRY, 730bbe56de7715cf62e37026711a6eb3f1c5be6d1cdMarcel Holtmann NULL, &entry); 731bbe56de7715cf62e37026711a6eb3f1c5be6d1cdMarcel Holtmann 732bbe56de7715cf62e37026711a6eb3f1c5be6d1cdMarcel Holtmann dbus_message_iter_append_basic(&entry, DBUS_TYPE_UINT32, &handle); 733bbe56de7715cf62e37026711a6eb3f1c5be6d1cdMarcel Holtmann 734bbe56de7715cf62e37026711a6eb3f1c5be6d1cdMarcel Holtmann dbus_message_iter_append_basic(&entry, DBUS_TYPE_STRING, &record); 735bbe56de7715cf62e37026711a6eb3f1c5be6d1cdMarcel Holtmann 736bbe56de7715cf62e37026711a6eb3f1c5be6d1cdMarcel Holtmann dbus_message_iter_close_container(dict, &entry); 737bbe56de7715cf62e37026711a6eb3f1c5be6d1cdMarcel Holtmann} 738bbe56de7715cf62e37026711a6eb3f1c5be6d1cdMarcel Holtmann 739730775d1226a30c37ff551955f093ddfcd18e600Claudio Takahasistatic void append_and_grow_string(void *data, const char *str) 740c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz{ 741c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz sdp_buf_t *buff = data; 742c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz int len; 743c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz 744c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz len = strlen(str); 745c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz 746c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz if (!buff->data) { 747c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz buff->data = malloc(DEFAULT_XML_BUF_SIZE); 748c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz if (!buff->data) 749c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz return; 750c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz buff->buf_size = DEFAULT_XML_BUF_SIZE; 751c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz } 752c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz 753c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz /* Grow string */ 754c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz while (buff->buf_size < (buff->data_size + len + 1)) { 755c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz void *tmp; 756c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz uint32_t new_size; 757c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz 758c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz /* Grow buffer by a factor of 2 */ 759c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz new_size = (buff->buf_size << 1); 760c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz 761c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz tmp = realloc(buff->data, new_size); 762c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz if (!tmp) 763c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz return; 764c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz 765c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz buff->data = tmp; 766c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz buff->buf_size = new_size; 767c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz } 768c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz 769c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz /* Include the NULL character */ 770c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz memcpy(buff->data + buff->data_size, str, len + 1); 771c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz buff->data_size += len; 772c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz} 773c36942e998cd6187181df3033e53f1d624a5fd1aLuiz Augusto von Dentz 7741e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentzstatic void discover_device_reply(struct browse_req *req, sdp_list_t *recs) 7751e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz{ 7761e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz DBusMessage *reply; 7771e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz DBusMessageIter iter, dict; 7781e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz sdp_list_t *seq; 7791e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz 7801e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz reply = dbus_message_new_method_return(req->msg); 7811e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz if (!reply) 7821e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz return; 7831e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz 7841e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz dbus_message_iter_init_append(reply, &iter); 7851e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz 7861e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz dbus_message_iter_open_container(&iter, DBUS_TYPE_ARRAY, 7871e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz DBUS_DICT_ENTRY_BEGIN_CHAR_AS_STRING 7881e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz DBUS_TYPE_UINT32_AS_STRING DBUS_TYPE_STRING_AS_STRING 7891e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz DBUS_DICT_ENTRY_END_CHAR_AS_STRING, &dict); 7901e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz 7911e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz for (seq = recs; seq; seq = seq->next) { 7921e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz sdp_record_t *rec = (sdp_record_t *) seq->data; 7931e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz sdp_buf_t result; 7941e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz 7951e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz if (!rec) 7961e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz break; 7971e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz 7981e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz memset(&result, 0, sizeof(sdp_buf_t)); 7991e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz 8001e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz convert_sdp_record_to_xml(rec, &result, 8011e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz append_and_grow_string); 8021e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz 8031e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz if (result.data) { 8041e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz const char *val = (char *) result.data; 8051e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz iter_append_record(&dict, rec->handle, val); 8061e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz free(result.data); 8071e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz } 8081e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz } 8091e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz 8101e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz dbus_message_iter_close_container(&iter, &dict); 8111e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz 8121e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz dbus_connection_send(req->conn, reply, NULL); 8131e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz dbus_message_unref(reply); 8141e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz} 8151e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz 81636dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentzstatic void services_changed(struct browse_req *req) 8173d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz{ 818533655873c4978091edf3698b20d2b96c43dafc8Johan Hedberg DBusConnection *conn = get_dbus_connection(); 819555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsode struct btd_device *device = req->device; 8203d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz char **uuids; 8213d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz GSList *l; 82236dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz int i; 8233d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz 82436dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz uuids = g_new0(char *, g_slist_length(device->uuids) + 1); 82536dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz for (i = 0, l = device->uuids; l; l = l->next, i++) 82636dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz uuids[i] = l->data; 82736dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz 828533655873c4978091edf3698b20d2b96c43dafc8Johan Hedberg dbus_connection_emit_property_changed(conn, device->path, 82936dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz DEVICE_INTERFACE, "UUIDs", 83036dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz DBUS_TYPE_ARRAY, &uuids); 83136dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz 83236dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz g_free(uuids); 83336dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz} 83436dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz 8358b2e688eaf5b71006c72cf91a8e4df3c0c41c306Johan Hedbergstatic int rec_cmp(const void *a, const void *b) 8368b2e688eaf5b71006c72cf91a8e4df3c0c41c306Johan Hedberg{ 8378b2e688eaf5b71006c72cf91a8e4df3c0c41c306Johan Hedberg const sdp_record_t *r1 = a; 8388b2e688eaf5b71006c72cf91a8e4df3c0c41c306Johan Hedberg const sdp_record_t *r2 = b; 8398b2e688eaf5b71006c72cf91a8e4df3c0c41c306Johan Hedberg 8408b2e688eaf5b71006c72cf91a8e4df3c0c41c306Johan Hedberg return r1->handle - r2->handle; 8418b2e688eaf5b71006c72cf91a8e4df3c0c41c306Johan Hedberg} 8428b2e688eaf5b71006c72cf91a8e4df3c0c41c306Johan Hedberg 84336dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentzstatic void update_services(struct browse_req *req, sdp_list_t *recs) 84436dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz{ 845555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsode struct btd_device *device = req->device; 84618614bd2b008cb9f3879990883c569c37b72f195Alok Barsode struct btd_adapter *adapter = device_get_adapter(device); 84736dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz sdp_list_t *seq; 848cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode char srcaddr[18], dstaddr[18]; 8492a8fb41c4c57b24a22f3adaab472b416faae122eAlok Barsode bdaddr_t src; 8502a8fb41c4c57b24a22f3adaab472b416faae122eAlok Barsode 8512a8fb41c4c57b24a22f3adaab472b416faae122eAlok Barsode adapter_get_address(adapter, &src); 852cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode ba2str(&src, srcaddr); 853cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode ba2str(&device->bdaddr, dstaddr); 8543d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz 85536dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz for (seq = recs; seq; seq = seq->next) { 8563d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz sdp_record_t *rec = (sdp_record_t *) seq->data; 857681e50c618d246483728bca6628a18c1c44c5b36Luiz Augusto von Dentz sdp_buf_t pdu; 85836dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz sdp_list_t *svcclass = NULL; 85936dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz gchar *uuid_str; 86036dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz GSList *l; 8613d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz 8623d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz if (!rec) 8633d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz break; 8643d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz 86536dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz if (sdp_get_service_classes(rec, &svcclass) < 0) 86636dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz continue; 86736dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz 86836dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz /* Extract the first element and skip the remainning */ 86936dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz uuid_str = bt_uuid2string(svcclass->data); 870aaf0f75d2a18a86bca3c418ddd63e936627c4446Johan Hedberg if (!uuid_str) { 871aaf0f75d2a18a86bca3c418ddd63e936627c4446Johan Hedberg sdp_list_free(svcclass, free); 87236dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz continue; 873aaf0f75d2a18a86bca3c418ddd63e936627c4446Johan Hedberg } 87436dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz 875e2a5786af8c8278eeeb0bedccda32c7422e9a2b7David Woodhouse if (!strcasecmp(uuid_str, PNP_UUID)) { 876fce6db565f747ca9ad560f7d8bff6a45522d905cMarcel Holtmann uint16_t source, vendor, product, version; 877e2a5786af8c8278eeeb0bedccda32c7422e9a2b7David Woodhouse sdp_data_t *pdlist; 878e2a5786af8c8278eeeb0bedccda32c7422e9a2b7David Woodhouse 879fce6db565f747ca9ad560f7d8bff6a45522d905cMarcel Holtmann pdlist = sdp_data_get(rec, SDP_ATTR_VENDOR_ID_SOURCE); 880fce6db565f747ca9ad560f7d8bff6a45522d905cMarcel Holtmann source = pdlist ? pdlist->val.uint16 : 0x0000; 881fce6db565f747ca9ad560f7d8bff6a45522d905cMarcel Holtmann 882e2a5786af8c8278eeeb0bedccda32c7422e9a2b7David Woodhouse pdlist = sdp_data_get(rec, SDP_ATTR_VENDOR_ID); 883e2a5786af8c8278eeeb0bedccda32c7422e9a2b7David Woodhouse vendor = pdlist ? pdlist->val.uint16 : 0x0000; 884e2a5786af8c8278eeeb0bedccda32c7422e9a2b7David Woodhouse 885e2a5786af8c8278eeeb0bedccda32c7422e9a2b7David Woodhouse pdlist = sdp_data_get(rec, SDP_ATTR_PRODUCT_ID); 886e2a5786af8c8278eeeb0bedccda32c7422e9a2b7David Woodhouse product = pdlist ? pdlist->val.uint16 : 0x0000; 887e2a5786af8c8278eeeb0bedccda32c7422e9a2b7David Woodhouse 888e2a5786af8c8278eeeb0bedccda32c7422e9a2b7David Woodhouse pdlist = sdp_data_get(rec, SDP_ATTR_VERSION); 889e2a5786af8c8278eeeb0bedccda32c7422e9a2b7David Woodhouse version = pdlist ? pdlist->val.uint16 : 0x0000; 890e2a5786af8c8278eeeb0bedccda32c7422e9a2b7David Woodhouse 891fce6db565f747ca9ad560f7d8bff6a45522d905cMarcel Holtmann if (source || vendor || product || version) 892fce6db565f747ca9ad560f7d8bff6a45522d905cMarcel Holtmann store_device_id(srcaddr, dstaddr, source, 893fce6db565f747ca9ad560f7d8bff6a45522d905cMarcel Holtmann vendor, product, version); 894e2a5786af8c8278eeeb0bedccda32c7422e9a2b7David Woodhouse } 895e2a5786af8c8278eeeb0bedccda32c7422e9a2b7David Woodhouse 896fce6db565f747ca9ad560f7d8bff6a45522d905cMarcel Holtmann /* Driver UUID found */ 89758d8ea3c3a8ea69e652d8a39649a19426f31933bLuiz Augusto von Dentz l = g_slist_find_custom(req->uuids, uuid_str, 89858d8ea3c3a8ea69e652d8a39649a19426f31933bLuiz Augusto von Dentz (GCompareFunc) strcasecmp); 899e62d9fec6ad663d335a8f915568e5f35cd0633b1Luiz Augusto von Dentz if (l) { 900e62d9fec6ad663d335a8f915568e5f35cd0633b1Luiz Augusto von Dentz char *uuid = l->data; 901e62d9fec6ad663d335a8f915568e5f35cd0633b1Luiz Augusto von Dentz 902e62d9fec6ad663d335a8f915568e5f35cd0633b1Luiz Augusto von Dentz req->uuids = g_slist_remove(req->uuids, uuid); 903e62d9fec6ad663d335a8f915568e5f35cd0633b1Luiz Augusto von Dentz g_free(uuid); 904e62d9fec6ad663d335a8f915568e5f35cd0633b1Luiz Augusto von Dentz } 90558d8ea3c3a8ea69e652d8a39649a19426f31933bLuiz Augusto von Dentz 90637a7d2aba17bcb47a3e9bfba78ad23a8a3cbe420Johan Hedberg /* Check for duplicates */ 907981f4416220e01a3eab92aa3c8d03c16dcad450dJohan Hedberg if (sdp_list_find(req->records, rec, rec_cmp)) { 908981f4416220e01a3eab92aa3c8d03c16dcad450dJohan Hedberg g_free(uuid_str); 909aaf0f75d2a18a86bca3c418ddd63e936627c4446Johan Hedberg sdp_list_free(svcclass, free); 91037a7d2aba17bcb47a3e9bfba78ad23a8a3cbe420Johan Hedberg continue; 911981f4416220e01a3eab92aa3c8d03c16dcad450dJohan Hedberg } 91237a7d2aba17bcb47a3e9bfba78ad23a8a3cbe420Johan Hedberg 913cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode store_record(srcaddr, dstaddr, rec); 91437a7d2aba17bcb47a3e9bfba78ad23a8a3cbe420Johan Hedberg 915681e50c618d246483728bca6628a18c1c44c5b36Luiz Augusto von Dentz /* Copy record */ 916681e50c618d246483728bca6628a18c1c44c5b36Luiz Augusto von Dentz if (sdp_gen_record_pdu(rec, &pdu) == 0) { 917681e50c618d246483728bca6628a18c1c44c5b36Luiz Augusto von Dentz sdp_record_t *record; 918681e50c618d246483728bca6628a18c1c44c5b36Luiz Augusto von Dentz int scanned; 919681e50c618d246483728bca6628a18c1c44c5b36Luiz Augusto von Dentz 920681e50c618d246483728bca6628a18c1c44c5b36Luiz Augusto von Dentz record = sdp_extract_pdu(pdu.data, pdu.data_size, 921681e50c618d246483728bca6628a18c1c44c5b36Luiz Augusto von Dentz &scanned); 9221d40bababe8114b88ec654b7764ff20c22a258c1Johan Hedberg free(pdu.data); 923681e50c618d246483728bca6628a18c1c44c5b36Luiz Augusto von Dentz req->records = sdp_list_append(req->records, record); 924681e50c618d246483728bca6628a18c1c44c5b36Luiz Augusto von Dentz } 925681e50c618d246483728bca6628a18c1c44c5b36Luiz Augusto von Dentz 92636dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz l = g_slist_find_custom(device->uuids, uuid_str, 927c4c130d3922dedc992e00fbf94bde64a180306c2Marcel Holtmann (GCompareFunc) strcmp); 92836dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz if (!l) 92936dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz req->uuids_added = g_slist_append(req->uuids_added, 930c4c130d3922dedc992e00fbf94bde64a180306c2Marcel Holtmann uuid_str); 93136dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz else { 93236dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz req->uuids_removed = g_slist_remove(req->uuids_removed, 933c4c130d3922dedc992e00fbf94bde64a180306c2Marcel Holtmann l->data); 93436dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz g_free(uuid_str); 9353d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz } 9363d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz 93736dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz sdp_list_free(svcclass, free); 9383d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz } 93936dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz} 94036dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz 941555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsodestatic void store(struct btd_device *device) 94236dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz{ 94318614bd2b008cb9f3879990883c569c37b72f195Alok Barsode struct btd_adapter *adapter = device->adapter; 944cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode bdaddr_t src; 94536dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz char *str; 9463d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz 9472a8fb41c4c57b24a22f3adaab472b416faae122eAlok Barsode adapter_get_address(adapter, &src); 9483d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz 94936dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz if (!device->uuids) { 950cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode write_device_profiles(&src, &device->bdaddr, ""); 95136dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz return; 95236dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz } 95336dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz 95436dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz str = bt_list2string(device->uuids); 955cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode write_device_profiles(&src, &device->bdaddr, str); 95636dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz g_free(str); 95736dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz} 95836dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz 959a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentzstatic void browse_req_free(struct browse_req *req) 960a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz{ 961a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz struct btd_device *device = req->device; 962a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz 963a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz device->discov_active = 0; 964a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz 965a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz if (device->discov_requestor) { 966a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz g_dbus_remove_watch(req->conn, device->discov_listener); 967a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz device->discov_listener = 0; 968a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz g_free(device->discov_requestor); 969a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz device->discov_requestor = NULL; 970a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz } 971a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz 972a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz if (req->msg) 973a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz dbus_message_unref(req->msg); 974a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz if (req->conn) 975a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz dbus_connection_unref(req->conn); 976a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz g_slist_free(req->uuids_added); 977a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz g_slist_free(req->uuids_removed); 978a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz if (req->records) 979a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz sdp_list_free(req->records, (sdp_free_func_t) sdp_record_free); 980a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz g_free(req); 981a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz} 982a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz 983da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentzstatic void search_cb(sdp_list_t *recs, int err, gpointer user_data) 98436dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz{ 98536dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz struct browse_req *req = user_data; 986555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsode struct btd_device *device = req->device; 98736dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz DBusMessage *reply; 9882a8fb41c4c57b24a22f3adaab472b416faae122eAlok Barsode 989681e50c618d246483728bca6628a18c1c44c5b36Luiz Augusto von Dentz if (err < 0) { 990681e50c618d246483728bca6628a18c1c44c5b36Luiz Augusto von Dentz error("%s: error updating services: %s (%d)", 991681e50c618d246483728bca6628a18c1c44c5b36Luiz Augusto von Dentz device->path, strerror(-err), -err); 99236dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz goto proceed; 993681e50c618d246483728bca6628a18c1c44c5b36Luiz Augusto von Dentz } 99436dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz 99536dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz update_services(req, recs); 99636dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz 997681e50c618d246483728bca6628a18c1c44c5b36Luiz Augusto von Dentz if (!req->uuids_added && !req->uuids_removed) { 998e62d9fec6ad663d335a8f915568e5f35cd0633b1Luiz Augusto von Dentz debug("%s: No service update", device->path); 99936dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz goto proceed; 1000681e50c618d246483728bca6628a18c1c44c5b36Luiz Augusto von Dentz } 10012efdbe3a944fb2c8c6e0f581b899140b4ef84bcbLuiz Augusto von Dentz 100236dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz /* Probe matching drivers for services added */ 100336dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz if (req->uuids_added) 1004681e50c618d246483728bca6628a18c1c44c5b36Luiz Augusto von Dentz device_probe_drivers(device, req->uuids_added, req->records); 10052efdbe3a944fb2c8c6e0f581b899140b4ef84bcbLuiz Augusto von Dentz 100636dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz /* Remove drivers for services removed */ 100736dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz if (req->uuids_removed) 1008681e50c618d246483728bca6628a18c1c44c5b36Luiz Augusto von Dentz device_remove_drivers(device, req->uuids_removed, req->records); 10092efdbe3a944fb2c8c6e0f581b899140b4ef84bcbLuiz Augusto von Dentz 101036dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz /* Propagate services changes */ 101136dedff329b5ced8979a2161075e6a9d38c58785Luiz Augusto von Dentz services_changed(req); 1012f4eb9e2dea643f41e261bb9e2bff33fc03bd9eccMarcel Holtmann 10137b67507336f98dda5523902806dd2e33684fab6bLuiz Augusto von Dentzproceed: 1014681e50c618d246483728bca6628a18c1c44c5b36Luiz Augusto von Dentz /* Store the device's profiles in the filesystem */ 1015681e50c618d246483728bca6628a18c1c44c5b36Luiz Augusto von Dentz store(device); 1016681e50c618d246483728bca6628a18c1c44c5b36Luiz Augusto von Dentz 10172ba670eae0d7d0d57160b7e5bd387079f86d933cJohan Hedberg if (req->msg) { 10182ba670eae0d7d0d57160b7e5bd387079f86d933cJohan Hedberg if (dbus_message_is_method_call(req->msg, DEVICE_INTERFACE, 10192ba670eae0d7d0d57160b7e5bd387079f86d933cJohan Hedberg "DiscoverServices")) { 10202ba670eae0d7d0d57160b7e5bd387079f86d933cJohan Hedberg discover_device_reply(req, req->records); 10212ba670eae0d7d0d57160b7e5bd387079f86d933cJohan Hedberg goto cleanup; 10222ba670eae0d7d0d57160b7e5bd387079f86d933cJohan Hedberg } 1023a2529a9b417959a52f5d501cba4bcaf32caf6964Marcel Holtmann 10242ba670eae0d7d0d57160b7e5bd387079f86d933cJohan Hedberg g_dbus_emit_signal(req->conn, dbus_message_get_path(req->msg), 10258d8f45c98ddabe1ffb5b2b4f93fa3983027ba740Luiz Augusto von Dentz ADAPTER_INTERFACE, "DeviceCreated", 10268d8f45c98ddabe1ffb5b2b4f93fa3983027ba740Luiz Augusto von Dentz DBUS_TYPE_OBJECT_PATH, &device->path, 10278d8f45c98ddabe1ffb5b2b4f93fa3983027ba740Luiz Augusto von Dentz DBUS_TYPE_INVALID); 10282ba670eae0d7d0d57160b7e5bd387079f86d933cJohan Hedberg } 10298d8f45c98ddabe1ffb5b2b4f93fa3983027ba740Luiz Augusto von Dentz 1030b5f810d74530a62bb389d40ade8581f7317bf3a9Luiz Augusto von Dentz /* Update device list */ 1031b5f810d74530a62bb389d40ade8581f7317bf3a9Luiz Augusto von Dentz adapter_update_devices(device->adapter); 1032b5f810d74530a62bb389d40ade8581f7317bf3a9Luiz Augusto von Dentz 10332ba670eae0d7d0d57160b7e5bd387079f86d933cJohan Hedberg if (!req->msg) 10342ba670eae0d7d0d57160b7e5bd387079f86d933cJohan Hedberg goto cleanup; 10352ba670eae0d7d0d57160b7e5bd387079f86d933cJohan Hedberg 10363d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz /* Reply create device request */ 10373d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz reply = dbus_message_new_method_return(req->msg); 10383d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz if (!reply) 10391e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentz goto cleanup; 10403d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz 10413d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz dbus_message_append_args(reply, DBUS_TYPE_OBJECT_PATH, &device->path, 1042a2529a9b417959a52f5d501cba4bcaf32caf6964Marcel Holtmann DBUS_TYPE_INVALID); 10433d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz 10440472470e5059e702f0e7e69ee0155dfea11baa25Marcel Holtmann dbus_connection_send(req->conn, reply, NULL); 10450472470e5059e702f0e7e69ee0155dfea11baa25Marcel Holtmann dbus_message_unref(reply); 10463d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz 10471e8fbfbfa6fbcf88a668f77e5601bbc505eb483fLuiz Augusto von Dentzcleanup: 1048a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz browse_req_free(req); 1049da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz} 1050da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz 1051da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentzstatic void browse_cb(sdp_list_t *recs, int err, gpointer user_data) 1052da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz{ 1053da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz struct browse_req *req = user_data; 1054da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz struct btd_device *device = req->device; 1055da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz struct btd_adapter *adapter = device->adapter; 1056cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode bdaddr_t src; 1057da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz uuid_t uuid; 1058da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz 10597d3301934f1b30d90646c97f40464ed198be91d3David Woodhouse /* If we have a valid response and req->search_uuid == 1, then 10607d3301934f1b30d90646c97f40464ed198be91d3David Woodhouse public browsing was successful -- we don't need any more */ 10617d3301934f1b30d90646c97f40464ed198be91d3David Woodhouse if (err < 0 || (req->search_uuid == 1 && recs)) 1062da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz goto done; 1063da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz 1064da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz update_services(req, recs); 1065da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz 1066da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz adapter_get_address(adapter, &src); 1067da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz 1068da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz /* Search for mandatory uuids */ 10697d3301934f1b30d90646c97f40464ed198be91d3David Woodhouse if (uuid_list[req->search_uuid]) { 10707d3301934f1b30d90646c97f40464ed198be91d3David Woodhouse sdp_uuid16_create(&uuid, uuid_list[req->search_uuid++]); 1071c4c130d3922dedc992e00fbf94bde64a180306c2Marcel Holtmann bt_search_service(&src, &device->bdaddr, &uuid, 1072c4c130d3922dedc992e00fbf94bde64a180306c2Marcel Holtmann browse_cb, user_data, NULL); 1073da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz return; 1074da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz } 1075da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz 107658d8ea3c3a8ea69e652d8a39649a19426f31933bLuiz Augusto von Dentz /* Search for drivers uuids */ 107758d8ea3c3a8ea69e652d8a39649a19426f31933bLuiz Augusto von Dentz if (req->uuids) { 1078e62d9fec6ad663d335a8f915568e5f35cd0633b1Luiz Augusto von Dentz char *uuid_str = req->uuids->data; 1079e62d9fec6ad663d335a8f915568e5f35cd0633b1Luiz Augusto von Dentz 1080e62d9fec6ad663d335a8f915568e5f35cd0633b1Luiz Augusto von Dentz bt_string2uuid(&uuid, uuid_str); 1081e62d9fec6ad663d335a8f915568e5f35cd0633b1Luiz Augusto von Dentz req->uuids = g_slist_remove(req->uuids, uuid_str); 1082e62d9fec6ad663d335a8f915568e5f35cd0633b1Luiz Augusto von Dentz g_free(uuid_str); 1083c4c130d3922dedc992e00fbf94bde64a180306c2Marcel Holtmann bt_search_service(&src, &device->bdaddr, &uuid, 1084c4c130d3922dedc992e00fbf94bde64a180306c2Marcel Holtmann browse_cb, user_data, NULL); 108558d8ea3c3a8ea69e652d8a39649a19426f31933bLuiz Augusto von Dentz return; 108678eadf19bbee1f52b738d39133296186b3e944feLuiz Augusto von Dentz } 108778eadf19bbee1f52b738d39133296186b3e944feLuiz Augusto von Dentz 108878eadf19bbee1f52b738d39133296186b3e944feLuiz Augusto von Dentz /* Search for l2cap uuid */ 108978eadf19bbee1f52b738d39133296186b3e944feLuiz Augusto von Dentz if (!req->records) { 109078eadf19bbee1f52b738d39133296186b3e944feLuiz Augusto von Dentz sdp_uuid16_create(&uuid, L2CAP_UUID); 1091c4c130d3922dedc992e00fbf94bde64a180306c2Marcel Holtmann bt_search_service(&src, &device->bdaddr, &uuid, 1092c4c130d3922dedc992e00fbf94bde64a180306c2Marcel Holtmann search_cb, user_data, NULL); 109378eadf19bbee1f52b738d39133296186b3e944feLuiz Augusto von Dentz return; 109458d8ea3c3a8ea69e652d8a39649a19426f31933bLuiz Augusto von Dentz } 109558d8ea3c3a8ea69e652d8a39649a19426f31933bLuiz Augusto von Dentz 1096da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentzdone: 1097da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz search_cb(recs, err, user_data); 1098da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz} 1099da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz 1100da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentzstatic void init_browse(struct browse_req *req) 1101da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz{ 1102da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz GSList *l; 1103da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz 110458d8ea3c3a8ea69e652d8a39649a19426f31933bLuiz Augusto von Dentz for (l = device_drivers; l; l = l->next) { 110558d8ea3c3a8ea69e652d8a39649a19426f31933bLuiz Augusto von Dentz struct btd_device_driver *driver = l->data; 110658d8ea3c3a8ea69e652d8a39649a19426f31933bLuiz Augusto von Dentz int i; 110758d8ea3c3a8ea69e652d8a39649a19426f31933bLuiz Augusto von Dentz 110858d8ea3c3a8ea69e652d8a39649a19426f31933bLuiz Augusto von Dentz for (i = 0; driver->uuids[i]; i++) { 1109e62d9fec6ad663d335a8f915568e5f35cd0633b1Luiz Augusto von Dentz char *uuid; 11100144612a3d800c5d657cf141634f6b6cd47b4128David Woodhouse int j; 11110144612a3d800c5d657cf141634f6b6cd47b4128David Woodhouse 11120144612a3d800c5d657cf141634f6b6cd47b4128David Woodhouse /* Eliminate duplicates of UUIDs in uuid_list[]... */ 11130144612a3d800c5d657cf141634f6b6cd47b4128David Woodhouse if (strlen(driver->uuids[i]) == 36 && 11140144612a3d800c5d657cf141634f6b6cd47b4128David Woodhouse !strncmp(driver->uuids[i], "0000", 4) && 11150144612a3d800c5d657cf141634f6b6cd47b4128David Woodhouse !strcasecmp(driver->uuids[i] + 8, 11160144612a3d800c5d657cf141634f6b6cd47b4128David Woodhouse "-0000-1000-8000-00805F9B34FB")) { 11170144612a3d800c5d657cf141634f6b6cd47b4128David Woodhouse uint16_t uuid16 = strtol(driver->uuids[i], 11180144612a3d800c5d657cf141634f6b6cd47b4128David Woodhouse NULL, 16); 11190144612a3d800c5d657cf141634f6b6cd47b4128David Woodhouse for (j = 0; uuid_list[j]; j++) { 11200144612a3d800c5d657cf141634f6b6cd47b4128David Woodhouse if (uuid16 == uuid_list[j]) 11210144612a3d800c5d657cf141634f6b6cd47b4128David Woodhouse continue; 11220144612a3d800c5d657cf141634f6b6cd47b4128David Woodhouse } 11232ba670eae0d7d0d57160b7e5bd387079f86d933cJohan Hedberg 11240144612a3d800c5d657cf141634f6b6cd47b4128David Woodhouse } 11250144612a3d800c5d657cf141634f6b6cd47b4128David Woodhouse /* ... and of UUIDs another driver already asked for */ 112658d8ea3c3a8ea69e652d8a39649a19426f31933bLuiz Augusto von Dentz if (g_slist_find_custom(req->uuids, driver->uuids[i], 112758d8ea3c3a8ea69e652d8a39649a19426f31933bLuiz Augusto von Dentz (GCompareFunc) strcasecmp)) 11280144612a3d800c5d657cf141634f6b6cd47b4128David Woodhouse continue; 1129e62d9fec6ad663d335a8f915568e5f35cd0633b1Luiz Augusto von Dentz 1130e62d9fec6ad663d335a8f915568e5f35cd0633b1Luiz Augusto von Dentz uuid = g_strdup(driver->uuids[i]); 1131e62d9fec6ad663d335a8f915568e5f35cd0633b1Luiz Augusto von Dentz req->uuids = g_slist_append(req->uuids, uuid); 113258d8ea3c3a8ea69e652d8a39649a19426f31933bLuiz Augusto von Dentz } 113358d8ea3c3a8ea69e652d8a39649a19426f31933bLuiz Augusto von Dentz } 113458d8ea3c3a8ea69e652d8a39649a19426f31933bLuiz Augusto von Dentz 1135da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz for (l = req->device->uuids; l; l = l->next) 1136da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz req->uuids_removed = g_slist_append(req->uuids_removed, 1137da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz l->data); 11383d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz} 11393d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz 1140555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsodeint device_browse(struct btd_device *device, DBusConnection *conn, 1141040728e5019fce4eba5790939329fae0aa9104ffClaudio Takahasi DBusMessage *msg, uuid_t *search) 11423d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz{ 114318614bd2b008cb9f3879990883c569c37b72f195Alok Barsode struct btd_adapter *adapter = device->adapter; 11443d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz struct browse_req *req; 1145cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode bdaddr_t src; 1146d69e08eb0d567b61106ca37e0546402f4ae0c34eMarcel Holtmann uuid_t uuid; 1147da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz bt_callback_t cb; 1148a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz int err; 11492a8fb41c4c57b24a22f3adaab472b416faae122eAlok Barsode 11501af86fb9d1717a27b3a776fc0fb62c96045ccb9aJohan Hedberg if (device->discov_active) 11511af86fb9d1717a27b3a776fc0fb62c96045ccb9aJohan Hedberg return -EBUSY; 11521af86fb9d1717a27b3a776fc0fb62c96045ccb9aJohan Hedberg 11532a8fb41c4c57b24a22f3adaab472b416faae122eAlok Barsode adapter_get_address(adapter, &src); 11543d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz 11553d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz req = g_new0(struct browse_req, 1); 11562ba670eae0d7d0d57160b7e5bd387079f86d933cJohan Hedberg if (conn && msg) { 11572ba670eae0d7d0d57160b7e5bd387079f86d933cJohan Hedberg req->conn = dbus_connection_ref(conn); 11582ba670eae0d7d0d57160b7e5bd387079f86d933cJohan Hedberg req->msg = dbus_message_ref(msg); 11592ba670eae0d7d0d57160b7e5bd387079f86d933cJohan Hedberg } 11603d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz req->device = device; 11613d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz 1162a6f07d2bf12942854072c37c3c42d7447921beeeMarcel Holtmann if (search) { 1163040728e5019fce4eba5790939329fae0aa9104ffClaudio Takahasi memcpy(&uuid, search, sizeof(uuid_t)); 1164da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz cb = search_cb; 1165a6f07d2bf12942854072c37c3c42d7447921beeeMarcel Holtmann } else { 11667d3301934f1b30d90646c97f40464ed198be91d3David Woodhouse sdp_uuid16_create(&uuid, uuid_list[req->search_uuid++]); 1167da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz init_browse(req); 1168da8ef81cf060726782614baeea5b7e2c466b2341Luiz Augusto von Dentz cb = browse_cb; 1169a6f07d2bf12942854072c37c3c42d7447921beeeMarcel Holtmann } 1170d69e08eb0d567b61106ca37e0546402f4ae0c34eMarcel Holtmann 117195e5960735be4066d43f77d91ebe78771cd76a43Luiz Augusto von Dentz device->discov_active = 1; 1172d0c0409d8ad37a042539706ff5382899acc81395Johan Hedberg 1173d0c0409d8ad37a042539706ff5382899acc81395Johan Hedberg if (msg) { 1174d0c0409d8ad37a042539706ff5382899acc81395Johan Hedberg device->discov_requestor = g_strdup(dbus_message_get_sender(msg)); 1175d0c0409d8ad37a042539706ff5382899acc81395Johan Hedberg /* Track the request owner to cancel it 1176d0c0409d8ad37a042539706ff5382899acc81395Johan Hedberg * automatically if the owner exits */ 1177d0c0409d8ad37a042539706ff5382899acc81395Johan Hedberg device->discov_listener = g_dbus_add_disconnect_watch(conn, 117895e5960735be4066d43f77d91ebe78771cd76a43Luiz Augusto von Dentz dbus_message_get_sender(msg), 117995e5960735be4066d43f77d91ebe78771cd76a43Luiz Augusto von Dentz discover_services_req_exit, 118095e5960735be4066d43f77d91ebe78771cd76a43Luiz Augusto von Dentz device, NULL); 1181d0c0409d8ad37a042539706ff5382899acc81395Johan Hedberg } 118295e5960735be4066d43f77d91ebe78771cd76a43Luiz Augusto von Dentz 1183a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz err = bt_search_service(&src, &device->bdaddr, 1184a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz &uuid, cb, req, NULL); 1185a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz if (err < 0) 1186a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz browse_req_free(req); 1187a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz 1188a4145c63530b4c3575b7da5f117c0df352f939fcLuiz Augusto von Dentz return err; 11893d9966f38f1d6ca12c9e9e2eace5181ba04844b4Luiz Augusto von Dentz} 119024cce397c3479e95f3e525da9285234fbafd2984Marcel Holtmann 119118614bd2b008cb9f3879990883c569c37b72f195Alok Barsodestruct btd_adapter *device_get_adapter(struct btd_device *device) 1192dcf5298e8173e946e3ac2ef6150ad78d030b15d0Alok Barsode{ 1193dcf5298e8173e946e3ac2ef6150ad78d030b15d0Alok Barsode if (!device) 1194dcf5298e8173e946e3ac2ef6150ad78d030b15d0Alok Barsode return NULL; 1195dcf5298e8173e946e3ac2ef6150ad78d030b15d0Alok Barsode 1196dcf5298e8173e946e3ac2ef6150ad78d030b15d0Alok Barsode return device->adapter; 1197dcf5298e8173e946e3ac2ef6150ad78d030b15d0Alok Barsode} 1198dcf5298e8173e946e3ac2ef6150ad78d030b15d0Alok Barsode 119919ce4933f3dadf3b04a2a9bd84d66d750cc010c3Alok Barsodevoid device_get_address(struct btd_device *device, bdaddr_t *bdaddr) 1200aec749f0732638f182c4b50fb59d6c905a80d42dAlok Barsode{ 1201cbf6ef965b0db117ec9b762aad9cff995fd3b0bfAlok Barsode bacpy(bdaddr, &device->bdaddr); 1202aec749f0732638f182c4b50fb59d6c905a80d42dAlok Barsode} 1203aec749f0732638f182c4b50fb59d6c905a80d42dAlok Barsode 1204555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsodeconst gchar *device_get_path(struct btd_device *device) 120546fd7beaa5b27f74e64d77449247e5459d7a3084Alok Barsode{ 120646fd7beaa5b27f74e64d77449247e5459d7a3084Alok Barsode if (!device) 120746fd7beaa5b27f74e64d77449247e5459d7a3084Alok Barsode return NULL; 120846fd7beaa5b27f74e64d77449247e5459d7a3084Alok Barsode 120946fd7beaa5b27f74e64d77449247e5459d7a3084Alok Barsode return device->path; 121046fd7beaa5b27f74e64d77449247e5459d7a3084Alok Barsode} 121146fd7beaa5b27f74e64d77449247e5459d7a3084Alok Barsode 1212555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsodestruct agent *device_get_agent(struct btd_device *device) 1213a2335a65bb61313b3e46be861c90ca8bdb786eb8Alok Barsode{ 1214a2335a65bb61313b3e46be861c90ca8bdb786eb8Alok Barsode if (!device) 1215a2335a65bb61313b3e46be861c90ca8bdb786eb8Alok Barsode return NULL; 1216a2335a65bb61313b3e46be861c90ca8bdb786eb8Alok Barsode 1217a2335a65bb61313b3e46be861c90ca8bdb786eb8Alok Barsode return device->agent; 1218a2335a65bb61313b3e46be861c90ca8bdb786eb8Alok Barsode} 1219a2335a65bb61313b3e46be861c90ca8bdb786eb8Alok Barsode 1220555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsodevoid device_set_agent(struct btd_device *device, struct agent *agent) 1221d8b1e6017c0198bc996f9f9518037d69902b7830Alok Barsode{ 1222d8b1e6017c0198bc996f9f9518037d69902b7830Alok Barsode if (!device) 1223d8b1e6017c0198bc996f9f9518037d69902b7830Alok Barsode return; 1224d8b1e6017c0198bc996f9f9518037d69902b7830Alok Barsode 1225d8b1e6017c0198bc996f9f9518037d69902b7830Alok Barsode device->agent = agent; 1226d8b1e6017c0198bc996f9f9518037d69902b7830Alok Barsode} 1227d8b1e6017c0198bc996f9f9518037d69902b7830Alok Barsode 1228555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsodegboolean device_is_busy(struct btd_device *device) 12299f94306bcd017a6acb152685c940ed6d027a98c7Alok Barsode{ 12309f94306bcd017a6acb152685c940ed6d027a98c7Alok Barsode return device->discov_active ? TRUE : FALSE; 12319f94306bcd017a6acb152685c940ed6d027a98c7Alok Barsode} 12329f94306bcd017a6acb152685c940ed6d027a98c7Alok Barsode 1233555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsodegboolean device_is_temporary(struct btd_device *device) 1234f169545f05c25960c094c12f11a4ee452fb96ba8Alok Barsode{ 1235f169545f05c25960c094c12f11a4ee452fb96ba8Alok Barsode return device->temporary; 1236f169545f05c25960c094c12f11a4ee452fb96ba8Alok Barsode} 1237f169545f05c25960c094c12f11a4ee452fb96ba8Alok Barsode 1238555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsodevoid device_set_temporary(struct btd_device *device, gboolean temporary) 1239595bd38a9fe105ef20d1b0527e04c7d28532d22dAlok Barsode{ 1240595bd38a9fe105ef20d1b0527e04c7d28532d22dAlok Barsode if (!device) 1241595bd38a9fe105ef20d1b0527e04c7d28532d22dAlok Barsode return; 1242595bd38a9fe105ef20d1b0527e04c7d28532d22dAlok Barsode 1243595bd38a9fe105ef20d1b0527e04c7d28532d22dAlok Barsode device->temporary = temporary; 1244595bd38a9fe105ef20d1b0527e04c7d28532d22dAlok Barsode} 1245595bd38a9fe105ef20d1b0527e04c7d28532d22dAlok Barsode 1246555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsodevoid device_set_cap(struct btd_device *device, uint8_t cap) 1247491190e5dde601e4876f24a922f1ba16ae4d2e6dAlok Barsode{ 1248491190e5dde601e4876f24a922f1ba16ae4d2e6dAlok Barsode if (!device) 1249491190e5dde601e4876f24a922f1ba16ae4d2e6dAlok Barsode return; 1250491190e5dde601e4876f24a922f1ba16ae4d2e6dAlok Barsode 1251491190e5dde601e4876f24a922f1ba16ae4d2e6dAlok Barsode device->cap = cap; 1252491190e5dde601e4876f24a922f1ba16ae4d2e6dAlok Barsode} 1253491190e5dde601e4876f24a922f1ba16ae4d2e6dAlok Barsode 1254555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsodevoid device_set_auth(struct btd_device *device, uint8_t auth) 125529227ad09e8996699e1b1d7e1c90d45fc80cab65Alok Barsode{ 125629227ad09e8996699e1b1d7e1c90d45fc80cab65Alok Barsode if (!device) 125729227ad09e8996699e1b1d7e1c90d45fc80cab65Alok Barsode return; 125829227ad09e8996699e1b1d7e1c90d45fc80cab65Alok Barsode 125929227ad09e8996699e1b1d7e1c90d45fc80cab65Alok Barsode device->auth = auth; 126029227ad09e8996699e1b1d7e1c90d45fc80cab65Alok Barsode} 126129227ad09e8996699e1b1d7e1c90d45fc80cab65Alok Barsode 1262555fcc9b4bf67e923708af8de46aa91b7077f050Alok Barsodeuint8_t device_get_auth(struct btd_device *device) 12632203f153c53189ec1c30df99b717e035681196e6Alok Barsode{ 12642203f153c53189ec1c30df99b717e035681196e6Alok Barsode return device->auth; 12652203f153c53189ec1c30df99b717e035681196e6Alok Barsode} 1266c560d02ccf1dd156f068b1da8a3e7d75d2319dfdLuiz Augusto von Dentz 1267013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedbergstatic gboolean start_discovery(gpointer user_data) 1268013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg{ 1269013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg struct btd_device *device = user_data; 1270013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg 1271013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg device_browse(device, NULL, NULL, NULL); 1272013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg 1273013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg device->discov_timer = 0; 1274013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg 1275013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg return FALSE; 1276013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg} 1277013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg 1278e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberggboolean device_set_paired(DBusConnection *conn, struct btd_device *device, 127968b27e68b50b1e68d663142d2b0432c435329ea6Johan Hedberg struct bonding_request_info *bonding) 1280013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg{ 128168b27e68b50b1e68d663142d2b0432c435329ea6Johan Hedberg dbus_bool_t paired = TRUE; 128268b27e68b50b1e68d663142d2b0432c435329ea6Johan Hedberg 128368b27e68b50b1e68d663142d2b0432c435329ea6Johan Hedberg device_set_temporary(device, FALSE); 128468b27e68b50b1e68d663142d2b0432c435329ea6Johan Hedberg 128568b27e68b50b1e68d663142d2b0432c435329ea6Johan Hedberg dbus_connection_emit_property_changed(conn, device->path, 128668b27e68b50b1e68d663142d2b0432c435329ea6Johan Hedberg DEVICE_INTERFACE, "Paired", 128768b27e68b50b1e68d663142d2b0432c435329ea6Johan Hedberg DBUS_TYPE_BOOLEAN, &paired); 128868b27e68b50b1e68d663142d2b0432c435329ea6Johan Hedberg 1289013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg if (device->discov_timer) 1290e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg return FALSE; 1291013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg 129268b27e68b50b1e68d663142d2b0432c435329ea6Johan Hedberg /* If we were initiators start service discovery immediately. 129368b27e68b50b1e68d663142d2b0432c435329ea6Johan Hedberg * However if the other end was the initator wait a few seconds 129468b27e68b50b1e68d663142d2b0432c435329ea6Johan Hedberg * before SDP. This is due to potential IOP issues if the other 129568b27e68b50b1e68d663142d2b0432c435329ea6Johan Hedberg * end starts doing SDP at the same time as us */ 129668b27e68b50b1e68d663142d2b0432c435329ea6Johan Hedberg if (bonding) 129768b27e68b50b1e68d663142d2b0432c435329ea6Johan Hedberg device_browse(device, bonding->conn, 129868b27e68b50b1e68d663142d2b0432c435329ea6Johan Hedberg bonding->msg, NULL); 129968b27e68b50b1e68d663142d2b0432c435329ea6Johan Hedberg else 130068b27e68b50b1e68d663142d2b0432c435329ea6Johan Hedberg device->discov_timer = g_timeout_add(DISCOVERY_TIMER, 130168b27e68b50b1e68d663142d2b0432c435329ea6Johan Hedberg start_discovery, 130268b27e68b50b1e68d663142d2b0432c435329ea6Johan Hedberg device); 1303e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg 1304e21ec2652c54dbc8abbf84039b43fbd3be0b5ebcJohan Hedberg return TRUE; 1305013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg} 1306013d376e47dc68ec385e9f88d6bc6c07c921ee1aJohan Hedberg 1307c560d02ccf1dd156f068b1da8a3e7d75d2319dfdLuiz Augusto von Dentzint btd_register_device_driver(struct btd_device_driver *driver) 1308c560d02ccf1dd156f068b1da8a3e7d75d2319dfdLuiz Augusto von Dentz{ 1309c560d02ccf1dd156f068b1da8a3e7d75d2319dfdLuiz Augusto von Dentz device_drivers = g_slist_append(device_drivers, driver); 1310c560d02ccf1dd156f068b1da8a3e7d75d2319dfdLuiz Augusto von Dentz 1311c560d02ccf1dd156f068b1da8a3e7d75d2319dfdLuiz Augusto von Dentz return 0; 1312c560d02ccf1dd156f068b1da8a3e7d75d2319dfdLuiz Augusto von Dentz} 1313c560d02ccf1dd156f068b1da8a3e7d75d2319dfdLuiz Augusto von Dentz 1314c560d02ccf1dd156f068b1da8a3e7d75d2319dfdLuiz Augusto von Dentzvoid btd_unregister_device_driver(struct btd_device_driver *driver) 1315c560d02ccf1dd156f068b1da8a3e7d75d2319dfdLuiz Augusto von Dentz{ 1316c560d02ccf1dd156f068b1da8a3e7d75d2319dfdLuiz Augusto von Dentz device_drivers = g_slist_remove(device_drivers, driver); 1317c560d02ccf1dd156f068b1da8a3e7d75d2319dfdLuiz Augusto von Dentz} 1318