/* Discoverable Modes */
#define BTA_DM_NON_DISC BTM_NON_DISCOVERABLE /* Device is not discoverable. */
#define BTA_DM_GENERAL_DISC BTM_GENERAL_DISCOVERABLE /* General discoverable. */
-#define BTA_DM_LIMITED_DISC BTM_LIMITED_DISCOVERABLE /* Limited discoverable. */
#if (BLE_INCLUDED == TRUE)
#define BTA_DM_BLE_NON_DISCOVERABLE BTM_BLE_NON_DISCOVERABLE /* Device is not LE discoverable */
#define BTA_DM_BLE_GENERAL_DISCOVERABLE BTM_BLE_GENERAL_DISCOVERABLE /* Device is LE General discoverable */
} tBTA_DM_EIR_CONF;
#if (BLE_INCLUDED == TRUE)
-/* ADV data flag bit definition used for BTM_BLE_AD_TYPE_FLAG */
-#define BTA_BLE_LIMIT_DISC_FLAG BTM_BLE_LIMIT_DISC_FLAG
-#define BTA_BLE_GEN_DISC_FLAG BTM_BLE_GEN_DISC_FLAG
-#define BTA_BLE_BREDR_NOT_SPT BTM_BLE_BREDR_NOT_SPT
-#define BTA_BLE_DMT_CONTROLLER_SPT BTM_BLE_DMT_CONTROLLER_SPT
-#define BTA_BLE_DMT_HOST_SPT BTM_BLE_DMT_HOST_SPT
-#define BTA_BLE_NON_LIMIT_DISC_FLAG BTM_BLE_NON_LIMIT_DISC_FLAG
-#define BTA_BLE_ADV_FLAG_MASK BTM_BLE_ADV_FLAG_MASK
-#define BTA_BLE_LIMIT_DISC_MASK BTM_BLE_LIMIT_DISC_MASK
-
-/* ADV data bit mask */
-#define BTA_BLE_AD_BIT_DEV_NAME BTM_BLE_AD_BIT_DEV_NAME
-#define BTA_BLE_AD_BIT_FLAGS BTM_BLE_AD_BIT_FLAGS
-#define BTA_BLE_AD_BIT_MANU BTM_BLE_AD_BIT_MANU
-#define BTA_BLE_AD_BIT_TX_PWR BTM_BLE_AD_BIT_TX_PWR
-#define BTA_BLE_AD_BIT_INT_RANGE BTM_BLE_AD_BIT_INT_RANGE
-#define BTA_BLE_AD_BIT_SERVICE BTM_BLE_AD_BIT_SERVICE
-#define BTA_BLE_AD_BIT_APPEARANCE BTM_BLE_AD_BIT_APPEARANCE
-#define BTA_BLE_AD_BIT_PROPRIETARY BTM_BLE_AD_BIT_PROPRIETARY
-#define BTA_DM_BLE_AD_BIT_SERVICE_SOL BTM_BLE_AD_BIT_SERVICE_SOL
-#define BTA_DM_BLE_AD_BIT_SERVICE_DATA BTM_BLE_AD_BIT_SERVICE_DATA
-#define BTA_DM_BLE_AD_BIT_SIGN_DATA BTM_BLE_AD_BIT_SIGN_DATA
-#define BTA_DM_BLE_AD_BIT_SERVICE_128SOL BTM_BLE_AD_BIT_SERVICE_128SOL
-#define BTA_DM_BLE_AD_BIT_PUBLIC_ADDR BTM_BLE_AD_BIT_PUBLIC_ADDR
-#define BTA_DM_BLE_AD_BIT_RANDOM_ADDR BTM_BLE_AD_BIT_RANDOM_ADDR
-#define BTA_DM_BLE_AD_BIT_SERVICE_128 BTM_BLE_AD_BIT_SERVICE_128 /*128-bit Service UUIDs*/
-
-typedef tBTM_BLE_AD_MASK tBTA_BLE_AD_MASK;
-typedef tBTM_BLE_INT_RANGE tBTA_BLE_INT_RANGE;
-typedef tBTM_BLE_SERVICE tBTA_BLE_SERVICE;
-typedef tBTM_BLE_PROP_ELEM tBTA_BLE_PROP_ELEM;
-typedef tBTM_BLE_PROPRIETARY tBTA_BLE_PROPRIETARY;
-typedef tBTM_BLE_MANU tBTA_BLE_MANU;
-typedef tBTM_BLE_SERVICE_DATA tBTA_BLE_SERVICE_DATA;
-typedef tBTM_BLE_128SERVICE tBTA_BLE_128SERVICE;
-typedef tBTM_BLE_32SERVICE tBTA_BLE_32SERVICE;
-
-typedef struct
-{
- tBTA_BLE_INT_RANGE int_range; /* slave prefered conn interval range */
- tBTA_BLE_MANU manu; /* manufacturer data */
- tBTA_BLE_SERVICE services; /* 16 bits services */
- tBTA_BLE_128SERVICE services_128b; /* 128 bits service */
- tBTA_BLE_32SERVICE service_32b; /* 32 bits Service UUID */
- tBTA_BLE_SERVICE sol_services; /* 16 bits services Solicitation UUIDs */
- tBTA_BLE_32SERVICE sol_service_32b; /* List of 32 bit Service Solicitation UUIDs */
- tBTA_BLE_128SERVICE sol_service_128b;/* List of 128 bit Service Solicitation UUIDs */
- tBTA_BLE_PROPRIETARY proprietary; /* proprietary data */
- tBTA_BLE_SERVICE_DATA service_data; /* service data */
- uint16_t appearance; /* appearance data */
- uint8_t flag;
- uint8_t tx_power;
-}tBTA_BLE_ADV_DATA;
-
-typedef void (tBTA_SET_ADV_DATA_CMPL_CBACK) (tBTA_STATUS status);
/* advertising filter policy */
typedef tBTM_BLE_AFP tBTA_BLE_AFP;
-/* These are the fields returned in each device adv packet. It
-** is returned in the results callback if registered.
-*/
-typedef struct
-{
- uint8_t conn_mode;
- tBTA_BLE_AD_MASK ad_mask; /* mask of the valid adv data field */
- uint8_t flag;
- uint8_t tx_power_level;
- uint8_t remote_name_len;
- uint8_t *p_remote_name;
- tBTA_BLE_SERVICE service;
-} tBTA_BLE_INQ_DATA;
-
enum
{
BTA_BLE_BATCH_SCAN_MODE_PASS = 1,
src/btif_dm.cc \
src/btif_gatt.cc \
src/btif_gatt_client.cc \
- src/btif_gatt_multi_adv_util.cc \
src/btif_gatt_server.cc \
src/btif_gatt_test.cc \
src/btif_gatt_util.cc \
"src/btif_ble_advertiser.cc",
"src/btif_gatt.cc",
"src/btif_gatt_client.cc",
- "src/btif_gatt_multi_adv_util.cc",
"src/btif_gatt_server.cc",
"src/btif_gatt_test.cc",
"src/btif_gatt_util.cc",
+++ /dev/null
-/******************************************************************************
- *
- * Copyright (C) 2014 Broadcom Corporation
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-#pragma once
-
-#include <hardware/bluetooth.h>
-#include <vector>
-
-#include "ble_advertiser.h"
-
-#define CLNT_IF_IDX 0
-#define INST_ID_IDX 1
-#define INST_ID_IDX_MAX (INST_ID_IDX + 1)
-#define INVALID_ADV_INST (-1)
-#define STD_ADV_INSTID 0
-
-/* Default ADV flags for general and limited discoverability */
-#define ADV_FLAGS_LIMITED BTA_DM_LIMITED_DISC
-#define ADV_FLAGS_GENERAL BTA_DM_GENERAL_DISC
-
-typedef struct
-{
- int advertiser_id;
- bool set_scan_rsp;
- bool include_name;
- bool include_txpower;
- int min_interval;
- int max_interval;
- int appearance;
- uint16_t manufacturer_len;
- uint8_t p_manufacturer_data[MAX_SIZE_MANUFACTURER_DATA];
- uint16_t service_data_len;
- uint8_t p_service_data[MAX_SIZE_SERVICE_DATA];
- uint16_t service_uuid_len;
- uint8_t p_service_uuid[MAX_SIZE_SERVICE_DATA];
-} btif_adv_data_t;
-
-
-typedef struct
-{
- uint8_t advertiser_id;
- tBTA_BLE_AD_MASK mask;
- tBTA_BLE_ADV_DATA data;
- tBTM_BLE_ADV_PARAMS param;
- alarm_t *multi_adv_timer;
- int timeout_s;
-} btgatt_multi_adv_inst_cb;
-
-typedef struct
-{
- // Includes the stored data for standard LE instance
- btgatt_multi_adv_inst_cb *inst_cb;
-
-} btgatt_multi_adv_common_data;
-
-extern btgatt_multi_adv_common_data *btif_obtain_multi_adv_data_cb();
-
-extern void btif_gattc_incr_app_count(void);
-extern void btif_gattc_decr_app_count(void);
-extern void btif_gattc_clear_clientif(int advertiser_id, bool stop_timer);
-extern void btif_gattc_cleanup_inst_cb(int inst_id, bool stop_timer);
-extern void btif_gattc_cleanup_multi_inst_cb(btgatt_multi_adv_inst_cb *p_inst_cb,
- bool stop_timer);
-extern bool btif_gattc_copy_datacb(int arrindex, const btif_adv_data_t *p_adv_data,
- bool bInstData);
-extern void btif_gattc_adv_data_packager(int advertiser_id, bool set_scan_rsp,
- bool include_name, bool include_txpower, int min_interval, int max_interval,
- int appearance, const std::vector<uint8_t> &manufacturer_data,
- const std::vector<uint8_t> &service_data, const std::vector<uint8_t> &service_uuid,
- btif_adv_data_t *p_multi_adv_inst);
-extern void btif_gattc_adv_data_cleanup(btif_adv_data_t* adv);
-void btif_multi_adv_timer_ctrl(int advertiser_id, alarm_callback_t cb);
#include <hardware/bt_gatt.h>
#include <base/bind.h>
+#include <vector>
#include "ble_advertiser.h"
#include "bta_closure_api.h"
#include "bta_gatt_api.h"
#include "btif_common.h"
#include "btif_gatt.h"
-#include "btif_gatt_multi_adv_util.h"
using base::Bind;
using base::Owned;
using std::vector;
-extern bt_status_t do_in_jni_thread(const base::Closure &task);
-extern const btgatt_callbacks_t *bt_gatt_callbacks;
+extern bt_status_t do_in_jni_thread(const base::Closure& task);
+extern const btgatt_callbacks_t* bt_gatt_callbacks;
#define CHECK_BTGATT_INIT() \
do { \
namespace {
-bt_status_t btif_multiadv_enable(int advertiser_id, bool enable, int timeout_s);
-void btif_multi_adv_stop_cb(void *data) {
- int advertiser_id = PTR_TO_INT(data);
- btif_multiadv_enable(advertiser_id, false, 0); // Does context switch
+template <typename T>
+class OwnedArrayWrapper {
+ public:
+ explicit OwnedArrayWrapper(T* o) : ptr_(o) {}
+ ~OwnedArrayWrapper() { delete[] ptr_; }
+ T* get() const { return ptr_; }
+ OwnedArrayWrapper(OwnedArrayWrapper&& other) {
+ ptr_ = other.ptr_;
+ other.ptr_ = NULL;
+ }
+
+ private:
+ mutable T* ptr_;
+};
+
+template <typename T>
+T* Unwrap(const OwnedArrayWrapper<T>& o) {
+ return o.get();
+}
+
+template <typename T>
+static inline OwnedArrayWrapper<T> OwnedArray(T* o) {
+ return OwnedArrayWrapper<T>(o);
}
-void bta_adv_set_data_cback(tBTA_STATUS call_status) {
- do_in_jni_thread(Bind(&btif_gattc_cleanup_inst_cb, STD_ADV_INSTID, false));
+/* return the actual power in dBm based on the mapping in config file */
+int ble_tx_power[BTM_BLE_ADV_TX_POWER_MAX + 1] = BTM_BLE_ADV_TX_POWER;
+char ble_map_adv_tx_power(int tx_power_index) {
+ if (0 <= tx_power_index && tx_power_index < BTM_BLE_ADV_TX_POWER_MAX)
+ return (char)ble_tx_power[tx_power_index];
+ return 0;
}
-void btif_adv_set_data_impl(btif_adv_data_t *p_adv_data) {
- const int cbindex = CLNT_IF_IDX;
- if (cbindex >= 0 && btif_gattc_copy_datacb(cbindex, p_adv_data, false)) {
- btgatt_multi_adv_common_data *p_multi_adv_data_cb =
- btif_obtain_multi_adv_data_cb();
-
- tBTM_BLE_ADV_DATA *adv_cfg = new tBTM_BLE_ADV_DATA;
- memcpy(adv_cfg, &p_multi_adv_data_cb->inst_cb[cbindex].data,
- sizeof(tBTM_BLE_ADV_DATA));
-
- if (!p_adv_data->set_scan_rsp) {
- do_in_bta_thread(
- FROM_HERE, base::Bind(&BTM_BleWriteAdvData,
- p_multi_adv_data_cb->inst_cb[cbindex].mask,
- base::Owned(adv_cfg), bta_adv_set_data_cback));
+#define MIN_ADV_LENGTH 2
+#define BLE_AD_DATA_LEN 31
+vector<uint8_t> build_adv_data(bool set_scan_rsp, bool include_name,
+ bool incl_txpower, uint16_t appearance,
+ vector<uint8_t> manufacturer_data,
+ vector<uint8_t> service_data,
+ vector<uint8_t> service_uuid) {
+ vector<uint8_t> data;
+
+ // Flags are added by lower layers of the stack, only if needed; no need to
+ // add them here.
+
+ // TODO(jpawlowski): appearance is a dead argument, never set by upper layers.
+ // Remove.
+
+ if (include_name) {
+ char* bd_name;
+ BTM_ReadLocalDeviceName(&bd_name);
+ size_t bd_name_len = strlen(bd_name);
+ uint8_t type;
+
+ // TODO(jpawlowski) put a better limit on device name!
+ if (data.size() + MIN_ADV_LENGTH + bd_name_len > BLE_AD_DATA_LEN) {
+ bd_name_len = BLE_AD_DATA_LEN - data.size() - 1;
+ type = BTM_BLE_AD_TYPE_NAME_SHORT;
} else {
- do_in_bta_thread(
- FROM_HERE, base::Bind(&BTM_BleWriteScanRsp,
- p_multi_adv_data_cb->inst_cb[cbindex].mask,
- base::Owned(adv_cfg), bta_adv_set_data_cback));
+ type = BTM_BLE_AD_TYPE_NAME_CMPL;
+ }
+
+ data.push_back(bd_name_len + 1);
+ data.push_back(type);
+ data.insert(data.end(), bd_name, bd_name + bd_name_len);
+ }
+
+ if (manufacturer_data.size()) {
+ data.push_back(manufacturer_data.size() + 1);
+ data.push_back(HCI_EIR_MANUFACTURER_SPECIFIC_TYPE);
+ data.insert(data.end(), manufacturer_data.begin(), manufacturer_data.end());
+ }
+
+ /* TX power */
+ if (incl_txpower) {
+ data.push_back(MIN_ADV_LENGTH);
+ data.push_back(HCI_EIR_TX_POWER_LEVEL_TYPE);
+ data.push_back(0); // lower layers will fill this value.
+ }
+
+ // TODO(jpawlowski): right now we can pass only one service, and it's size
+ // determine type (16/32/128bit), this must be fixed in future!
+ if (service_uuid.size()) {
+ data.push_back(service_uuid.size() + 1);
+ if (service_uuid.size() == LEN_UUID_16)
+ data.push_back(BT_EIR_COMPLETE_16BITS_UUID_TYPE);
+ else if (service_uuid.size() == LEN_UUID_32)
+ data.push_back(BT_EIR_COMPLETE_32BITS_UUID_TYPE);
+ else if (service_uuid.size() == LEN_UUID_128)
+ data.push_back(BT_EIR_COMPLETE_128BITS_UUID_TYPE);
+
+ data.insert(data.end(), service_uuid.begin(), service_uuid.end());
+ }
+
+ if (service_data.size()) {
+ data.push_back(service_data.size() + 1);
+ // TODO(jpawlowski): we can accept only 16bit uuid. Remove this restriction
+ // as we move this code up the stack
+ data.push_back(BT_EIR_SERVICE_DATA_16BITS_UUID_TYPE);
+
+ data.insert(data.end(), service_data.begin(), service_data.end());
+ }
+
+ return data;
+}
+
+void bta_adv_set_data_cback(tBTA_STATUS call_status) {}
+
+void btif_adv_set_data_impl(int advertiser_id, bool set_scan_rsp,
+ vector<uint8_t> data) {
+ uint8_t* data_ptr = nullptr;
+
+ if (data.size()) {
+ // base::Owned will free this ptr
+ data_ptr = new uint8_t[data.size()];
+ memcpy(data_ptr, data.data(), data.size());
+ }
+
+ if (!set_scan_rsp) {
+ if (data_ptr) {
+ do_in_bta_thread(FROM_HERE,
+ base::Bind(&BTM_BleWriteAdvData, OwnedArray(data_ptr),
+ data.size(), bta_adv_set_data_cback));
+ } else {
+ do_in_bta_thread(FROM_HERE,
+ base::Bind(&BTM_BleWriteAdvData, nullptr, data.size(),
+ bta_adv_set_data_cback));
}
} else {
- BTIF_TRACE_ERROR("%s: failed to get instance data cbindex: %d", __func__,
- cbindex);
+ if (data_ptr) {
+ do_in_bta_thread(FROM_HERE,
+ base::Bind(&BTM_BleWriteScanRsp, OwnedArray(data_ptr),
+ data.size(), bta_adv_set_data_cback));
+ } else {
+ do_in_bta_thread(FROM_HERE,
+ base::Bind(&BTM_BleWriteScanRsp, nullptr, data.size(),
+ bta_adv_set_data_cback));
+ }
}
}
vector<uint8_t> service_uuid) {
CHECK_BTGATT_INIT();
- btif_adv_data_t *adv_data = new btif_adv_data_t;
+ vector<uint8_t> data =
+ build_adv_data(set_scan_rsp, include_name, include_txpower, appearance,
+ manufacturer_data, service_data, service_uuid);
- btif_gattc_adv_data_packager(
- advertiser_id, set_scan_rsp, include_name, include_txpower, min_interval,
- max_interval, appearance, std::move(manufacturer_data),
- std::move(service_data), std::move(service_uuid), adv_data);
-
- return do_in_jni_thread(Bind(&btif_adv_set_data_impl, base::Owned(adv_data)));
+ return do_in_jni_thread(Bind(&btif_adv_set_data_impl, advertiser_id,
+ set_scan_rsp, std::move(data)));
}
void multi_adv_set_params_cb_impl(int advertiser_id, int status) {
HAL_CBACK(bt_gatt_callbacks, advertiser->multi_adv_set_params_cb,
advertiser_id, status);
- btif_multi_adv_timer_ctrl(
- advertiser_id, (status == BTA_GATT_OK) ? btif_multi_adv_stop_cb : NULL);
}
void multi_adv_set_params_cb(uint8_t advertiser_id, uint8_t status) {
void btif_multiadv_set_params_impl(int advertiser_id, int min_interval,
int max_interval, int adv_type, int chnl_map,
int tx_power) {
- tBTM_BLE_ADV_PARAMS param;
- param.adv_int_min = min_interval;
- param.adv_int_max = max_interval;
- param.adv_type = adv_type;
- param.channel_map = chnl_map;
- param.adv_filter_policy = 0;
- param.tx_power = tx_power;
-
- btgatt_multi_adv_common_data *p_multi_adv_data_cb =
- btif_obtain_multi_adv_data_cb();
- memcpy(&p_multi_adv_data_cb->inst_cb[advertiser_id].param, ¶m,
- sizeof(tBTM_BLE_ADV_PARAMS));
-
- tBTM_BLE_ADV_PARAMS *params = new tBTM_BLE_ADV_PARAMS;
- memcpy(params, &(p_multi_adv_data_cb->inst_cb[advertiser_id].param),
- sizeof(tBTM_BLE_ADV_PARAMS));
+ tBTM_BLE_ADV_PARAMS* params = new tBTM_BLE_ADV_PARAMS;
+ params->adv_int_min = min_interval;
+ params->adv_int_max = max_interval;
+ params->adv_type = adv_type;
+ params->channel_map = chnl_map;
+ params->adv_filter_policy = 0;
+ params->tx_power = ble_map_adv_tx_power(tx_power);
+
do_in_bta_thread(
FROM_HERE,
base::Bind(&BleAdvertisingManager::SetParameters,
}
void multi_adv_data_cb_impl(int advertiser_id, int status) {
- btif_gattc_clear_clientif(advertiser_id, false);
HAL_CBACK(bt_gatt_callbacks, advertiser->multi_adv_data_cb, advertiser_id,
status);
}
do_in_jni_thread(Bind(multi_adv_data_cb_impl, advertiser_id, status));
}
-void btif_multiadv_set_data_impl(btif_adv_data_t *p_adv_data) {
- uint8_t advertiser_id = p_adv_data->advertiser_id;
- if (!btif_gattc_copy_datacb(advertiser_id, p_adv_data, true)) {
- BTIF_TRACE_ERROR("%s: failed to copy instance data: advertiser_id:%d",
- __func__, advertiser_id);
- return;
- }
-
- btgatt_multi_adv_common_data *p_multi_adv_data_cb =
- btif_obtain_multi_adv_data_cb();
-
+void btif_multiadv_set_data_impl(int advertiser_id, bool set_scan_rsp,
+ vector<uint8_t> data) {
do_in_bta_thread(FROM_HERE,
base::Bind(&BleAdvertisingManager::SetData,
base::Unretained(BleAdvertisingManager::Get()),
- advertiser_id, p_adv_data->set_scan_rsp,
- p_multi_adv_data_cb->inst_cb[advertiser_id].mask,
- (tBTM_BLE_ADV_DATA *)&p_multi_adv_data_cb
- ->inst_cb[advertiser_id]
- .data,
+ advertiser_id, set_scan_rsp, std::move(data),
base::Bind(multi_adv_data_cb, advertiser_id)));
}
vector<uint8_t> service_uuid) {
CHECK_BTGATT_INIT();
- btif_adv_data_t *multi_adv_data_inst = new btif_adv_data_t;
+ vector<uint8_t> data =
+ build_adv_data(set_scan_rsp, include_name, incl_txpower, appearance,
+ manufacturer_data, service_data, service_uuid);
- const int min_interval = 0;
- const int max_interval = 0;
-
- btif_gattc_adv_data_packager(
- advertiser_id, set_scan_rsp, include_name, incl_txpower, min_interval,
- max_interval, appearance, std::move(manufacturer_data),
- std::move(service_data), std::move(service_uuid), multi_adv_data_inst);
-
- return do_in_jni_thread(
- Bind(&btif_multiadv_set_data_impl, base::Owned(multi_adv_data_inst)));
+ return do_in_jni_thread(Bind(&btif_multiadv_set_data_impl, advertiser_id,
+ set_scan_rsp, std::move(data)));
}
void multi_adv_enable_cb_impl(int advertiser_id, int status, bool enable) {
HAL_CBACK(bt_gatt_callbacks, advertiser->multi_adv_enable_cb, advertiser_id,
status, enable);
- if (!enable) {
- btif_multi_adv_timer_ctrl(
- advertiser_id, (status == BTA_GATT_OK) ? btif_multi_adv_stop_cb : NULL);
- }
}
-void multi_adv_enable_cb(bool enable, uint8_t advertiser_id,
- uint8_t status) {
- do_in_jni_thread(
- Bind(multi_adv_enable_cb_impl, advertiser_id, status, enable));
+void multi_adv_enable_cb(bool enable, uint8_t advertiser_id, uint8_t status) {
+ do_in_jni_thread(
+ Bind(multi_adv_enable_cb_impl, advertiser_id, status, enable));
+}
+
+void multi_adv_timeout_cb(uint8_t advertiser_id, uint8_t status) {
+ do_in_jni_thread(
+ Bind(multi_adv_enable_cb_impl, advertiser_id, status, false));
}
void btif_multiadv_enable_impl(int advertiser_id, bool enable, int timeout_s) {
BTIF_TRACE_DEBUG("%s: advertiser_id: %d, enable: %d", __func__, advertiser_id,
enable);
-
- btgatt_multi_adv_common_data *p_multi_adv_data_cb =
- btif_obtain_multi_adv_data_cb();
- if (enable) p_multi_adv_data_cb->inst_cb[advertiser_id].timeout_s = timeout_s;
-
do_in_bta_thread(
FROM_HERE,
base::Bind(&BleAdvertisingManager::Enable,
base::Unretained(BleAdvertisingManager::Get()), advertiser_id,
- enable,
- base::Bind(multi_adv_enable_cb, enable, advertiser_id)));
+ enable, base::Bind(multi_adv_enable_cb, enable, advertiser_id),
+ timeout_s, base::Bind(multi_adv_timeout_cb, advertiser_id)));
}
bt_status_t btif_multiadv_enable(int advertiser_id, bool enable,
do_in_jni_thread(Bind(multi_adv_reg_cb_impl, uuid, advertiser_id, status));
}
-bt_status_t btif_multiadv_register(bt_uuid_t *uuid) {
- btif_gattc_incr_app_count();
-
+bt_status_t btif_multiadv_register(bt_uuid_t* uuid) {
do_in_bta_thread(FROM_HERE,
base::Bind(&BleAdvertisingManager::RegisterAdvertiser,
base::Unretained(BleAdvertisingManager::Get()),
}
bt_status_t btif_multiadv_unregister(int advertiser_id) {
- btif_gattc_clear_clientif(advertiser_id, true);
- btif_gattc_decr_app_count();
-
do_in_bta_thread(FROM_HERE,
base::Bind(&BleAdvertisingManager::Unregister,
base::Unretained(BleAdvertisingManager::Get()),
+++ /dev/null
-/******************************************************************************
- *
- * Copyright (C) 2014 Broadcom Corporation
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-/*******************************************************************************
- *
- * Filename: btif_gatt_multi_adv_util.c
- *
- * Description: Multi ADV helper implementation
- *
- *******************************************************************************/
-
-#define LOG_TAG "bt_btif_gatt"
-
-
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-
-#include "btu.h"
-#include "bt_target.h"
-
-#if (BLE_INCLUDED == TRUE)
-
-#include <hardware/bluetooth.h>
-#include <hardware/bt_gatt.h>
-
-#include "bta_gatt_api.h"
-#include "btif_common.h"
-#include "btif_gatt_multi_adv_util.h"
-#include "btif_gatt_util.h"
-
-using std::vector;
-
-extern fixed_queue_t *btu_general_alarm_queue;
-
-/*******************************************************************************
-** Static variables
-********************************************************************************/
-static int user_app_count = 0;
-static btgatt_multi_adv_common_data *p_multi_adv_com_data_cb = NULL;
-
-btgatt_multi_adv_common_data *btif_obtain_multi_adv_data_cb()
-{
- int max_adv_inst = BTM_BleMaxMultiAdvInstanceCount();
- if (0 == max_adv_inst)
- max_adv_inst = 1;
-
- BTIF_TRACE_DEBUG("%s, Count:%d", __func__, max_adv_inst);
-
- if (NULL == p_multi_adv_com_data_cb)
- {
- p_multi_adv_com_data_cb = (btgatt_multi_adv_common_data*)osi_calloc(sizeof(btgatt_multi_adv_common_data));
- /* Storing both advertiser_id and inst_id details */
-
- p_multi_adv_com_data_cb->inst_cb = (btgatt_multi_adv_inst_cb*)
- osi_calloc((max_adv_inst + 1) * sizeof(btgatt_multi_adv_inst_cb));
- }
-
- return p_multi_adv_com_data_cb;
-}
-
-void btif_gattc_incr_app_count(void)
-{
- // TODO: Instead of using a fragile reference counter here, one could
- // simply track the advertiser_id instances that are in the map.
- ++user_app_count;
-}
-
-void btif_gattc_decr_app_count(void)
-{
- if (user_app_count > 0)
- user_app_count--;
-
- if ((user_app_count == 0) && (p_multi_adv_com_data_cb != NULL)) {
- osi_free(p_multi_adv_com_data_cb->inst_cb);
- osi_free_and_reset((void **)&p_multi_adv_com_data_cb);
- }
-}
-
-void btif_gattc_adv_data_packager(int advertiser_id, bool set_scan_rsp,
- bool include_name, bool include_txpower, int min_interval, int max_interval,
- int appearance, const vector<uint8_t> &manufacturer_data,
- const vector<uint8_t> &service_data, const vector<uint8_t> &service_uuid,
- btif_adv_data_t *p_multi_adv_inst)
-{
- memset(p_multi_adv_inst, 0 , sizeof(btif_adv_data_t));
-
- p_multi_adv_inst->advertiser_id = (uint8_t) advertiser_id;
- p_multi_adv_inst->set_scan_rsp = set_scan_rsp;
- p_multi_adv_inst->include_name = include_name;
- p_multi_adv_inst->include_txpower = include_txpower;
- p_multi_adv_inst->min_interval = min_interval;
- p_multi_adv_inst->max_interval = max_interval;
- p_multi_adv_inst->appearance = appearance;
-
- if (manufacturer_data.size() > 0)
- {
- size_t manufacturer_len = manufacturer_data.size();
- if (manufacturer_len > MAX_SIZE_MANUFACTURER_DATA)
- manufacturer_len = MAX_SIZE_MANUFACTURER_DATA;
-
- p_multi_adv_inst->manufacturer_len = manufacturer_len;
- memcpy(p_multi_adv_inst->p_manufacturer_data, manufacturer_data.data(), manufacturer_len);
- }
-
- if (service_data.size() > 0)
- {
- size_t service_data_len = service_data.size();
- if (service_data_len > MAX_SIZE_PROPRIETARY_ELEMENT)
- service_data_len = MAX_SIZE_PROPRIETARY_ELEMENT;
-
- p_multi_adv_inst->service_data_len = service_data_len;
- memcpy(p_multi_adv_inst->p_service_data, service_data.data(), service_data_len);
- }
-
- if (service_uuid.size() > 0)
- {
- size_t service_uuid_len = service_uuid.size();
- if (service_uuid_len > MAX_SIZE_SERVICE_DATA)
- service_uuid_len = MAX_SIZE_SERVICE_DATA;
-
- p_multi_adv_inst->service_uuid_len = service_uuid_len;
- memcpy(p_multi_adv_inst->p_service_uuid, service_uuid.data(), service_uuid_len);
- }
-}
-
-bool btif_gattc_copy_datacb(int cbindex, const btif_adv_data_t *p_adv_data,
- bool bInstData) {
- btgatt_multi_adv_common_data *p_multi_adv_data_cb = btif_obtain_multi_adv_data_cb();
- if (NULL == p_multi_adv_data_cb || cbindex < 0)
- return false;
-
- BTIF_TRACE_DEBUG("%s", __func__);
-
- memset(&p_multi_adv_data_cb->inst_cb[cbindex].data, 0,
- sizeof(p_multi_adv_data_cb->inst_cb[cbindex].data));
- p_multi_adv_data_cb->inst_cb[cbindex].mask = 0;
-
- if (!p_adv_data->set_scan_rsp)
- {
- p_multi_adv_data_cb->inst_cb[cbindex].mask = BTM_BLE_AD_BIT_FLAGS;
- p_multi_adv_data_cb->inst_cb[cbindex].data.flag = ADV_FLAGS_GENERAL;
- if (p_multi_adv_data_cb->inst_cb[cbindex].timeout_s)
- p_multi_adv_data_cb->inst_cb[cbindex].data.flag = ADV_FLAGS_LIMITED;
- if (p_multi_adv_data_cb->inst_cb[cbindex].param.adv_type == BTM_BLE_NON_CONNECT_EVT)
- p_multi_adv_data_cb->inst_cb[cbindex].data.flag &=
- ~(BTA_DM_LIMITED_DISC | BTA_DM_GENERAL_DISC);
- if (p_multi_adv_data_cb->inst_cb[cbindex].data.flag == 0)
- p_multi_adv_data_cb->inst_cb[cbindex].mask = 0;
- }
-
- if (p_adv_data->include_name)
- p_multi_adv_data_cb->inst_cb[cbindex].mask |= BTM_BLE_AD_BIT_DEV_NAME;
-
- if (p_adv_data->include_txpower)
- p_multi_adv_data_cb->inst_cb[cbindex].mask |= BTM_BLE_AD_BIT_TX_PWR;
-
- if (false == bInstData && p_adv_data->min_interval > 0 && p_adv_data->max_interval > 0 &&
- p_adv_data->max_interval > p_adv_data->min_interval)
- {
- p_multi_adv_data_cb->inst_cb[cbindex].mask |= BTM_BLE_AD_BIT_INT_RANGE;
- p_multi_adv_data_cb->inst_cb[cbindex].data.int_range.low =
- p_adv_data->min_interval;
- p_multi_adv_data_cb->inst_cb[cbindex].data.int_range.hi =
- p_adv_data->max_interval;
- }
- else
- if (true == bInstData)
- {
- if (p_multi_adv_data_cb->inst_cb[cbindex].param.adv_int_min > 0 &&
- p_multi_adv_data_cb->inst_cb[cbindex].param.adv_int_max > 0 &&
- p_multi_adv_data_cb->inst_cb[cbindex].param.adv_int_max >
- p_multi_adv_data_cb->inst_cb[cbindex].param.adv_int_min)
- {
- p_multi_adv_data_cb->inst_cb[cbindex].data.int_range.low =
- p_multi_adv_data_cb->inst_cb[cbindex].param.adv_int_min;
- p_multi_adv_data_cb->inst_cb[cbindex].data.int_range.hi =
- p_multi_adv_data_cb->inst_cb[cbindex].param.adv_int_max;
- }
-
- if (p_adv_data->include_txpower)
- {
- p_multi_adv_data_cb->inst_cb[cbindex].data.tx_power =
- p_multi_adv_data_cb->inst_cb[cbindex].param.tx_power;
- }
- }
-
- if (p_adv_data->appearance != 0)
- {
- p_multi_adv_data_cb->inst_cb[cbindex].mask |= BTM_BLE_AD_BIT_APPEARANCE;
- p_multi_adv_data_cb->inst_cb[cbindex].data.appearance = p_adv_data->appearance;
- }
-
- if (p_adv_data->manufacturer_len > 0 &&
- p_adv_data->manufacturer_len < MAX_SIZE_MANUFACTURER_DATA)
- {
- p_multi_adv_data_cb->inst_cb[cbindex].mask |= BTM_BLE_AD_BIT_MANU;
- p_multi_adv_data_cb->inst_cb[cbindex].data.manu.len =
- p_adv_data->manufacturer_len;
- memcpy(&p_multi_adv_data_cb->inst_cb[cbindex].data.manu.val,
- p_adv_data->p_manufacturer_data, p_adv_data->manufacturer_len);
- }
-
- if (p_adv_data->service_data_len > 0 &&
- p_adv_data->service_data_len < MAX_SIZE_PROPRIETARY_ELEMENT)
- {
- BTIF_TRACE_DEBUG("%s - In service_data", __func__);
- tBTA_BLE_PROPRIETARY *p_prop = &p_multi_adv_data_cb->inst_cb[cbindex].data.proprietary;
- p_prop->num_elem = 1;
-
- tBTA_BLE_PROP_ELEM *p_elem = &p_prop->elem[0];
- p_elem->adv_type = BTM_BLE_AD_TYPE_SERVICE_DATA;
- p_elem->len = p_adv_data->service_data_len;
- memcpy(p_elem->val, p_adv_data->p_service_data,
- p_adv_data->service_data_len);
-
- p_multi_adv_data_cb->inst_cb[cbindex].mask |= BTM_BLE_AD_BIT_PROPRIETARY;
- }
-
- if (p_adv_data->service_uuid_len)
- {
- uint16_t *p_uuid_out16 = NULL;
- uint32_t *p_uuid_out32 = NULL;
- for (int position = 0; position < p_adv_data->service_uuid_len; position += LEN_UUID_128)
- {
- bt_uuid_t uuid;
- memset(&uuid, 0, sizeof(uuid));
- memcpy(&uuid.uu, p_adv_data->p_service_uuid + position, LEN_UUID_128);
-
- tBT_UUID bt_uuid;
- memset(&bt_uuid, 0, sizeof(bt_uuid));
- btif_to_bta_uuid(&bt_uuid, &uuid);
-
- switch(bt_uuid.len)
- {
- case (LEN_UUID_16):
- {
- if (p_multi_adv_data_cb->inst_cb[cbindex].data.services.num_service == 0)
- {
- p_multi_adv_data_cb->inst_cb[cbindex].data.services.list_cmpl = false;
- p_uuid_out16 = p_multi_adv_data_cb->inst_cb[cbindex].data.services.uuid;
- }
-
- if (p_multi_adv_data_cb->inst_cb[cbindex].data.services.num_service < MAX_16BIT_SERVICES)
- {
- BTIF_TRACE_DEBUG("%s - In 16-UUID_data", __func__);
- p_multi_adv_data_cb->inst_cb[cbindex].mask |= BTM_BLE_AD_BIT_SERVICE;
- ++p_multi_adv_data_cb->inst_cb[cbindex].data.services.num_service;
- *p_uuid_out16++ = bt_uuid.uu.uuid16;
- }
- break;
- }
-
- case (LEN_UUID_32):
- {
- if (p_multi_adv_data_cb->inst_cb[cbindex].data.service_32b.num_service == 0)
- {
- p_multi_adv_data_cb->inst_cb[cbindex].data.service_32b.list_cmpl = false;
- p_uuid_out32 = p_multi_adv_data_cb->inst_cb[cbindex].data.service_32b.uuid;
- }
-
- if (p_multi_adv_data_cb->inst_cb[cbindex].data.service_32b.num_service < MAX_32BIT_SERVICES)
- {
- BTIF_TRACE_DEBUG("%s - In 32-UUID_data", __func__);
- p_multi_adv_data_cb->inst_cb[cbindex].mask |= BTM_BLE_AD_BIT_SERVICE_32;
- ++p_multi_adv_data_cb->inst_cb[cbindex].data.service_32b.num_service;
- *p_uuid_out32++ = bt_uuid.uu.uuid32;
- }
- break;
- }
-
- case (LEN_UUID_128):
- {
- /* Currently, only one 128-bit UUID is supported */
- if (p_multi_adv_data_cb->inst_cb[cbindex].data.services_128b.num_service == 0)
- {
- BTIF_TRACE_DEBUG("%s - In 128-UUID_data", __func__);
- p_multi_adv_data_cb->inst_cb[cbindex].mask |=
- BTM_BLE_AD_BIT_SERVICE_128;
- memcpy(p_multi_adv_data_cb->inst_cb[cbindex]
- .data.services_128b.uuid128,
- bt_uuid.uu.uuid128, LEN_UUID_128);
- BTIF_TRACE_DEBUG(
- "%x,%x,%x,%x,%x,%x,%x,%x,%x,%x,%x,%x,%x,%x,%x,%x",
- bt_uuid.uu.uuid128[0], bt_uuid.uu.uuid128[1],
- bt_uuid.uu.uuid128[2], bt_uuid.uu.uuid128[3],
- bt_uuid.uu.uuid128[4], bt_uuid.uu.uuid128[5],
- bt_uuid.uu.uuid128[6], bt_uuid.uu.uuid128[7],
- bt_uuid.uu.uuid128[8], bt_uuid.uu.uuid128[9],
- bt_uuid.uu.uuid128[10], bt_uuid.uu.uuid128[11],
- bt_uuid.uu.uuid128[12], bt_uuid.uu.uuid128[13],
- bt_uuid.uu.uuid128[14], bt_uuid.uu.uuid128[15]);
- ++p_multi_adv_data_cb->inst_cb[cbindex]
- .data.services_128b.num_service;
- p_multi_adv_data_cb->inst_cb[cbindex]
- .data.services_128b.list_cmpl = true;
- }
- break;
- }
-
- default:
- break;
- }
- }
- }
-
- return true;
-}
-
-void btif_gattc_clear_clientif(int advertiser_id, bool stop_timer)
-{
- btgatt_multi_adv_common_data *p_multi_adv_data_cb = btif_obtain_multi_adv_data_cb();
- if (NULL == p_multi_adv_data_cb)
- return;
-
- btif_gattc_cleanup_inst_cb(advertiser_id, stop_timer);
-}
-
-void btif_gattc_cleanup_inst_cb(int inst_id, bool stop_timer)
-{
- // Check for invalid instance id
- if (inst_id < 0 || inst_id >= BTM_BleMaxMultiAdvInstanceCount())
- return;
-
- btgatt_multi_adv_common_data *p_multi_adv_data_cb = btif_obtain_multi_adv_data_cb();
- if (NULL == p_multi_adv_data_cb)
- return;
-
- BTIF_TRACE_DEBUG("%s: inst_id %d", __func__, inst_id);
- btif_gattc_cleanup_multi_inst_cb(&p_multi_adv_data_cb->inst_cb[inst_id], stop_timer);
-}
-
-void btif_gattc_cleanup_multi_inst_cb(btgatt_multi_adv_inst_cb *p_multi_inst_cb,
- bool stop_timer)
-{
- if (p_multi_inst_cb == NULL)
- return;
-
- // Discoverability timer cleanup
- if (stop_timer)
- {
- alarm_free(p_multi_inst_cb->multi_adv_timer);
- p_multi_inst_cb->multi_adv_timer = NULL;
- }
-
- memset(&p_multi_inst_cb->data, 0, sizeof(p_multi_inst_cb->data));
-}
-
-void btif_multi_adv_timer_ctrl(int advertiser_id, alarm_callback_t cb)
-{
- btgatt_multi_adv_common_data *p_multi_adv_data_cb = btif_obtain_multi_adv_data_cb();
- if (p_multi_adv_data_cb == NULL)
- return;
-
- btgatt_multi_adv_inst_cb *inst_cb = &p_multi_adv_data_cb->inst_cb[advertiser_id];
- if (cb == NULL)
- {
- alarm_free(inst_cb->multi_adv_timer);
- inst_cb->multi_adv_timer = NULL;
- } else {
- if (inst_cb->timeout_s != 0)
- {
- alarm_free(inst_cb->multi_adv_timer);
- inst_cb->multi_adv_timer = alarm_new("btif_gatt.multi_adv_timer");
- alarm_set_on_queue(inst_cb->multi_adv_timer,
- inst_cb->timeout_s * 1000,
- cb, INT_TO_PTR(advertiser_id),
- btu_general_alarm_queue);
- }
- }
-}
-
-#endif
*******************************************************************************/
static void btm_ble_update_adv_flag(uint8_t flag);
static void btm_ble_process_adv_pkt_cont(BD_ADDR bda, uint8_t addr_type, uint8_t evt_type, uint8_t *p);
-uint8_t *btm_ble_build_adv_data(tBTM_BLE_AD_MASK *p_data_mask, uint8_t **p_dst,
- tBTM_BLE_ADV_DATA *p_data);
static uint8_t btm_set_conn_mode_adv_init_addr(tBTM_BLE_INQ_CB *p_cb,
BD_ADDR_PTR p_peer_addr_ptr,
tBLE_ADDR_TYPE *p_peer_addr_type,
** Returns void
**
*******************************************************************************/
-void BTM_BleWriteScanRsp(tBTM_BLE_AD_MASK data_mask, tBTM_BLE_ADV_DATA *p_data,
+void BTM_BleWriteScanRsp(uint8_t* data, uint8_t length,
tBTM_BLE_ADV_DATA_CMPL_CBACK *p_adv_data_cback)
{
tBTM_STATUS status = BTM_NO_RESOURCES;
- uint8_t rsp_data[BTM_BLE_AD_DATA_LEN],
- *p = rsp_data;
- BTM_TRACE_EVENT ("%s: data_mask:%08x", __func__, data_mask);
+ BTM_TRACE_EVENT ("%s: length: %d", __func__, length);
if (!controller_get_interface()->supports_ble()) {
p_adv_data_cback(BTM_ILLEGAL_VALUE);
return;
}
- memset(rsp_data, 0, BTM_BLE_AD_DATA_LEN);
- btm_ble_build_adv_data(&data_mask, &p, p_data);
-
- if (btsnd_hcic_ble_set_scan_rsp_data((uint8_t)(p - rsp_data), rsp_data))
+ if (btsnd_hcic_ble_set_scan_rsp_data(length, data))
{
status = BTM_SUCCESS;
- if (data_mask != 0)
+ if (length != 0)
btm_cb.ble_ctr_cb.inq_var.scan_rsp = true;
else
btm_cb.ble_ctr_cb.inq_var.scan_rsp = false;
** Returns void
**
*******************************************************************************/
-void BTM_BleWriteAdvData(tBTM_BLE_AD_MASK data_mask, tBTM_BLE_ADV_DATA *p_data,
+void BTM_BleWriteAdvData(uint8_t* data, uint8_t length,
tBTM_BLE_ADV_DATA_CMPL_CBACK *p_adv_data_cback)
{
- tBTM_BLE_LOCAL_ADV_DATA *p_cb_data = &btm_cb.ble_ctr_cb.inq_var.adv_data;
- uint8_t *p;
- tBTM_BLE_AD_MASK mask = data_mask;
-
+ //TODO(jpawlowski) : delete btm_cb.ble_ctr_cb.inq_var.adv_data ??
BTM_TRACE_EVENT ("BTM_BleWriteAdvData ");
if (!controller_get_interface()->supports_ble()) {
return;
}
- memset(p_cb_data, 0, sizeof(tBTM_BLE_LOCAL_ADV_DATA));
- p = p_cb_data->ad_data;
- p_cb_data->data_mask = data_mask;
-
- p_cb_data->p_flags = btm_ble_build_adv_data(&mask, &p, p_data);
-
- p_cb_data->p_pad = p;
-
- if (mask != 0)
- {
- BTM_TRACE_ERROR("Partial data write into ADV");
- }
-
- p_cb_data->data_mask &= ~mask;
+ //TODO(jpawlowski): fill flags, old code had them empty always.
- if (btsnd_hcic_ble_set_adv_data((uint8_t)(p_cb_data->p_pad - p_cb_data->ad_data),
- p_cb_data->ad_data))
+ if (btsnd_hcic_ble_set_adv_data(length, data))
p_adv_data_cback(BTM_SUCCESS);
else
p_adv_data_cback(BTM_NO_RESOURCES);
-
}
/*******************************************************************************
/*******************************************************************************
**
-** Function btm_ble_build_adv_data
-**
-** Description This function is called build the adv data and rsp data.
-*******************************************************************************/
-uint8_t *btm_ble_build_adv_data(tBTM_BLE_AD_MASK *p_data_mask, uint8_t **p_dst,
- tBTM_BLE_ADV_DATA *p_data)
-{
- uint32_t data_mask = *p_data_mask;
- uint8_t *p = *p_dst,
- *p_flag = NULL;
- uint16_t len = BTM_BLE_AD_DATA_LEN, cp_len = 0;
- uint8_t i = 0;
- tBTM_BLE_PROP_ELEM *p_elem;
-
- BTM_TRACE_EVENT (" btm_ble_build_adv_data");
-
- /* build the adv data structure and build the data string */
- if (data_mask)
- {
- /* flags */
- if (data_mask & BTM_BLE_AD_BIT_FLAGS)
- {
- *p++ = MIN_ADV_LENGTH;
- *p++ = BTM_BLE_AD_TYPE_FLAG;
- p_flag = p;
- if (p_data)
- *p++ = p_data->flag;
- else
- *p++ = 0;
-
- len -= 3;
-
- data_mask &= ~BTM_BLE_AD_BIT_FLAGS;
- }
- /* appearance data */
- if (len > 3 && data_mask & BTM_BLE_AD_BIT_APPEARANCE)
- {
- *p++ = 3; /* length */
- *p++ = BTM_BLE_AD_TYPE_APPEARANCE;
- UINT16_TO_STREAM(p, p_data->appearance);
- len -= 4;
-
- data_mask &= ~BTM_BLE_AD_BIT_APPEARANCE;
- }
- /* device name */
- if (len > MIN_ADV_LENGTH && data_mask & BTM_BLE_AD_BIT_DEV_NAME)
- {
- if (strlen(btm_cb.cfg.bd_name) > (uint16_t)(len - MIN_ADV_LENGTH))
- {
- *p++ = len - MIN_ADV_LENGTH + 1;
- *p++ = BTM_BLE_AD_TYPE_NAME_SHORT;
- ARRAY_TO_STREAM(p, btm_cb.cfg.bd_name, len - MIN_ADV_LENGTH);
- }
- else
- {
- cp_len = (uint16_t)strlen(btm_cb.cfg.bd_name);
- *p++ = cp_len + 1;
- *p++ = BTM_BLE_AD_TYPE_NAME_CMPL;
- ARRAY_TO_STREAM(p, btm_cb.cfg.bd_name, cp_len);
- }
- len -= (cp_len + MIN_ADV_LENGTH);
- data_mask &= ~BTM_BLE_AD_BIT_DEV_NAME;
- }
- /* manufacturer data */
- if (len > MIN_ADV_LENGTH && data_mask & BTM_BLE_AD_BIT_MANU &&
- p_data && p_data->manu.len != 0)
- {
- if (p_data->manu.len > (len - MIN_ADV_LENGTH))
- cp_len = len - MIN_ADV_LENGTH;
- else
- cp_len = p_data->manu.len;
-
- *p++ = cp_len + 1;
- *p++ = BTM_BLE_AD_TYPE_MANU;
- ARRAY_TO_STREAM(p, p_data->manu.val, cp_len);
-
- len -= (cp_len + MIN_ADV_LENGTH);
- data_mask &= ~BTM_BLE_AD_BIT_MANU;
- }
- /* TX power */
- if (len > MIN_ADV_LENGTH && data_mask & BTM_BLE_AD_BIT_TX_PWR)
- {
- *p++ = MIN_ADV_LENGTH;
- *p++ = BTM_BLE_AD_TYPE_TX_PWR;
- if (p_data->tx_power > BTM_BLE_ADV_TX_POWER_MAX)
- p_data->tx_power = BTM_BLE_ADV_TX_POWER_MAX;
- *p++ = btm_ble_map_adv_tx_power(p_data->tx_power);
- len -= 3;
- data_mask &= ~BTM_BLE_AD_BIT_TX_PWR;
- }
- /* 16 bits services */
- if (len > MIN_ADV_LENGTH && data_mask & BTM_BLE_AD_BIT_SERVICE &&
- p_data && p_data->services.num_service != 0)
- {
- if (p_data->services.num_service * LEN_UUID_16 > (len - MIN_ADV_LENGTH))
- {
- cp_len = (len - MIN_ADV_LENGTH)/LEN_UUID_16;
- *p ++ = 1 + cp_len * LEN_UUID_16;
- *p++ = BTM_BLE_AD_TYPE_16SRV_PART;
- }
- else
- {
- cp_len = p_data->services.num_service;
- *p++ = 1 + cp_len * LEN_UUID_16;
- *p++ = BTM_BLE_AD_TYPE_16SRV_CMPL;
- }
- for (i = 0; i < cp_len; i ++)
- {
- UINT16_TO_STREAM(p, *(p_data->services.uuid + i));
- }
-
- len -= (cp_len * MIN_ADV_LENGTH + MIN_ADV_LENGTH);
- data_mask &= ~BTM_BLE_AD_BIT_SERVICE;
- }
- /* 32 bits service uuid */
- if (len > MIN_ADV_LENGTH && data_mask & BTM_BLE_AD_BIT_SERVICE_32 &&
- p_data && p_data->service_32b.num_service != 0)
- {
- if ((p_data->service_32b.num_service * LEN_UUID_32) > (len - MIN_ADV_LENGTH))
- {
- cp_len = (len - MIN_ADV_LENGTH)/LEN_UUID_32;
- *p ++ = 1 + cp_len * LEN_UUID_32;
- *p++ = BTM_BLE_AD_TYPE_32SRV_PART;
- }
- else
- {
- cp_len = p_data->service_32b.num_service;
- *p++ = 1 + cp_len * LEN_UUID_32;
- *p++ = BTM_BLE_AD_TYPE_32SRV_CMPL;
- }
- for (i = 0; i < cp_len; i ++)
- {
- UINT32_TO_STREAM(p, *(p_data->service_32b.uuid + i));
- }
-
- len -= (cp_len * LEN_UUID_32 + MIN_ADV_LENGTH);
- data_mask &= ~BTM_BLE_AD_BIT_SERVICE_32;
- }
- /* 128 bits services */
- if (len >= (MAX_UUID_SIZE + 2) && data_mask & BTM_BLE_AD_BIT_SERVICE_128 &&
- p_data && p_data->services_128b.num_service)
- {
- *p ++ = 1 + MAX_UUID_SIZE;
- if (!p_data->services_128b.list_cmpl)
- *p++ = BTM_BLE_AD_TYPE_128SRV_PART;
- else
- *p++ = BTM_BLE_AD_TYPE_128SRV_CMPL;
-
- ARRAY_TO_STREAM(p, p_data->services_128b.uuid128, MAX_UUID_SIZE);
-
- len -= (MAX_UUID_SIZE + MIN_ADV_LENGTH);
- data_mask &= ~BTM_BLE_AD_BIT_SERVICE_128;
- }
- /* 32 bits Service Solicitation UUIDs */
- if (len > MIN_ADV_LENGTH && data_mask & BTM_BLE_AD_BIT_SERVICE_32SOL &&
- p_data->sol_service_32b.num_service != 0)
- {
- if ((p_data->sol_service_32b.num_service * LEN_UUID_32) > (len - MIN_ADV_LENGTH))
- {
- cp_len = (len - MIN_ADV_LENGTH)/LEN_UUID_32;
- *p ++ = 1 + cp_len * LEN_UUID_32;
- }
- else
- {
- cp_len = p_data->sol_service_32b.num_service;
- *p++ = 1 + cp_len * LEN_UUID_32;
- }
-
- *p++ = BTM_BLE_AD_TYPE_32SOL_SRV_UUID;
- for (i = 0; i < cp_len; i ++)
- {
- UINT32_TO_STREAM(p, *(p_data->sol_service_32b.uuid + i));
- }
-
- len -= (cp_len * LEN_UUID_32 + MIN_ADV_LENGTH);
- data_mask &= ~BTM_BLE_AD_BIT_SERVICE_32SOL;
- }
- /* 128 bits Solicitation services UUID */
- if (len >= (MAX_UUID_SIZE + MIN_ADV_LENGTH) && data_mask & BTM_BLE_AD_BIT_SERVICE_128SOL &&
- p_data && p_data->sol_service_128b.num_service)
- {
- *p ++ = 1 + MAX_UUID_SIZE;
- *p++ = BTM_BLE_AD_TYPE_128SOL_SRV_UUID;
- ARRAY_TO_STREAM(p, p_data->sol_service_128b.uuid128, MAX_UUID_SIZE);
- len -= (MAX_UUID_SIZE + MIN_ADV_LENGTH);
- data_mask &= ~BTM_BLE_AD_BIT_SERVICE_128SOL;
- }
- /* 16bits/32bits/128bits Service Data */
- if (len > MIN_ADV_LENGTH && data_mask & BTM_BLE_AD_BIT_SERVICE_DATA &&
- p_data && p_data->service_data.len != 0)
- {
- if (len > (p_data->service_data.service_uuid.len + MIN_ADV_LENGTH))
- {
- if (p_data->service_data.len > (len - MIN_ADV_LENGTH))
- cp_len = len - MIN_ADV_LENGTH- p_data->service_data.service_uuid.len;
- else
- cp_len = p_data->service_data.len;
-
- *p++ = cp_len + 1 + p_data->service_data.service_uuid.len;
- if (p_data->service_data.service_uuid.len == LEN_UUID_16)
- {
- *p++ = BTM_BLE_AD_TYPE_SERVICE_DATA;
- UINT16_TO_STREAM(p, p_data->service_data.service_uuid.uu.uuid16);
- }
- else if (p_data->service_data.service_uuid.len == LEN_UUID_32)
- {
- *p++ = BTM_BLE_AD_TYPE_32SERVICE_DATA;
- UINT32_TO_STREAM(p, p_data->service_data.service_uuid.uu.uuid32);
- }
- else
- {
- *p++ = BTM_BLE_AD_TYPE_128SERVICE_DATA;
- ARRAY_TO_STREAM(p, p_data->service_data.service_uuid.uu.uuid128,
- LEN_UUID_128);
- }
-
- ARRAY_TO_STREAM(p, p_data->service_data.val, cp_len);
-
- len -= (cp_len + MIN_ADV_LENGTH + p_data->service_data.service_uuid.len);
- data_mask &= ~BTM_BLE_AD_BIT_SERVICE_DATA;
- }
- else
- {
- BTM_TRACE_WARNING("service data does not fit");
- }
- }
-
- if (len >= 6 && data_mask & BTM_BLE_AD_BIT_INT_RANGE &&
- p_data)
- {
- *p++ = 5;
- *p++ = BTM_BLE_AD_TYPE_INT_RANGE;
- UINT16_TO_STREAM(p, p_data->int_range.low);
- UINT16_TO_STREAM(p, p_data->int_range.hi);
- len -= 6;
- data_mask &= ~BTM_BLE_AD_BIT_INT_RANGE;
- }
- if (data_mask & BTM_BLE_AD_BIT_PROPRIETARY && p_data)
- {
- for (i = 0; i < p_data->proprietary.num_elem; ++i)
- {
- p_elem = &p_data->proprietary.elem[i];
-
- if (len >= (MIN_ADV_LENGTH + p_elem->len))/* len byte(1) + ATTR type(1) + Uuid len(2)
- + value length */
- {
- *p ++ = p_elem->len + 1; /* Uuid len + value length */
- *p ++ = p_elem->adv_type;
- ARRAY_TO_STREAM(p, p_elem->val, p_elem->len);
-
- len -= (MIN_ADV_LENGTH + p_elem->len);
- }
- else
- {
- BTM_TRACE_WARNING("data exceed max adv packet length");
- break;
- }
- }
- data_mask &= ~BTM_BLE_AD_BIT_PROPRIETARY;
- }
- }
-
- *p_data_mask = data_mask;
- *p_dst = p;
-
- return p_flag;
-}
-/*******************************************************************************
-**
** Function btm_ble_select_adv_interval
**
** Description select adv interval based on device mode
}
-#if 0
-/*******************************************************************************
-**
-** Function btm_ble_parse_adv_data
-**
-** Description This function parse the adv data into a structure.
-**
-** Returns pointer to entry, or NULL if not found
-**
-*******************************************************************************/
-static void btm_ble_parse_adv_data(tBTM_INQ_INFO *p_info, uint8_t *p_data,
- uint8_t len, tBTM_BLE_INQ_DATA *p_adv_data, uint8_t *p_buf)
-{
- uint8_t *p_cur = p_data;
- uint8_t ad_len, ad_type, ad_flag;
-
- BTM_TRACE_EVENT (" btm_ble_parse_adv_data");
-
- while (len > 0)
- {
- BTM_TRACE_DEBUG("btm_ble_parse_adv_data: len = %d", len);
- if ((ad_len = *p_cur ++) == 0)
- break;
-
- ad_type = *p_cur ++;
-
- BTM_TRACE_DEBUG(" ad_type = %02x ad_len = %d", ad_type, ad_len);
-
- switch (ad_type)
- {
- case BTM_BLE_AD_TYPE_NAME_SHORT:
-
- case BTM_BLE_AD_TYPE_NAME_CMPL:
- p_adv_data->ad_mask |= BTM_BLE_AD_BIT_DEV_NAME;
- if (p_info)
- {
- p_info->remote_name_type =(ad_type == BTM_BLE_AD_TYPE_NAME_SHORT) ?
- BTM_BLE_NAME_SHORT: BTM_BLE_NAME_CMPL;
- memcpy(p_info->remote_name, p_cur, ad_len -1);
- p_info->remote_name[ad_len] = 0;
- p_adv_data->p_remote_name = p_info->remote_name;
- p_info->remote_name_len = p_adv_data->remote_name_len = ad_len - 1;
- BTM_TRACE_DEBUG("BTM_BLE_AD_TYPE_NAME name = %s",p_adv_data->p_remote_name);
- }
- p_cur += (ad_len -1);
-
- break;
-
- case BTM_BLE_AD_TYPE_FLAG:
- p_adv_data->ad_mask |= BTM_BLE_AD_BIT_FLAGS;
- ad_flag = *p_cur ++;
- p_adv_data->flag = (uint8_t)(ad_flag & BTM_BLE_ADV_FLAG_MASK) ;
- BTM_TRACE_DEBUG("BTM_BLE_AD_TYPE_FLAG flag = %s | %s | %s",
- (p_adv_data->flag & BTM_BLE_LIMIT_DISC_FLAG)? "LE_LIMIT_DISC" : "",
- (p_adv_data->flag & BTM_BLE_GEN_DISC_FLAG)? "LE_GENERAL_DISC" : "",
- (p_adv_data->flag & BTM_BLE_BREDR_NOT_SPT)? "LE Only device" : "");
- break;
-
- case BTM_BLE_AD_TYPE_TX_PWR:
- p_adv_data->ad_mask |= BTM_BLE_AD_BIT_TX_PWR;
- p_adv_data->tx_power_level = (int8_t)*p_cur ++;
- BTM_TRACE_DEBUG("BTM_BLE_AD_TYPE_TX_PWR tx_level = %d", p_adv_data->tx_power_level);
- break;
-
- case BTM_BLE_AD_TYPE_MANU:
-
- case BTM_BLE_AD_TYPE_16SRV_PART:
- case BTM_BLE_AD_TYPE_16SRV_CMPL:
- p_adv_data->ad_mask |= BTM_BLE_AD_BIT_SERVICE;
- /* need allocate memory to store UUID list */
- p_adv_data->service.num_service = (ad_len - 1)/2;
- BTM_TRACE_DEBUG("service UUID list, num = %d", p_adv_data->service.num_service);
- p_cur += (ad_len - 1);
- break;
-
- case BTM_BLE_AD_TYPE_SOL_SRV_UUID:
- p_adv_data->ad_mask |= BTM_BLE_AD_BIT_SERVICE_SOL;
- /* need allocate memory to store UUID list */
- p_adv_data->service.num_service = (ad_len - 1)/2;
- BTM_TRACE_DEBUG("service UUID list, num = %d", p_adv_data->service.num_service);
- p_cur += (ad_len - 1);
- break;
-
- case BTM_BLE_AD_TYPE_128SOL_SRV_UUID:
- p_adv_data->ad_mask |= BTM_BLE_AD_BIT_SERVICE_128SOL;
- /* need allocate memory to store UUID list */
- p_adv_data->service.num_service = (ad_len - 1)/16;
- BTM_TRACE_DEBUG("service UUID list, num = %d", p_adv_data->service.num_service);
- p_cur += (ad_len - 1);
- break;
-
- case BTM_BLE_AD_TYPE_APPEARANCE:
- case BTM_BLE_AD_TYPE_PUBLIC_TARGET:
- case BTM_BLE_AD_TYPE_RANDOM_TARGET:
- default:
- break;
- }
- len -= (ad_len + 1);
- }
-}
-#endif
-
/*******************************************************************************
**
** Function btm_ble_cache_adv_data
extern void btm_read_ble_local_supported_states_complete(uint8_t *p, uint16_t evt_len);
extern tBTM_BLE_CONN_ST btm_ble_get_conn_st(void);
extern void btm_ble_set_conn_st(tBTM_BLE_CONN_ST new_st);
-extern uint8_t *btm_ble_build_adv_data(tBTM_BLE_AD_MASK *p_data_mask, uint8_t **p_dst,
- tBTM_BLE_ADV_DATA *p_data);
extern tBTM_STATUS btm_ble_start_adv(void);
extern tBTM_STATUS btm_ble_stop_adv(void);
extern tBTM_STATUS btm_ble_start_scan(void);
extern void btm_ble_multi_adv_init(void);
extern void* btm_ble_multi_adv_get_ref(uint8_t inst_id);
extern void btm_ble_multi_adv_cleanup(void);
-extern char btm_ble_map_adv_tx_power(int tx_power_index);
extern void btm_ble_batchscan_init(void);
extern void btm_ble_batchscan_cleanup(void);
extern void btm_ble_adv_filter_init(void);
uint8_t adv_evt;
BD_ADDR rpa;
alarm_t *adv_raddr_timer;
+ int8_t tx_power;
+ int timeout_s;
+ MultiAdvCb timeout_cb;
+ alarm_t *timeout_timer;
AdvertisingInstance(int inst_id)
- : inst_id(inst_id), in_use(false), adv_evt(0), rpa{0} {
+ : inst_id(inst_id),
+ in_use(false),
+ adv_evt(0),
+ rpa{0},
+ tx_power(0),
+ timeout_s(0),
+ timeout_cb(),
+ timeout_timer(nullptr) {
adv_raddr_timer = alarm_new_periodic("btm_ble.adv_raddr_timer");
}
- ~AdvertisingInstance() { alarm_free(adv_raddr_timer); }
+ ~AdvertisingInstance() {
+ alarm_free(adv_raddr_timer);
+ if (timeout_timer) alarm_free(timeout_timer);
+ }
};
/************************************************************************************
void DoNothing(uint8_t) {}
-/* return the actual power in dBm based on the mapping in config file */
-int btm_ble_tx_power[BTM_BLE_ADV_TX_POWER_MAX + 1] = BTM_BLE_ADV_TX_POWER;
-char btm_ble_map_adv_tx_power(int tx_power_index) {
- if (0 <= tx_power_index && tx_power_index < BTM_BLE_ADV_TX_POWER_MAX)
- return (char)btm_ble_tx_power[tx_power_index];
- return 0;
-}
-
std::queue<base::Callback<void(tBTM_RAND_ENC *p)>> *rand_gen_inst_id = nullptr;
/* RPA generation completion callback for each adv instance. Will continue write
cb.Run(0xFF, BTM_BLE_MULTI_ADV_FAILURE);
}
- void Enable(uint8_t inst_id, bool enable, MultiAdvCb cb) {
- VLOG(1) << __func__ << " inst_id: " << +inst_id << ", enable: " << enable;
+ void EnableWithTimerCb(uint8_t inst_id, int timeout_s, MultiAdvCb timeout_cb,
+ uint8_t status) {
+ AdvertisingInstance *p_inst = &adv_inst[inst_id - 1];
+ p_inst->timeout_s = timeout_s;
+ p_inst->timeout_cb = std::move(timeout_cb);
+
+ p_inst->timeout_timer = alarm_new("btm_ble.adv_timeout");
+ alarm_set_on_queue(p_inst->timeout_timer, p_inst->timeout_s * 1000, nullptr,
+ p_inst, btu_general_alarm_queue);
+ }
+ void Enable(uint8_t inst_id, bool enable, MultiAdvCb cb, int timeout_s,
+ MultiAdvCb timeout_cb) {
+ AdvertisingInstance *p_inst = &adv_inst[inst_id - 1];
+
+ VLOG(1) << __func__ << " inst_id: " << +inst_id << ", enable: " << enable;
if (BTM_BleMaxMultiAdvInstanceCount() == 0) {
LOG(ERROR) << "multi adv not supported";
return;
}
- AdvertisingInstance *p_inst = &adv_inst[inst_id - 1];
if (!p_inst || !p_inst->in_use) {
LOG(ERROR) << "Invalid or no active instance";
cb.Run(BTM_BLE_MULTI_ADV_FAILURE);
return;
}
- GetHciInterface()->Enable(enable, p_inst->inst_id, cb);
+ if (enable && timeout_s) {
+ GetHciInterface()->Enable(
+ enable, p_inst->inst_id,
+ Bind(&BleAdvertisingManagerImpl::EnableWithTimerCb,
+ base::Unretained(this), inst_id, timeout_s, timeout_cb));
+ } else {
+ if (p_inst->timeout_timer) {
+ alarm_cancel(p_inst->timeout_timer);
+ alarm_free(p_inst->timeout_timer);
+ p_inst->timeout_timer = nullptr;
+ }
+
+ GetHciInterface()->Enable(enable, p_inst->inst_id, cb);
+ }
}
void SetParameters(uint8_t inst_id, tBTM_BLE_ADV_PARAMS *p_params,
#endif
memcpy(own_address, controller_get_interface()->get_address()->address,
BD_ADDR_LEN);
- p_inst->adv_evt = p_params->adv_type;
}
BD_ADDR dummy = {0, 0, 0, 0, 0, 0};
+
+ p_inst->adv_evt = p_params->adv_type;
+ p_inst->tx_power = p_params->tx_power;
+
GetHciInterface()->SetParameters(
p_params->adv_int_min, p_params->adv_int_max, p_params->adv_type,
own_address_type, own_address, 0, dummy, p_params->channel_map,
- p_params->adv_filter_policy, p_inst->inst_id,
- btm_ble_map_adv_tx_power(p_params->tx_power), cb);
+ p_params->adv_filter_policy, p_inst->inst_id, p_inst->tx_power, cb);
// TODO: re-enable only if it was enabled, properly call
// SetParamsCallback
// GetHciInterface()->Enable(true, inst_id, BTM_BleUpdateAdvInstParamCb);
}
- void SetData(uint8_t inst_id, bool is_scan_rsp, tBTM_BLE_AD_MASK data_mask,
- tBTM_BLE_ADV_DATA *p_data, MultiAdvCb cb) override {
+ void SetData(uint8_t inst_id, bool is_scan_rsp, std::vector<uint8_t> data,
+ MultiAdvCb cb) override {
+ AdvertisingInstance *p_inst = &adv_inst[inst_id - 1];
+
VLOG(1) << "inst_id = " << +inst_id << ", is_scan_rsp = " << is_scan_rsp;
if (BTM_BleMaxMultiAdvInstanceCount() == 0) {
return;
}
- btm_ble_update_dmt_flag_bits(&p_data->flag,
- BTM_ReadConnectability(nullptr, nullptr),
- BTM_ReadDiscoverability(nullptr, nullptr));
+ if (!is_scan_rsp && p_inst->adv_evt != BTM_BLE_NON_CONNECT_EVT) {
+ uint8_t flags_val = BTM_GENERAL_DISCOVERABLE;
+
+ if (p_inst->timeout_s) flags_val = BTM_LIMITED_DISCOVERABLE;
+
+ std::vector<uint8_t> flags;
+ flags.push_back(2); // length
+ flags.push_back(HCI_EIR_FLAGS_TYPE);
+ flags.push_back(flags_val);
+
+ data.insert(data.begin(), flags.begin(), flags.end());
+ }
+
+ // Find and fill TX Power with the correct value
+ if (data.size()) {
+ size_t i = 0;
+ while (i < data.size()) {
+ uint8_t type = data[i + 1];
+ if (type == HCI_EIR_TX_POWER_LEVEL_TYPE) {
+ int8_t tx_power = adv_inst[inst_id - 1].tx_power;
+ data[i + 2] = tx_power;
+ }
+ i += data[i] + 1;
+ }
+ }
if (inst_id > BTM_BleMaxMultiAdvInstanceCount() || inst_id < 0 ||
inst_id == BTM_BLE_MULTI_ADV_DEFAULT_STD) {
return;
}
- uint8_t data[BTM_BLE_AD_DATA_LEN], *pp = data;
- memset(data, 0, BTM_BLE_AD_DATA_LEN);
-
- btm_ble_build_adv_data(&data_mask, &pp, p_data);
- uint8_t len = (uint8_t)(pp - data);
-
- VLOG(1) << "data is: " << base::HexEncode(data, len);
+ VLOG(1) << "data is: " << base::HexEncode(data.data(), data.size());
if (is_scan_rsp) {
- GetHciInterface()->SetScanResponseData(len, data, inst_id, cb);
+ GetHciInterface()->SetScanResponseData(data.size(), data.data(), inst_id,
+ cb);
} else {
- GetHciInterface()->SetAdvertisingData(len, data, inst_id, cb);
+ GetHciInterface()->SetAdvertisingData(data.size(), data.data(), inst_id,
+ cb);
}
}
#define BLE_ADVERTISER_H
#include <base/bind.h>
+#include <vector>
#include "btm_ble_api.h"
#define BTM_BLE_MULTI_ADV_DEFAULT_STD 0
const uint16_t connect_mode,
const uint16_t disc_mode);
void btm_gen_resolvable_private_addr(void *p_cmd_cplt_cback);
-uint8_t *btm_ble_build_adv_data(tBTM_BLE_AD_MASK *p_data_mask, uint8_t **p_dst,
- tBTM_BLE_ADV_DATA *p_data);
void btm_acl_update_conn_addr(uint8_t conn_handle, BD_ADDR address);
// methods we expose to c code:
void btm_ble_multi_adv_cleanup(void);
void btm_ble_multi_adv_init();
-char btm_ble_map_adv_tx_power(int tx_power_index);
}
typedef struct {
/* This function enables/disables an advertising instance. Operation status is
* returned in |cb| */
- virtual void Enable(uint8_t inst_id, bool enable, MultiAdvCb cb);
+ virtual void Enable(uint8_t inst_id, bool enable, MultiAdvCb cb, int timeout_s,
+ MultiAdvCb timeout_cb);
/* This function update a Multi-ADV instance with the specififed adv
* parameters. */
/* This function configure a Multi-ADV instance with the specified adv data or
* scan response data.*/
virtual void SetData(uint8_t inst_id, bool is_scan_rsp,
- tBTM_BLE_AD_MASK data_mask, tBTM_BLE_ADV_DATA *p_data,
- MultiAdvCb cb);
+ std::vector<uint8_t> data, MultiAdvCb cb);
/* This function disable a Multi-ADV instance */
virtual void Unregister(uint8_t inst_id);
** Returns void
**
*******************************************************************************/
-extern void BTM_BleWriteAdvData(tBTM_BLE_AD_MASK data_mask, tBTM_BLE_ADV_DATA *p_data,
+extern void BTM_BleWriteAdvData(uint8_t* data, uint8_t length,
tBTM_BLE_ADV_DATA_CMPL_CBACK *p_adv_data_cback);
/*******************************************************************************
** Returns status
**
*******************************************************************************/
-extern void BTM_BleWriteScanRsp(tBTM_BLE_AD_MASK data_mask, tBTM_BLE_ADV_DATA *p_data,
+extern void BTM_BleWriteScanRsp(uint8_t* data, uint8_t length,
tBTM_BLE_ADV_DATA_CMPL_CBACK *p_adv_data_cback);
/*******************************************************************************
#define BTM_BLE_ADV_FLAG_MASK (BTM_BLE_LIMIT_DISC_FLAG | BTM_BLE_BREDR_NOT_SPT | BTM_BLE_GEN_DISC_FLAG)
#define BTM_BLE_LIMIT_DISC_MASK (BTM_BLE_LIMIT_DISC_FLAG )
-#define BTM_BLE_AD_BIT_DEV_NAME (0x00000001 << 0)
+//TODO(jpawlowski): this should be removed with code that depend on it.
#define BTM_BLE_AD_BIT_FLAGS (0x00000001 << 1)
-#define BTM_BLE_AD_BIT_MANU (0x00000001 << 2)
-#define BTM_BLE_AD_BIT_TX_PWR (0x00000001 << 3)
-#define BTM_BLE_AD_BIT_INT_RANGE (0x00000001 << 5)
-#define BTM_BLE_AD_BIT_SERVICE (0x00000001 << 6)
-#define BTM_BLE_AD_BIT_SERVICE_SOL (0x00000001 << 7)
-#define BTM_BLE_AD_BIT_SERVICE_DATA (0x00000001 << 8)
-#define BTM_BLE_AD_BIT_SIGN_DATA (0x00000001 << 9)
-#define BTM_BLE_AD_BIT_SERVICE_128SOL (0x00000001 << 10)
-#define BTM_BLE_AD_BIT_APPEARANCE (0x00000001 << 11)
-#define BTM_BLE_AD_BIT_PUBLIC_ADDR (0x00000001 << 12)
-#define BTM_BLE_AD_BIT_RANDOM_ADDR (0x00000001 << 13)
-#define BTM_BLE_AD_BIT_SERVICE_32 (0x00000001 << 4)
-#define BTM_BLE_AD_BIT_SERVICE_32SOL (0x00000001 << 14)
-#define BTM_BLE_AD_BIT_PROPRIETARY (0x00000001 << 15)
-#define BTM_BLE_AD_BIT_SERVICE_128 (0x00000001 << 16) /*128-bit Service UUIDs*/
-
-typedef uint32_t tBTM_BLE_AD_MASK;
#define BTM_BLE_AD_TYPE_FLAG HCI_EIR_FLAGS_TYPE /* 0x01 */
-#define BTM_BLE_AD_TYPE_16SRV_PART HCI_EIR_MORE_16BITS_UUID_TYPE /* 0x02 */
#define BTM_BLE_AD_TYPE_16SRV_CMPL HCI_EIR_COMPLETE_16BITS_UUID_TYPE /* 0x03 */
-#define BTM_BLE_AD_TYPE_32SRV_PART HCI_EIR_MORE_32BITS_UUID_TYPE /* 0x04 */
-#define BTM_BLE_AD_TYPE_32SRV_CMPL HCI_EIR_COMPLETE_32BITS_UUID_TYPE /* 0x05 */
-#define BTM_BLE_AD_TYPE_128SRV_PART HCI_EIR_MORE_128BITS_UUID_TYPE /* 0x06 */
-#define BTM_BLE_AD_TYPE_128SRV_CMPL HCI_EIR_COMPLETE_128BITS_UUID_TYPE /* 0x07 */
#define BTM_BLE_AD_TYPE_NAME_SHORT HCI_EIR_SHORTENED_LOCAL_NAME_TYPE /* 0x08 */
#define BTM_BLE_AD_TYPE_NAME_CMPL HCI_EIR_COMPLETE_LOCAL_NAME_TYPE /* 0x09 */
-#define BTM_BLE_AD_TYPE_TX_PWR HCI_EIR_TX_POWER_LEVEL_TYPE /* 0x0A */
-#define BTM_BLE_AD_TYPE_DEV_CLASS 0x0D
-#define BTM_BLE_AD_TYPE_SM_TK 0x10
-#define BTM_BLE_AD_TYPE_SM_OOB_FLAG 0x11
-#define BTM_BLE_AD_TYPE_INT_RANGE 0x12
-#define BTM_BLE_AD_TYPE_SOL_SRV_UUID 0x14
-#define BTM_BLE_AD_TYPE_128SOL_SRV_UUID 0x15
-#define BTM_BLE_AD_TYPE_SERVICE_DATA 0x16
-#define BTM_BLE_AD_TYPE_PUBLIC_TARGET 0x17
-#define BTM_BLE_AD_TYPE_RANDOM_TARGET 0x18
-#define BTM_BLE_AD_TYPE_APPEARANCE 0x19
-#define BTM_BLE_AD_TYPE_ADV_INT 0x1a
-#define BTM_BLE_AD_TYPE_32SOL_SRV_UUID 0x1b
-#define BTM_BLE_AD_TYPE_32SERVICE_DATA 0x1c
-#define BTM_BLE_AD_TYPE_128SERVICE_DATA 0x1d
-#define BTM_BLE_AD_TYPE_MANU HCI_EIR_MANUFACTURER_SPECIFIC_TYPE /* 0xff */
-typedef uint8_t tBTM_BLE_AD_TYPE;
+#define BTM_BLE_AD_TYPE_APPEARANCE 0x19
/* Security settings used with L2CAP LE COC */
#define BTM_SEC_LE_LINK_ENCRYPTED 0x01
uint8_t debug_logging_supported;
}tBTM_BLE_VSC_CB;
-/* slave preferred connection interval range */
-typedef struct
-{
- uint16_t low;
- uint16_t hi;
-
-}tBTM_BLE_INT_RANGE;
-
-/* Service tag supported in the device */
-#define MAX_16BIT_SERVICES 16
-typedef struct
-{
- uint8_t num_service;
- bool list_cmpl;
- uint16_t uuid[MAX_16BIT_SERVICES];
-}tBTM_BLE_SERVICE;
-
-/* 32 bits Service supported in the device */
-#define MAX_32BIT_SERVICES 4
-typedef struct
-{
- uint8_t num_service;
- bool list_cmpl;
- uint32_t uuid[MAX_32BIT_SERVICES];
-}tBTM_BLE_32SERVICE;
-
-/* 128 bits Service supported in the device */
-typedef struct
-{
- uint8_t num_service;
- bool list_cmpl;
- uint8_t uuid128[MAX_UUID_SIZE];
-}tBTM_BLE_128SERVICE;
-
-#define MAX_SIZE_MANUFACTURER_DATA 32
-typedef struct
-{
- uint8_t len;
- uint8_t val[MAX_SIZE_MANUFACTURER_DATA];
-}tBTM_BLE_MANU;
-
-#define MAX_SIZE_SERVICE_DATA 32
-typedef struct
-{
- tBT_UUID service_uuid;
- uint8_t len;
- uint8_t val[MAX_SIZE_SERVICE_DATA];
-}tBTM_BLE_SERVICE_DATA;
-
-#define MAX_SIZE_PROPRIETARY_ELEMENT 32
-typedef struct
-{
- uint8_t adv_type;
- uint8_t len;
- uint8_t val[MAX_SIZE_PROPRIETARY_ELEMENT]; /* number of len byte */
-}tBTM_BLE_PROP_ELEM;
-
-#define MAX_PROPRIETARY_ELEMENTS 4
-typedef struct
-{
- uint8_t num_elem;
- tBTM_BLE_PROP_ELEM elem[MAX_PROPRIETARY_ELEMENTS];
-}tBTM_BLE_PROPRIETARY;
-
-typedef struct
-{
- tBTM_BLE_INT_RANGE int_range; /* slave prefered conn interval range */
- tBTM_BLE_MANU manu; /* manufactuer data */
- tBTM_BLE_SERVICE services; /* services */
- tBTM_BLE_128SERVICE services_128b; /* 128 bits service */
- tBTM_BLE_32SERVICE service_32b; /* 32 bits Service UUID */
- tBTM_BLE_SERVICE sol_services; /* 16 bits services Solicitation UUIDs */
- tBTM_BLE_32SERVICE sol_service_32b; /* List of 32 bit Service Solicitation UUIDs */
- tBTM_BLE_128SERVICE sol_service_128b; /* List of 128 bit Service Solicitation UUIDs */
- tBTM_BLE_PROPRIETARY proprietary;
- tBTM_BLE_SERVICE_DATA service_data; /* service data */
- uint16_t appearance;
- uint8_t flag;
- uint8_t tx_power;
-}tBTM_BLE_ADV_DATA;
-
typedef void (tBTM_BLE_ADV_DATA_CMPL_CBACK) (tBTM_STATUS status);
#ifndef BTM_BLE_MULTI_ADV_MAX
typedef uint8_t BTM_BLE_RSSI_VALUE;
typedef uint16_t BTM_BLE_ADV_INFO_TIMESTAMP;
-/* These are the fields returned in each device adv packet. It
-** is returned in the results callback if registered.
-*/
-typedef struct
-{
- uint8_t conn_mode;
- tBTM_BLE_AD_MASK ad_mask; /* mask of the valid adv data field */
- uint8_t flag;
- uint8_t tx_power_level;
- uint8_t remote_name_len;
- uint8_t *p_remote_name;
- tBTM_BLE_SERVICE service;
-} tBTM_BLE_INQ_DATA;
-
enum
{
BTM_BLE_CONN_NONE,
#include "stack/include/ble_advertiser.h"
using ::testing::_;
+using ::testing::Args;
+using ::testing::ElementsAreArray;
+using ::testing::IsEmpty;
using ::testing::SaveArg;
using status_cb = BleAdvertiserHciInterface::status_cb;
}
void BTM_GetDeviceIDRoot(BT_OCTET16 irk) {}
tBTM_STATUS btm_ble_set_connectability(uint16_t combined_mode) { return 0; }
-uint8_t *btm_ble_build_adv_data(tBTM_BLE_AD_MASK *p_data_mask, uint8_t **p_dst,
- tBTM_BLE_ADV_DATA *p_data) {
- return nullptr;
-}
void btm_ble_update_dmt_flag_bits(uint8_t *flag_value,
const uint16_t connect_mode,
const uint16_t disc_mode) {}
}
void alarm_cancel(alarm_t *alarm) {}
alarm_t *alarm_new_periodic(const char *name) { return nullptr; }
+alarm_t *alarm_new(const char *name) { return nullptr; }
void alarm_free(alarm_t *alarm) {}
const controller_t *controller_get_interface() { return nullptr; }
fixed_queue_t *btu_general_alarm_queue = nullptr;
AdvertiserHciMock() = default;
~AdvertiserHciMock() override = default;
- MOCK_METHOD4(SetAdvertisingData, void(uint8_t, uint8_t *, uint8_t, status_cb));
- MOCK_METHOD4(SetScanResponseData, void(uint8_t, uint8_t *, uint8_t, status_cb));
+ MOCK_METHOD4(SetAdvertisingData,
+ void(uint8_t, uint8_t *, uint8_t, status_cb));
+ MOCK_METHOD4(SetScanResponseData,
+ void(uint8_t, uint8_t *, uint8_t, status_cb));
MOCK_METHOD3(SetRandomAddress, void(BD_ADDR, uint8_t, status_cb));
MOCK_METHOD3(Enable, void(uint8_t, uint8_t, status_cb));
void(BD_ADDR, uint8_t, uint8_t, uint8_t, uint8_t, status_cb));
void SetParameters(uint8_t adv_int_min, uint8_t adv_int_max,
- uint8_t advertising_type, uint8_t own_address_type,
- BD_ADDR own_address, uint8_t direct_address_type,
- BD_ADDR direct_address, uint8_t channel_map,
- uint8_t filter_policy, uint8_t instance, uint8_t tx_power,
- status_cb cmd_complete) override {
+ uint8_t advertising_type, uint8_t own_address_type,
+ BD_ADDR own_address, uint8_t direct_address_type,
+ BD_ADDR direct_address, uint8_t channel_map,
+ uint8_t filter_policy, uint8_t instance, uint8_t tx_power,
+ status_cb cmd_complete) override {
SetParameters1(adv_int_min, adv_int_max, advertising_type, own_address_type,
- own_address, direct_address_type);
- SetParameters2(direct_address, channel_map, filter_policy, instance, tx_power,
- cmd_complete);
+ own_address, direct_address_type);
+ SetParameters2(direct_address, channel_map, filter_policy, instance,
+ tx_power, cmd_complete);
};
private:
.Times(1)
.WillOnce(SaveArg<3>(&set_data_cb));
BleAdvertisingManager::Get()->SetData(
- advertiser_id, false, 0, nullptr,
+ advertiser_id, false, std::vector<uint8_t>(),
base::Bind(&BleAdvertisingManagerTest::SetDataCb,
base::Unretained(this)));
set_data_cb.Run(0);
.WillOnce(SaveArg<2>(&enable_cb));
BleAdvertisingManager::Get()->Enable(
advertiser_id, true,
- base::Bind(&BleAdvertisingManagerTest::EnableCb, base::Unretained(this)));
+ base::Bind(&BleAdvertisingManagerTest::EnableCb, base::Unretained(this)),
+ 0, base::Callback<void(uint8_t)>());
enable_cb.Run(0);
EXPECT_EQ(BTM_BLE_MULTI_ADV_SUCCESS, enable_status);
::testing::Mock::VerifyAndClearExpectations(hci_mock.get());
EXPECT_EQ(BTM_BLE_MULTI_ADV_SUCCESS, enable_status);
::testing::Mock::VerifyAndClearExpectations(hci_mock.get());
}
+
+/* This test verifies that when advertising data is set, tx power and flags will
+ * be properly filled. */
+TEST_F(BleAdvertisingManagerTest, test_adv_data_filling) {
+ BleAdvertisingManager::Get()->RegisterAdvertiser(base::Bind(
+ &BleAdvertisingManagerTest::RegistrationCb, base::Unretained(this)));
+ EXPECT_EQ(BTM_BLE_MULTI_ADV_SUCCESS, reg_status);
+ int advertiser_id = reg_inst_id;
+
+ status_cb set_params_cb;
+ tBTM_BLE_ADV_PARAMS params;
+ params.adv_type = BTM_BLE_CONNECT_EVT;
+ params.tx_power = -15;
+ EXPECT_CALL(*hci_mock, SetParameters1(_, _, _, _, _, _)).Times(1);
+ EXPECT_CALL(*hci_mock, SetParameters2(_, _, _, advertiser_id,
+ (uint8_t)params.tx_power, _))
+ .Times(1)
+ .WillOnce(SaveArg<5>(&set_params_cb));
+ BleAdvertisingManager::Get()->SetParameters(
+ advertiser_id, ¶ms,
+ base::Bind(&BleAdvertisingManagerTest::SetParametersCb,
+ base::Unretained(this)));
+
+ // let the set parameters command succeed!
+ set_params_cb.Run(0);
+ EXPECT_EQ(BTM_BLE_MULTI_ADV_SUCCESS, set_params_status);
+ ::testing::Mock::VerifyAndClearExpectations(hci_mock.get());
+
+ status_cb set_data_cb;
+ /* verify that flags will be added, and tx power filled, if call to SetData
+ * contained only tx power, and the advertisement is connectable */
+ uint8_t expected_adv_data[] = {0x02 /* len */, 0x01 /* flags */,
+ 0x02 /* flags value */, 0x02 /* len */,
+ 0x0A /* tx_power */, params.tx_power};
+ EXPECT_CALL(*hci_mock, SetAdvertisingData(_, _, advertiser_id, _))
+ .With(Args<1, 0>(ElementsAreArray(expected_adv_data)))
+ .Times(1)
+ .WillOnce(SaveArg<3>(&set_data_cb));
+ BleAdvertisingManager::Get()->SetData(
+ advertiser_id, false,
+ std::vector<uint8_t>({0x02 /* len */, 0x0A /* tx_power */, 0x00}),
+ base::Bind(&BleAdvertisingManagerTest::SetDataCb,
+ base::Unretained(this)));
+ set_data_cb.Run(0);
+ EXPECT_EQ(BTM_BLE_MULTI_ADV_SUCCESS, set_data_status);
+ ::testing::Mock::VerifyAndClearExpectations(hci_mock.get());
+}
+
+/* This test verifies that when advertising is non-connectable, flags will not
+ * be added. */
+TEST_F(BleAdvertisingManagerTest, test_adv_data_not_filling) {
+ BleAdvertisingManager::Get()->RegisterAdvertiser(base::Bind(
+ &BleAdvertisingManagerTest::RegistrationCb, base::Unretained(this)));
+ EXPECT_EQ(BTM_BLE_MULTI_ADV_SUCCESS, reg_status);
+ int advertiser_id = reg_inst_id;
+
+ status_cb set_params_cb;
+ tBTM_BLE_ADV_PARAMS params;
+ params.adv_type = BTM_BLE_NON_CONNECT_EVT;
+ params.tx_power = -15;
+ EXPECT_CALL(*hci_mock, SetParameters1(_, _, _, _, _, _)).Times(1);
+ EXPECT_CALL(*hci_mock, SetParameters2(_, _, _, advertiser_id,
+ (uint8_t)params.tx_power, _))
+ .Times(1)
+ .WillOnce(SaveArg<5>(&set_params_cb));
+ BleAdvertisingManager::Get()->SetParameters(
+ advertiser_id, ¶ms,
+ base::Bind(&BleAdvertisingManagerTest::SetParametersCb,
+ base::Unretained(this)));
+
+ // let the set parameters command succeed!
+ set_params_cb.Run(0);
+ EXPECT_EQ(BTM_BLE_MULTI_ADV_SUCCESS, set_params_status);
+ ::testing::Mock::VerifyAndClearExpectations(hci_mock.get());
+
+ status_cb set_data_cb;
+ /* verify that flags will not be added */
+ uint8_t expected_adv_data[] = {
+ 0x02 /* len */, 0xFF /* manufacturer specific */, 0x01 /* data */};
+ EXPECT_CALL(*hci_mock, SetAdvertisingData(_, _, advertiser_id, _))
+ .With(Args<1, 0>(ElementsAreArray(expected_adv_data)))
+ .Times(1)
+ .WillOnce(SaveArg<3>(&set_data_cb));
+ BleAdvertisingManager::Get()->SetData(
+ advertiser_id, false, std::vector<uint8_t>({0x02 /* len */, 0xFF, 0x01}),
+ base::Bind(&BleAdvertisingManagerTest::SetDataCb,
+ base::Unretained(this)));
+ set_data_cb.Run(0);
+ EXPECT_EQ(BTM_BLE_MULTI_ADV_SUCCESS, set_data_status);
+ ::testing::Mock::VerifyAndClearExpectations(hci_mock.get());
+}