From: Atul Rai Date: Mon, 4 Jul 2016 09:24:50 +0000 (+0900) Subject: [Adapt:BluezHAL]Handle remote device properties X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=fe60082afdfd6eb7943c35b00408fbfc7d46d081;p=platform%2Fcore%2Fconnectivity%2Fbluetooth-frwk.git [Adapt:BluezHAL]Handle remote device properties This patch implements HAL API get_remote_device_properties() and handles remote device properties events from stack. Change-Id: I7116e633bad5182b20d660d6c0ca10a221874cfc Signed-off-by: Atul Rai --- diff --git a/bt-oal/bluez_hal/src/bt-hal-bluetooth.c b/bt-oal/bluez_hal/src/bt-hal-bluetooth.c index ac4ca98..47f1a2f 100644 --- a/bt-oal/bluez_hal/src/bt-hal-bluetooth.c +++ b/bt-oal/bluez_hal/src/bt-hal-bluetooth.c @@ -120,7 +120,12 @@ static int set_adapter_property(const bt_property_t *property) static int get_remote_device_properties(bt_bdaddr_t *remote_addr) { - return BT_STATUS_UNSUPPORTED; + if (!remote_addr) { + ERR("Invalid param"); + return BT_STATUS_PARM_INVALID; + } + + return _bt_hal_dbus_get_remote_device_properties(remote_addr); } static int get_remote_device_property(bt_bdaddr_t *remote_addr, @@ -505,6 +510,25 @@ static void __bt_hal_handle_device_found_event(void *buf, uint16_t len) bt_hal_cbacks->device_found_cb(ev->num_props, props); } +static void __bt_hal_handle_remote_device_properties_event(void *buf, uint16_t len) +{ + struct hal_ev_remote_device_props *ev = (struct hal_ev_remote_device_props *) buf; + bt_bdaddr_t bd_addr; + bt_property_t props[ev->num_props]; + + DBG("+"); + + if (!bt_hal_cbacks->remote_device_properties_cb) + return; + + len -= sizeof(*ev); + __bt_device_props_to_hal(props, ev->props, ev->num_props, len); + memcpy(bd_addr.address, ev->bdaddr, 6); + bt_hal_cbacks->remote_device_properties_cb( + ev->status, &bd_addr, ev->num_props, props); + DBG("-"); +} + static void __bt_hal_handle_stack_messages(int message, void *buf, uint16_t len) { DBG("+"); @@ -524,6 +548,11 @@ static void __bt_hal_handle_stack_messages(int message, void *buf, uint16_t len) case HAL_EV_DEVICE_FOUND: DBG("Event: HAL_EV_DEVICE_FOUND"); __bt_hal_handle_device_found_event(buf, len); + break; + case HAL_EV_REMOTE_DEVICE_PROPS: + DBG("Event: HAL_EV_REMOTE_DEVICE_PROPS"); + __bt_hal_handle_remote_device_properties_event(buf, len); + break; default: DBG("Event Currently not handled!!"); break; diff --git a/bt-oal/bluez_hal/src/bt-hal-device-dbus-handler.c b/bt-oal/bluez_hal/src/bt-hal-device-dbus-handler.c index 2ab3f3f..bfb3639 100644 --- a/bt-oal/bluez_hal/src/bt-hal-device-dbus-handler.c +++ b/bt-oal/bluez_hal/src/bt-hal-device-dbus-handler.c @@ -46,6 +46,8 @@ #include "bt-hal-device-dbus-handler.h" #include "bt-hal-event-receiver.h" +static handle_stack_msg event_cb = NULL; + /* Forward Delcaration */ static void __bt_bond_device_cb(GDBusProxy *proxy, GAsyncResult *res, gpointer user_data); @@ -66,7 +68,8 @@ int _bt_hal_device_create_bond(const bt_bdaddr_t *bd_addr) memset(&ev, 0, sizeof(ev)); DBG("+"); - DBG("Transport [%d] Add[0x%x] [0x%x][0x%x][0x%x][0x%x][0x%x]", transport, bd_addr->address[0], bd_addr->address[1], + DBG("Transport [%d] Add[0x%x] [0x%x][0x%x][0x%x][0x%x][0x%x]", + transport, bd_addr->address[0], bd_addr->address[1], bd_addr->address[2], bd_addr->address[3], bd_addr->address[4], bd_addr->address[5]); conn = _bt_get_system_gconn(); @@ -133,7 +136,8 @@ int _bt_hal_device_create_bond(const bt_bdaddr_t *bd_addr) _bt_convert_addr_string_to_type(ev.bdaddr, address); - handle_stack_msg event_cb = _bt_hal_get_stack_message_handler(); + if (!event_cb) + event_cb = _bt_hal_get_stack_message_handler(); if (event_cb) { DBG("Sending HAL_EV_BOND_STATE_CHANGED event"); event_cb(HAL_EV_BOND_STATE_CHANGED, (void*)&ev, sizeof(ev)); @@ -285,7 +289,8 @@ static void __bt_bond_device_cb(GDBusProxy *proxy, GAsyncResult *res, _bt_convert_addr_string_to_type(ev.bdaddr, dev_address); - handle_stack_msg event_cb = _bt_hal_get_stack_message_handler(); + if (!event_cb) + event_cb = _bt_hal_get_stack_message_handler(); if (event_cb) { DBG("Sending HAL_EV_BOND_STATE_CHANGED event"); event_cb(HAL_EV_BOND_STATE_CHANGED, (void*)&ev, sizeof(ev)); @@ -321,7 +326,8 @@ static void __bt_unbond_device_cb(GDBusProxy *proxy, GAsyncResult *res, _bt_convert_device_path_to_address(device_path, dev_address); _bt_convert_addr_string_to_type(ev.bdaddr, dev_address); - handle_stack_msg event_cb = _bt_hal_get_stack_message_handler(); + if (!event_cb) + event_cb = _bt_hal_get_stack_message_handler(); if (event_cb) { DBG("Sending HAL_EV_BOND_STATE_CHANGED event"); event_cb(HAL_EV_BOND_STATE_CHANGED, (void*)&ev, sizeof(ev)); @@ -329,3 +335,230 @@ static void __bt_unbond_device_cb(GDBusProxy *proxy, GAsyncResult *res, g_free(device_path); DBG("-"); } + +static gboolean __bt_device_bonded_device_info_cb(gpointer user_data) +{ + /* Buffer and propety count management */ + uint8_t buf[BT_HAL_MAX_PROPERTY_BUF_SIZE]; + struct hal_ev_remote_device_props *ev = (void*) buf;; + size_t size = 0; + + GVariant *result = user_data; + GVariantIter *property_iter; + GVariantIter *char_value_iter; + + const gchar *address = NULL; + const gchar *name = NULL; + unsigned int cod = 0; + gint rssi = 0; + gboolean trust = FALSE; + gboolean paired = FALSE; + int connected = 0; + GByteArray *manufacturer_data = NULL; + const gchar *key; + GVariant *value; + guint8 char_value; + unsigned int data_len = 0; + + memset(buf, 0, sizeof(buf)); + size = sizeof(*ev); + ev->num_props = 0; + ev->status = BT_STATUS_SUCCESS; + + g_variant_get(result, "(a{sv})", &property_iter); + while (g_variant_iter_loop(property_iter, "{sv}", &key, &value)) { + if(!g_strcmp0(key, "Address")) { + address = g_variant_get_string(value, NULL); + DBG("Address [%s]", address); + _bt_convert_addr_string_to_type(ev->bdaddr, address); + } else if (!g_strcmp0(key, "Alias")) { + name = g_variant_get_string(value, NULL); + DBG("Alias [%s]", name); + size += __bt_insert_hal_properties(buf + size, + HAL_PROP_DEVICE_FRIENDLY_NAME, strlen(name) + 1, name); + ev->num_props++; + } else if (!g_strcmp0(key, "Class")) { + cod = g_variant_get_uint32(value); + DBG("Class [%d]", cod); + size += __bt_insert_hal_properties(buf + size, + HAL_PROP_DEVICE_CLASS, sizeof(unsigned int), &cod); + ev->num_props++; + } else if (!g_strcmp0(key, "Connected")) { + connected = g_variant_get_byte(value); + DBG("Connected [%d]", connected); + size += __bt_insert_hal_properties(buf + size, HAL_PROP_DEVICE_CONNECTED, + sizeof(unsigned int), &connected); + ev->num_props++; + } else if (!g_strcmp0(key,"Paired")) { + paired = g_variant_get_boolean(value); + DBG("Paired [%d]", paired); + size += __bt_insert_hal_properties(buf + size, + HAL_PROP_DEVICE_PAIRED, sizeof(unsigned int), &paired); + ev->num_props++; + } else if (!g_strcmp0(key, "Trusted")) { + trust = g_variant_get_boolean(value); + DBG("Trusted [%d]", trust); + size += __bt_insert_hal_properties(buf + size, + HAL_PROP_DEVICE_TRUSTED, sizeof(unsigned int), &trust); + ev->num_props++; + } else if (!g_strcmp0(key, "Name")) { + name = g_variant_get_string(value, NULL); + DBG("Name [%s]", name); + size += __bt_insert_hal_properties(buf + size, + HAL_PROP_DEVICE_NAME, strlen(name) + 1, name); + ev->num_props++; + } else if (!g_strcmp0(key, "RSSI")) { + rssi = g_variant_get_int16(value); + DBG("RSSI [%d]", rssi); + size += __bt_insert_hal_properties(buf + size, + HAL_PROP_DEVICE_RSSI, sizeof(unsigned int), &rssi); + ev->num_props++; + } else if (!g_strcmp0(key, "UUIDs")) { + char **uuid_value; + int uuid_count = 0; + gsize size1 = 0; + int i =0; + size1 = g_variant_get_size(value); + int num_props_tmp = ev->num_props; + if (size1 > 0) { + uuid_value = (char **)g_variant_get_strv(value, &size1); + for (i = 0; uuid_value[i] != NULL; i++) + uuid_count++; + /* UUID collection */ + uint8_t uuids[BT_HAL_STACK_UUID_SIZE * uuid_count]; + for (i = 0; uuid_value[i] != NULL; i++) { + char *uuid_str = NULL; + uint8_t uuid[BT_HAL_STACK_UUID_SIZE]; + memset(uuid, 0x00, BT_HAL_STACK_UUID_SIZE); + uuid_str = g_strdup(uuid_value[i]); + DBG("UUID string [%s]\n", uuid_str); + _bt_convert_uuid_string_to_type(uuid, uuid_str); + memcpy(uuids + i * BT_HAL_STACK_UUID_SIZE, uuid, BT_HAL_STACK_UUID_SIZE); + } + size += __bt_insert_hal_properties(buf + size, HAL_PROP_DEVICE_UUIDS, + (BT_HAL_STACK_UUID_SIZE * uuid_count), uuids); + ev->num_props = num_props_tmp + 1; + g_free(uuid_value); + } + } else if (!g_strcmp0(key, "ManufacturerDataLen")) { + data_len = g_variant_get_uint16(value); + DBG("ManufacturerDataLen [%d]", data_len); + } else if (!g_strcmp0(key, "ManufacturerData")) { + manufacturer_data = g_byte_array_new(); + g_variant_get(value, "ay", &char_value_iter); + while(g_variant_iter_loop(char_value_iter, "y", &char_value)) { + g_byte_array_append(manufacturer_data, &char_value, 1); + } + + if (manufacturer_data) { + if (manufacturer_data->len > 0) { + size += __bt_insert_hal_properties( + buf + size, HAL_PROP_DEVICE_BLE_ADV_DATA, + manufacturer_data->len, manufacturer_data->data); + ev->num_props++; + } + } + g_byte_array_free(manufacturer_data, FALSE); + } else { + ERR("Unhandled Property:[%s]", key); + } + } + + DBG("trust: %d, paired: %d", trust, paired); + if (!event_cb) + event_cb = _bt_hal_get_stack_message_handler(); + if (!event_cb) { + ERR("event_cb is NULL"); + goto done; + } + + if ((paired == FALSE) && (trust == FALSE)) { + ev->status = BT_STATUS_FAIL; + ev->num_props = 0; + size = sizeof(*ev); + DBG("Send Remote Device properties event to HAL," + " Num Prop [%d] total size [%d]",ev->num_props, size); + event_cb(HAL_EV_REMOTE_DEVICE_PROPS, (void*) buf, size); + } else { + if (size > 2) { + DBG("Send Remote Device properties event to HAL," + " Num Prop [%d] total size [%d]",ev->num_props, size); + event_cb(HAL_EV_REMOTE_DEVICE_PROPS, (void*) buf, size); + } + } + +done: + g_variant_unref(result); + return FALSE; +} + +int _bt_hal_dbus_get_remote_device_properties(bt_bdaddr_t *remote_addr) +{ + char *device_path = NULL; + char address[BT_HAL_ADDRESS_STRING_SIZE] = { 0 }; + GError *error = NULL; + GDBusProxy *device_proxy; + GDBusConnection *conn; + GVariant *result; + + if(!remote_addr) { + ERR("Invalid device address ptr received"); + return BT_STATUS_PARM_INVALID; + } + + _bt_convert_addr_type_to_string(address, remote_addr->address); + device_path = _bt_get_device_object_path(address); + if (!device_path) { + ERR("Device not paired"); + return BT_STATUS_FAIL; + } + + conn = _bt_get_system_gconn(); + if (!conn) { + ERR("_bt_get_system_gconn failed"); + return BT_STATUS_FAIL; + } + + device_proxy = g_dbus_proxy_new_sync(conn, G_DBUS_PROXY_FLAGS_NONE, + NULL, + BT_HAL_BLUEZ_NAME, + device_path, + BT_HAL_PROPERTIES_INTERFACE, + NULL, NULL); + + if (!device_proxy) { + ERR("Error creating device_proxy"); + g_free(device_path); + return BT_STATUS_FAIL; + } + + result = g_dbus_proxy_call_sync(device_proxy, + "GetAll", + g_variant_new("(s)", BT_HAL_DEVICE_INTERFACE), + G_DBUS_CALL_FLAGS_NONE, + -1, + NULL, + &error); + + if (!result) { + ERR("Error occured in Proxy call"); + if (error != NULL) { + ERR("Error occured in Proxy call (Error: %s)", error->message); + g_clear_error(&error); + } + g_object_unref(device_proxy); + g_free(device_path); + return BT_STATUS_FAIL; + } + + g_object_unref(device_proxy); + g_free(device_path); + /* + * As we need to provide async callback to user from HAL, simply schedule a + * callback method which will carry actual result + */ + g_idle_add(__bt_device_bonded_device_info_cb, (gpointer)result); + + DBG("-"); + return BT_STATUS_SUCCESS; +} diff --git a/bt-oal/bluez_hal/src/bt-hal-device-dbus-handler.h b/bt-oal/bluez_hal/src/bt-hal-device-dbus-handler.h index a619a83..a7841fb 100644 --- a/bt-oal/bluez_hal/src/bt-hal-device-dbus-handler.h +++ b/bt-oal/bluez_hal/src/bt-hal-device-dbus-handler.h @@ -40,6 +40,8 @@ int _bt_hal_device_create_bond(const bt_bdaddr_t *bd_addr); int _bt_hal_device_remove_bond(const bt_bdaddr_t *bd_addr); +int _bt_hal_dbus_get_remote_device_properties(bt_bdaddr_t *remote_addr); + #ifdef __cplusplus } #endif /* __cplusplus */