+int _bt_get_trusted_profile_from_flag(bluetooth_trusted_profile_t profile,
+ guint trusted_profile_flag, guint *trusted)
+{
+ int trust_profile = FALSE;
+ *trusted = FALSE;
+
+ switch (profile) {
+ case TRUSTED_PROFILE_PBAP:
+ if (trusted_profile_flag & (PROFILE_SUPPORTED << 0))
+ trust_profile = trusted_profile_flag & (1 << 1);
+ else
+ return BLUETOOTH_ERROR_NOT_SUPPORT;
+ break;
+ case TRUSTED_PROFILE_MAP:
+ if (trusted_profile_flag & (PROFILE_SUPPORTED << 2))
+ trust_profile = trusted_profile_flag & (1 << 3);
+ else
+ return BLUETOOTH_ERROR_NOT_SUPPORT;
+ break;
+ case TRUSTED_PROFILE_SAP:
+ if (trusted_profile_flag & (PROFILE_SUPPORTED << 4))
+ trust_profile = trusted_profile_flag & (1 << 5);
+ else
+ return BLUETOOTH_ERROR_NOT_SUPPORT;
+ break;
+ case TRUSTED_PROFILE_HFP_HF: {
+ guint flag = (trusted_profile_flag & (PROFILE_SUPPORTED << 6)) >> 6;
+ BT_DBG("trusted_profile_flag %x", trusted_profile_flag);
+ if (flag != PROFILE_BLOCKED)
+ trust_profile = TRUE;
+ else
+ *trusted = FALSE;
+ break;
+ }
+ case TRUSTED_PROFILE_A2DP: {
+ guint flag = (trusted_profile_flag & (PROFILE_SUPPORTED << 8)) >> 8;
+ BT_DBG("trusted_profile_flag %x", trusted_profile_flag);
+ if (flag != PROFILE_BLOCKED)
+ trust_profile = TRUE;
+ else
+ *trusted = FALSE;
+ break;
+ }
+ case TRUSTED_PROFILE_ALL: /* Return Flag for All profiles*/
+ *trusted = trusted_profile_flag;
+ return BLUETOOTH_ERROR_NONE;
+ default:
+ return BLUETOOTH_ERROR_NOT_SUPPORT;
+ }
+
+ if (trust_profile)
+ *trusted = TRUE;
+
+ return BLUETOOTH_ERROR_NONE;
+}
+
+char *_bt_get_trusted_profile_uuid(bluetooth_trusted_profile_t profile)
+{
+ switch (profile) {
+ case TRUSTED_PROFILE_PBAP:
+ return g_strdup("00001130-0000-1000-8000-00805f9b34fb");
+ case TRUSTED_PROFILE_MAP:
+ return g_strdup("00001134-0000-1000-8000-00805f9b34fb");
+ case TRUSTED_PROFILE_SAP:
+ return g_strdup("0000112D-0000-1000-8000-00805f9b34fb");
+ case TRUSTED_PROFILE_HFP_HF:
+ return g_strdup("0000111e-0000-1000-8000-00805f9b34fb");
+ case TRUSTED_PROFILE_A2DP:
+ return g_strdup("0000110b-0000-1000-8000-00805f9b34fb");
+ case TRUSTED_PROFILE_ALL:
+ return NULL;
+ }
+
+ return NULL;
+}
+
+bluetooth_trusted_profile_t _bt_get_trusted_profile_enum(const char *uuid)
+{
+ if (g_strcmp0("0000112f-0000-1000-8000-00805f9b34fb", uuid) == 0)
+ return TRUSTED_PROFILE_PBAP;
+ else if (g_strcmp0("00001132-0000-1000-8000-00805f9b34fb", uuid) == 0)
+ return TRUSTED_PROFILE_MAP;
+ else if (g_strcmp0("0000112D-0000-1000-8000-00805f9b34fb", uuid) == 0)
+ return TRUSTED_PROFILE_SAP;
+
+ return 0; /* 0 - Unknown Profile */
+}
+
+int _bt_set_trust_profile(bluetooth_device_address_t *bd_addr,
+ bluetooth_trusted_profile_t profile, gboolean trust)
+{
+ int ret = BLUETOOTH_ERROR_NONE;
+ GDBusConnection *conn;
+ GDBusProxy *proxy;
+ GError *error = NULL;
+ char *device_path = NULL;
+ char *uuid = NULL;
+ char address[BT_ADDRESS_STRING_SIZE] = { 0 };
+ GVariant *reply;
+
+ BT_CHECK_PARAMETER(bd_addr, return);
+ BT_DBG("BD Address [%2.2X %2.2X %2.2X %2.2X %2.2X %2.2X] profile[%d] trust[%d]",
+ bd_addr->addr[0], bd_addr->addr[1],
+ bd_addr->addr[2], bd_addr->addr[3],
+ bd_addr->addr[4], bd_addr->addr[5],
+ profile, trust);
+
+ conn = _bt_gdbus_get_system_gconn();
+ retv_if(conn == NULL, BLUETOOTH_ERROR_INTERNAL);
+
+ _bt_convert_addr_type_to_string(address, bd_addr->addr);
+
+ device_path = _bt_get_device_object_path(address);
+ retv_if(device_path == NULL, BLUETOOTH_ERROR_INTERNAL);
+
+ proxy = g_dbus_proxy_new_sync(conn, G_DBUS_PROXY_FLAGS_NONE,
+ NULL, BT_BLUEZ_NAME, device_path,
+ BT_DEVICE_INTERFACE, NULL, NULL);
+
+ g_free(device_path);
+ retv_if(proxy == NULL, BLUETOOTH_ERROR_INTERNAL);
+
+ uuid = _bt_get_trusted_profile_uuid(profile);
+ if (uuid == NULL) {
+ g_object_unref(proxy);
+ return BLUETOOTH_ERROR_NOT_SUPPORT;
+ }
+
+ reply = g_dbus_proxy_call_sync(proxy, "SetTrustedProfile",
+ g_variant_new("(sb)", uuid, trust),
+ G_DBUS_CALL_FLAGS_NONE, -1,
+ NULL, &error);
+ g_object_unref(proxy);
+
+ if (reply == NULL) {
+ BT_ERR("Failed to Set Profile Trusted");
+ ret = BLUETOOTH_ERROR_INTERNAL;
+ if (error) {
+ BT_ERR("Error %s[%s]", error->message, address);
+ g_error_free(error);
+ }
+ goto finish;
+ }
+ g_variant_unref(reply);
+
+finish:
+ g_free(uuid);
+ return ret;
+}
+
+int _bt_get_trust_profile(bluetooth_device_address_t *bd_addr,
+ bluetooth_trusted_profile_t profile, guint *trust)
+{
+ int ret = BLUETOOTH_ERROR_NONE;
+ GDBusConnection *conn;
+ GDBusProxy *proxy;
+ GError *error = NULL;
+ char *device_path = NULL;
+ guint trusted_profile_flag;
+ char address[BT_ADDRESS_STRING_SIZE] = { 0 };
+ GVariant *reply;
+
+ BT_CHECK_PARAMETER(bd_addr, return);
+ BT_DBG("BD Address [%2.2X %2.2X %2.2X %2.2X %2.2X %2.2X] profile[%d] trust[%d]",
+ bd_addr->addr[0], bd_addr->addr[1],
+ bd_addr->addr[2], bd_addr->addr[3],
+ bd_addr->addr[4], bd_addr->addr[5],
+ profile, *trust);
+
+ conn = _bt_gdbus_get_system_gconn();
+ retv_if(conn == NULL, BLUETOOTH_ERROR_INTERNAL);
+
+ _bt_convert_addr_type_to_string(address, bd_addr->addr);
+
+ device_path = _bt_get_device_object_path(address);
+ retv_if(device_path == NULL, BLUETOOTH_ERROR_INTERNAL);
+
+ proxy = g_dbus_proxy_new_sync(conn, G_DBUS_PROXY_FLAGS_NONE,
+ NULL, BT_BLUEZ_NAME, device_path,
+ BT_PROPERTIES_INTERFACE, NULL, NULL);
+
+ g_free(device_path);
+ retv_if(proxy == NULL, BLUETOOTH_ERROR_INTERNAL);
+
+ reply = g_dbus_proxy_call_sync(proxy, "Get",
+ g_variant_new("(ss)", BT_DEVICE_INTERFACE, "TrustedProfiles"),
+ G_DBUS_CALL_FLAGS_NONE, -1,
+ NULL, &error);
+ g_object_unref(proxy);
+
+ if (reply == NULL) {
+ BT_ERR("Failed to Get Profile Trusted");
+ ret = BLUETOOTH_ERROR_INTERNAL;
+ if (error) {
+ BT_ERR("Error %s[%s]", error->message, address);
+ g_error_free(error);
+ }
+ *trust = 0;
+ } else {
+ GVariant *temp;
+ g_variant_get(reply, "(v)", &temp);
+ trusted_profile_flag = g_variant_get_uint32(temp);
+ BT_DBG("TRUST_FLAG %d", trusted_profile_flag);
+
+ ret = _bt_get_trusted_profile_from_flag(profile,
+ trusted_profile_flag, trust);
+ g_variant_unref(temp);
+ g_variant_unref(reply);
+ }
+
+ BT_DBG("TRUST %d", *trust);
+ return ret;
+}
+
+static void __bt_request_att_mtu_device_cb(GDBusProxy *proxy, GAsyncResult *res,
+ gpointer user_data)
+{
+ GError *err = NULL;
+ GVariant *out_param1;
+ request_info_t *req_info;
+ GVariant *val = NULL;
+ GVariant *param = NULL;
+ guint8 status = 0;
+ guint16 mtu = 0;
+ bluetooth_device_address_t device_addr = { {0} };
+ int result = BLUETOOTH_ERROR_NONE;
+
+ BT_DBG("+");
+ val = g_dbus_proxy_call_finish(proxy, res, &err);
+
+ req_info = _bt_get_request_info(att_mtu_req_info->req_id);
+ if (req_info == NULL) {
+ BT_ERR("req_info == NULL");
+ g_object_unref(proxy);
+ att_mtu_req_info->device_proxy = NULL;
+ goto done;
+ }
+
+ if (err != NULL) {
+ BT_ERR("Error occured in RequestAttMtu [%s]", err->message);
+
+ if (g_strrstr(err->message, "NotSupported")) {
+ BT_INFO("Connection Not Supported");
+ result = BLUETOOTH_ERROR_NOT_SUPPORT;
+ } else if (g_strrstr(err->message, "NotConnected")) {
+ BT_INFO("Not connected");
+ result = BLUETOOTH_ERROR_NOT_CONNECTED;
+ } else if (g_strrstr(err->message, "InvalidArguments")) {
+ BT_INFO("Not connected");
+ result = BLUETOOTH_ERROR_INVALID_PARAM;
+ } else {
+ BT_DBG("Default case");
+ result = BLUETOOTH_ERROR_INTERNAL;
+ }
+ }
+
+ g_object_unref(proxy);
+ att_mtu_req_info->device_proxy = NULL;
+
+ if (result != BLUETOOTH_ERROR_NONE)
+ goto dbus_return;
+
+ if (val) {
+ g_variant_get(val, "(qy)", &mtu, &status);
+ g_variant_unref(val);
+ }
+
+ BT_DBG("MTU %d, Status %d, %s", mtu, status, att_mtu_req_info->addr);
+
+ param = g_variant_new("(isqy)",
+ result,
+ att_mtu_req_info->addr,
+ mtu,
+ status);
+
+ /* Send the event to application */
+ _bt_send_event(BT_DEVICE_EVENT,
+ BLUETOOTH_EVENT_GATT_ATT_MTU_CHANGED,
+ param);
+
+dbus_return:
+ if (req_info->context == NULL)
+ goto done;
+
+ _bt_convert_addr_string_to_type(device_addr.addr,
+ (const char *)att_mtu_req_info->addr);
+
+ out_param1 = g_variant_new_from_data((const GVariantType *)"ay",
+ &device_addr, sizeof(bluetooth_device_address_t), TRUE, NULL, NULL);
+ g_dbus_method_invocation_return_value(req_info->context,
+ g_variant_new("(iv)", result, out_param1));
+
+ _bt_delete_request_list(req_info->req_id);
+done:
+ if (err)
+ g_error_free(err);
+
+ g_free(att_mtu_req_info->addr);
+ g_free(att_mtu_req_info);
+ att_mtu_req_info = NULL;
+
+ BT_DBG("-");
+}
+
+int _bt_request_att_mtu(int request_id, bluetooth_device_address_t *device_address,
+ unsigned int mtu)
+{
+ char address[BT_ADDRESS_STRING_SIZE] = { 0 };
+ gchar *device_path = NULL;
+ GDBusProxy *adapter_proxy;
+ GDBusProxy *device_proxy;
+ GDBusConnection *conn;
+ int ret = BLUETOOTH_ERROR_NONE;
+
+ BT_CHECK_PARAMETER(device_address, return);
+
+ if (att_mtu_req_info) {
+ BT_ERR("ATT MTU request in progress");
+ return BLUETOOTH_ERROR_DEVICE_BUSY;
+ }
+
+ conn = _bt_gdbus_get_system_gconn();
+ retv_if(conn == NULL, BLUETOOTH_ERROR_INTERNAL);
+
+ adapter_proxy = _bt_get_adapter_proxy();
+ retv_if(adapter_proxy == NULL, BLUETOOTH_ERROR_INTERNAL);
+
+ _bt_convert_addr_type_to_string(address, device_address->addr);
+
+ BT_DBG("Remote device address: %s", address);
+
+ device_path = _bt_get_device_object_path(address);
+
+ retv_if(device_path == NULL, BLUETOOTH_ERROR_INTERNAL);
+
+ device_proxy = g_dbus_proxy_new_sync(conn, G_DBUS_PROXY_FLAGS_NONE,
+ NULL, BT_BLUEZ_NAME,
+ device_path, BT_DEVICE_INTERFACE, NULL, NULL);
+ g_free(device_path);
+ retv_if(device_proxy == NULL, BLUETOOTH_ERROR_INTERNAL);
+
+ att_mtu_req_info = g_malloc0(sizeof(bt_funcion_data_t));
+ att_mtu_req_info->addr = (char *)g_strdup(address);
+ att_mtu_req_info->req_id = request_id;
+ att_mtu_req_info->device_proxy = device_proxy;
+
+ g_dbus_proxy_call(device_proxy, "RequestAttMtu",
+ g_variant_new("(q)", mtu),
+ G_DBUS_CALL_FLAGS_NONE,
+ BT_MAX_DBUS_TIMEOUT,
+ NULL,
+ (GAsyncReadyCallback)__bt_request_att_mtu_device_cb,
+ NULL);
+
+ return ret;
+}
+
+int _bt_get_att_mtu(bluetooth_device_address_t *device_address,
+ unsigned int *mtu)
+{
+ char address[BT_ADDRESS_STRING_SIZE] = { 0 };
+ char *object_path = NULL;
+
+ GDBusProxy *device_proxy;
+ GError *error = NULL;
+ GVariant *value;
+ GDBusConnection *conn;
+ GVariant *result = NULL;
+
+ BT_CHECK_PARAMETER(device_address, return);
+
+ conn = _bt_gdbus_get_system_gconn();
+ retv_if(conn == NULL, BLUETOOTH_ERROR_INTERNAL);
+
+ _bt_convert_addr_type_to_string(address, device_address->addr);
+
+ object_path = _bt_get_device_object_path(address);
+ retv_if(object_path == NULL, BLUETOOTH_ERROR_NOT_PAIRED);
+
+ device_proxy = g_dbus_proxy_new_sync(conn, G_DBUS_PROXY_FLAGS_NONE,
+ NULL, BT_BLUEZ_NAME, object_path,
+ BT_PROPERTIES_INTERFACE, NULL, NULL);
+ g_free(object_path);
+ retv_if(device_proxy == NULL, BLUETOOTH_ERROR_INTERNAL);
+
+ result = g_dbus_proxy_call_sync(device_proxy, "Get",
+ g_variant_new("(ss)", BT_DEVICE_INTERFACE, "AttMtu"),
+ G_DBUS_CALL_FLAGS_NONE, -1, NULL, &error);
+ if (error) {
+ ERR("DBus Error : %s", error->message);
+ g_clear_error(&error);
+ g_object_unref(device_proxy);
+ return BLUETOOTH_ERROR_INTERNAL;
+ } else {
+ g_variant_get(result, "(v)", &value);
+ *mtu = g_variant_get_uint16(value);
+ BT_DBG("ATT MTU : %d", *mtu);
+ g_variant_unref(value);
+ g_variant_unref(result);
+ }
+
+ g_object_unref(device_proxy);
+ return BLUETOOTH_ERROR_NONE;
+}
+
+int _bt_get_device_ida(bluetooth_device_address_t *device_address,
+ bluetooth_device_address_t *id_address)
+{
+ char address[BT_ADDRESS_STRING_SIZE] = { 0 };
+ gchar *device_path = NULL;
+ const gchar *idaddress = NULL;
+ GDBusProxy *device_proxy;
+ GError *error = NULL;
+ GVariant *result = NULL;
+ GDBusConnection *conn;
+ int ret = BLUETOOTH_ERROR_NONE;
+
+ BT_CHECK_PARAMETER(device_address, return);
+
+ conn = _bt_gdbus_get_system_gconn();
+ retv_if(conn == NULL, BLUETOOTH_ERROR_INTERNAL);
+
+ _bt_convert_addr_type_to_string(address, device_address->addr);
+
+ device_path = _bt_get_device_object_path(address);
+ retv_if(device_path == NULL, BLUETOOTH_ERROR_NOT_PAIRED);
+
+ device_proxy = g_dbus_proxy_new_sync(conn, G_DBUS_PROXY_FLAGS_NONE,
+ NULL, BT_BLUEZ_NAME,
+ device_path, BT_DEVICE_INTERFACE, NULL, NULL);
+ g_free(device_path);
+ if (!device_proxy) {
+ BT_ERR("Unable to get proxy");
+ return BLUETOOTH_ERROR_INTERNAL;
+ }
+
+ result = g_dbus_proxy_call_sync(device_proxy, "GetIDAddress", NULL,
+ G_DBUS_CALL_FLAGS_NONE, -1, NULL, &error);
+ if (result == NULL) {
+ BT_ERR("Failed to get device ID address");
+ if (error != NULL) {
+ BT_ERR("Error occured in Proxy call [%s]", error->message);
+ g_error_free(error);
+ }
+ g_object_unref(device_proxy);
+ return BLUETOOTH_ERROR_INTERNAL;
+ }
+
+ g_variant_get(result , "(&s)", &idaddress);
+ if (idaddress == NULL) {
+ BT_ERR("No paired device");
+ ret = BLUETOOTH_ERROR_NOT_PAIRED;
+ } else {
+ DBG_SECURE("ID Address : %s", idaddress);
+ _bt_convert_addr_string_to_type(id_address->addr, idaddress);
+ }
+
+ g_variant_unref(result);
+ g_object_unref(device_proxy);
+
+ return ret;
+}
+