./jv/bta_jv_cfg.c \
./jv/bta_jv_main.c \
./jv/bta_jv_api.c \
- ../vnd/ble/bta_vendor.c
LOCAL_MODULE := libbt-brcm_bta
LOCAL_MODULE_CLASS := STATIC_LIBRARIES
/******************************************************************************
*
- * Copyright (C) 2003-2012 Broadcom Corporation
+ * Copyright (C) 2003-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.
bta_dm_cb.p_setup_cback(bta_evt, ref_value, status);
}
+
+#if BLE_ANDROID_CONTROLLER_SCAN_FILTER == TRUE
+/*******************************************************************************
+**
+** Function bta_ble_scan_pf_cmpl
+**
+** Description ADV payload filtering operation complete callback
+**
+**
+** Returns TRUE if handled, otherwise FALSE.
+**
+*******************************************************************************/
+static void bta_ble_scan_cfg_cmpl(tBTM_BLE_PF_ACTION action, tBTM_BLE_SCAN_COND_OP cfg_op,
+ tBTM_BLE_PF_AVBL_SPACE avbl_space, tBTM_STATUS status,
+ tBTM_BLE_REF_VALUE ref_value)
+{
+ tBTA_STATUS st = (status == BTM_SUCCESS) ? BTA_SUCCESS: BTA_FAILURE;
+
+ APPL_TRACE_DEBUG("bta_ble_scan_cfg_cmpl: %d, %d, %d, %d", action, cfg_op, avbl_space, status);
+
+ if(bta_dm_cb.p_scan_filt_cfg_cback)
+ bta_dm_cb.p_scan_filt_cfg_cback(action, cfg_op, avbl_space, st, ref_value);
+}
+
+/*******************************************************************************
+**
+** Function bta_ble_enable_scan_cmpl
+**
+** Description ADV payload filtering enable / disable complete callback
+**
+**
+** Returns None
+**
+*******************************************************************************/
+static void bta_ble_status_cmpl(tBTM_BLE_PF_ACTION action, tBTM_BLE_REF_VALUE ref_value,
+ tBTM_STATUS status)
+{
+ tBTA_STATUS st = (status == BTM_SUCCESS) ? BTA_SUCCESS: BTA_FAILURE;
+
+ APPL_TRACE_DEBUG("bta_ble_status_cmpl: %d, %d", action, status);
+
+ if(bta_dm_cb.p_scan_filt_status_cback)
+ bta_dm_cb.p_scan_filt_status_cback(action, ref_value, st);
+}
+
+/*******************************************************************************
+**
+** Function bta_dm_cfg_filter_cond
+**
+** Description This function configure adv payload filtering condition
+**
+** Parameters:
+**
+*******************************************************************************/
+void bta_dm_cfg_filter_cond (tBTA_DM_MSG *p_data)
+{
+ tBTM_STATUS st = BTM_MODE_UNSUPPORTED;
+ tBTA_STATUS status = BTA_FAILURE;
+
+ tBTM_BLE_VSC_CB cmn_vsc_cb;
+
+ APPL_TRACE_DEBUG("bta_dm_cfg_filter_cond");
+ BTM_BleGetVendorCapabilities(&cmn_vsc_cb);
+ if(0 != cmn_vsc_cb.filter_support)
+ {
+ if ((st = BTM_BleCfgFilterCondition(p_data->ble_cfg_filter_cond.action,
+ p_data->ble_cfg_filter_cond.cond_type,
+ (tBTM_BLE_PF_FILT_INDEX)p_data->ble_cfg_filter_cond.filt_index,
+ (tBTM_BLE_PF_COND_PARAM *)p_data->ble_cfg_filter_cond.p_cond_param,
+ bta_ble_scan_cfg_cmpl, p_data->ble_cfg_filter_cond.ref_value))
+ == BTM_CMD_STARTED)
+ {
+ bta_dm_cb.p_scan_filt_cfg_cback = p_data->ble_cfg_filter_cond.p_filt_cfg_cback;
+ return;
+ }
+ }
+
+ if (p_data->ble_cfg_filter_cond.p_filt_cfg_cback)
+ p_data->ble_cfg_filter_cond.p_filt_cfg_cback(BTA_DM_BLE_PF_CONFIG_EVT,
+ p_data->ble_cfg_filter_cond.cond_type, 0, status,
+ p_data->ble_cfg_filter_cond.ref_value);
+ return;
+}
+
+/*******************************************************************************
+**
+** Function bta_dm_enable_scan_filter
+**
+** Description This function enable/disable adv payload filtering condition
+**
+** Parameters:
+**
+*******************************************************************************/
+void bta_dm_enable_scan_filter(tBTA_DM_MSG *p_data)
+{
+ tBTM_STATUS st = BTM_MODE_UNSUPPORTED;
+ tBTA_STATUS status = BTA_FAILURE;
+
+ tBTM_BLE_VSC_CB cmn_vsc_cb;
+ APPL_TRACE_DEBUG("bta_dm_enable_scan_filter");
+ BTM_BleGetVendorCapabilities(&cmn_vsc_cb);
+
+ if(0 != cmn_vsc_cb.filter_support)
+ {
+ if((st = BTM_BleEnableDisableFilterFeature(p_data->ble_enable_scan_filt.action,
+ p_data->ble_enable_scan_filt.p_filt_status_cback,
+ (tBTM_BLE_REF_VALUE)p_data->ble_enable_scan_filt.ref_value)) == BTM_CMD_STARTED)
+ bta_dm_cb.p_scan_filt_status_cback = p_data->ble_enable_scan_filt.p_filt_status_cback;
+ return;
+ }
+
+ if (p_data->ble_enable_scan_filt.p_filt_status_cback)
+ p_data->ble_enable_scan_filt.p_filt_status_cback (BTA_DM_BLE_PF_ENABLE_EVT,
+ p_data->ble_enable_scan_filt.ref_value, status);
+
+}
+/*******************************************************************************
+**
+** Function bta_dm_scan_filter_param_setup
+**
+** Description This function sets up scan filter params
+**
+** Parameters:
+**
+*******************************************************************************/
+void bta_dm_scan_filter_param_setup (tBTA_DM_MSG *p_data)
+{
+ tBTM_STATUS st = BTM_MODE_UNSUPPORTED;
+ tBTA_STATUS status = BTA_FAILURE;
+
+ tBTM_BLE_VSC_CB cmn_vsc_cb;
+
+ APPL_TRACE_DEBUG("bta_dm_scan_filter_param_setup");
+ BTM_BleGetVendorCapabilities(&cmn_vsc_cb);
+ if(0 != cmn_vsc_cb.filter_support)
+ {
+ if ((st = BTM_BleAdvFilterParamSetup(p_data->ble_scan_filt_param_setup.action,
+ p_data->ble_scan_filt_param_setup.filt_index,
+ (tBTM_BLE_PF_FILT_PARAMS *)p_data->ble_scan_filt_param_setup.p_filt_params,
+ p_data->ble_scan_filt_param_setup.p_target,
+ p_data->ble_scan_filt_param_setup.p_filt_param_cback,
+ p_data->ble_scan_filt_param_setup.ref_value)) == BTM_CMD_STARTED)
+ {
+ bta_dm_cb.p_scan_filt_param_cback = p_data->ble_scan_filt_param_setup.p_filt_param_cback;
+ return;
+ }
+ }
+
+ if (p_data->ble_scan_filt_param_setup.p_filt_param_cback)
+ p_data->ble_scan_filt_param_setup.p_filt_param_cback (BTA_DM_BLE_PF_ENABLE_EVT, 0,
+ p_data->ble_scan_filt_param_setup.ref_value, status);
+
+ return;
+}
+#endif
+
#if ((defined BTA_GATT_INCLUDED) && (BTA_GATT_INCLUDED == TRUE))
#ifndef BTA_DM_GATT_CLOSE_DELAY_TOUT
#define BTA_DM_GATT_CLOSE_DELAY_TOUT 1000
#endif /* BTA_GATT_INCLUDED */
-#if BLE_ANDROID_CONTROLLER_SCAN_FILTER == TRUE
-/*******************************************************************************
-**
-** Function bta_dm_enable_scan_filter
-**
-** Description This function enable/disable adv payload filtering condition
-**
-** Parameters:
-**
-*******************************************************************************/
-void bta_dm_enable_scan_filter (tBTA_DM_MSG *p_data)
-{
- tBTA_SYS_VS_BLE_SCAN_PF_ENABLE param;
-
- param.enable = p_data->ble_enable_scan_filter.enable;
- param.p_target = p_data->ble_enable_scan_filter.p_target;
- param.p_cmpl_cback = p_data->ble_enable_scan_filter.p_cmpl_cback;
-
- bta_sys_vs_hdl(BTA_VS_BLE_SCAN_PF_ENABLE_EVT, (void *)¶m);
-}
-
-/*******************************************************************************
-**
-** Function bta_dm_cfg_filter_cond
-**
-** Description This function configure adv payload filtering condition
-**
-** Parameters:
-**
-*******************************************************************************/
-void bta_dm_cfg_filter_cond (tBTA_DM_MSG *p_data)
-{
- tBTA_SYS_VS_BLE_SCAN_PF_COND param;
-
- param.action = p_data->ble_cfg_filter_cond.action;
- param.cond_type = p_data->ble_cfg_filter_cond.cond_type;
- param.p_cond = (void *)p_data->ble_cfg_filter_cond.p_cond_param;
- param.p_cmpl_cback = p_data->ble_cfg_filter_cond.p_cmpl_cback;
-
- bta_sys_vs_hdl(BTA_VS_BLE_SCAN_PF_COND_EVT, (void *)¶m);
-}
-#endif /* BLE_ANDROID_CONTROLLER_SCAN_FILTER */
-
/*******************************************************************************
**
** Function bta_dm_ctrl_features_rd_cmpl_cback
** scan_window - Scan window
** discard_rule -Discard rules
** addr_type - Address type
+** ref_value - Reference value
**
** Returns None
**
**
** Description This function is called to disable the batch scan
**
-** Parameters
+** Parameters ref_value - Reference value
**
** Returns None
**
** Description This function is called to read scan reports
**
** Parameters scan_type -Batch scan mode
+** ref_value - Reference value
**
** Returns None
**
/*******************************************************************************
**
+** Function BTA_DmBleCfgFilterCondition
+**
+** Description This function is called to configure the adv data payload filter
+** condition.
+**
+** Parameters action: to read/write/clear
+** cond_type: filter condition type
+** filt_index - Filter index
+** p_cond: filter condition parameter
+** p_cmpl_back - Command completed callback
+** ref_value - Reference value
+**
+** Returns void
+**
+*******************************************************************************/
+void BTA_DmBleCfgFilterCondition(tBTA_DM_BLE_SCAN_COND_OP action,
+ tBTA_DM_BLE_PF_COND_TYPE cond_type,
+ tBTA_DM_BLE_PF_FILT_INDEX filt_index,
+ tBTA_DM_BLE_PF_COND_PARAM *p_cond,
+ tBTA_DM_BLE_PF_CFG_CBACK *p_cmpl_cback,
+ tBTA_DM_BLE_REF_VALUE ref_value)
+{
+#if BLE_ANDROID_CONTROLLER_SCAN_FILTER == TRUE
+ tBTA_DM_API_CFG_FILTER_COND *p_msg;
+ APPL_TRACE_API ("BTA_DmBleCfgFilterCondition: %d, %d", action, cond_type);
+
+ UINT16 len = sizeof(tBTA_DM_API_CFG_FILTER_COND) + sizeof(tBTA_DM_BLE_PF_COND_PARAM) + \
+ BTM_BLE_PF_STR_LEN_MAX + BTM_BLE_PF_STR_LEN_MAX + sizeof(tBTA_DM_BLE_PF_COND_MASK);
+
+ UINT8 *p;
+
+ if ((p_msg = (tBTA_DM_API_CFG_FILTER_COND *) GKI_getbuf(len)) != NULL)
+ {
+ memset (p_msg, 0, len);
+
+ p_msg->hdr.event = BTA_DM_API_CFG_FILTER_COND_EVT;
+ p_msg->action = action;
+ p_msg->cond_type = cond_type;
+ p_msg->filt_index = filt_index;
+ p_msg->p_filt_cfg_cback = p_cmpl_cback;
+ p_msg->ref_value = ref_value;
+ if (p_cond)
+ {
+ p_msg->p_cond_param = (tBTA_DM_BLE_PF_COND_PARAM *)(p_msg + 1);
+ memcpy(p_msg->p_cond_param, p_cond, sizeof(tBTA_DM_BLE_PF_COND_PARAM));
+
+ p = (UINT8 *)(p_msg->p_cond_param + 1);
+
+ if (cond_type == BTA_DM_BLE_PF_SRVC_DATA_PATTERN ||
+ cond_type == BTA_DM_BLE_PF_MANU_DATA)
+ {
+ p_msg->p_cond_param->manu_data.p_pattern = p;
+ p_msg->p_cond_param->manu_data.data_len = p_cond->manu_data.data_len;
+ memcpy(p_msg->p_cond_param->manu_data.p_pattern, p_cond->manu_data.p_pattern,
+ p_cond->manu_data.data_len);
+ p += p_cond->manu_data.data_len;
+
+ if (cond_type == BTA_DM_BLE_PF_MANU_DATA)
+ {
+ p_msg->p_cond_param->manu_data.company_id_mask =
+ p_cond->manu_data.company_id_mask;
+ if ( p_cond->manu_data.p_pattern_mask != NULL)
+ {
+ p_msg->p_cond_param->manu_data.p_pattern_mask = p;
+ memcpy(p_msg->p_cond_param->manu_data.p_pattern_mask,
+ p_cond->manu_data.p_pattern_mask, p_cond->manu_data.data_len);
+ }
+ }
+ }
+ else if (cond_type == BTA_DM_BLE_PF_LOCAL_NAME)
+ {
+ p_msg->p_cond_param->local_name.p_data = p;
+ memcpy(p_msg->p_cond_param->local_name.p_data,
+ p_cond->local_name.p_data, p_cond->local_name.data_len);
+ }
+ else if ((cond_type == BTM_BLE_PF_SRVC_UUID || cond_type == BTM_BLE_PF_SRVC_SOL_UUID))
+ {
+ if (p_cond->srvc_uuid.p_target_addr != NULL)
+ {
+ p_msg->p_cond_param->srvc_uuid.p_target_addr = (tBLE_BD_ADDR *)(p);
+ p_msg->p_cond_param->srvc_uuid.p_target_addr->type =
+ p_cond->srvc_uuid.p_target_addr->type;
+ memcpy(p_msg->p_cond_param->srvc_uuid.p_target_addr->bda,
+ p_cond->srvc_uuid.p_target_addr->bda, BD_ADDR_LEN);
+ p = (UINT8*)( p_msg->p_cond_param->srvc_uuid.p_target_addr + 1);
+ }
+ if (p_cond->srvc_uuid.p_uuid_mask)
+ {
+ p_msg->p_cond_param->srvc_uuid.p_uuid_mask = (tBTA_DM_BLE_PF_COND_MASK *)p;
+ memcpy(p_msg->p_cond_param->srvc_uuid.p_uuid_mask,
+ p_cond->srvc_uuid.p_uuid_mask, sizeof(tBTA_DM_BLE_PF_COND_MASK));
+ }
+ }
+ }
+
+ bta_sys_sendmsg(p_msg);
+ }
+#else
+ UNUSED(action);
+ UNUSED(cond_type);
+ UNUSED(filt_index);
+ UNUSED(p_cond);
+ UNUSED(p_cmpl_cback);
+ UNUSED(ref_value);
+#endif
+}
+
+/*******************************************************************************
+**
+** Function BTA_DmBleScanFilterSetup
+**
+** Description This function is called to setup the adv data payload filter param
+**
+** Parameters p_target: enable the filter condition on a target device; if NULL
+** filt_index - Filter index
+** p_filt_params -Filter parameters
+** ref_value - Reference value
+** action - Add, delete or clear
+** p_cmpl_back - Command completed callback
+**
+** Returns void
+**
+*******************************************************************************/
+void BTA_DmBleScanFilterSetup(UINT8 action, tBTA_DM_BLE_PF_FILT_INDEX filt_index,
+ tBTA_DM_BLE_PF_FILT_PARAMS *p_filt_params,
+ tBLE_BD_ADDR *p_target,
+ tBTA_DM_BLE_PF_PARAM_CBACK *p_cmpl_cback,
+ tBTA_DM_BLE_REF_VALUE ref_value)
+{
+#if BLE_ANDROID_CONTROLLER_SCAN_FILTER == TRUE
+ tBTA_DM_API_SCAN_FILTER_PARAM_SETUP *p_msg;
+ APPL_TRACE_API ("BTA_DmBleScanFilterSetup: %d", action);
+
+ UINT16 len = sizeof(tBTA_DM_API_SCAN_FILTER_PARAM_SETUP) + sizeof(tBLE_BD_ADDR);
+
+ if ((p_msg = (tBTA_DM_API_SCAN_FILTER_PARAM_SETUP *) GKI_getbuf(len)) != NULL)
+ {
+ memset (p_msg, 0, len);
+
+ p_msg->hdr.event = BTA_DM_API_SCAN_FILTER_SETUP_EVT;
+ p_msg->action = action;
+ p_msg->filt_index = filt_index;
+ p_msg->p_filt_params = p_filt_params;
+ p_msg->p_filt_param_cback = p_cmpl_cback;
+ p_msg->ref_value = ref_value;
+
+ if (p_target)
+ {
+ p_msg->p_target = (tBLE_BD_ADDR *)(p_msg + 1);
+ memcpy(p_msg->p_target, p_target, sizeof(tBLE_BD_ADDR));
+ }
+
+ bta_sys_sendmsg(p_msg);
+ }
+#else
+ UNUSED(action);
+ UNUSED(filt_index);
+ UNUSED(p_filt_params);
+ UNUSED(p_target);
+ UNUSED(p_cmpl_cback);
+ UNUSED(ref_value);
+#endif
+}
+
+/*******************************************************************************
+**
+** Function BTA_DmEnableScanFilter
+**
+** Description This function is called to enable the adv data payload filter
+**
+** Parameters action - enable or disable the APCF feature
+** p_cmpl_cback - Command completed callback
+** ref_value - Reference value
+**
+** Returns void
+**
+*******************************************************************************/
+void BTA_DmEnableScanFilter(UINT8 action, tBTA_DM_BLE_PF_STATUS_CBACK *p_cmpl_cback,
+ tBTA_DM_BLE_REF_VALUE ref_value)
+{
+#if BLE_ANDROID_CONTROLLER_SCAN_FILTER == TRUE
+ tBTA_DM_API_ENABLE_SCAN_FILTER *p_msg;
+ APPL_TRACE_API ("BTA_DmEnableScanFilter: %d", action);
+
+ UINT16 len = sizeof(tBTA_DM_API_ENABLE_SCAN_FILTER) + sizeof(tBLE_BD_ADDR);
+
+ if ((p_msg = (tBTA_DM_API_ENABLE_SCAN_FILTER *) GKI_getbuf(len)) != NULL)
+ {
+ memset (p_msg, 0, len);
+
+ p_msg->hdr.event = BTA_DM_API_SCAN_FILTER_ENABLE_EVT;
+ p_msg->action = action;
+ p_msg->ref_value = ref_value;
+ p_msg->p_filt_status_cback = p_cmpl_cback;
+
+ bta_sys_sendmsg(p_msg);
+ }
+#else
+ UNUSED(action);
+ UNUSED(p_cmpl_cback);
+ UNUSED(ref_value);
+#endif
+}
+
+/*******************************************************************************
+**
** Function BTA_DmBleUpdateConnectionParams
**
** Description Update connection parameters, can only be used when connection is up.
#if BLE_ANDROID_CONTROLLER_SCAN_FILTER == TRUE
BTA_DM_API_CFG_FILTER_COND_EVT,
- BTA_DM_API_ENABLE_SCAN_FILTER_EVT,
+ BTA_DM_API_SCAN_FILTER_SETUP_EVT,
+ BTA_DM_API_SCAN_FILTER_ENABLE_EVT,
#endif
BTA_DM_API_BLE_MULTI_ADV_ENB_EVT,
BTA_DM_API_BLE_MULTI_ADV_PARAM_UPD_EVT,
BT_HDR hdr;
tBTA_DM_BLE_SCAN_COND_OP action;
tBTA_DM_BLE_PF_COND_TYPE cond_type;
+ tBTA_DM_BLE_PF_FILT_INDEX filt_index;
tBTA_DM_BLE_PF_COND_PARAM *p_cond_param;
- void *p_cmpl_cback;
+ tBTA_DM_BLE_PF_CFG_CBACK *p_filt_cfg_cback;
+ tBTA_DM_BLE_REF_VALUE ref_value;
}tBTA_DM_API_CFG_FILTER_COND;
typedef struct
{
BT_HDR hdr;
- BOOLEAN enable;
- tBLE_BD_ADDR *p_target;
- void *p_cmpl_cback;
+ UINT8 action;
+ tBTA_DM_BLE_PF_STATUS_CBACK *p_filt_status_cback;
+ tBTA_DM_BLE_REF_VALUE ref_value;
}tBTA_DM_API_ENABLE_SCAN_FILTER;
+
+typedef struct
+{
+ BT_HDR hdr;
+ UINT8 action;
+ tBTA_DM_BLE_PF_FILT_INDEX filt_index;
+ tBTA_DM_BLE_PF_FILT_PARAMS *p_filt_params;
+ tBLE_BD_ADDR *p_target;
+ tBTA_DM_BLE_PF_PARAM_CBACK *p_filt_param_cback;
+ tBTA_DM_BLE_REF_VALUE ref_value;
+}tBTA_DM_API_SCAN_FILTER_PARAM_SETUP;
#endif
/* union of all data types */
tBTA_DM_API_BLE_ADV_PARAMS ble_set_adv_params;
tBTA_DM_API_SET_ADV_CONFIG ble_set_adv_data;
#if BLE_ANDROID_CONTROLLER_SCAN_FILTER == TRUE
- tBTA_DM_API_ENABLE_SCAN_FILTER ble_enable_scan_filter;
+ tBTA_DM_API_SCAN_FILTER_PARAM_SETUP ble_scan_filt_param_setup;
tBTA_DM_API_CFG_FILTER_COND ble_cfg_filter_cond;
+ tBTA_DM_API_ENABLE_SCAN_FILTER ble_enable_scan_filt;
#endif
tBTA_DM_API_UPDATE_CONN_PARAM ble_update_conn_params;
tBTA_DM_API_BLE_MULTI_ADV_ENB ble_multi_adv_enb;
tBTA_DM_ACTIVE_LINK device_list;
tBTA_DM_SEC_CBACK *p_sec_cback;
tBTA_BLE_SCAN_SETUP_CBACK *p_setup_cback;
- void *p_ref;
+ tBTA_DM_BLE_PF_CFG_CBACK *p_scan_filt_cfg_cback;
+ tBTA_DM_BLE_PF_STATUS_CBACK *p_scan_filt_status_cback;
+ tBTA_DM_BLE_PF_PARAM_CBACK *p_scan_filt_param_cback;
TIMER_LIST_ENT signal_strength_timer;
tBTA_SIG_STRENGTH_MASK signal_strength_mask;
UINT16 state;
extern void bta_dm_ble_broadcast (tBTA_DM_MSG *p_data);
#if BLE_ANDROID_CONTROLLER_SCAN_FILTER == TRUE
-extern void bta_dm_enable_scan_filter (tBTA_DM_MSG *p_data);
extern void bta_dm_cfg_filter_cond (tBTA_DM_MSG *p_data);
+extern void bta_dm_scan_filter_param_setup (tBTA_DM_MSG *p_data);
+extern void bta_dm_enable_scan_filter(tBTA_DM_MSG *p_data);
#endif
extern void btm_dm_ble_multi_adv_disable(tBTA_DM_MSG *p_data);
extern void bta_dm_ble_multi_adv_data(tBTA_DM_MSG *p_data);
bta_dm_ble_broadcast, /* BTA_DM_API_BLE_BROADCAST_EVT */
#if BLE_ANDROID_CONTROLLER_SCAN_FILTER == TRUE
bta_dm_cfg_filter_cond, /* BTA_DM_API_CFG_FILTER_COND_EVT */
- bta_dm_enable_scan_filter, /* BTA_DM_API_ENABLE_SCAN_FILTER_EVT */
+ bta_dm_scan_filter_param_setup, /* BTA_DM_API_SCAN_FILTER_SETUP_EVT */
+ bta_dm_enable_scan_filter, /* BTA_DM_API_SCAN_FILTER_ENABLE_EVT */
#endif
bta_dm_ble_multi_adv_enb, /* BTA_DM_API_BLE_MULTI_ADV_ENB_EVT*/
bta_dm_ble_multi_adv_upd_param, /* BTA_DM_API_BLE_MULTI_ADV_PARAM_UPD_EVT */
};
typedef UINT8 tBTA_DM_BLE_SCAN_COND_OP;
+/* ADV payload filtering vendor specific call event */
+enum
+{
+ BTA_BLE_SCAN_PF_ENABLE_EVT = 7,
+ BTA_BLE_SCAN_PF_COND_EVT
+};
+
/* filter selection bit index */
#define BTA_DM_BLE_PF_ADDR_FILTER BTM_BLE_PF_ADDR_FILTER
#define BTA_DM_BLE_PF_SRVC_DATA BTM_BLE_PF_SRVC_DATA
#define BTA_DM_BLE_PF_LOCAL_NAME BTM_BLE_PF_LOCAL_NAME
#define BTA_DM_BLE_PF_MANU_DATA BTM_BLE_PF_MANU_DATA
#define BTA_DM_BLE_PF_SRVC_DATA_PATTERN BTM_BLE_PF_SRVC_DATA_PATTERN
-#define BTA_DM_BLE_PF_TYPE_MAX BTM_BLE_PF_TYPE_MAX
-#define BTA_DM_BLE_PF_SRVC_DATA BTM_BLE_PF_SRVC_DATA
#define BTA_DM_BLE_PF_TYPE_ALL BTM_BLE_PF_TYPE_ALL
#define BTA_DM_BLE_PF_TYPE_MAX BTM_BLE_PF_TYPE_MAX
typedef UINT8 tBTA_DM_BLE_PF_COND_TYPE;
UINT16 uuid; /* service ID */
UINT8 data_len; /* <= 20 bytes */
UINT8 *p_pattern;
+ UINT8 *p_pattern_mask; /* Service data matching mask, same length
+ as data pattern, set to all 0xff, match exact data */
}tBTA_DM_BLE_PF_SRVC_PATTERN_COND;
typedef union
tBTA_DM_BLE_PF_SRVC_PATTERN_COND srvc_data; /* service data pattern */
}tBTA_DM_BLE_PF_COND_PARAM;
+typedef UINT8 tBTA_DM_BLE_PF_FILT_INDEX;
+typedef UINT8 tBTA_DM_BLE_PF_AVBL_SPACE;
+
typedef INT8 tBTA_DM_RSSI_VALUE;
typedef UINT8 tBTA_DM_LINK_QUALITY_VALUE;
UINT8 inst_id, void *p_ref, tBTA_STATUS status);
typedef UINT8 tBTA_DM_BLE_REF_VALUE;
+#define BTA_DM_BLE_PF_ENABLE_EVT BTM_BLE_PF_ENABLE
+#define BTA_DM_BLE_PF_CONFIG_EVT BTM_BLE_PF_CONFIG
+typedef UINT8 tBTA_DM_BLE_PF_EVT;
+
+typedef UINT8 tBTA_DM_BLE_PF_COND_TYPE;
+
+#define BTA_DM_BLE_PF_LOGIC_OR 0
+#define BTA_DM_BLE_PF_LOGIC_AND 1
+typedef UINT8 tBTA_DM_BLE_PF_LOGIC_TYPE;
+
+#define BTA_DM_BLE_PF_ENABLE 1
+#define BTA_DM_BLE_PF_CONFIG 2
+typedef UINT8 tBTA_DM_BLE_PF_ACTION;
+
+typedef UINT8 tBTA_DM_BLE_PF_FILT_INDEX;
+
+typedef UINT8 tBTA_DM_BLE_PF_AVBL_SPACE;
+
+/* Config callback */
+typedef void (tBTA_DM_BLE_PF_CFG_CBACK) (tBTA_DM_BLE_PF_ACTION action,
+ tBTA_DM_BLE_PF_COND_TYPE cfg_cond,
+ tBTA_DM_BLE_PF_AVBL_SPACE avbl_space, tBTA_STATUS status,
+ tBTA_DM_BLE_REF_VALUE ref_value);
+/* Param callback */
+typedef void (tBTA_DM_BLE_PF_PARAM_CBACK) (UINT8 action_type, tBTA_DM_BLE_PF_AVBL_SPACE avbl_space,
+ tBTA_DM_BLE_REF_VALUE ref_value, tBTA_STATUS status);
+
+/* Status callback */
+typedef void (tBTA_DM_BLE_PF_STATUS_CBACK) (UINT8 action, tBTA_DM_BLE_REF_VALUE ref_value,
+ tBTA_STATUS status);
+
+
+#define BTA_DM_BLE_PF_BRDCAST_ADDR_FILT 1
+#define BTA_DM_BLE_PF_SERV_DATA_CHG_FILT 2
+#define BTA_DM_BLE_PF_SERV_UUID 4
+#define BTA_DM_BLE_PF_SERV_SOLC_UUID 8
+#define BTA_DM_BLE_PF_LOC_NAME_CHECK 16
+#define BTA_DM_BLE_PF_MANUF_NAME_CHECK 32
+#define BTA_DM_BLE_PF_SERV_DATA_CHECK 64
+typedef UINT16 tBTA_DM_BLE_PF_FEAT_SEL;
+
+#define BTA_DM_BLE_PF_LIST_LOGIC_OR 1
+#define BTA_DM_BLE_PF_LIST_LOGIC_AND 2
+typedef UINT16 tBTA_DM_BLE_PF_LIST_LOGIC_TYPE;
+
+#define BTA_DM_BLE_PF_FILT_LOGIC_OR 0
+#define BTA_DM_BLE_PF_FILT_LOGIC_AND 1
+typedef UINT16 tBTA_DM_BLE_PF_FILT_LOGIC_TYPE;
+
+typedef UINT8 tBTA_DM_BLE_PF_RSSI_THRESHOLD;
+typedef UINT8 tBTA_DM_BLE_PF_DELIVERY_MODE;
+typedef UINT16 tBTA_DM_BLE_PF_TIMEOUT;
+typedef UINT8 tBTA_DM_BLE_PF_TIMEOUT_CNT;
+
+typedef struct
+{
+ tBTA_DM_BLE_PF_FEAT_SEL feat_seln;
+ tBTA_DM_BLE_PF_LIST_LOGIC_TYPE list_logic_type;
+ tBTA_DM_BLE_PF_FILT_LOGIC_TYPE filt_logic_type;
+ tBTA_DM_BLE_PF_RSSI_THRESHOLD rssi_high_thres;
+ tBTA_DM_BLE_PF_RSSI_THRESHOLD rssi_low_thres;
+ tBTA_DM_BLE_PF_DELIVERY_MODE dely_mode;
+ tBTA_DM_BLE_PF_TIMEOUT found_timeout;
+ tBTA_DM_BLE_PF_TIMEOUT lost_timeout;
+ tBTA_DM_BLE_PF_TIMEOUT_CNT found_timeout_cnt;
+} tBTA_DM_BLE_PF_FILT_PARAMS;
+
/* Vendor Specific Command Callback */
typedef tBTM_VSC_CMPL_CB tBTA_VENDOR_CMPL_CBACK;
typedef tBTM_BLE_SEC_ACT tBTA_DM_BLE_SEC_ACT;
typedef void (tBTA_BLE_SCAN_THRESHOLD_CBACK)(tBTA_DM_BLE_REF_VALUE ref_value);
-typedef void (tBTA_BLE_SCAN_REP_CBACK) (tBTA_DM_BLE_REF_VALUE ref_value, UINT8 report_format,
+typedef void (tBTA_BLE_SCAN_REP_CBACK) (tBTA_DM_BLE_REF_VALUE ref_value, UINT8 report_format,
UINT8 num_records, UINT16 data_len,
UINT8* p_rep_data, tBTA_STATUS status);
typedef void (tBTA_BLE_SCAN_SETUP_CBACK) (tBTA_BLE_BATCH_SCAN_EVT evt, tBTA_DM_BLE_REF_VALUE ref_value,
UINT8 batch_scan_notify_threshold,
tBTA_BLE_SCAN_SETUP_CBACK *p_setup_cback,
tBTA_BLE_SCAN_THRESHOLD_CBACK *p_thres_cback,
- tBTA_BLE_SCAN_REP_CBACK* p_rep_cback,
+ tBTA_BLE_SCAN_REP_CBACK* p_rep_cback,
tBTA_DM_BLE_REF_VALUE ref_value);
/*******************************************************************************
*******************************************************************************/
BTA_API extern void BTA_DmBleDisableBatchScan(tBTA_DM_BLE_REF_VALUE ref_value);
+/*******************************************************************************
+**
+** Function BTA_DmEnableScanFilter
+**
+** Description This function is called to enable the adv data payload filter
+**
+** Parameters action -1: enable the filter condition, 0 - disables the filter condition
+**
+** Returns void
+**
+*******************************************************************************/
+BTA_API extern void BTA_DmEnableScanFilter(UINT8 action,
+ tBTA_DM_BLE_PF_STATUS_CBACK *p_cmpl_cback,
+ tBTA_DM_BLE_REF_VALUE ref_value);
+
+/*******************************************************************************
+**
+** Function BTA_DmBleScanFilterSetup
+**
+** Description This function is called to setup the filter params
+**
+** Parameters action: to read/write/clear
+** filt_index - filter index
+**
+** Returns void
+**
+*******************************************************************************/
+BTA_API extern void BTA_DmBleScanFilterSetup(UINT8 action,
+ tBTA_DM_BLE_PF_FILT_INDEX filt_index,
+ tBTA_DM_BLE_PF_FILT_PARAMS *p_filt_params,
+ tBLE_BD_ADDR *p_target,
+ tBTA_DM_BLE_PF_PARAM_CBACK *p_cmpl_cback,
+ tBTA_DM_BLE_REF_VALUE ref_value);
+
+/*******************************************************************************
+**
+** Function BTA_DmBleCfgFilterCondition
+**
+** Description This function is called to configure the adv data payload filter
+** condition.
+**
+** Parameters action: to read/write/clear
+** cond_type: filter condition type.
+** filt_index - filter index
+** p_cond: filter condition parameter
+** ref_value: Reference
+**
+** Returns void
+**
+*******************************************************************************/
+BTA_API extern void BTA_DmBleCfgFilterCondition(tBTA_DM_BLE_SCAN_COND_OP action,
+ tBTA_DM_BLE_PF_COND_TYPE cond_type,
+ tBTA_DM_BLE_PF_FILT_INDEX filt_index,
+ tBTA_DM_BLE_PF_COND_PARAM *p_cond,
+ tBTA_DM_BLE_PF_CFG_CBACK *p_cmpl_cback,
+ tBTA_DM_BLE_REF_VALUE ref_value);
+
#endif
#ifdef __cplusplus
#define BTA_GATTC_MULT_ADV_DATA_EVT 22 /* Multi ADV data event */
#define BTA_GATTC_MULT_ADV_DIS_EVT 23 /* Disable Multi ADV event */
#define BTA_GATTC_CONGEST_EVT 24 /* Congestion event */
-#define BTA_GATTC_BTH_SCAN_ENB_EVT 25 /* Enable batch scan event */
-#define BTA_GATTC_BTH_SCAN_CFG_EVT 26 /* Config storage event */
-#define BTA_GATTC_BTH_SCAN_RD_EVT 27 /* Batch scan reports read event */
-#define BTA_GATTC_BTH_SCAN_THR_EVT 28 /* Batch scan threshold event */
-#define BTA_GATTC_BTH_SCAN_PARAM_EVT 29 /* Batch scan param event */
-#define BTA_GATTC_BTH_SCAN_DIS_EVT 30 /* Disable batch scan event */
+#define BTA_GATTC_BTH_SCAN_ENB_EVT 24 /* Enable batch scan event */
+#define BTA_GATTC_BTH_SCAN_CFG_EVT 25 /* Config storage event */
+#define BTA_GATTC_BTH_SCAN_RD_EVT 26 /* Batch scan reports read event */
+#define BTA_GATTC_BTH_SCAN_THR_EVT 27 /* Batch scan threshold event */
+#define BTA_GATTC_BTH_SCAN_PARAM_EVT 28 /* Batch scan param event */
+#define BTA_GATTC_BTH_SCAN_DIS_EVT 29 /* Disable batch scan event */
+#define BTA_GATTC_SCAN_FLT_CFG_EVT 30 /* Scan filter config event */
+#define BTA_GATTC_SCAN_FLT_PARAM_EVT 31 /* Param filter event */
+#define BTA_GATTC_SCAN_FLT_STATUS_EVT 32 /* Filter status event */
typedef UINT8 tBTA_GATTC_EVT;
/*****************************************************************************
** Constants and data types
*****************************************************************************/
-/* ADV payload filtering vendor specific call event */
-enum
-{
- BTA_VS_BLE_SCAN_PF_ENABLE_EVT = 7,
- BTA_VS_BLE_SCAN_PF_COND_EVT
-};
-
-typedef struct
-{
- BOOLEAN enable;
- tBLE_BD_ADDR *p_target;
- void *p_cmpl_cback;
-}tBTA_SYS_VS_BLE_SCAN_PF_ENABLE;
-
-typedef struct
-{
- UINT8 action;
- INT8 cond_type;
- void *p_cond;
- void *p_cmpl_cback;
-}tBTA_SYS_VS_BLE_SCAN_PF_COND;
/* vendor specific event handler function type */
typedef BOOLEAN (tBTA_SYS_VS_EVT_HDLR)(UINT16 evt, void *p);
#include "btif_pan.h"
#include "btif_profile_queue.h"
#include "btif_config.h"
-#include "bta_vendor_api.h"
/************************************************************************************
** Constants & Macros
************************************************************************************/
/* callback to HAL */
if (status == BTA_SUCCESS)
{
-#if (BLE_INCLUDED == TRUE )
- BTA_BrcmInit();
-#endif
+ /* initialize a2dp service */
+ btif_av_init();
/* init rfcomm & l2cap api */
btif_sock_init();
#include "btif_dm.h"
#include "btif_storage.h"
-#include "bta_vendor_api.h"
#include "vendor_api.h"
/*******************************************************************************
BTIF_GATTC_LISTEN,
BTIF_GATTC_SET_ADV_DATA,
BTIF_GATTC_CONFIGURE_MTU,
- BTIF_GATTC_SCAN_FILTER_ENABLE,
+ BTIF_GATTC_SCAN_FILTER_PARAM_SETUP,
BTIF_GATTC_SCAN_FILTER_CONFIG,
BTIF_GATTC_SCAN_FILTER_CLEAR,
+ BTIF_GATTC_SCAN_FILTER_ENABLE,
BTIF_GATTC_SET_SCAN_PARAMS,
BTIF_GATTC_ADV_INSTANCE_ENABLE,
BTIF_GATTC_ADV_INSTANCE_UPDATE,
btgatt_batch_reports read_reports;
} btgatt_batch_track_cb_t;
+typedef tBTA_DM_BLE_PF_FILT_PARAMS btgatt_adv_filt_param_t;
+
+typedef struct
+{
+ uint8_t client_if;
+ uint8_t action;
+ tBTA_DM_BLE_PF_COND_TYPE filt_type;
+ bt_bdaddr_t bd_addr;
+ uint8_t value[BTGATT_MAX_ATTR_LEN];
+ uint8_t value_len;
+ uint8_t filt_index;
+ uint16_t conn_id;
+ uint16_t company_id_mask;
+ bt_uuid_t uuid;
+ bt_uuid_t uuid_mask;
+ uint8_t value_mask[BTGATT_MAX_ATTR_LEN];
+ uint8_t value_mask_len;
+ uint8_t has_mask;
+ uint8_t addr_type;
+ uint8_t status;
+ tBTA_DM_BLE_PF_AVBL_SPACE avbl_space;
+ tBTA_DM_BLE_SCAN_COND_OP cond_op;
+ btgatt_adv_filt_param_t adv_filt_param;
+} btgatt_adv_filter_cb_t;
+
typedef struct
{
uint8_t value[BTGATT_MAX_ATTR_LEN];
break;
}
- case BTIF_GATTC_SCAN_FILTER_EVT:
- {
- btif_gattc_cb_t *p_btif_cb = (btif_gattc_cb_t*)p_param;
- HAL_CBACK(bt_gatt_callbacks, client->scan_filter_cb, p_btif_cb->action,
- p_btif_cb->status);
- break;
- }
-
case BTA_GATTC_MULT_ADV_ENB_EVT:
{
btif_gattc_cb_t *p_btif_cb = (btif_gattc_cb_t*)p_param;
break;
}
+ case BTA_GATTC_SCAN_FLT_CFG_EVT:
+ {
+ btgatt_adv_filter_cb_t *p_btif_cb = (btgatt_adv_filter_cb_t*)p_param;
+ HAL_CBACK(bt_gatt_callbacks, client->scan_filter_cfg_cb, p_btif_cb->action,
+ p_btif_cb->client_if, p_btif_cb->status, p_btif_cb->cond_op,
+ p_btif_cb->avbl_space);
+ break;
+ }
+
+ case BTA_GATTC_SCAN_FLT_PARAM_EVT:
+ {
+ btgatt_adv_filter_cb_t *p_data = (btgatt_adv_filter_cb_t*) p_param;
+ BTIF_TRACE_DEBUG("BTA_GATTC_SCAN_FLT_PARAM_EVT: %d, %d, %d, %d",p_data->client_if,
+ p_data->action, p_data->avbl_space, p_data->status);
+ HAL_CBACK(bt_gatt_callbacks, client->scan_filter_param_cb
+ , p_data->action, p_data->client_if, p_data->status
+ , p_data->avbl_space);
+ break;
+ }
+
+ case BTA_GATTC_SCAN_FLT_STATUS_EVT:
+ {
+ btgatt_adv_filter_cb_t *p_data = (btgatt_adv_filter_cb_t*) p_param;
+ BTIF_TRACE_DEBUG("BTA_GATTC_SCAN_FLT_STATUS_EVT: %d, %d, %d",p_data->client_if,
+ p_data->action, p_data->status);
+ HAL_CBACK(bt_gatt_callbacks, client->scan_filter_status_cb
+ , p_data->action, p_data->client_if, p_data->status);
+ break;
+ }
+
default:
ALOGE("%s: Unhandled event (%d)!", __FUNCTION__, event);
break;
btif_scan_track_cb.status = status;
btif_scan_track_cb.client_if = ref_value;
- BTIF_TRACE_DEBUG3("bta_batch_scan_setup_cb-Status:%x, client_if:%d, evt=%d",
+ BTIF_TRACE_DEBUG("bta_batch_scan_setup_cb-Status:%x, client_if:%d, evt=%d",
status, ref_value, evt);
switch(evt)
btif_scan_track_cb.status = 0;
btif_scan_track_cb.client_if = ref_value;
- BTIF_TRACE_DEBUG2("%s - client_if:%d",__FUNCTION__, ref_value);
+ BTIF_TRACE_DEBUG("%s - client_if:%d",__FUNCTION__, ref_value);
btif_transfer_context(btif_gattc_upstreams_evt, BTA_GATTC_BTH_SCAN_THR_EVT,
(char*) &btif_scan_track_cb, sizeof(btif_gattc_cb_t), NULL);
UINT8* p_rep_data, tBTA_STATUS status)
{
btgatt_batch_track_cb_t btif_scan_track_cb;
- BTIF_TRACE_DEBUG5("%s - client_if:%d, %d, %d, %d",__FUNCTION__, ref_value, status, num_records,
+ BTIF_TRACE_DEBUG("%s - client_if:%d, %d, %d, %d",__FUNCTION__, ref_value, status, num_records,
data_len);
btif_scan_track_cb.status = status;
(char*) &btif_cb, sizeof(btif_gattc_cb_t), NULL);
}
-static void bta_scan_filter_cmpl_cb(tBTA_DM_BLE_PF_EVT event,
- tBTA_DM_BLE_PF_COND_TYPE cfg_cond, tBTA_STATUS status)
+static void bta_scan_filt_cfg_cb(tBTA_DM_BLE_PF_ACTION action, tBTA_DM_BLE_SCAN_COND_OP cfg_op,
+ tBTA_DM_BLE_PF_AVBL_SPACE avbl_space, tBTA_STATUS status,
+ tBTA_DM_BLE_REF_VALUE ref_value)
{
- btif_gattc_cb_t btif_cb;
+ btgatt_adv_filter_cb_t btif_cb;
btif_cb.status = status;
- btif_cb.action = event;
- btif_transfer_context(btif_gattc_upstreams_evt, BTIF_GATTC_SCAN_FILTER_EVT,
- (char*) &btif_cb, sizeof(btif_gattc_cb_t), NULL);
+ btif_cb.action = action;
+ btif_cb.cond_op = cfg_op;
+ btif_cb.avbl_space = avbl_space;
+ btif_cb.client_if = ref_value;
+ btif_transfer_context(btif_gattc_upstreams_evt, BTA_GATTC_SCAN_FLT_CFG_EVT,
+ (char*) &btif_cb, sizeof(btgatt_adv_filter_cb_t), NULL);
+}
+
+static void bta_scan_filt_param_setup_cb(UINT8 action_type,
+ tBTA_DM_BLE_PF_AVBL_SPACE avbl_space,
+ tBTA_DM_BLE_REF_VALUE ref_value, tBTA_STATUS status)
+{
+ btgatt_adv_filter_cb_t btif_cb;
+
+ btif_cb.status = status;
+ btif_cb.action = action_type;
+ btif_cb.client_if = ref_value;
+ btif_cb.avbl_space = avbl_space;
+ btif_transfer_context(btif_gattc_upstreams_evt, BTA_GATTC_SCAN_FLT_PARAM_EVT,
+ (char*) &btif_cb, sizeof(btgatt_adv_filter_cb_t), NULL);
+}
+
+static void bta_scan_filt_status_cb(UINT8 action, tBTA_STATUS status,
+ tBTA_DM_BLE_REF_VALUE ref_value)
+{
+ btgatt_adv_filter_cb_t btif_cb;
+
+ btif_cb.status = status;
+ btif_cb.action = action;
+ btif_cb.client_if = ref_value;
+ btif_transfer_context(btif_gattc_upstreams_evt, BTA_GATTC_SCAN_FLT_STATUS_EVT,
+ (char*) &btif_cb, sizeof(btgatt_adv_filter_cb_t), NULL);
}
static void btgattc_handle_event(uint16_t event, char* p_param)
btif_adv_data_t *p_adv_data = NULL;
btgatt_multi_adv_inst_cb *p_inst_cb = NULL;
btgatt_batch_track_cb_t *p_scan_track_cb = NULL;
+ btgatt_adv_filter_cb_t *p_adv_filt_cb = NULL;
if(BTIF_GATTC_ADV_INSTANCE_ENABLE == event || BTIF_GATTC_ADV_INSTANCE_DISABLE == event ||
BTIF_GATTC_ADV_INSTANCE_UPDATE == event)
|| BTIF_GATTC_READ_BATCH_SCAN_REPORTS == event || BTIF_GATTC_DISABLE_BATCH_SCAN == event)
p_scan_track_cb = (btgatt_batch_track_cb_t *) p_param;
else
+ if(BTIF_GATTC_SCAN_FILTER_PARAM_SETUP == event || BTIF_GATTC_SCAN_FILTER_CONFIG == event
+ || BTIF_GATTC_SCAN_FILTER_CLEAR == event || BTIF_GATTC_SCAN_FILTER_ENABLE == event)
+ p_adv_filt_cb = (btgatt_adv_filter_cb_t *) p_param;
+ else
p_cb = (btif_gattc_cb_t*)p_param;
}
- if (!p_cb && !p_adv_data && !p_inst_cb && !p_scan_track_cb) return;
+ if (!p_cb && !p_adv_data && !p_inst_cb && !p_scan_track_cb && !p_adv_filt_cb) return;
ALOGD("%s: Event %d", __FUNCTION__, event);
BTM_ReadRSSI (p_cb->bd_addr.address, (tBTM_CMPL_CB *)btm_read_rssi_cb);
break;
- case BTIF_GATTC_SCAN_FILTER_ENABLE:
- BTA_DmBleEnableFilterCondition(p_cb->action, NULL, bta_scan_filter_cmpl_cb);
+ case BTIF_GATTC_SCAN_FILTER_PARAM_SETUP:
+ {
+ if(NULL == p_adv_filt_cb)
+ return;
+ BTA_DmBleScanFilterSetup(p_adv_filt_cb->action, p_adv_filt_cb->filt_index,
+ &p_adv_filt_cb->adv_filt_param, NULL, bta_scan_filt_param_setup_cb,
+ p_adv_filt_cb->client_if);
break;
+ }
case BTIF_GATTC_SCAN_FILTER_CONFIG:
{
+ if(NULL == p_adv_filt_cb)
+ return;
tBTA_DM_BLE_PF_COND_PARAM cond;
memset(&cond, 0, sizeof(cond));
- switch (p_cb->action)
+ switch (p_adv_filt_cb->filt_type)
{
case BTA_DM_BLE_PF_ADDR_FILTER: // 0
- bdcpy(cond.target_addr.bda, p_cb->bd_addr.address);
- cond.target_addr.type = p_cb->addr_type;
- BTA_DmBleCfgFilterCondition(BTA_DM_BLE_SCAN_COND_ADD,
- p_cb->action, &cond,
- bta_scan_filter_cmpl_cb);
+ bdcpy(cond.target_addr.bda, p_adv_filt_cb->bd_addr.address);
+ cond.target_addr.type = p_adv_filt_cb->addr_type;
+ BTA_DmBleCfgFilterCondition(p_adv_filt_cb->action,
+ p_adv_filt_cb->filt_type, p_adv_filt_cb->filt_index,
+ &cond, bta_scan_filt_cfg_cb,
+ p_adv_filt_cb->client_if);
break;
case BTA_DM_BLE_PF_SRVC_DATA: // 1
- BTA_DmBleCfgFilterCondition(BTA_DM_BLE_SCAN_COND_ADD,
- p_cb->action, NULL,
- bta_scan_filter_cmpl_cb);
+ BTA_DmBleCfgFilterCondition(p_adv_filt_cb->action,
+ p_adv_filt_cb->filt_type, p_adv_filt_cb->filt_index,
+ NULL, bta_scan_filt_cfg_cb, p_adv_filt_cb->client_if);
break;
case BTA_DM_BLE_PF_SRVC_UUID: // 2
cond.srvc_uuid.p_target_addr = NULL;
cond.srvc_uuid.cond_logic = BTA_DM_BLE_PF_LOGIC_AND;
- btif_to_bta_uuid(&cond.srvc_uuid.uuid, &p_cb->uuid);
+ btif_to_bta_uuid(&cond.srvc_uuid.uuid, &p_adv_filt_cb->uuid);
cond.srvc_uuid.p_uuid_mask = NULL;
- if (p_cb->has_mask)
+ if (p_adv_filt_cb->has_mask)
{
- btif_to_bta_uuid_mask(&uuid_mask, &p_cb->uuid_mask);
+ btif_to_bta_uuid_mask(&uuid_mask, &p_adv_filt_cb->uuid_mask);
cond.srvc_uuid.p_uuid_mask = &uuid_mask;
}
- BTA_DmBleCfgFilterCondition(BTA_DM_BLE_SCAN_COND_ADD,
- p_cb->action, &cond,
- bta_scan_filter_cmpl_cb);
+ BTA_DmBleCfgFilterCondition(p_adv_filt_cb->action,
+ p_adv_filt_cb->filt_type, p_adv_filt_cb->filt_index,
+ &cond, bta_scan_filt_cfg_cb,
+ p_adv_filt_cb->client_if);
break;
}
{
cond.solicitate_uuid.p_target_addr = NULL;
cond.solicitate_uuid.cond_logic = BTA_DM_BLE_PF_LOGIC_AND;
- btif_to_bta_uuid(&cond.solicitate_uuid.uuid, &p_cb->uuid);
- BTA_DmBleCfgFilterCondition(BTA_DM_BLE_SCAN_COND_ADD,
- p_cb->action, &cond,
- bta_scan_filter_cmpl_cb);
+ btif_to_bta_uuid(&cond.solicitate_uuid.uuid, &p_adv_filt_cb->uuid);
+ BTA_DmBleCfgFilterCondition(p_adv_filt_cb->action,
+ p_adv_filt_cb->filt_type, p_adv_filt_cb->filt_index,
+ &cond, bta_scan_filt_cfg_cb,
+ p_adv_filt_cb->client_if);
break;
}
case BTA_DM_BLE_PF_LOCAL_NAME: // 4
{
- cond.local_name.data_len = p_cb->len;
- cond.local_name.p_data = p_cb->value;
- BTA_DmBleCfgFilterCondition(BTA_DM_BLE_SCAN_COND_ADD,
- p_cb->action, &cond,
- bta_scan_filter_cmpl_cb);
+ cond.local_name.data_len = p_adv_filt_cb->value_len;
+ cond.local_name.p_data = p_adv_filt_cb->value;
+ BTA_DmBleCfgFilterCondition(p_adv_filt_cb->action,
+ p_adv_filt_cb->filt_type, p_adv_filt_cb->filt_index,
+ &cond, bta_scan_filt_cfg_cb,
+ p_adv_filt_cb->client_if);
break;
}
case BTA_DM_BLE_PF_MANU_DATA: // 5
{
- cond.manu_data.company_id = p_cb->conn_id;
- cond.manu_data.company_id_mask = p_cb->mask;
- cond.manu_data.data_len = p_cb->len;
- cond.manu_data.p_pattern = p_cb->value;
- cond.manu_data.p_pattern_mask = &p_cb->value[p_cb->len];
- BTA_DmBleCfgFilterCondition(BTA_DM_BLE_SCAN_COND_ADD,
- p_cb->action, &cond,
- bta_scan_filter_cmpl_cb);
+ cond.manu_data.company_id = p_adv_filt_cb->conn_id;
+ cond.manu_data.company_id_mask = p_adv_filt_cb->company_id_mask;
+ cond.manu_data.data_len = p_adv_filt_cb->value_len;
+ cond.manu_data.p_pattern = p_adv_filt_cb->value;
+ cond.manu_data.p_pattern_mask = p_adv_filt_cb->value_mask;
+ BTA_DmBleCfgFilterCondition(p_adv_filt_cb->action,
+ p_adv_filt_cb->filt_type, p_adv_filt_cb->filt_index,
+ &cond, bta_scan_filt_cfg_cb,
+ p_adv_filt_cb->client_if);
break;
}
+ case BTA_DM_BLE_PF_SRVC_DATA_PATTERN: //6
+ {
+ cond.srvc_data.data_len = p_adv_filt_cb->value_len;
+ cond.srvc_data.p_pattern = p_adv_filt_cb->value;
+ cond.srvc_data.p_pattern_mask = p_adv_filt_cb->value_mask;
+ BTA_DmBleCfgFilterCondition(p_adv_filt_cb->action,
+ p_adv_filt_cb->filt_type, p_adv_filt_cb->filt_index,
+ &cond, bta_scan_filt_cfg_cb,
+ p_adv_filt_cb->client_if);
+ break;
+ }
+
default:
ALOGE("%s: Unknown filter type (%d)!", __FUNCTION__, p_cb->action);
break;
case BTIF_GATTC_SCAN_FILTER_CLEAR:
{
+ if(NULL == p_adv_filt_cb)
+ return;
BTA_DmBleCfgFilterCondition(BTA_DM_BLE_SCAN_COND_CLEAR, BTA_DM_BLE_PF_TYPE_ALL,
- NULL, bta_scan_filter_cmpl_cb);
+ 0, NULL, bta_scan_filt_cfg_cb, p_adv_filt_cb->client_if);
+ break;
+ }
+
+ case BTIF_GATTC_SCAN_FILTER_ENABLE:
+ {
+ if(NULL == p_adv_filt_cb)
+ return;
+ BTA_DmEnableScanFilter(p_adv_filt_cb->action, bta_scan_filt_status_cb,
+ p_adv_filt_cb->client_if);
break;
}
(char*) &btif_cb, sizeof(btif_gattc_cb_t), NULL);
}
-static bt_status_t btif_gattc_scan_filter_enable(int enable )
+static bt_status_t btif_gattc_scan_filter_param_setup(int client_if, int action,
+ int filt_index, int feat_seln, int list_logic_type, int filt_logic_type, int rssi_high_thres,
+ int rssi_low_thres, int dely_mode, int found_timeout, int lost_timeout, int found_timeout_cnt)
{
CHECK_BTGATT_INIT();
- btif_gattc_cb_t btif_cb;
- btif_cb.action = enable;
- return btif_transfer_context(btgattc_handle_event, BTIF_GATTC_SCAN_FILTER_ENABLE,
- (char*) &btif_cb, sizeof(btif_gattc_cb_t), NULL);
+ BTIF_TRACE_DEBUG("%s", __FUNCTION__);
+ btgatt_adv_filter_cb_t btif_filt_cb;
+ btif_filt_cb.action = action;
+ btif_filt_cb.client_if = client_if;
+ btif_filt_cb.filt_index = filt_index;
+ btif_filt_cb.adv_filt_param.feat_seln = feat_seln;
+ btif_filt_cb.adv_filt_param.list_logic_type = list_logic_type;
+ btif_filt_cb.adv_filt_param.filt_logic_type = filt_logic_type;
+ btif_filt_cb.adv_filt_param.rssi_high_thres = rssi_high_thres;
+ btif_filt_cb.adv_filt_param.rssi_low_thres = rssi_low_thres;
+ btif_filt_cb.adv_filt_param.dely_mode = dely_mode;
+ btif_filt_cb.adv_filt_param.found_timeout = found_timeout;
+ btif_filt_cb.adv_filt_param.lost_timeout = lost_timeout;
+ btif_filt_cb.adv_filt_param.found_timeout_cnt = found_timeout_cnt;
+ return btif_transfer_context(btgattc_handle_event, BTIF_GATTC_SCAN_FILTER_PARAM_SETUP,
+ (char*) &btif_filt_cb, sizeof(btgatt_adv_filter_cb_t), NULL);
}
-static bt_status_t btif_gattc_scan_filter_add(int type, int company_id, int company_mask,
- int len, const bt_uuid_t *p_uuid, const bt_uuid_t *p_uuid_mask,
- const bt_bdaddr_t *bd_addr, char addr_type, const char* p_value)
+static bt_status_t btif_gattc_scan_filter_add_remove(int client_if, int action,
+ int filt_type, int filt_index, int company_id,
+ int company_id_mask, const bt_uuid_t *p_uuid,
+ const bt_uuid_t *p_uuid_mask, const bt_bdaddr_t *bd_addr,
+ char addr_type, int data_len, char* p_data, int mask_len,
+ char* p_mask)
{
CHECK_BTGATT_INIT();
- btif_gattc_cb_t btif_cb;
-
- if (len > (BTGATT_MAX_ATTR_LEN / 2))
- len = BTGATT_MAX_ATTR_LEN / 2;
-
- btif_cb.action = type;
- btif_cb.len = len;
- btif_cb.conn_id = company_id;
- btif_cb.mask = company_mask ? company_mask : 0xFFFF;
+ btgatt_adv_filter_cb_t btif_filt_cb;
+ BTIF_TRACE_DEBUG("%s, %d, %d", __FUNCTION__, action, filt_type);
+
+ /* If data is passed, both mask and data have to be the same length */
+ if(data_len != mask_len && NULL != p_data && NULL != p_mask)
+ return BT_STATUS_PARM_INVALID;
+
+ btif_filt_cb.client_if = client_if;
+ btif_filt_cb.action = action;
+ btif_filt_cb.filt_index = filt_index;
+ btif_filt_cb.filt_type = filt_type;
+ btif_filt_cb.conn_id = company_id;
+ btif_filt_cb.company_id_mask = company_id_mask ? company_id_mask : 0xFFFF;
if(bd_addr)
- bdcpy(btif_cb.bd_addr.address, bd_addr->address);
- btif_cb.addr_type = addr_type;
- btif_cb.has_mask = (p_uuid_mask != NULL);
+ bdcpy(btif_filt_cb.bd_addr.address, bd_addr->address);
+
+ btif_filt_cb.addr_type = addr_type;
+ btif_filt_cb.has_mask = (p_uuid_mask != NULL);
if (p_uuid != NULL)
- memcpy(&btif_cb.uuid, p_uuid, sizeof(bt_uuid_t));
+ memcpy(&btif_filt_cb.uuid, p_uuid, sizeof(bt_uuid_t));
if (p_uuid_mask != NULL)
- memcpy(&btif_cb.uuid_mask, p_uuid_mask, sizeof(bt_uuid_t));
- if (p_value != NULL && len != 0)
- memcpy(btif_cb.value, p_value, len * 2 /* PATTERN CONTAINS MASK */);
+ memcpy(&btif_filt_cb.uuid_mask, p_uuid_mask, sizeof(bt_uuid_t));
+ if (p_data != NULL && data_len != 0)
+ {
+ memcpy(btif_filt_cb.value, p_data, data_len);
+ btif_filt_cb.value_len = data_len;
+ memcpy(btif_filt_cb.value_mask, p_mask, mask_len);
+ btif_filt_cb.value_mask_len = mask_len;
+ }
return btif_transfer_context(btgattc_handle_event, BTIF_GATTC_SCAN_FILTER_CONFIG,
- (char*) &btif_cb, sizeof(btif_gattc_cb_t), NULL);
+ (char*) &btif_filt_cb, sizeof(btgatt_adv_filter_cb_t), NULL);
}
-static bt_status_t btif_gattc_scan_filter_clear()
+static bt_status_t btif_gattc_scan_filter_clear(int client_if, int filt_index)
{
CHECK_BTGATT_INIT();
- btif_gattc_cb_t btif_cb;
- return btif_transfer_context(btgattc_handle_event, BTIF_GATTC_SCAN_FILTER_CLEAR,
- (char*) &btif_cb, sizeof(btif_gattc_cb_t), NULL);
+ BTIF_TRACE_DEBUG("%s, %d", __FUNCTION__, filt_index);
+
+ btgatt_adv_filter_cb_t btif_filt_cb;
+ btif_filt_cb.client_if = client_if;
+ btif_filt_cb.filt_index = filt_index;
+ btif_filt_cb.action = BTA_DM_BLE_SCAN_COND_CLEAR;
+ return btif_transfer_context(btgattc_handle_event, BTIF_GATTC_SCAN_FILTER_CONFIG,
+ (char*) &btif_filt_cb, sizeof(btgatt_adv_filter_cb_t), NULL);
+}
+
+static bt_status_t btif_gattc_scan_filter_enable(int client_if, bool enable)
+{
+ int action = 0;
+ CHECK_BTGATT_INIT();
+ BTIF_TRACE_DEBUG("%s, %d", __FUNCTION__, enable);
+
+ btgatt_adv_filter_cb_t btif_filt_cb;
+ btif_filt_cb.client_if = client_if;
+ if(true == enable)
+ action = 1;
+ btif_filt_cb.action = action;
+ return btif_transfer_context(btgattc_handle_event, BTIF_GATTC_SCAN_FILTER_ENABLE,
+ (char*) &btif_filt_cb, sizeof(btgatt_adv_filter_cb_t), NULL);
}
static bt_status_t btif_gattc_set_scan_parameters(int scan_interval, int scan_window)
btif_gattc_reg_for_notification,
btif_gattc_dereg_for_notification,
btif_gattc_read_remote_rssi,
- btif_gattc_scan_filter_enable,
- btif_gattc_scan_filter_add,
+ btif_gattc_scan_filter_param_setup,
+ btif_gattc_scan_filter_add_remove,
btif_gattc_scan_filter_clear,
+ btif_gattc_scan_filter_enable,
btif_gattc_get_device_type,
btif_gattc_set_adv_data,
btif_gattc_configure_mtu,
./btm/btm_main.c \
./btm/btm_dev.c \
./btm/btm_ble_gap.c \
+ ./btm/btm_ble_adv_filter.c \
./btm/btm_ble_multi_adv.c \
./btm/btm_ble_batchscan.c \
./btm/btm_acl.c \
--- /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.
+ *
+ ******************************************************************************/
+
+#include <string.h>
+#include "bt_target.h"
+
+#if (BLE_INCLUDED == TRUE)
+#if BLE_BATCH_SCAN_INCLUDED == TRUE
+#include "bt_types.h"
+#include "hcimsgs.h"
+#include "btu.h"
+#include "btm_int.h"
+#include "bt_utils.h"
+#include "hcidefs.h"
+#include "btm_ble_api.h"
+#include "vendor_ble.h"
+
+#define BTM_BLE_ADV_FILT_META_HDR_LENGTH 3
+#define BTM_BLE_ADV_FILT_FEAT_SELN_LEN 13
+
+#define BTM_BLE_PF_BIT_TO_MASK(x) (UINT16)(1 << (x))
+
+
+tBTM_BLE_ADV_FILTER_CB btm_ble_adv_filt_cb;
+tBTM_BLE_VSC_CB cmn_ble_vsc_cb;
+static const BD_ADDR na_bda= {0};
+
+static UINT8 btm_ble_cs_update_pf_counter(tBTM_BLE_SCAN_COND_OP action,
+ UINT8 cond_type, tBLE_BD_ADDR *p_bd_addr, UINT8 num_available);
+
+#define BTM_BLE_SET_SCAN_PF_OPCODE(x, y) (((x)<<4)|y)
+#define BTM_BLE_GET_SCAN_PF_SUBCODE(x) ((x) >> 4)
+#define BTM_BLE_GET_SCAN_PF_ACTION(x) ((x) & 0x0f)
+#define BTM_BLE_INVALID_COUNTER 0xff
+
+
+/* length of each multi adv sub command */
+#define BTM_BLE_ADV_FILTER_ENB_LEN 3
+
+/* length of each batch scan command */
+#define BTM_BLE_ADV_FILTER_CLEAR_LEN 3
+#define BTM_BLE_ADV_FILTER_LEN 2
+
+#define BTM_BLE_ADV_FILT_CB_EVT_MASK 0xF0
+#define BTM_BLE_ADV_FILT_SUBCODE_MASK 0x0F
+
+
+/*******************************************************************************
+**
+** Function btm_ble_advfilt_enq_op_q
+**
+** Description enqueue an adv filter operation in q to check command complete
+** status
+**
+** Returns void
+**
+*******************************************************************************/
+void btm_ble_advfilt_enq_op_q(UINT8 action, UINT8 cond_type, tBTM_BLE_REF_VALUE ref)
+{
+ btm_ble_adv_filt_cb.op_q.action_condtype[btm_ble_adv_filt_cb.op_q.next_idx] =
+ (action |(cond_type << 4));
+ btm_ble_adv_filt_cb.op_q.ref_value[btm_ble_adv_filt_cb.op_q.next_idx] = ref;
+ BTM_TRACE_DEBUG("btm_ble_advfilt_enq_op_q: act_condtype:%d, action:%d, Cond_type:%d",
+ btm_ble_adv_filt_cb.op_q.action_condtype[btm_ble_adv_filt_cb.op_q.next_idx], action, cond_type);
+ btm_ble_adv_filt_cb.op_q.next_idx = (btm_ble_adv_filt_cb.op_q.next_idx + 1)
+ % BTM_BLE_PF_TYPE_MAX;
+}
+
+/*******************************************************************************
+**
+** Function btm_ble_advfilt_deq_op_q
+**
+** Description dequeue an adv filter operation from q when command complete
+** is received
+**
+** Returns void
+**
+*******************************************************************************/
+void btm_ble_advfilt_deq_op_q(UINT8 *p_action,UINT8 *p_cond_type, tBTM_BLE_REF_VALUE *p_ref)
+{
+ *p_cond_type =
+ (btm_ble_adv_filt_cb.op_q.action_condtype[btm_ble_adv_filt_cb.op_q.pending_idx] >> 4);
+ *p_action =
+ (btm_ble_adv_filt_cb.op_q.action_condtype[btm_ble_adv_filt_cb.op_q.pending_idx]
+ & BTM_BLE_ADV_FILT_SUBCODE_MASK);
+ *p_ref = btm_ble_adv_filt_cb.op_q.ref_value[btm_ble_adv_filt_cb.op_q.pending_idx];
+ btm_ble_adv_filt_cb.op_q.pending_idx = (btm_ble_adv_filt_cb.op_q.pending_idx + 1)
+ % BTM_BLE_PF_TYPE_MAX;
+}
+
+/*******************************************************************************
+**
+** Function btm_ble_ocf_to_condtype
+**
+** Description Convert OCF to cond type
+**
+** Returns Returns ocf value
+**
+*******************************************************************************/
+UINT8 btm_ble_ocf_to_condtype(UINT8 ocf)
+{
+ UINT8 cond_type = 0;
+
+ switch(ocf)
+ {
+ case BTM_BLE_META_PF_FEAT_SEL:
+ cond_type = BTM_BLE_META_PF_FEAT_SEL;
+ break;
+ case BTM_BLE_META_PF_ADDR:
+ cond_type = BTM_BLE_PF_ADDR_FILTER;
+ break;
+ case BTM_BLE_META_PF_UUID:
+ cond_type = BTM_BLE_PF_SRVC_UUID;
+ break;
+ case BTM_BLE_META_PF_SOL_UUID:
+ cond_type = BTM_BLE_PF_SRVC_SOL_UUID;
+ break;
+ case BTM_BLE_META_PF_LOCAL_NAME:
+ cond_type = BTM_BLE_PF_LOCAL_NAME;
+ break;
+ case BTM_BLE_META_PF_MANU_DATA:
+ cond_type = BTM_BLE_PF_MANU_DATA;
+ break;
+ case BTM_BLE_META_PF_SRVC_DATA:
+ cond_type = BTM_BLE_PF_SRVC_DATA_PATTERN;
+ break;
+ case BTM_BLE_META_PF_ALL:
+ cond_type = BTM_BLE_PF_TYPE_ALL;
+ break;
+ default:
+ cond_type = BTM_BLE_PF_TYPE_MAX;
+ break;
+ }
+ return cond_type;
+}
+
+/*******************************************************************************
+**
+** Function btm_ble_scan_pf_cmpl_cback
+**
+** Description the BTM BLE customer feature VSC complete callback for ADV PF filtering
+**
+** Returns pointer to the counter if found; NULL otherwise.
+**
+*******************************************************************************/
+void btm_ble_scan_pf_cmpl_cback(tBTM_VSC_CMPL *p_params)
+{
+ UINT8 status = 0;
+ UINT8 *p = p_params->p_param_buf, op_subcode = 0, action = 0xff;
+ UINT16 evt_len = p_params->param_len;
+ UINT8 cond_type = BTM_BLE_PF_TYPE_MAX;
+ UINT8 num_avail = 0;
+ tBTM_BLE_REF_VALUE ref_value = 0;
+
+ if (evt_len < 3 || evt_len > 4)
+ {
+ BTM_TRACE_ERROR("cannot interpret APCF callback status = %d, length = %d", status, evt_len);
+ btm_ble_advfilt_deq_op_q(&action, &cond_type, &ref_value);
+ return;
+ }
+
+ STREAM_TO_UINT8(status, p);
+
+ btm_ble_advfilt_deq_op_q(&action, &cond_type, &ref_value);
+
+ STREAM_TO_UINT8(op_subcode, p);
+ STREAM_TO_UINT8(action, p);
+
+ /* Ignore the event, if it is not the same one expected */
+ if(3 == evt_len)
+ {
+ if(cond_type != op_subcode)
+ {
+ BTM_TRACE_ERROR("btm_ble_scan_pf_cmpl_cback-Incorrect opcode :%d, %d, %d, %d, %d, %d",
+ cond_type, op_subcode, action, evt_len, ref_value, status);
+ return;
+ }
+ else
+ {
+ btm_ble_adv_filt_cb.p_filt_stat_cback(action, status, ref_value);
+ BTM_TRACE_DEBUG("btm_ble_scan_pf_cmpl_cback enabled/disabled, %d, %d, %d, %d",
+ cond_type, action, status, ref_value);
+ return;
+ }
+ }
+
+ if (4 == evt_len && cond_type != btm_ble_ocf_to_condtype(op_subcode))
+ {
+ BTM_TRACE_ERROR("btm_ble_scan_pf_cmpl_cback-Incorrect opcode: %d, %d, %d, %d, %d",
+ cond_type, op_subcode, action, status, ref_value);
+ return;
+ }
+
+ STREAM_TO_UINT8(num_avail, p);
+ switch (op_subcode)
+ {
+ case BTM_BLE_META_PF_ADDR:
+ case BTM_BLE_META_PF_UUID:
+ case BTM_BLE_META_PF_SOL_UUID:
+ case BTM_BLE_META_PF_LOCAL_NAME:
+ case BTM_BLE_META_PF_MANU_DATA:
+ case BTM_BLE_META_PF_SRVC_DATA:
+ BTM_TRACE_DEBUG("btm_ble_scan_pf_cmpl_cback: %d, %d, %d, %d, %d", cond_type, action,
+ status, ref_value, num_avail);
+
+ if (HCI_SUCCESS == status)
+ {
+ if (memcmp(&btm_ble_adv_filt_cb.cur_filter_target.bda, &na_bda, BD_ADDR_LEN) == 0)
+ btm_ble_cs_update_pf_counter(action, cond_type, NULL, num_avail);
+ else
+ btm_ble_cs_update_pf_counter(action, cond_type,
+ &btm_ble_adv_filt_cb.cur_filter_target, num_avail);
+ }
+
+ /* send ADV PF operation complete */
+ btm_ble_adv_filt_cb.op_type = 0;
+ btm_ble_adv_filt_cb.p_scan_cfg_cback(action, cond_type, num_avail, status, ref_value);
+ break;
+
+ case BTM_BLE_META_PF_FEAT_SEL:
+ if(NULL != btm_ble_adv_filt_cb.p_filt_param_cback)
+ btm_ble_adv_filt_cb.p_filt_param_cback(action, num_avail, ref_value, status);
+ BTM_TRACE_DEBUG("btm_ble_scan_pf_cmpl_cback-Feat sel event: %d, %d, %d, %d, %d",
+ cond_type, action, status, ref_value, num_avail);
+ break;
+
+ default:
+ BTM_TRACE_ERROR("btm_ble_scan_pf_cmpl_cback: unknown operation: %d", op_subcode);
+ break;
+ }
+}
+
+/*******************************************************************************
+**
+** Function btm_ble_find_addr_filter_counter
+**
+** Description find the per bd address ADV payload filter counter by BD_ADDR.
+**
+** Returns pointer to the counter if found; NULL otherwise.
+**
+*******************************************************************************/
+tBTM_BLE_PF_COUNT* btm_ble_find_addr_filter_counter(tBLE_BD_ADDR *p_le_bda)
+{
+ UINT8 i;
+ tBTM_BLE_PF_COUNT *p_addr_filter = &btm_ble_adv_filt_cb.addr_filter_count[1];
+
+ if (p_le_bda == NULL)
+ return &btm_ble_adv_filt_cb.addr_filter_count[0];
+
+ for (i = 0; i < cmn_ble_vsc_cb.max_filter; i ++, p_addr_filter ++)
+ {
+ if (p_addr_filter->in_use &&
+ memcmp(p_le_bda->bda, p_addr_filter->bd_addr, BD_ADDR_LEN) == 0)
+ {
+ return p_addr_filter;
+ }
+ }
+ return NULL;
+}
+
+/*******************************************************************************
+**
+** Function btm_ble_alloc_addr_filter_counter
+**
+** Description allocate the per device adv payload filter counter.
+**
+** Returns pointer to the counter if allocation succeed; NULL otherwise.
+**
+*******************************************************************************/
+tBTM_BLE_PF_COUNT * btm_ble_alloc_addr_filter_counter(BD_ADDR bd_addr)
+{
+ UINT8 i;
+ tBTM_BLE_PF_COUNT *p_addr_filter = &btm_ble_adv_filt_cb.addr_filter_count[1];
+
+ for (i = 0; i < cmn_ble_vsc_cb.max_filter; i ++, p_addr_filter ++)
+ {
+ if (memcmp(na_bda, p_addr_filter->bd_addr, BD_ADDR_LEN) == 0)
+ {
+ memcpy(p_addr_filter->bd_addr, bd_addr, BD_ADDR_LEN);
+ p_addr_filter->in_use = TRUE;
+ return p_addr_filter;
+ }
+ }
+ return NULL;
+}
+/*******************************************************************************
+**
+** Function btm_ble_dealloc_addr_filter_counter
+**
+** Description de-allocate the per device adv payload filter counter.
+**
+** Returns TRUE if deallocation succeed; FALSE otherwise.
+**
+*******************************************************************************/
+BOOLEAN btm_ble_dealloc_addr_filter_counter(tBLE_BD_ADDR *p_bd_addr, UINT8 filter_type)
+{
+ UINT8 i;
+ tBTM_BLE_PF_COUNT *p_addr_filter = &btm_ble_adv_filt_cb.addr_filter_count[1];
+ BOOLEAN found = FALSE;
+
+ if (BTM_BLE_PF_TYPE_ALL == filter_type && NULL == p_bd_addr)
+ memset(&btm_ble_adv_filt_cb.addr_filter_count[0], 0, sizeof(tBTM_BLE_PF_COUNT));
+
+ for (i = 0; i < cmn_ble_vsc_cb.max_filter; i ++, p_addr_filter ++)
+ {
+ if ((p_addr_filter->in_use) && (NULL == p_bd_addr ||
+ (NULL != p_bd_addr &&
+ memcmp(p_bd_addr->bda, p_addr_filter->bd_addr, BD_ADDR_LEN) == 0)))
+ {
+ found = TRUE;
+ memset(p_addr_filter, 0, sizeof(tBTM_BLE_PF_COUNT));
+
+ if (NULL != p_bd_addr) break;
+ }
+ }
+ return found;
+}
+
+/*******************************************************************************
+**
+** Function btm_ble_update_pf_local_name
+**
+** Description this function update(add,delete or clear) the adv lcoal name filtering condition.
+**
+**
+** Returns BTM_SUCCESS if sucessful,
+** BTM_ILLEGAL_VALUE if paramter is not valid.
+**
+*******************************************************************************/
+tBTM_STATUS btm_ble_update_pf_local_name(tBTM_BLE_SCAN_COND_OP action,
+ tBTM_BLE_PF_FILT_INDEX filt_index,
+ tBTM_BLE_PF_COND_PARAM *p_cond)
+{
+ tBTM_BLE_PF_LOCAL_NAME_COND *p_local_name = (p_cond == NULL) ? NULL : &p_cond->local_name;
+ UINT8 param[BTM_BLE_PF_STR_LEN_MAX + BTM_BLE_ADV_FILT_META_HDR_LENGTH],
+ *p = param,
+ len = BTM_BLE_ADV_FILT_META_HDR_LENGTH;
+ tBTM_STATUS st = BTM_ILLEGAL_VALUE;
+
+ memset(param, 0, BTM_BLE_PF_STR_LEN_MAX + BTM_BLE_ADV_FILT_META_HDR_LENGTH);
+
+ UINT8_TO_STREAM(p, BTM_BLE_META_PF_LOCAL_NAME);
+ UINT8_TO_STREAM(p, action);
+
+ /* Filter index */
+ UINT8_TO_STREAM(p, filt_index);
+
+ if (BTM_BLE_SCAN_COND_ADD == action ||
+ BTM_BLE_SCAN_COND_DELETE == action)
+ {
+ if (NULL == p_local_name)
+ return st;
+
+ if (p_local_name->data_len > BTM_BLE_PF_STR_LEN_MAX)
+ p_local_name->data_len = BTM_BLE_PF_STR_LEN_MAX;
+
+ ARRAY_TO_STREAM(p, p_local_name->p_data, p_local_name->data_len);
+ len += p_local_name->data_len;
+ }
+
+ /* send local name filter */
+ if ((st = BTM_VendorSpecificCommand (HCI_BLE_ADV_FILTER_OCF,
+ len,
+ param,
+ btm_ble_scan_pf_cmpl_cback))
+ != BTM_NO_RESOURCES)
+ {
+ memset(&btm_ble_adv_filt_cb.cur_filter_target, 0, sizeof(tBLE_BD_ADDR));
+ }
+ else
+ {
+ BTM_TRACE_ERROR("Local Name PF filter update failed");
+ }
+
+ return st;
+}
+
+
+/*******************************************************************************
+**
+** Function btm_ble_update_srvc_data_change
+**
+** Description this function update(add/remove) service data change filter.
+**
+**
+** Returns BTM_SUCCESS if sucessful,
+** BTM_ILLEGAL_VALUE if paramter is not valid.
+**
+*******************************************************************************/
+tBTM_STATUS btm_ble_update_srvc_data_change(tBTM_BLE_SCAN_COND_OP action,
+ tBTM_BLE_PF_FILT_INDEX filt_index,
+ tBTM_BLE_PF_COND_PARAM *p_cond)
+{
+ tBTM_STATUS st = BTM_ILLEGAL_VALUE;
+ tBLE_BD_ADDR *p_bd_addr = p_cond ? &p_cond->target_addr : NULL;
+ UINT8 num_avail = (action == BTM_BLE_SCAN_COND_ADD) ? 0 : 1;
+
+ if (btm_ble_cs_update_pf_counter (action, BTM_BLE_PF_SRVC_DATA, p_bd_addr, num_avail)
+ != BTM_BLE_INVALID_COUNTER)
+ st = BTM_SUCCESS;
+
+ return st;
+}
+
+/*******************************************************************************
+**
+** Function btm_ble_update_pf_manu_data
+**
+** Description this function update(add,delete or clear) the adv manufacturer
+** data filtering condition.
+**
+**
+** Returns BTM_SUCCESS if sucessful,
+** BTM_ILLEGAL_VALUE if paramter is not valid.
+**
+*******************************************************************************/
+tBTM_STATUS btm_ble_update_pf_manu_data(tBTM_BLE_SCAN_COND_OP action,
+ tBTM_BLE_PF_FILT_INDEX filt_index,
+ tBTM_BLE_PF_COND_PARAM *p_data,
+ tBTM_BLE_PF_COND_TYPE cond_type)
+{
+ tBTM_BLE_PF_MANU_COND *p_manu_data = (p_data == NULL) ? NULL : &p_data->manu_data;
+ tBTM_BLE_PF_SRVC_PATTERN_COND *p_srvc_data = (p_data == NULL) ? NULL : &p_data->srvc_data;
+
+ UINT8 param[BTM_BLE_PF_STR_LEN_MAX + BTM_BLE_PF_STR_LEN_MAX + BTM_BLE_ADV_FILT_META_HDR_LENGTH],
+ *p = param,
+ len = BTM_BLE_ADV_FILT_META_HDR_LENGTH;
+ tBTM_STATUS st = BTM_ILLEGAL_VALUE;
+
+ if(NULL!= p_data && 0 == p_data->manu_data.data_len && 0 == p_data->srvc_data.data_len)
+ return st;
+
+ memset(param, 0, BTM_BLE_PF_STR_LEN_MAX + BTM_BLE_PF_STR_LEN_MAX
+ + BTM_BLE_ADV_FILT_META_HDR_LENGTH);
+
+ if (BTM_BLE_PF_SRVC_DATA_PATTERN == cond_type)
+ {
+ UINT8_TO_STREAM(p, BTM_BLE_META_PF_SRVC_DATA);
+ }
+ else
+ {
+ UINT8_TO_STREAM(p, BTM_BLE_META_PF_MANU_DATA);
+ }
+
+ UINT8_TO_STREAM(p, action);
+
+ /* Filter index */
+ UINT8_TO_STREAM(p, filt_index);
+
+ if (BTM_BLE_SCAN_COND_ADD == action ||
+ BTM_BLE_SCAN_COND_DELETE == action)
+ {
+ if (BTM_BLE_PF_SRVC_DATA_PATTERN == cond_type)
+ {
+ if (NULL == p_srvc_data)
+ return st;
+ if (p_srvc_data->data_len > (BTM_BLE_PF_STR_LEN_MAX - 2))
+ p_srvc_data->data_len = (BTM_BLE_PF_STR_LEN_MAX - 2);
+
+ if(p_srvc_data->data_len > 0)
+ {
+ ARRAY_TO_STREAM(p, p_srvc_data->p_pattern, p_srvc_data->data_len);
+ len += (p_srvc_data->data_len);
+ ARRAY_TO_STREAM(p, p_srvc_data->p_pattern_mask, p_srvc_data->data_len);
+ }
+
+ len += (p_srvc_data->data_len);
+ BTM_TRACE_DEBUG("Service data length: %d", len);
+ }
+ else
+ {
+ if (NULL == p_manu_data)
+ return st;
+ if (p_manu_data->data_len > (BTM_BLE_PF_STR_LEN_MAX - 2))
+ p_manu_data->data_len = (BTM_BLE_PF_STR_LEN_MAX - 2);
+
+ UINT16_TO_STREAM(p, p_manu_data->company_id);
+
+ if(p_manu_data->data_len > 0)
+ ARRAY_TO_STREAM(p, p_manu_data->p_pattern, p_manu_data->data_len);
+ len += (p_manu_data->data_len + 2);
+
+ if (p_manu_data->company_id_mask != 0)
+ {
+ UINT16_TO_STREAM (p, p_manu_data->company_id_mask);
+ }
+ else
+ {
+ memset(p, 0xff, 2);
+ p += 2;
+ }
+
+ if(p_manu_data->data_len > 0)
+ ARRAY_TO_STREAM(p, p_manu_data->p_pattern_mask, p_manu_data->data_len);
+ len += (p_manu_data->data_len + 2);
+
+ BTM_TRACE_DEBUG("Manuf data length: %d", len);
+ }
+ }
+
+ /* send manufacturer*/
+ if ((st = BTM_VendorSpecificCommand (HCI_BLE_ADV_FILTER_OCF,
+ len,
+ param,
+ btm_ble_scan_pf_cmpl_cback)) != BTM_NO_RESOURCES)
+ {
+ memset(&btm_ble_adv_filt_cb.cur_filter_target, 0, sizeof(tBLE_BD_ADDR));
+ }
+ else
+ {
+ BTM_TRACE_ERROR("manufacturer data PF filter update failed");
+ }
+
+ return st;
+}
+
+/*******************************************************************************
+**
+** Function btm_ble_cs_update_pf_counter
+**
+** Description this function is to update the adv data payload filter counter
+**
+** Returns current number of the counter; BTM_BLE_INVALID_COUNTER if
+** counter update failed.
+**
+*******************************************************************************/
+UINT8 btm_ble_cs_update_pf_counter(tBTM_BLE_SCAN_COND_OP action,
+ UINT8 cond_type, tBLE_BD_ADDR *p_bd_addr,
+ UINT8 num_available)
+{
+ tBTM_BLE_PF_COUNT *p_addr_filter = NULL;
+ UINT8 *p_counter = NULL;
+
+ BTM_BleGetVendorCapabilities(&cmn_ble_vsc_cb);
+
+ if (cond_type > BTM_BLE_PF_TYPE_ALL)
+ {
+ BTM_TRACE_ERROR("unknown PF filter condition type %d", cond_type);
+ return BTM_BLE_INVALID_COUNTER;
+ }
+
+ /* for these three types of filter, always generic */
+ if (BTM_BLE_PF_ADDR_FILTER == cond_type ||
+ BTM_BLE_PF_MANU_DATA == cond_type ||
+ BTM_BLE_PF_LOCAL_NAME == cond_type ||
+ BTM_BLE_PF_SRVC_DATA_PATTERN == cond_type)
+ p_bd_addr = NULL;
+
+ if ((p_addr_filter = btm_ble_find_addr_filter_counter(p_bd_addr)) == NULL &&
+ BTM_BLE_SCAN_COND_ADD == action)
+ {
+ p_addr_filter = btm_ble_alloc_addr_filter_counter(p_bd_addr->bda);
+ }
+
+ if (NULL != p_addr_filter)
+ {
+ /* all filter just cleared */
+ if ((BTM_BLE_PF_TYPE_ALL == cond_type && BTM_BLE_SCAN_COND_CLEAR == action) ||
+ /* or bd address filter been deleted */
+ (BTM_BLE_PF_ADDR_FILTER == cond_type &&
+ (BTM_BLE_SCAN_COND_DELETE == action || BTM_BLE_SCAN_COND_CLEAR == action)))
+ {
+ btm_ble_dealloc_addr_filter_counter(p_bd_addr, cond_type);
+ }
+ /* if not feature selection, update new addition/reduction of the filter counter */
+ else if (cond_type != BTM_BLE_PF_TYPE_ALL)
+ {
+ p_counter = p_addr_filter->pf_counter;
+ if(num_available > 0)
+ p_counter[cond_type] += 1;
+
+ /* update corresponding feature mask */
+ if (num_available > 0)
+ p_addr_filter->feat_mask |= (BTM_BLE_PF_BIT_TO_MASK(cond_type));
+ else
+ p_addr_filter->feat_mask &= ~(BTM_BLE_PF_BIT_TO_MASK(cond_type));
+
+ BTM_TRACE_DEBUG("counter = %d, maxfilt = %d, num_avbl=%d, feat_mask = %d",
+ p_counter[cond_type], cmn_ble_vsc_cb.max_filter, num_available,
+ p_addr_filter->feat_mask);
+ return p_counter[cond_type];
+ }
+ }
+ else
+ {
+ BTM_TRACE_ERROR("no matching filter counter found");
+ }
+ /* no matching filter located and updated */
+ return BTM_BLE_INVALID_COUNTER;
+}
+
+
+/*******************************************************************************
+**
+** Function btm_ble_update_addr_filter
+**
+** Description this function update(add,delete or clear) the address filter of adv.
+**
+**
+** Returns BTM_SUCCESS if sucessful,
+** BTM_ILLEGAL_VALUE if paramter is not valid.
+**
+*******************************************************************************/
+tBTM_STATUS btm_ble_update_addr_filter(tBTM_BLE_SCAN_COND_OP action,
+ tBTM_BLE_PF_FILT_INDEX filt_index,
+ tBTM_BLE_PF_COND_PARAM *p_cond)
+{
+ UINT8 param[BTM_BLE_META_ADDR_LEN + BTM_BLE_ADV_FILT_META_HDR_LENGTH],
+ * p= param;
+ tBTM_STATUS st = BTM_ILLEGAL_VALUE;
+ tBLE_BD_ADDR *p_addr = (p_cond == NULL) ? NULL : &p_cond->target_addr;
+
+ memset(param, 0, BTM_BLE_META_ADDR_LEN + BTM_BLE_ADV_FILT_META_HDR_LENGTH);
+
+ UINT8_TO_STREAM(p, BTM_BLE_META_PF_ADDR);
+ UINT8_TO_STREAM(p, action);
+
+ /* Filter index */
+ UINT8_TO_STREAM(p, filt_index);
+
+ if (BTM_BLE_SCAN_COND_ADD == action ||
+ BTM_BLE_SCAN_COND_DELETE == action)
+ {
+ if (NULL == p_addr)
+ return st;
+
+ BDADDR_TO_STREAM(p, p_addr->bda);
+ UINT8_TO_STREAM(p, p_addr->type);
+ }
+ /* send address filter */
+ if ((st = BTM_VendorSpecificCommand (HCI_BLE_ADV_FILTER_OCF,
+ (UINT8)(BTM_BLE_ADV_FILT_META_HDR_LENGTH + BTM_BLE_META_ADDR_LEN),
+ param,
+ btm_ble_scan_pf_cmpl_cback)) != BTM_NO_RESOURCES)
+ {
+ memset(&btm_ble_adv_filt_cb.cur_filter_target, 0, sizeof(tBLE_BD_ADDR));
+ }
+ else
+ {
+ BTM_TRACE_ERROR("Broadcaster Address Filter Update failed");
+ }
+ return st;
+}
+
+/*******************************************************************************
+**
+** Function btm_ble_update_uuid_filter
+**
+** Description this function update(add,delete or clear) service UUID filter.
+**
+**
+** Returns BTM_SUCCESS if sucessful,
+** BTM_ILLEGAL_VALUE if paramter is not valid.
+**
+*******************************************************************************/
+tBTM_STATUS btm_ble_update_uuid_filter(tBTM_BLE_SCAN_COND_OP action,
+ tBTM_BLE_PF_FILT_INDEX filt_index,
+ tBTM_BLE_PF_COND_TYPE filter_type,
+ tBTM_BLE_PF_COND_PARAM *p_cond)
+{
+ UINT8 param[BTM_BLE_META_UUID_LEN + BTM_BLE_ADV_FILT_META_HDR_LENGTH],
+ * p= param,
+ len = BTM_BLE_ADV_FILT_META_HDR_LENGTH;
+ tBTM_STATUS st = BTM_ILLEGAL_VALUE;
+ tBTM_BLE_PF_UUID_COND *p_uuid_cond;
+ UINT8 evt_type;
+
+ memset(param, 0, BTM_BLE_META_UUID_LEN + BTM_BLE_ADV_FILT_META_HDR_LENGTH);
+
+ if (BTM_BLE_PF_SRVC_UUID == filter_type)
+ {
+ evt_type = BTM_BLE_META_PF_UUID;
+ p_uuid_cond = p_cond ? &p_cond->srvc_uuid : NULL;
+ }
+ else
+ {
+ evt_type = BTM_BLE_META_PF_SOL_UUID;
+ p_uuid_cond = p_cond ? &p_cond->solicitate_uuid : NULL;
+ }
+
+ if (NULL == p_uuid_cond && action != BTM_BLE_SCAN_COND_CLEAR)
+ {
+ BTM_TRACE_ERROR("Illegal param for add/delete UUID filter");
+ return st;
+ }
+
+ /* need to add address fitler first, if adding per bda UUID filter without address filter */
+ if (BTM_BLE_SCAN_COND_ADD == action &&
+ p_uuid_cond->p_target_addr &&
+ btm_ble_find_addr_filter_counter(p_uuid_cond->p_target_addr) == NULL)
+ {
+ UINT8_TO_STREAM(p, BTM_BLE_META_PF_ADDR);
+ UINT8_TO_STREAM(p, action);
+
+ /* Filter index */
+ UINT8_TO_STREAM(p, filt_index);
+
+ BDADDR_TO_STREAM(p, p_uuid_cond->p_target_addr->bda);
+ UINT8_TO_STREAM(p, p_uuid_cond->p_target_addr->type);
+
+ /* send address filter */
+ if ((st = BTM_VendorSpecificCommand (HCI_BLE_ADV_FILTER_OCF,
+ (UINT8)(BTM_BLE_ADV_FILT_META_HDR_LENGTH + BTM_BLE_META_ADDR_LEN),
+ param,
+ btm_ble_scan_pf_cmpl_cback)) == BTM_NO_RESOURCES)
+ {
+ BTM_TRACE_ERROR("Update Address filter into controller failed.");
+ return st;
+ }
+ BTM_TRACE_DEBUG("Updated Address filter");
+ }
+
+ p = param;
+ UINT8_TO_STREAM(p, evt_type);
+ UINT8_TO_STREAM(p, action);
+
+ /* Filter index */
+ UINT8_TO_STREAM(p, filt_index);
+
+ if (BTM_BLE_SCAN_COND_ADD == action ||
+ BTM_BLE_SCAN_COND_DELETE == action)
+ {
+ if (p_uuid_cond->uuid.len == LEN_UUID_16)
+ {
+ UINT16_TO_STREAM(p, p_uuid_cond->uuid.uu.uuid16);
+ len += LEN_UUID_16;
+ }
+ else if (p_uuid_cond->uuid.len == LEN_UUID_32)/*4 bytes */
+ {
+ UINT32_TO_STREAM(p, p_uuid_cond->uuid.uu.uuid32);
+ len += LEN_UUID_32;
+ }
+ else if (p_uuid_cond->uuid.len == LEN_UUID_128)
+ {
+ ARRAY_TO_STREAM (p, p_uuid_cond->uuid.uu.uuid128, LEN_UUID_128);
+ len += LEN_UUID_128;
+ }
+ else
+ {
+ BTM_TRACE_ERROR("illegal UUID length: %d", p_uuid_cond->uuid.len);
+ return BTM_ILLEGAL_VALUE;
+ }
+
+ if (NULL != p_uuid_cond->p_uuid_mask)
+ {
+ if (p_uuid_cond->uuid.len == LEN_UUID_16)
+ {
+ UINT16_TO_STREAM(p, p_uuid_cond->p_uuid_mask->uuid16_mask);
+ len += LEN_UUID_16;
+ }
+ else if (p_uuid_cond->uuid.len == LEN_UUID_32)/*4 bytes */
+ {
+ UINT32_TO_STREAM(p, p_uuid_cond->p_uuid_mask->uuid32_mask);
+ len += LEN_UUID_32;
+ }
+ else if (p_uuid_cond->uuid.len == LEN_UUID_128)
+ {
+ ARRAY_TO_STREAM (p, p_uuid_cond->p_uuid_mask->uuid128_mask, LEN_UUID_128);
+ len += LEN_UUID_128;
+ }
+ }
+ else
+ {
+ memset(p, 0xff, p_uuid_cond->uuid.len);
+ len += p_uuid_cond->uuid.len;
+ }
+ }
+
+ BTM_TRACE_DEBUG("btm_ble_update_uuid_filter : %d, %d, %d, %d", filter_type, evt_type,
+ p_uuid_cond->uuid.len, len);
+ /* send UUID filter update */
+ if ((st = BTM_VendorSpecificCommand (HCI_BLE_ADV_FILTER_OCF,
+ len,
+ param,
+ btm_ble_scan_pf_cmpl_cback)) != BTM_NO_RESOURCES)
+ {
+ if (p_uuid_cond && p_uuid_cond->p_target_addr)
+ memcpy(&btm_ble_adv_filt_cb.cur_filter_target, p_uuid_cond->p_target_addr,
+ sizeof(tBLE_BD_ADDR));
+ else
+ memset(&btm_ble_adv_filt_cb.cur_filter_target, 0, sizeof(tBLE_BD_ADDR));
+ }
+ else
+ {
+ BTM_TRACE_ERROR("UUID filter udpating failed");
+ }
+
+ return st;
+}
+
+
+/*******************************************************************************
+**
+** Function btm_ble_clear_scan_pf_filter
+**
+** Description clear all adv payload filter by de-select all the adv pf feature bits
+**
+**
+** Returns BTM_SUCCESS if sucessful,
+** BTM_ILLEGAL_VALUE if paramter is not valid.
+**
+*******************************************************************************/
+tBTM_STATUS btm_ble_clear_scan_pf_filter(tBTM_BLE_SCAN_COND_OP action,
+ tBTM_BLE_PF_FILT_INDEX filt_index,
+ tBTM_BLE_PF_COND_PARAM *p_cond,
+ tBTM_BLE_REF_VALUE ref_value)
+{
+ tBLE_BD_ADDR *p_target = (p_cond == NULL)? NULL : &p_cond->target_addr;
+ tBTM_BLE_PF_COUNT *p_bda_filter;
+ tBTM_STATUS st = BTM_WRONG_MODE;
+ UINT8 param[20], *p;
+
+ if (BTM_BLE_SCAN_COND_CLEAR != action)
+ {
+ BTM_TRACE_ERROR("unable to perform action:%d for generic adv filter type", action);
+ return BTM_ILLEGAL_VALUE;
+ }
+
+ p = param;
+ memset(param, 0, 20);
+
+ p_bda_filter = btm_ble_find_addr_filter_counter(p_target);
+
+ if (NULL == p_bda_filter ||
+ /* not a generic filter, and feature selection is empty */
+ (p_target != NULL && p_bda_filter && 0 == p_bda_filter->feat_mask))
+ {
+ BTM_TRACE_ERROR("Error: Can not clear filter, No PF filter has been configured!");
+ return st;
+ }
+
+ /* clear the general filter entry */
+ if (NULL == p_target)
+ {
+ /* clear manufactuer data filter */
+ btm_ble_update_pf_manu_data(BTM_BLE_SCAN_COND_CLEAR, filt_index, NULL,
+ BTM_BLE_PF_MANU_DATA);
+ /* clear local name filter */
+ btm_ble_update_pf_local_name(BTM_BLE_SCAN_COND_CLEAR, filt_index, NULL);
+ /* update the counter for service data */
+ btm_ble_update_srvc_data_change(BTM_BLE_SCAN_COND_CLEAR, filt_index, NULL);
+ /* clear UUID filter */
+ btm_ble_update_uuid_filter(BTM_BLE_SCAN_COND_CLEAR, filt_index,
+ BTM_BLE_PF_SRVC_UUID, NULL);
+ btm_ble_update_uuid_filter(BTM_BLE_SCAN_COND_CLEAR, filt_index,
+ BTM_BLE_PF_SRVC_SOL_UUID, NULL);
+ /* clear service data filter */
+ btm_ble_update_pf_manu_data(BTM_BLE_SCAN_COND_CLEAR, filt_index, NULL,
+ BTM_BLE_PF_SRVC_DATA_PATTERN);
+ }
+
+ /* select feature based on control block settings */
+ UINT8_TO_STREAM(p, BTM_BLE_META_PF_FEAT_SEL);
+ UINT8_TO_STREAM(p, BTM_BLE_SCAN_COND_CLEAR);
+
+ /* Filter index */
+ UINT8_TO_STREAM(p, filt_index);
+
+ /* set PCF selection */
+ UINT32_TO_STREAM(p, BTM_BLE_PF_SELECT_NONE);
+ /* set logic condition as OR as default */
+ UINT8_TO_STREAM(p, BTM_BLE_PF_LOGIC_OR);
+
+ if ((st = BTM_VendorSpecificCommand (HCI_BLE_ADV_FILTER_OCF,
+ (UINT8)(BTM_BLE_ADV_FILT_META_HDR_LENGTH + BTM_BLE_PF_FEAT_SEL_LEN),
+ param,
+ btm_ble_scan_pf_cmpl_cback))
+ != BTM_NO_RESOURCES)
+ {
+ if (p_bda_filter)
+ p_bda_filter->feat_mask = BTM_BLE_PF_SELECT_NONE;
+
+ if (p_target)
+ memcpy(&btm_ble_adv_filt_cb.cur_filter_target, p_target, sizeof(tBLE_BD_ADDR));
+ else
+ memset(&btm_ble_adv_filt_cb.cur_filter_target, 0, sizeof(tBLE_BD_ADDR));
+ }
+
+ btm_ble_advfilt_enq_op_q(action, BTM_BLE_PF_TYPE_MAX, ref_value);
+ return st;
+}
+
+/*******************************************************************************
+**
+** Function BTM_BleAdvFilterParamSetup
+**
+** Description This function is called to setup the adv data payload filter
+** condition.
+**
+** Parameters action - Type of action to be performed
+** filt_index - Filter index
+** p_filt_params - Filter parameters
+** p_target - Target device
+** p_cmpl_back - Callback pointer
+** ref_value - reference value
+**
+** Returns void
+**
+*******************************************************************************/
+tBTM_STATUS BTM_BleAdvFilterParamSetup(int action, tBTM_BLE_PF_FILT_INDEX filt_index,
+ tBTM_BLE_PF_FILT_PARAMS *p_filt_params,
+ tBLE_BD_ADDR *p_target, tBTM_BLE_PF_PARAM_CBACK *p_cmpl_cback,
+ tBTM_BLE_REF_VALUE ref_value)
+{
+ UINT8 param[20], *p;
+ tBTM_STATUS st = BTM_WRONG_MODE;
+ tBTM_BLE_PF_COUNT *p_bda_filter = NULL;
+ UINT8 len =0;
+
+ p = param;
+ memset(param, 0, 20);
+ BTM_TRACE_EVENT (" BTM_BleAdvFilterParamSetup");
+
+ BTM_BleGetVendorCapabilities(&cmn_ble_vsc_cb);
+ if (0 == cmn_ble_vsc_cb.max_filter)
+ {
+ st = BTM_MODE_UNSUPPORTED;
+ return st;
+ }
+
+ btm_ble_adv_filt_cb.p_filt_param_cback = p_cmpl_cback;
+
+ if (BTM_BLE_SCAN_COND_ADD == action)
+ {
+ p_bda_filter = btm_ble_find_addr_filter_counter(p_target);
+ if (NULL == p_bda_filter)
+ {
+ BTM_TRACE_ERROR("BD Address not found!");
+ return st;
+ }
+
+ BTM_TRACE_DEBUG("BTM_BleAdvFilterParamSetup : Feat mask:%d", p_bda_filter->feat_mask);
+ /* select feature based on control block settings */
+ UINT8_TO_STREAM(p, BTM_BLE_META_PF_FEAT_SEL);
+ UINT8_TO_STREAM(p, BTM_BLE_SCAN_COND_ADD);
+
+ /* Filter index */
+ UINT8_TO_STREAM(p, filt_index);
+
+ /* set PCF selection */
+ UINT16_TO_STREAM(p, p_filt_params->feat_seln);
+ /* set logic type */
+ UINT16_TO_STREAM(p, p_filt_params->logic_type);
+ /* set logic condition */
+ UINT8_TO_STREAM(p, p_filt_params->filt_logic_type);
+ /* set RSSI high threshold */
+ UINT8_TO_STREAM(p, p_filt_params->rssi_high_thres);
+ /* set delivery mode */
+ UINT8_TO_STREAM(p, p_filt_params->dely_mode);
+
+ if(0x01 == p_filt_params->dely_mode)
+ {
+ /* set onfound timeout */
+ UINT16_TO_STREAM(p, p_filt_params->found_timeout);
+ /* set onfound timeout count*/
+ UINT8_TO_STREAM(p, p_filt_params->found_timeout_cnt);
+ /* set RSSI low threshold */
+ UINT8_TO_STREAM(p, p_filt_params->rssi_low_thres);
+ /* set onlost timeout */
+ UINT16_TO_STREAM(p, p_filt_params->lost_timeout);
+ }
+
+ len = BTM_BLE_ADV_FILT_META_HDR_LENGTH + BTM_BLE_ADV_FILT_FEAT_SELN_LEN;
+
+ if ((st = BTM_VendorSpecificCommand (HCI_BLE_ADV_FILTER_OCF,
+ (UINT8)len,
+ param,
+ btm_ble_scan_pf_cmpl_cback))
+ == BTM_NO_RESOURCES)
+ {
+ return st;
+ }
+ btm_ble_advfilt_enq_op_q(action, BTM_BLE_META_PF_FEAT_SEL, ref_value);
+ }
+ else
+ if(BTM_BLE_SCAN_COND_DELETE == action)
+ {
+ /* select feature based on control block settings */
+ UINT8_TO_STREAM(p, BTM_BLE_META_PF_FEAT_SEL);
+ UINT8_TO_STREAM(p, BTM_BLE_SCAN_COND_DELETE);
+ /* Filter index */
+ UINT8_TO_STREAM(p, filt_index);
+
+ if ((st = BTM_VendorSpecificCommand (HCI_BLE_ADV_FILTER_OCF,
+ (UINT8)(BTM_BLE_ADV_FILT_META_HDR_LENGTH),
+ param,
+ btm_ble_scan_pf_cmpl_cback))
+ == BTM_NO_RESOURCES)
+ {
+ return st;
+ }
+ btm_ble_advfilt_enq_op_q(action, BTM_BLE_META_PF_FEAT_SEL, ref_value);
+ }
+ else
+ if(BTM_BLE_SCAN_COND_CLEAR == action)
+ {
+ /* Deallocate all filters here */
+ btm_ble_dealloc_addr_filter_counter(NULL, BTM_BLE_PF_TYPE_ALL);
+
+ /* select feature based on control block settings */
+ UINT8_TO_STREAM(p, BTM_BLE_META_PF_FEAT_SEL);
+ UINT8_TO_STREAM(p, BTM_BLE_SCAN_COND_CLEAR);
+
+ if ((st = BTM_VendorSpecificCommand (HCI_BLE_ADV_FILTER_OCF,
+ (UINT8)(BTM_BLE_ADV_FILT_META_HDR_LENGTH-1),
+ param,
+ btm_ble_scan_pf_cmpl_cback))
+ == BTM_NO_RESOURCES)
+ {
+ return st;
+ }
+ btm_ble_advfilt_enq_op_q(action, BTM_BLE_META_PF_FEAT_SEL, ref_value);
+ }
+
+ return st;
+}
+
+/*******************************************************************************
+**
+** Function BTM_BleEnableDisableFilterFeature
+**
+** Description This function is called to enable / disable the APCF feature
+**
+** Parameters enable the generic scan condition.
+** enable: enable or disable the filter condition
+** p_stat_cback - Status callback pointer
+** ref_value - Ref value
+** Returns void
+**
+*******************************************************************************/
+tBTM_STATUS BTM_BleEnableDisableFilterFeature(UINT8 enable,
+ tBTM_BLE_PF_STATUS_CBACK *p_stat_cback,
+ tBTM_BLE_REF_VALUE ref_value)
+{
+ UINT8 param[20], *p;
+ tBTM_STATUS st = BTM_WRONG_MODE;
+
+ BTM_BleGetVendorCapabilities(&cmn_ble_vsc_cb);
+ if (0 == cmn_ble_vsc_cb.max_filter)
+ {
+ st = BTM_MODE_UNSUPPORTED;
+ return st;
+ }
+
+ p = param;
+ memset(param, 0, 20);
+
+ /* enable the content filter in controller */
+ p = param;
+ UINT8_TO_STREAM(p, BTM_BLE_META_PF_ENABLE);
+ /* enable adv data payload filtering */
+ UINT8_TO_STREAM(p, enable);
+
+ if ((st = BTM_VendorSpecificCommand (HCI_BLE_ADV_FILTER_OCF,
+ BTM_BLE_PCF_ENABLE_LEN, param,
+ btm_ble_scan_pf_cmpl_cback)) == BTM_CMD_STARTED)
+ {
+ btm_ble_adv_filt_cb.p_filt_stat_cback = p_stat_cback;
+ btm_ble_advfilt_enq_op_q(enable, BTM_BLE_META_PF_ENABLE, ref_value);
+ }
+ return st;
+}
+
+/*******************************************************************************
+**
+** Function BTM_BleCfgFilterCondition
+**
+** Description This function is called to configure the adv data payload filter
+** condition.
+**
+** Parameters action: to read/write/clear
+** cond_type: filter condition type.
+** filt_index - Filter index
+** p_cond: filter condition parameter
+** p_cmpl_cback - Config callback pointer
+** ref_value - Reference value
+**
+** Returns void
+**
+*******************************************************************************/
+tBTM_STATUS BTM_BleCfgFilterCondition(tBTM_BLE_SCAN_COND_OP action,
+ tBTM_BLE_PF_COND_TYPE cond_type,
+ tBTM_BLE_PF_FILT_INDEX filt_index,
+ tBTM_BLE_PF_COND_PARAM *p_cond,
+ tBTM_BLE_PF_CFG_CBACK *p_cmpl_cback,
+ tBTM_BLE_REF_VALUE ref_value)
+{
+ tBTM_STATUS st = BTM_ILLEGAL_VALUE;
+ BTM_TRACE_EVENT (" BTM_BleCfgFilterCondition action:%d, cond_type:%d, index:%d", action,
+ cond_type, filt_index);
+
+ BTM_BleGetVendorCapabilities(&cmn_ble_vsc_cb);
+ if (0 == cmn_ble_vsc_cb.max_filter)
+ {
+ st = BTM_MODE_UNSUPPORTED;
+ return st;
+ }
+
+ switch (cond_type)
+ {
+ /* write service data filter */
+ case BTM_BLE_PF_SRVC_DATA_PATTERN:
+ /* write manufacturer data filter */
+ case BTM_BLE_PF_MANU_DATA:
+ st = btm_ble_update_pf_manu_data(action, filt_index, p_cond, cond_type);
+ break;
+
+ /* write local name filter */
+ case BTM_BLE_PF_LOCAL_NAME:
+ st = btm_ble_update_pf_local_name(action, filt_index, p_cond);
+ break;
+
+ /* filter on advertiser address */
+ case BTM_BLE_PF_ADDR_FILTER:
+ st = btm_ble_update_addr_filter(action, filt_index, p_cond);
+ break;
+
+ /* filter on service/solicitated UUID */
+ case BTM_BLE_PF_SRVC_UUID:
+ case BTM_BLE_PF_SRVC_SOL_UUID:
+ st = btm_ble_update_uuid_filter(action, filt_index, cond_type, p_cond);
+ break;
+
+ case BTM_BLE_PF_SRVC_DATA:
+ st = btm_ble_update_srvc_data_change(action, filt_index, p_cond);
+ break;
+
+ case BTM_BLE_PF_TYPE_ALL: /* only used to clear filter */
+ st = btm_ble_clear_scan_pf_filter(action, filt_index, p_cond, ref_value);
+ break;
+
+ default:
+ BTM_TRACE_WARNING("condition type [%d] not supported currently.", cond_type);
+ break;
+ }
+
+ if (BTM_CMD_STARTED == st)
+ btm_ble_adv_filt_cb.p_scan_cfg_cback = p_cmpl_cback;
+ if(BTM_CMD_STARTED == st && cond_type != BTM_BLE_PF_TYPE_ALL)
+ btm_ble_advfilt_enq_op_q(action, cond_type, ref_value);
+
+ return st;
+}
+
+/*******************************************************************************
+**
+** Function btm_ble_adv_filter_init
+**
+** Description This function initializes the adv filter control block
+**
+** Parameters
+**
+** Returns status
+**
+*******************************************************************************/
+void btm_ble_adv_filter_init(void)
+{
+ memset(&btm_ble_adv_filt_cb, 0, sizeof(tBTM_BLE_MULTI_ADV_CB));
+ if (!HCI_LE_HOST_SUPPORTED(btm_cb.devcb.local_lmp_features[HCI_EXT_FEATURES_PAGE_1]))
+ return;
+}
+
+#endif
+#endif
*******************************************************************************/
BTM_API extern void BTM_BleGetVendorCapabilities(tBTM_BLE_VSC_CB *p_cmn_vsc_cb)
{
- BTM_TRACE_DEBUG("btm_ble_vendor_capability_init");
+ BTM_TRACE_DEBUG("BTM_BleGetVendorCapabilities");
if(NULL != p_cmn_vsc_cb)
{
btm_ble_batchscan_init();
#endif
+#if BLE_ANDROID_CONTROLLER_SCAN_FILTER == TRUE
+ btm_ble_adv_filter_init();
+#endif
}
/*******************************************************************************
extern void btm_ble_batchscan_init(void);
extern void btm_ble_multi_adv_reenable(UINT8 inst_id);
extern void btm_ble_multi_adv_enb_privacy(BOOLEAN enable);
+extern void btm_ble_adv_filter_init(void);
extern BOOLEAN btm_ble_topology_check(tBTM_BLE_STATE_MASK request);
extern BOOLEAN btm_ble_clear_topology_mask(tBTM_BLE_STATE_MASK request_state);
extern BOOLEAN btm_ble_set_topology_mask(tBTM_BLE_STATE_MASK request_state);
typedef void (tBTM_BLE_SCAN_THRESHOLD_CBACK)(tBTM_BLE_REF_VALUE ref_value);
typedef void (tBTM_BLE_SCAN_REP_CBACK)(tBTM_BLE_REF_VALUE ref_value, UINT8 report_format,
UINT8 num_records, UINT16 total_len,
- UINT8* p_rep_data, UINT8 status);
+ UINT8* p_rep_data, UINT8 status);
typedef void (tBTM_BLE_SCAN_SETUP_CBACK)(UINT8 evt, tBTM_BLE_REF_VALUE ref_value, UINT8 status);
#ifndef BTM_BLE_BATCH_SCAN_MAX
tBTM_BLE_REF_VALUE ref_value;
}tBTM_BLE_BATCH_SCAN_CB;
+/* filter selection bit index */
+#define BTM_BLE_PF_ADDR_FILTER 0
+#define BTM_BLE_PF_SRVC_DATA 1
+#define BTM_BLE_PF_SRVC_UUID 2
+#define BTM_BLE_PF_SRVC_SOL_UUID 3
+#define BTM_BLE_PF_LOCAL_NAME 4
+#define BTM_BLE_PF_MANU_DATA 5
+#define BTM_BLE_PF_SRVC_DATA_PATTERN 6
+#define BTM_BLE_PF_TYPE_ALL 7 /* when passed in payload filter type all, only clear action is applicable */
+#define BTM_BLE_PF_TYPE_MAX 8
+
+/* max number of filter spot for different filter type */
+#ifndef BTM_BLE_MAX_UUID_FILTER
+#define BTM_BLE_MAX_UUID_FILTER 8
+#endif
+#ifndef BTM_BLE_MAX_ADDR_FILTER
+#define BTM_BLE_MAX_ADDR_FILTER 8
+#endif
+#ifndef BTM_BLE_PF_STR_COND_MAX
+#define BTM_BLE_PF_STR_COND_MAX 4 /* apply to manu data , or local name */
+#endif
+#ifndef BTM_BLE_PF_STR_LEN_MAX
+#define BTM_BLE_PF_STR_LEN_MAX 29 /* match for first 29 bytes */
+#endif
+
+typedef UINT8 tBTM_BLE_PF_COND_TYPE;
+
+#define BTM_BLE_PF_LOGIC_OR 0
+#define BTM_BLE_PF_LOGIC_AND 1
+typedef UINT8 tBTM_BLE_PF_LOGIC_TYPE;
+
+#define BTM_BLE_PF_ENABLE 1
+#define BTM_BLE_PF_CONFIG 2
+typedef UINT8 tBTM_BLE_PF_ACTION;
+
+typedef UINT8 tBTM_BLE_PF_FILT_INDEX;
+
+typedef UINT8 tBTM_BLE_PF_AVBL_SPACE;
+
+#define BTM_BLE_PF_BRDCAST_ADDR_FILT 1
+#define BTM_BLE_PF_SERV_DATA_CHG_FILT 2
+#define BTM_BLE_PF_SERV_UUID 4
+#define BTM_BLE_PF_SERV_SOLC_UUID 8
+#define BTM_BLE_PF_LOC_NAME_CHECK 16
+#define BTM_BLE_PF_MANUF_NAME_CHECK 32
+#define BTM_BLE_PF_SERV_DATA_CHECK 64
+typedef UINT16 tBTM_BLE_PF_FEAT_SEL;
+
+#define BTM_BLE_PF_LIST_LOGIC_OR 1
+#define BTM_BLE_PF_LIST_LOGIC_AND 2
+typedef UINT16 tBTM_BLE_PF_LIST_LOGIC_TYPE;
+
+#define BTM_BLE_PF_FILT_LOGIC_OR 0
+#define BTM_BLE_PF_FILT_LOGIC_AND 1
+typedef UINT16 tBTM_BLE_PF_FILT_LOGIC_TYPE;
+
+typedef UINT8 tBTM_BLE_PF_RSSI_THRESHOLD;
+typedef UINT8 tBTM_BLE_PF_DELIVERY_MODE;
+typedef UINT16 tBTM_BLE_PF_TIMEOUT;
+typedef UINT8 tBTM_BLE_PF_TIMEOUT_CNT;
+
+typedef struct
+{
+ tBTM_BLE_PF_FEAT_SEL feat_seln;
+ tBTM_BLE_PF_LIST_LOGIC_TYPE logic_type;
+ tBTM_BLE_PF_FILT_LOGIC_TYPE filt_logic_type;
+ tBTM_BLE_PF_RSSI_THRESHOLD rssi_high_thres;
+ tBTM_BLE_PF_RSSI_THRESHOLD rssi_low_thres;
+ tBTM_BLE_PF_DELIVERY_MODE dely_mode;
+ tBTM_BLE_PF_TIMEOUT found_timeout;
+ tBTM_BLE_PF_TIMEOUT lost_timeout;
+ tBTM_BLE_PF_TIMEOUT_CNT found_timeout_cnt;
+}tBTM_BLE_PF_FILT_PARAMS;
+
+enum
+{
+ BTM_BLE_SCAN_COND_ADD,
+ BTM_BLE_SCAN_COND_DELETE,
+ BTM_BLE_SCAN_COND_CLEAR = 2
+};
+typedef UINT8 tBTM_BLE_SCAN_COND_OP;
+
+enum
+{
+ BTM_BLE_FILT_DISABLE = 0,
+ BTM_BLE_FILT_ENABLE = 1
+};
+typedef UINT8 tBTM_BLE_FILT_OP;
+
+/* BLE adv payload filtering config complete callback */
+typedef void (tBTM_BLE_PF_CFG_CBACK)(tBTM_BLE_PF_ACTION action, tBTM_BLE_SCAN_COND_OP cfg_op,
+ tBTM_BLE_PF_AVBL_SPACE avbl_space, tBTM_STATUS status,
+ tBTM_BLE_REF_VALUE ref_value);
+
+typedef void (tBTM_BLE_PF_CMPL_CBACK) (tBTM_BLE_PF_CFG_CBACK);
+
+/* BLE adv payload filtering status setup complete callback */
+typedef void (tBTM_BLE_PF_STATUS_CBACK) (UINT8 action, tBTM_STATUS status,
+ tBTM_BLE_REF_VALUE ref_value);
+
+/* BLE adv payload filtering param setup complete callback */
+typedef void (tBTM_BLE_PF_PARAM_CBACK) (tBTM_BLE_PF_ACTION action_type,
+ tBTM_BLE_PF_AVBL_SPACE avbl_space,
+ tBTM_BLE_REF_VALUE ref_value, tBTM_STATUS status);
+
+typedef union
+{
+ UINT16 uuid16_mask;
+ UINT32 uuid32_mask;
+ UINT8 uuid128_mask[LEN_UUID_128];
+}tBTM_BLE_PF_COND_MASK;
+
+typedef struct
+{
+ tBLE_BD_ADDR *p_target_addr; /* target address, if NULL, generic UUID filter */
+ tBT_UUID uuid; /* UUID condition */
+ tBTM_BLE_PF_LOGIC_TYPE cond_logic; /* AND/OR */
+ tBTM_BLE_PF_COND_MASK *p_uuid_mask; /* UUID mask */
+}tBTM_BLE_PF_UUID_COND;
+
+typedef struct
+{
+ UINT8 data_len; /* <= 20 bytes */
+ UINT8 *p_data;
+}tBTM_BLE_PF_LOCAL_NAME_COND;
+
+typedef struct
+{
+ UINT16 company_id; /* company ID */
+ UINT8 data_len; /* <= 20 bytes */
+ UINT8 *p_pattern;
+ UINT16 company_id_mask; /* UUID value mask */
+ UINT8 *p_pattern_mask; /* Manufactuer data matching mask, same length as data pattern,
+ set to all 0xff, match exact data */
+}tBTM_BLE_PF_MANU_COND;
+
+typedef struct
+{
+ UINT16 uuid; /* service ID */
+ UINT8 data_len; /* <= 20 bytes */
+ UINT8 *p_pattern;
+ UINT8 *p_pattern_mask; /* Service data matching mask, same length as data pattern,
+ set to all 0xff, match exact data */
+}tBTM_BLE_PF_SRVC_PATTERN_COND;
+
+
+typedef union
+{
+ tBLE_BD_ADDR target_addr;
+ tBTM_BLE_PF_LOCAL_NAME_COND local_name; /* lcoal name filtering */
+ tBTM_BLE_PF_MANU_COND manu_data; /* manufactuer data filtering */
+ tBTM_BLE_PF_UUID_COND srvc_uuid; /* service UUID filtering */
+ tBTM_BLE_PF_UUID_COND solicitate_uuid; /* solicitated service UUID filtering */
+ tBTM_BLE_PF_SRVC_PATTERN_COND srvc_data; /* service data pattern */
+}tBTM_BLE_PF_COND_PARAM;
+
+typedef struct
+{
+ UINT8 action_condtype[BTM_BLE_PF_TYPE_MAX];
+ tBTM_BLE_REF_VALUE ref_value[BTM_BLE_PF_TYPE_MAX];
+ UINT8 pending_idx;
+ UINT8 next_idx;
+}tBTM_BLE_ADV_FILTER_ADV_OPQ;
+
+#define BTM_BLE_MAX_FILTER_COUNTER (BTM_BLE_MAX_ADDR_FILTER + 1) /* per device filter + one generic filter indexed by 0 */
+
+typedef struct
+{
+ BOOLEAN in_use;
+ BD_ADDR bd_addr;
+ UINT16 feat_mask; /* per BD_ADDR feature mask */
+ UINT8 pf_counter[BTM_BLE_PF_TYPE_MAX]; /* number of filter indexed by tBTM_BLE_PF_COND_TYPE */
+}tBTM_BLE_PF_COUNT;
+
+typedef struct
+{
+ BOOLEAN enable;
+ UINT8 op_type;
+ tBTM_BLE_PF_COUNT addr_filter_count[BTM_BLE_MAX_FILTER_COUNTER]; /* per BDA filter indexed by tBTM_BLE_PF_COND_TYPE */
+ tBLE_BD_ADDR cur_filter_target;
+ tBTM_BLE_PF_CFG_CBACK *p_scan_cfg_cback;
+ tBTM_BLE_PF_PARAM_CBACK *p_filt_param_cback;
+ tBTM_BLE_PF_STATUS_CBACK *p_filt_stat_cback;
+ tBTM_BLE_ADV_FILTER_ADV_OPQ op_q;
+}tBTM_BLE_ADV_FILTER_CB;
+
+/* Sub codes */
+#define BTM_BLE_META_PF_ENABLE 0x00
+#define BTM_BLE_META_PF_FEAT_SEL 0x01
+#define BTM_BLE_META_PF_ADDR 0x02
+#define BTM_BLE_META_PF_UUID 0x03
+#define BTM_BLE_META_PF_SOL_UUID 0x04
+#define BTM_BLE_META_PF_LOCAL_NAME 0x05
+#define BTM_BLE_META_PF_MANU_DATA 0x06
+#define BTM_BLE_META_PF_SRVC_DATA 0x07
+#define BTM_BLE_META_PF_ALL 0x08
+
/* These are the fields returned in each device adv packet. It
** is returned in the results callback if registered.
*/
*******************************************************************************/
BTM_API extern tBTM_STATUS BTM_BleDisableAdvInstance (UINT8 inst_id);
+/*******************************************************************************
+**
+** Function BTM_BleAdvFilterParamSetup
+**
+** Description This function is called to setup the adv data payload filter
+** condition.
+**
+** Parameters p_target: enabble the filter condition on a target device; if NULL
+** enable the generic scan condition.
+** enable: enable or disable the filter condition
+**
+** Returns void
+**
+*******************************************************************************/
+BTM_API extern tBTM_STATUS BTM_BleAdvFilterParamSetup(int action,
+ tBTM_BLE_PF_FILT_INDEX filt_index,
+ tBTM_BLE_PF_FILT_PARAMS *p_filt_params,
+ tBLE_BD_ADDR *p_target, tBTM_BLE_PF_PARAM_CBACK *p_cmpl_cback,
+ tBTM_BLE_REF_VALUE ref_value);
+
+/*******************************************************************************
+**
+** Function BTM_BleCfgFilterCondition
+**
+** Description This function is called to configure the adv data payload filter
+** condition.
+**
+** Parameters action: to read/write/clear
+** cond_type: filter condition type.
+** p_cond: filter condition paramter
+**
+** Returns tBTM_STATUS
+**
+*******************************************************************************/
+BTM_API extern tBTM_STATUS BTM_BleCfgFilterCondition(tBTM_BLE_SCAN_COND_OP action,
+ tBTM_BLE_PF_COND_TYPE cond_type,
+ tBTM_BLE_PF_FILT_INDEX filt_index,
+ tBTM_BLE_PF_COND_PARAM *p_cond,
+ tBTM_BLE_PF_CFG_CBACK *p_cmpl_cback,
+ tBTM_BLE_REF_VALUE ref_value);
+
+/*******************************************************************************
+**
+** Function BTM_BleEnableDisableFilterFeature
+**
+** Description This function is called to enable or disable the APCF feature
+**
+** Parameters enable - TRUE - enables the APCF, FALSE - disables the APCF
+** ref_value - Ref value
+**
+** Returns tBTM_STATUS
+**
+*******************************************************************************/
+BTM_API extern tBTM_STATUS BTM_BleEnableDisableFilterFeature(UINT8 enable,
+ tBTM_BLE_PF_STATUS_CBACK *p_stat_cback,
+ tBTM_BLE_REF_VALUE ref_value);
+
+
#ifdef __cplusplus
}
#endif
/* Batch scan OCF */
#define HCI_BLE_BATCH_SCAN_OCF (0x0156 | HCI_GRP_VENDOR_SPECIFIC)
+/* ADV filter OCF */
+#define HCI_BLE_ADV_FILTER_OCF (0x0157 | HCI_GRP_VENDOR_SPECIFIC)
+
/* Tracking OCF */
#define HCI_BLE_TRACK_ADV_OCF (0x0158 | HCI_GRP_VENDOR_SPECIFIC)
#include "vendor_hcidefs.h"
#include "gatt_int.h"
-#define BTM_BLE_INVALID_COUNTER 0xff
-
-
-static UINT8 btm_ble_cs_update_pf_counter(tBTM_BLE_SCAN_COND_OP action,
- UINT8 cond_type,
- tBLE_BD_ADDR *p_bd_addr,
- UINT8 num_available);
-
-#define BTM_BLE_SET_SCAN_PF_OPCODE(x, y) (((x)<<4)|y)
-#define BTM_BLE_GET_SCAN_PF_SUBCODE(x) ((x) >> 4)
-#define BTM_BLE_GET_SCAN_PF_ACTION(x) ((x) & 0x0f)
-
-/* max number of filter available for different filter type, controller dependent number */
-static const UINT8 btm_ble_cs_filter_max[BTM_BLE_PF_TYPE_MAX] =
-{
- BTM_BLE_MAX_ADDR_FILTER, /* address filter */
- 1, /* no limit for service data change, always enable or disable */
- BTM_BLE_MAX_UUID_FILTER, /* service UUID filter */
- BTM_BLE_MAX_UUID_FILTER, /* solicitated UUID filter */
- BTM_BLE_PF_STR_COND_MAX, /* local name filter */
- BTM_BLE_PF_STR_COND_MAX /* manufacturer data filter */
-};
-
/*** This needs to be moved to a VSC control block eventually per coding conventions ***/
#if VENDOR_DYNAMIC_MEMORY == FALSE
tBTM_BLE_VENDOR_CB btm_ble_vendor_cb;
#endif
-static const UINT8 op_code_to_cond_type[] =
-{
- BTM_BLE_PF_TYPE_ALL,
- BTM_BLE_PF_ADDR_FILTER,
- BTM_BLE_PF_SRVC_UUID,
- BTM_BLE_PF_SRVC_SOL_UUID,
- BTM_BLE_PF_LOCAL_NAME,
- BTM_BLE_PF_MANU_DATA,
- BTM_BLE_PF_SRVC_DATA_PATTERN
-};
-
static const BD_ADDR na_bda= {0};
-/*******************************************************************************
-**
-** Function btm_ble_vendor_scan_pf_cmpl_cback
-**
-** Description the BTM BLE customer feature VSC complete callback for ADV PF
-** filtering
-**
-** Returns pointer to the counter if found; NULL otherwise.
-**
-*******************************************************************************/
-void btm_ble_vendor_scan_pf_cmpl_cback(tBTM_VSC_CMPL *p_params)
-{
- UINT8 status;
- UINT8 *p = p_params->p_param_buf, op_subcode, action = 0xff;
- UINT16 evt_len = p_params->param_len;
- UINT8 num_avail = 0, cond_type = BTM_BLE_PF_TYPE_MAX;
- tBTM_BLE_PF_CMPL_CBACK *p_cmpl_cback = btm_ble_vendor_cb.p_scan_pf_cback;
- UINT8 op = BTM_BLE_GET_SCAN_PF_ACTION(btm_ble_vendor_cb.op_type);
- UINT8 subcode = BTM_BLE_GET_SCAN_PF_SUBCODE(btm_ble_vendor_cb.op_type);
-
- STREAM_TO_UINT8(status, p);
-
- evt_len--;
-
- if (evt_len < 1 )
- {
- BTM_TRACE_ERROR("can not interpret ADV PF filter setting callback. status = %d", status);
- return;
- }
- op_subcode = *p ++;
- switch (op_subcode)
- {
- case BTM_BLE_META_PF_LOCAL_NAME:
- case BTM_BLE_META_PF_MANU_DATA:
- case BTM_BLE_META_PF_ADDR:
- case BTM_BLE_META_PF_UUID:
- case BTM_BLE_META_PF_SOL_UUID:
- case BTM_BLE_META_PF_FEAT_SEL:
- case BTM_BLE_META_PF_SRVC_DATA:
- cond_type = op_code_to_cond_type[op_subcode - BTM_BLE_META_PF_FEAT_SEL];
- if (status == HCI_SUCCESS)
- {
- action = *p ++;
- if (op_subcode != BTM_BLE_META_PF_FEAT_SEL)
- {
- STREAM_TO_UINT8(num_avail, p);
- }
-
- if (memcmp(&btm_ble_vendor_cb.cur_filter_target.bda, &na_bda, BD_ADDR_LEN) == 0)
- btm_ble_cs_update_pf_counter(action, cond_type, NULL, num_avail);
- else
- btm_ble_cs_update_pf_counter(action, cond_type, &btm_ble_vendor_cb.cur_filter_target, num_avail);
- }
- break;
-
- case BTM_BLE_META_PF_ENABLE:
- cond_type = BTM_BLE_META_PF_ENABLE;
- BTM_TRACE_DEBUG("CS feature Enabled");
- break;
-
- default:
- BTM_TRACE_ERROR("unknow operation: %d", op_subcode);
- break;
- }
-
- /* send ADV PF opeartion complete */
- if (p_cmpl_cback && subcode == cond_type)
- {
- btm_ble_vendor_cb.p_scan_pf_cback = NULL;
- btm_ble_vendor_cb.op_type = 0;
- (* p_cmpl_cback)(op, subcode, status);
- }
-}
-/*******************************************************************************
-** adv payload filtering functions
-*******************************************************************************/
-/*******************************************************************************
-**
-** Function btm_ble_find_addr_filter_counter
-**
-** Description find the per bd address ADV payload filter counter by BD_ADDR.
-**
-** Returns pointer to the counter if found; NULL otherwise.
-**
-*******************************************************************************/
-tBTM_BLE_PF_COUNT * btm_ble_find_addr_filter_counter(tBLE_BD_ADDR *p_le_bda)
-{
- UINT8 i;
- tBTM_BLE_PF_COUNT *p_addr_filter = &btm_ble_vendor_cb.addr_filter_count[1];
-
- if (p_le_bda == NULL)
- return &btm_ble_vendor_cb.addr_filter_count[0];
-
- for (i = 0; i < BTM_BLE_MAX_FILTER_COUNTER; i ++, p_addr_filter ++)
- {
- if (p_addr_filter->in_use &&
- memcmp(p_le_bda->bda, p_addr_filter->bd_addr, BD_ADDR_LEN) == 0)
- {
- return p_addr_filter;
- }
- }
- return NULL;
-}
-
-/*******************************************************************************
-**
-** Function btm_ble_alloc_addr_filter_counter
-**
-** Description allocate the per device adv payload filter counter.
-**
-** Returns pointer to the counter if allocation succeed; NULL otherwise.
-**
-*******************************************************************************/
-tBTM_BLE_PF_COUNT * btm_ble_alloc_addr_filter_counter(BD_ADDR bd_addr)
-{
- UINT8 i;
- tBTM_BLE_PF_COUNT *p_addr_filter = &btm_ble_vendor_cb.addr_filter_count[1];
-
- for (i = 0; i < BTM_BLE_MAX_FILTER_COUNTER; i ++, p_addr_filter ++)
- {
- if (memcmp(na_bda, p_addr_filter->bd_addr, BD_ADDR_LEN) == 0)
- {
- memcpy(p_addr_filter->bd_addr, bd_addr, BD_ADDR_LEN);
- p_addr_filter->in_use = TRUE;
- return p_addr_filter;
- }
- }
- return NULL;
-}
-/*******************************************************************************
-**
-** Function btm_ble_dealloc_addr_filter_counter
-**
-** Description de-allocate the per device adv payload filter counter.
-**
-** Returns TRUE if deallocation succeed; FALSE otherwise.
-**
-*******************************************************************************/
-BOOLEAN btm_ble_dealloc_addr_filter_counter(tBLE_BD_ADDR *p_bd_addr, UINT8 filter_type)
-{
- UINT8 i;
- tBTM_BLE_PF_COUNT *p_addr_filter = &btm_ble_vendor_cb.addr_filter_count[1];
- BOOLEAN found = FALSE;
-
- if (filter_type == BTM_BLE_PF_TYPE_ALL && p_bd_addr == NULL)
- memset(&btm_ble_vendor_cb.addr_filter_count[0], 0, sizeof(tBTM_BLE_PF_COUNT));
-
- for (i = 0; i < BTM_BLE_MAX_FILTER_COUNTER; i ++, p_addr_filter ++)
- {
- if ((p_addr_filter->in_use) &&
- (p_bd_addr == NULL ||
- (p_bd_addr != NULL && memcmp(p_bd_addr->bda, p_addr_filter->bd_addr, BD_ADDR_LEN) == 0)))
- {
- found = TRUE;
- memset(p_addr_filter, 0, sizeof(tBTM_BLE_PF_COUNT));
-
- if (p_bd_addr != NULL) break;
- }
- }
- return found;
-}
-/*******************************************************************************
-**
-** Function btm_ble_cs_update_pf_counter
-**
-** Description this function is to update the adv data payload filter counter
-**
-** Returns current number of the counter; BTM_BLE_INVALID_COUNTER if
-** counter update failed.
-**
-*******************************************************************************/
-UINT8 btm_ble_cs_update_pf_counter(tBTM_BLE_SCAN_COND_OP action,
- UINT8 cond_type,
- tBLE_BD_ADDR *p_bd_addr,
- UINT8 num_available)
-{
- tBTM_BLE_PF_COUNT *p_addr_filter = NULL;
- UINT8 *p_counter = NULL;
- UINT32 *p_feat_mask = NULL;
-
-
- if (cond_type > BTM_BLE_PF_TYPE_ALL)
- {
- BTM_TRACE_ERROR("unknown PF filter condition type %d", cond_type);
- return BTM_BLE_INVALID_COUNTER;
- }
- /* for these three types of filter, always generic */
- if (cond_type == BTM_BLE_PF_ADDR_FILTER ||
- cond_type == BTM_BLE_PF_MANU_DATA ||
- cond_type == BTM_BLE_PF_LOCAL_NAME ||
- cond_type == BTM_BLE_PF_SRVC_DATA_PATTERN)
- p_bd_addr = NULL;
-
- if ((p_addr_filter = btm_ble_find_addr_filter_counter(p_bd_addr)) == NULL &&
- action == BTM_BLE_SCAN_COND_ADD)
- {
- p_addr_filter = btm_ble_alloc_addr_filter_counter(p_bd_addr->bda);
- }
-
- if (p_addr_filter != NULL)
- {
- /* all filter just cleared */
- if ((cond_type == BTM_BLE_PF_TYPE_ALL && action == BTM_BLE_SCAN_COND_CLEAR) ||
- /* or bd address filter been deleted */
- (cond_type == BTM_BLE_PF_ADDR_FILTER &&
- (action == BTM_BLE_SCAN_COND_DELETE || action == BTM_BLE_SCAN_COND_CLEAR)))
- {
- btm_ble_dealloc_addr_filter_counter(p_bd_addr, cond_type);
- }
- /* if not feature selection, update new addition/reduction of the filter counter */
- else if (cond_type != BTM_BLE_PF_TYPE_ALL)
- {
- p_counter = p_addr_filter->pf_counter;
- p_feat_mask = &p_addr_filter->feat_mask;
-
- p_counter[cond_type] = btm_ble_cs_filter_max[cond_type] - num_available;
-
- BTM_TRACE_DEBUG("current filter counter number = %d", p_counter[cond_type]);
-
- /* update corresponding feature mask */
- if (p_counter[cond_type] > 0)
- *p_feat_mask |= (BTM_BLE_PF_BIT_TO_MASK(cond_type));
- else
- *p_feat_mask &= ~(BTM_BLE_PF_BIT_TO_MASK(cond_type));
-
- return p_counter[cond_type];
- }
- }
- else
- {
- BTM_TRACE_ERROR("no matching filter counter found");
- }
- /* no matching filter located and updated */
- return BTM_BLE_INVALID_COUNTER;
-}
-/*******************************************************************************
-**
-** Function btm_ble_update_pf_manu_data
-**
-** Description this function update(add,delete or clear) the adv manufacturer
-** data filtering condition.
-**
-**
-** Returns BTM_SUCCESS if sucessful,
-** BTM_ILLEGAL_VALUE if paramter is not valid.
-**
-*******************************************************************************/
-tBTM_STATUS btm_ble_update_pf_manu_data(tBTM_BLE_SCAN_COND_OP action,
- tBTM_BLE_PF_COND_PARAM *p_data,
- tBTM_BLE_PF_COND_TYPE cond_type)
-{
- tBTM_BLE_PF_MANU_COND *p_manu_data = (p_data == NULL) ? NULL : &p_data->manu_data;
- tBTM_BLE_PF_SRVC_PATTERN_COND *p_srvc_data = (p_data == NULL) ? NULL : &p_data->srvc_data;
- UINT8 param[BTM_BLE_PF_STR_LEN_MAX + BTM_BLE_PF_STR_LEN_MAX + BTM_BLE_META_HDR_LENGTH],
- *p = param,
- len = BTM_BLE_META_HDR_LENGTH;
- tBTM_STATUS st = BTM_ILLEGAL_VALUE;
-
- memset(param, 0, BTM_BLE_PF_STR_LEN_MAX + BTM_BLE_META_HDR_LENGTH);
-
- if (cond_type == BTM_BLE_PF_SRVC_DATA_PATTERN)
- {
- UINT8_TO_STREAM(p, BTM_BLE_META_PF_SRVC_DATA);
- }
- else
- {
- UINT8_TO_STREAM(p, BTM_BLE_META_PF_MANU_DATA);
- }
- UINT8_TO_STREAM(p, action);
-
- /* Filter index */
- UINT8_TO_STREAM(p, 0);
-
- if (action == BTM_BLE_SCAN_COND_ADD ||
- action == BTM_BLE_SCAN_COND_DELETE)
- {
- if (p_manu_data == NULL)
- return st;
- if (cond_type == BTM_BLE_PF_SRVC_DATA_PATTERN)
- {
- if (p_srvc_data->data_len > (BTM_BLE_PF_STR_LEN_MAX - 2))
- p_srvc_data->data_len = (BTM_BLE_PF_STR_LEN_MAX - 2);
-
- UINT16_TO_STREAM(p, p_srvc_data->uuid);
- ARRAY_TO_STREAM(p, p_srvc_data->p_pattern, p_srvc_data->data_len);
- len += (p_srvc_data->data_len + 2);
- }
- else
- {
- if (p_manu_data->data_len > (BTM_BLE_PF_STR_LEN_MAX - 2))
- p_manu_data->data_len = (BTM_BLE_PF_STR_LEN_MAX - 2);
-
- UINT16_TO_STREAM(p, p_manu_data->company_id);
- ARRAY_TO_STREAM(p, p_manu_data->p_pattern, p_manu_data->data_len);
- len += (p_manu_data->data_len + 2);
-
- if (p_manu_data->company_id_mask != 0)
- {
- UINT16_TO_STREAM (p, p_manu_data->company_id_mask);
- }
- else
- {
- memset(p, 0xff, 2);
- p += 2;
- }
- if (p_manu_data->p_pattern_mask != NULL)
- {
- ARRAY_TO_STREAM(p, p_manu_data->p_pattern_mask, p_manu_data->data_len);
- }
- else
- memset(p, 0xff, p_manu_data->data_len);
- len += (p_manu_data->data_len + 2);
- }
- }
-
- /* send manufacturer*/
- if ((st = BTM_VendorSpecificCommand (HCI_VENDOR_BLE_PCF_VSC,
- len,
- param,
- btm_ble_vendor_scan_pf_cmpl_cback)) != BTM_NO_RESOURCES)
- {
- memset(&btm_ble_vendor_cb.cur_filter_target, 0, sizeof(tBLE_BD_ADDR));
- }
- else
- {
- BTM_TRACE_ERROR("manufacturer data PF filter update failed");
- }
-
- return st;
-}
-/*******************************************************************************
-**
-** Function btm_ble_update_pf_local_name
-**
-** Description this function update(add,delete or clear) the adv lcoal name
-** filtering condition.
-**
-**
-** Returns BTM_SUCCESS if sucessful,
-** BTM_ILLEGAL_VALUE if paramter is not valid.
-**
-*******************************************************************************/
-tBTM_STATUS btm_ble_update_pf_local_name(tBTM_BLE_SCAN_COND_OP action,
- tBTM_BLE_PF_COND_PARAM *p_cond)
-{
- tBTM_BLE_PF_LOCAL_NAME_COND *p_local_name = (p_cond == NULL) ? NULL : &p_cond->local_name;
- UINT8 param[BTM_BLE_PF_STR_LEN_MAX + BTM_BLE_META_HDR_LENGTH],
- *p = param,
- len = BTM_BLE_META_HDR_LENGTH;
- tBTM_STATUS st = BTM_ILLEGAL_VALUE;
-
- memset(param, 0, BTM_BLE_PF_STR_LEN_MAX + BTM_BLE_META_HDR_LENGTH);
-
- UINT8_TO_STREAM(p, BTM_BLE_META_PF_LOCAL_NAME);
- UINT8_TO_STREAM(p, action);
-
- /* Filter index */
- UINT8_TO_STREAM(p, 0);
-
- if (action == BTM_BLE_SCAN_COND_ADD ||
- action == BTM_BLE_SCAN_COND_DELETE)
- {
- if (p_local_name == NULL)
- return st;
-
- if (p_local_name->data_len > BTM_BLE_PF_STR_LEN_MAX)
- p_local_name->data_len = BTM_BLE_PF_STR_LEN_MAX;
-
- ARRAY_TO_STREAM(p, p_local_name->p_data, p_local_name->data_len);
- len += p_local_name->data_len;
- }
- /* send local name filter */
- if ((st = BTM_VendorSpecificCommand (HCI_VENDOR_BLE_PCF_VSC,
- len,
- param,
- btm_ble_vendor_scan_pf_cmpl_cback))
- != BTM_NO_RESOURCES)
- {
- memset(&btm_ble_vendor_cb.cur_filter_target, 0, sizeof(tBLE_BD_ADDR));
- }
- else
- {
- BTM_TRACE_ERROR("Local Name PF filter update failed");
- }
-
- return st;
-}
-/*******************************************************************************
-**
-** Function btm_ble_update_addr_filter
-**
-** Description this function update(add,delete or clear) the address filter of adv.
-**
-**
-** Returns BTM_SUCCESS if sucessful,
-** BTM_ILLEGAL_VALUE if paramter is not valid.
-**
-*******************************************************************************/
-tBTM_STATUS btm_ble_update_addr_filter(tBTM_BLE_SCAN_COND_OP action,
- tBTM_BLE_PF_COND_PARAM *p_cond)
-{
- UINT8 param[BTM_BLE_META_ADDR_LEN + BTM_BLE_META_HDR_LENGTH],
- * p= param;
- tBTM_STATUS st = BTM_ILLEGAL_VALUE;
- tBLE_BD_ADDR *p_addr = (p_cond == NULL) ? NULL : &p_cond->target_addr;
-
- memset(param, 0, BTM_BLE_META_ADDR_LEN + BTM_BLE_META_HDR_LENGTH);
-
- UINT8_TO_STREAM(p, BTM_BLE_META_PF_ADDR);
- UINT8_TO_STREAM(p, action);
-
- /* Filter index */
- UINT8_TO_STREAM(p, 0);
-
- if (action == BTM_BLE_SCAN_COND_ADD ||
- action == BTM_BLE_SCAN_COND_DELETE)
- {
- if (p_addr == NULL)
- return st;
-
- BDADDR_TO_STREAM(p, p_addr->bda);
- UINT8_TO_STREAM(p, p_addr->type);
- }
- /* send address filter */
- if ((st = BTM_VendorSpecificCommand (HCI_VENDOR_BLE_PCF_VSC,
- (UINT8)(BTM_BLE_META_HDR_LENGTH + BTM_BLE_META_ADDR_LEN),
- param,
- btm_ble_vendor_scan_pf_cmpl_cback)) != BTM_NO_RESOURCES)
- {
- memset(&btm_ble_vendor_cb.cur_filter_target, 0, sizeof(tBLE_BD_ADDR));
- }
- else
- {
- BTM_TRACE_ERROR("Broadcaster Address Filter Update failed");
- }
- return st;
-}
-/*******************************************************************************
-**
-** Function btm_ble_update_uuid_filter
-**
-** Description this function update(add,delete or clear) service UUID filter.
-**
-**
-** Returns BTM_SUCCESS if sucessful,
-** BTM_ILLEGAL_VALUE if paramter is not valid.
-**
-*******************************************************************************/
-tBTM_STATUS btm_ble_update_uuid_filter(tBTM_BLE_SCAN_COND_OP action,
- tBTM_BLE_PF_COND_TYPE filter_type,
- tBTM_BLE_PF_COND_PARAM *p_cond)
-{
- UINT8 param[BTM_BLE_META_UUID_LEN + BTM_BLE_META_HDR_LENGTH],
- * p= param,
- len = BTM_BLE_META_HDR_LENGTH;
- tBTM_STATUS st = BTM_ILLEGAL_VALUE;
- tBTM_BLE_PF_UUID_COND *p_uuid_cond;
- UINT8 evt_type;
-
- memset(param, 0, BTM_BLE_META_UUID_LEN + BTM_BLE_META_HDR_LENGTH);
-
- if (filter_type == BTM_BLE_PF_SRVC_UUID)
- {
- evt_type = BTM_BLE_META_PF_UUID;
- p_uuid_cond = p_cond ? &p_cond->srvc_uuid : NULL;
- }
- else
- {
- evt_type = BTM_BLE_META_PF_SOL_UUID;
- p_uuid_cond = p_cond ? &p_cond->solicitate_uuid : NULL;
- }
-
- if (p_uuid_cond == NULL && action != BTM_BLE_SCAN_COND_CLEAR)
- {
- BTM_TRACE_ERROR("Illegal param for add/delete UUID filter");
- return st;
- }
-
- /* need to add address fitler first, if adding per bda UUID filter without address filter */
- if (action == BTM_BLE_SCAN_COND_ADD &&
- p_uuid_cond->p_target_addr &&
- btm_ble_find_addr_filter_counter(p_uuid_cond->p_target_addr) == NULL)
- {
- UINT8_TO_STREAM(p, BTM_BLE_META_PF_ADDR);
- UINT8_TO_STREAM(p, action);
-
- /* Filter index */
- UINT8_TO_STREAM(p, 0);
-
- BDADDR_TO_STREAM(p, p_uuid_cond->p_target_addr->bda);
- UINT8_TO_STREAM(p, p_uuid_cond->p_target_addr->type);
-
- /* send address filter */
- if ((st = BTM_VendorSpecificCommand (HCI_VENDOR_BLE_PCF_VSC,
- (UINT8)(BTM_BLE_META_HDR_LENGTH + BTM_BLE_META_ADDR_LEN),
- param,
- btm_ble_vendor_scan_pf_cmpl_cback)) == BTM_NO_RESOURCES)
- {
- BTM_TRACE_ERROR("Update Address filter into controller failed.");
- return st;
- }
- }
-
- p= param;
- UINT8_TO_STREAM(p, evt_type);
- UINT8_TO_STREAM(p, action);
-
- /* Filter index */
- UINT8_TO_STREAM(p, 0);
-
- if (action == BTM_BLE_SCAN_COND_ADD ||
- action == BTM_BLE_SCAN_COND_DELETE)
- {
- if (p_uuid_cond->uuid.len == LEN_UUID_16)
- {
- UINT16_TO_STREAM(p, p_uuid_cond->uuid.uu.uuid16);
- len += LEN_UUID_16;
- }
- else if (p_uuid_cond->uuid.len == LEN_UUID_32)/*4 bytes */
- {
- UINT32_TO_STREAM(p, p_uuid_cond->uuid.uu.uuid32);
- len += LEN_UUID_32;
- }
- else if (p_uuid_cond->uuid.len == LEN_UUID_128)
- {
- ARRAY_TO_STREAM (p, p_uuid_cond->uuid.uu.uuid128, LEN_UUID_128);
- len += LEN_UUID_128;
- }
- else
- {
- BTM_TRACE_ERROR("illegal UUID length: %d", p_uuid_cond->uuid.len);
- return BTM_ILLEGAL_VALUE;
- }
-#if !(defined VENDOR_ADV_PCF_LEGACY && VENDOR_ADV_PCF_LEGACY == TRUE)
- if (p_uuid_cond->p_uuid_mask != NULL)
- {
- if (p_uuid_cond->uuid.len == LEN_UUID_16)
- {
- UINT16_TO_STREAM(p, p_uuid_cond->p_uuid_mask->uuid16_mask);
- len += LEN_UUID_16;
- }
- else if (p_uuid_cond->uuid.len == LEN_UUID_32)/*4 bytes */
- {
- UINT32_TO_STREAM(p, p_uuid_cond->p_uuid_mask->uuid32_mask);
- len += LEN_UUID_32;
- }
- else if (p_uuid_cond->uuid.len == LEN_UUID_128)
- {
- ARRAY_TO_STREAM (p, p_uuid_cond->p_uuid_mask->uuid128_mask, LEN_UUID_128);
- len += LEN_UUID_128;
- }
- }
- else
- {
- memset(p, 0xff, p_uuid_cond->uuid.len);
- len += p_uuid_cond->uuid.len;
- }
-#endif
- }
-
- /* send UUID filter update */
- if ((st = BTM_VendorSpecificCommand (HCI_VENDOR_BLE_PCF_VSC,
- len,
- param,
- btm_ble_vendor_scan_pf_cmpl_cback)) != BTM_NO_RESOURCES)
- {
- if (p_uuid_cond && p_uuid_cond->p_target_addr)
- memcpy(&btm_ble_vendor_cb.cur_filter_target, p_uuid_cond->p_target_addr, sizeof(tBLE_BD_ADDR));
- else
- memset(&btm_ble_vendor_cb.cur_filter_target, 0, sizeof(tBLE_BD_ADDR));
- }
- else
- {
- BTM_TRACE_ERROR("UUID filter udpating failed");
- }
-
- return st;
-}
-/*******************************************************************************
-**
-** Function btm_ble_update_srvc_data_change
-**
-** Description this function update(add/remove) service data change filter.
-**
-**
-** Returns BTM_SUCCESS if sucessful,
-** BTM_ILLEGAL_VALUE if paramter is not valid.
-**
-*******************************************************************************/
-tBTM_STATUS btm_ble_update_srvc_data_change(tBTM_BLE_SCAN_COND_OP action,
- tBTM_BLE_PF_COND_PARAM *p_cond)
-{
- tBTM_STATUS st = BTM_ILLEGAL_VALUE;
- tBLE_BD_ADDR *p_bd_addr = p_cond ? &p_cond->target_addr : NULL;
- UINT8 num_avail = (action == BTM_BLE_SCAN_COND_ADD) ? 0 : 1;
-
- if (btm_ble_cs_update_pf_counter (action, BTM_BLE_PF_SRVC_DATA, p_bd_addr, num_avail)
- != BTM_BLE_INVALID_COUNTER)
- st = BTM_SUCCESS;
-
- return st;
-}
-
-/*******************************************************************************
-**
-** Function btm_ble_clear_scan_pf_filter
-**
-** Description clear all adv payload filter by de-select all the adv pf feature bits
-**
-**
-** Returns BTM_SUCCESS if sucessful,
-** BTM_ILLEGAL_VALUE if paramter is not valid.
-**
-*******************************************************************************/
-tBTM_STATUS btm_ble_clear_scan_pf_filter(tBTM_BLE_SCAN_COND_OP action,
- tBTM_BLE_PF_COND_PARAM *p_cond)
-{
- tBLE_BD_ADDR *p_target = (p_cond == NULL)? NULL : &p_cond->target_addr;
- tBTM_BLE_PF_COUNT *p_bda_filter;
- tBTM_STATUS st = BTM_WRONG_MODE;
- UINT8 param[20], *p;
-
- if (action != BTM_BLE_SCAN_COND_CLEAR)
- {
- BTM_TRACE_ERROR("unable to perform action:%d for generic adv filter type", action);
- return BTM_ILLEGAL_VALUE;
- }
-
- p = param;
- memset(param, 0, 20);
-
- p_bda_filter = btm_ble_find_addr_filter_counter(p_target);
-
- if (p_bda_filter == NULL ||
- /* not a generic filter, and feature selection is empty */
- (p_target != NULL && p_bda_filter && p_bda_filter->feat_mask == 0))
- {
- BTM_TRACE_ERROR("Error: Can not clear filter, No PF filter has been configured!");
- return st;
- }
-
- /* clear the general filter entry */
- if (p_target == NULL)
- {
- /* clear manufactuer data filter */
- btm_ble_update_pf_manu_data(BTM_BLE_SCAN_COND_CLEAR, NULL, BTM_BLE_PF_MANU_DATA);
- /* clear local name filter */
- btm_ble_update_pf_local_name(BTM_BLE_SCAN_COND_CLEAR, NULL);
- /* update the counter for service data */
- btm_ble_update_srvc_data_change(BTM_BLE_SCAN_COND_CLEAR, NULL);
- /* clear UUID filter */
- btm_ble_update_uuid_filter(BTM_BLE_SCAN_COND_CLEAR, BTM_BLE_PF_SRVC_UUID, NULL);
- btm_ble_update_uuid_filter(BTM_BLE_SCAN_COND_CLEAR, BTM_BLE_META_PF_SOL_UUID, NULL);
- /* clear service data filter */
- btm_ble_update_pf_manu_data(BTM_BLE_SCAN_COND_CLEAR, NULL, BTM_BLE_PF_MANU_DATA);
- }
-
- /* select feature based on control block settings */
- UINT8_TO_STREAM(p, BTM_BLE_META_PF_FEAT_SEL);
- UINT8_TO_STREAM(p, BTM_BLE_SCAN_COND_CLEAR);
-
- /* Filter index */
- UINT8_TO_STREAM(p, 0);
-
- /* set PCF selection */
- UINT32_TO_STREAM(p, BTM_BLE_PF_SELECT_NONE);
- /* set logic condition as OR as default */
- UINT8_TO_STREAM(p, BTM_BLE_PF_LOGIC_OR);
-
- if ((st = BTM_VendorSpecificCommand (HCI_VENDOR_BLE_PCF_VSC,
- (UINT8)(BTM_BLE_META_HDR_LENGTH + BTM_BLE_PF_FEAT_SEL_LEN),
- param,
- btm_ble_vendor_scan_pf_cmpl_cback))
- != BTM_NO_RESOURCES)
- {
- if (p_bda_filter)
- p_bda_filter->feat_mask = BTM_BLE_PF_SELECT_NONE;
-
- if (p_target)
- memcpy(&btm_ble_vendor_cb.cur_filter_target, p_target, sizeof(tBLE_BD_ADDR));
- else
- memset(&btm_ble_vendor_cb.cur_filter_target, 0, sizeof(tBLE_BD_ADDR));
- }
-
- return st;
-}
-/*******************************************************************************
-**
-** Function BTM_BleEnableFilterCondition
-**
-** Description This function is called to enable the adv data payload filter
-** condition.
-**
-** Parameters p_target: enabble the filter condition on a target device; if NULL
-** enable the generic scan condition.
-** enable: enable or disable the filter condition
-**
-** Returns void
-**
-*******************************************************************************/
-tBTM_STATUS BTM_BleEnableFilterCondition(BOOLEAN enable, tBLE_BD_ADDR *p_target,
- tBTM_BLE_PF_CMPL_CBACK *p_cmpl_cback)
-{
- UINT8 param[20], *p;
- tBTM_STATUS st = BTM_WRONG_MODE;
- tBTM_BLE_PF_COUNT *p_bda_filter;
-
- p = param;
- memset(param, 0, 20);
-
- if (btm_ble_vendor_cb.p_scan_pf_cback)
- {
- BTM_TRACE_ERROR("ADV PF Filter activity busy");
- return BTM_BUSY;
- }
-
- if (enable)
- {
- p_bda_filter = btm_ble_find_addr_filter_counter(p_target);
-
- if (p_bda_filter == NULL ||
- (p_bda_filter && p_bda_filter->feat_mask == BTM_BLE_PF_SELECT_NONE))
- {
- BTM_TRACE_ERROR("No PF filter has been configured!");
- return st;
- }
-
- /* select feature based on control block settings */
- UINT8_TO_STREAM(p, BTM_BLE_META_PF_FEAT_SEL);
- UINT8_TO_STREAM(p, BTM_BLE_SCAN_COND_ADD);
-
- /* Filter index */
- UINT8_TO_STREAM(p, 0);
-
- /* set PCF selection */
- UINT32_TO_STREAM(p, p_bda_filter->feat_mask);
- /* set logic condition as OR as default */
- UINT8_TO_STREAM(p, BTM_BLE_PF_LOGIC_OR);
-
- if ((st = BTM_VendorSpecificCommand (HCI_VENDOR_BLE_PCF_VSC,
- (UINT8)(BTM_BLE_META_HDR_LENGTH + BTM_BLE_PF_FEAT_SEL_LEN),
- param,
- btm_ble_vendor_scan_pf_cmpl_cback))
- == BTM_NO_RESOURCES)
- {
- return st;
- }
-
- /* enable the content filter in controller */
- p = param;
- UINT8_TO_STREAM(p, BTM_BLE_META_PF_ENABLE);
- /* enable adv data payload filtering */
- UINT8_TO_STREAM(p, enable);
- }
- else
- {
- UINT8_TO_STREAM(p, BTM_BLE_META_PF_ENABLE);
- /* disable adv data payload filtering */
- UINT8_TO_STREAM(p, enable);
- }
-
- if ((st = BTM_VendorSpecificCommand (HCI_VENDOR_BLE_PCF_VSC,
- BTM_BLE_PCF_ENABLE_LEN,
- param,
- btm_ble_vendor_scan_pf_cmpl_cback))
- == BTM_CMD_STARTED)
- {
- btm_ble_vendor_cb.op_type = BTM_BLE_SET_SCAN_PF_OPCODE(BTM_BLE_META_PF_ENABLE, BTM_BLE_PF_ENABLE);
- btm_ble_vendor_cb.p_scan_pf_cback = p_cmpl_cback;
- }
-
- return st;
-}
-/*******************************************************************************
-**
-** Function BTM_BleCfgFilterCondition
-**
-** Description This function is called to configure the adv data payload filter
-** condition.
-**
-** Parameters action: to read/write/clear
-** cond_type: filter condition type.
-** p_cond: filter condition paramter
-**
-** Returns void
-**
-*******************************************************************************/
-tBTM_STATUS BTM_BleCfgFilterCondition(tBTM_BLE_SCAN_COND_OP action,
- tBTM_BLE_PF_COND_TYPE cond_type,
- tBTM_BLE_PF_COND_PARAM *p_cond,
- tBTM_BLE_PF_CMPL_CBACK *p_cmpl_cback)
-{
- tBTM_STATUS st = BTM_ILLEGAL_VALUE;
-
- if (btm_ble_vendor_cb.p_scan_pf_cback != NULL)
- return BTM_BUSY;
-
- switch (cond_type)
- {
- case BTM_BLE_PF_SRVC_DATA_PATTERN:
- /* write manufacture data filter */
- case BTM_BLE_PF_MANU_DATA:
- st = btm_ble_update_pf_manu_data(action, p_cond, cond_type);
- break;
-
- /* write local name filter */
- case BTM_BLE_PF_LOCAL_NAME:
- st = btm_ble_update_pf_local_name(action, p_cond);
- break;
-
- /* filter on advertiser address */
- case BTM_BLE_PF_ADDR_FILTER:
- st = btm_ble_update_addr_filter(action, p_cond);
- break;
-
- /* filter on service/solicitated UUID */
- case BTM_BLE_PF_SRVC_UUID:
- case BTM_BLE_PF_SRVC_SOL_UUID:
- st = btm_ble_update_uuid_filter(action, cond_type, p_cond);
- break;
-
- case BTM_BLE_PF_SRVC_DATA:
- st = btm_ble_update_srvc_data_change(action, p_cond);
- break;
-
- case BTM_BLE_PF_TYPE_ALL: /* only used to clear filter */
- st = btm_ble_clear_scan_pf_filter(action, p_cond);
- break;
-
- default:
- BTM_TRACE_WARNING("condition type [%d] not supported currently.", cond_type);
- break;
- }
- if (st == BTM_CMD_STARTED
- /* no vsc needed for service data change */
- && cond_type != BTM_BLE_PF_SRVC_DATA)
- {
- btm_ble_vendor_cb.op_type = BTM_BLE_SET_SCAN_PF_OPCODE(cond_type, BTM_BLE_PF_CONFIG);
- btm_ble_vendor_cb.p_scan_pf_cback = p_cmpl_cback;
- }
-
- return st;
-}
/*******************************************************************************
** Resolve Address Using IRK List functions
}
#endif
-
-
-/*******************************************************************************
-**
-** Function btm_ble_vendor_init
-**
-** Description Initialize customer specific feature information in host stack
-**
-** Parameters
-**
-** Returns status
-**
-*******************************************************************************/
-void btm_ble_vendor_init(void)
-{
- //memset(&btm_ble_vendor_cb, 0, sizeof(tBTM_BLE_VENDOR_CB));
-
- if (!HCI_LE_HOST_SUPPORTED(btm_cb.devcb.local_lmp_features[HCI_EXT_FEATURES_PAGE_1]))
- return;
-}
-
#endif
/* VSC */
#define HCI_VENDOR_BLE_PCF_VSC (0x0157 | HCI_GRP_VENDOR_SPECIFIC)
-/* Sub codes */
-#define BTM_BLE_META_PF_ENABLE 0x00
-#define BTM_BLE_META_PF_FEAT_SEL 0x01
-#define BTM_BLE_META_PF_ADDR 0x02
-#define BTM_BLE_META_PF_UUID 0x03
-#define BTM_BLE_META_PF_SOL_UUID 0x04
-#define BTM_BLE_META_PF_LOCAL_NAME 0x05
-#define BTM_BLE_META_PF_MANU_DATA 0x06
-#define BTM_BLE_META_PF_SRVC_DATA 0x07
-
#endif
#include "vendor_api.h"
-#define BTA_DM_BLE_PF_ENABLE_EVT BTM_BLE_PF_ENABLE
-#define BTA_DM_BLE_PF_CONFIG_EVT BTM_BLE_PF_CONFIG
-typedef UINT8 tBTA_DM_BLE_PF_EVT;
-
-/* Search callback */
-typedef void (tBTA_DM_SCAN_PF_CBACK)(tBTA_DM_BLE_PF_EVT event, tBTA_DM_BLE_PF_COND_TYPE cfg_cond, tBTA_STATUS status);;
#if (BLE_INCLUDED == TRUE && BLE_ANDROID_CONTROLLER_SCAN_FILTER == TRUE)
-/*******************************************************************************
-**
-** Function BTA_DmBleEnableFilterCondition
-**
-** Description This function is called to enable the adv data payload filter
-** condition.
-**
-** Parameters p_target: enabble the filter condition on a target device; if NULL
-** enable the generic scan condition.
-** enable: enable or disable the filter condition
-**
-** Returns void
-**
-*******************************************************************************/
-BTA_API extern void BTA_DmBleEnableFilterCondition(BOOLEAN enable,
- tBLE_BD_ADDR *p_target,
- tBTA_DM_SCAN_PF_CBACK *p_cmpl_cback);
/*******************************************************************************
**
*******************************************************************************/
BTA_API extern void BTA_BrcmInit (void);
-
-/*******************************************************************************
-**
-** Function BTA_DmBleCfgFilterCondition
-**
-** Description This function is called to configure the adv data payload filter
-** condition.
-**
-** Parameters action: to read/write/clear
-** cond_type: filter condition type.
-** p_cond: filter condition paramter
-**
-** Returns void
-**
-*******************************************************************************/
-BTA_API extern void BTA_DmBleCfgFilterCondition(tBTA_DM_BLE_SCAN_COND_OP action,
- tBTA_DM_BLE_PF_COND_TYPE cond_type,
- tBTA_DM_BLE_PF_COND_PARAM *p_cond,
- tBTA_DM_SCAN_PF_CBACK *p_cmpl_cback);
#endif
#ifdef __cplusplus
** Advertising packet filter VSC specific definitions
******************************************************************************/
-enum
-{
- BTM_BLE_SCAN_COND_ADD,
- BTM_BLE_SCAN_COND_DELETE,
- BTM_BLE_SCAN_COND_CLEAR = 2
-};
-typedef UINT8 tBTM_BLE_SCAN_COND_OP;
-
-/* filter selection bit index */
-#define BTM_BLE_PF_ADDR_FILTER 0
-#define BTM_BLE_PF_SRVC_DATA 1
-#define BTM_BLE_PF_SRVC_UUID 2
-#define BTM_BLE_PF_SRVC_SOL_UUID 3
-#define BTM_BLE_PF_LOCAL_NAME 4
-#define BTM_BLE_PF_MANU_DATA 5
-#define BTM_BLE_PF_SRVC_DATA_PATTERN 6
-#define BTM_BLE_PF_TYPE_ALL 7 /* when passed in payload filter type all, only clear action is applicable */
-#define BTM_BLE_PF_TYPE_MAX 8
-
-typedef UINT8 tBTM_BLE_PF_COND_TYPE;
-
-#define BTM_BLE_PF_LOGIC_OR 0
-#define BTM_BLE_PF_LOGIC_AND 1
-typedef UINT8 tBTM_BLE_PF_LOGIC_TYPE;
-
-/* max number of filter spot for different filter type */
-#ifndef BTM_BLE_MAX_UUID_FILTER
-#define BTM_BLE_MAX_UUID_FILTER 8
-#endif
-#ifndef BTM_BLE_MAX_ADDR_FILTER
-#define BTM_BLE_MAX_ADDR_FILTER 8
-#endif
-#ifndef BTM_BLE_PF_STR_COND_MAX
-#define BTM_BLE_PF_STR_COND_MAX 4 /* apply to manu data , or local name */
-#endif
-#ifndef BTM_BLE_PF_STR_LEN_MAX
-#define BTM_BLE_PF_STR_LEN_MAX 20 /* match for first 20 bytes */
-#endif
-
-#define BTM_BLE_PF_ENABLE 1
-#define BTM_BLE_PF_CONFIG 2
-typedef UINT8 tBTM_BLE_PF_ACTION;
-
-/* BLE adv payload filtering operation complete callback */
-typedef void (tBTM_BLE_PF_CMPL_CBACK)(tBTM_BLE_PF_ACTION action, tBTM_BLE_PF_COND_TYPE cfg_cond, tBTM_STATUS status);
-
-typedef union
-{
- UINT16 uuid16_mask;
- UINT32 uuid32_mask;
- UINT8 uuid128_mask[LEN_UUID_128];
-}tBTM_BLE_PF_COND_MASK;
-
-typedef struct
-{
- tBLE_BD_ADDR *p_target_addr; /* target address, if NULL, generic UUID filter */
- tBT_UUID uuid; /* UUID condition */
- tBTM_BLE_PF_LOGIC_TYPE cond_logic; /* AND/OR */
- tBTM_BLE_PF_COND_MASK *p_uuid_mask; /* UUID mask */
-}tBTM_BLE_PF_UUID_COND;
-
-typedef struct
-{
- UINT8 data_len; /* <= 20 bytes */
- UINT8 *p_data;
-}tBTM_BLE_PF_LOCAL_NAME_COND;
-
-typedef struct
-{
- UINT16 company_id; /* company ID */
- UINT8 data_len; /* <= 20 bytes */
- UINT8 *p_pattern;
- UINT16 company_id_mask; /* UUID value mask */
- UINT8 *p_pattern_mask; /* Manufactuer data matching mask, same length as data pattern,
- set to all 0xff, match exact data */
-}tBTM_BLE_PF_MANU_COND;
-
-typedef struct
-{
- UINT16 uuid; /* service ID */
- UINT8 data_len; /* <= 20 bytes */
- UINT8 *p_pattern;
-}tBTM_BLE_PF_SRVC_PATTERN_COND;
-
-
-typedef union
-{
- tBLE_BD_ADDR target_addr;
- tBTM_BLE_PF_LOCAL_NAME_COND local_name; /* lcoal name filtering */
- tBTM_BLE_PF_MANU_COND manu_data; /* manufactuer data filtering */
- tBTM_BLE_PF_UUID_COND srvc_uuid; /* service UUID filtering */
- tBTM_BLE_PF_UUID_COND solicitate_uuid; /* solicitated service UUID filtering */
- tBTM_BLE_PF_SRVC_PATTERN_COND srvc_data; /* service data pattern */
-}tBTM_BLE_PF_COND_PARAM;
#ifdef __cplusplus
******************************************************************************/
#if BLE_ANDROID_CONTROLLER_SCAN_FILTER == TRUE
-/*******************************************************************************
-**
-** Function BTM_BleEnableFilterCondition
-**
-** Description This function is called to enable the adv data payload filter
-** condition.
-**
-** Parameters p_target: enabble the filter condition on a target device; if NULL
-** enable the generic scan condition.
-** enable: enable or disable the filter condition
-**
-** Returns void
-**
-*******************************************************************************/
-BTM_API extern tBTM_STATUS BTM_BleEnableFilterCondition(BOOLEAN enable,
- tBLE_BD_ADDR *p_target,
- tBTM_BLE_PF_CMPL_CBACK *p_cmpl_cback);
-
-/*******************************************************************************
-**
-** Function BTM_BleCfgFilterCondition
-**
-** Description This function is called to configure the adv data payload filter
-** condition.
-**
-** Parameters action: to read/write/clear
-** cond_type: filter condition type.
-** p_cond: filter condition paramter
-**
-** Returns tBTM_STATUS
-**
-*******************************************************************************/
-BTM_API extern tBTM_STATUS BTM_BleCfgFilterCondition(tBTM_BLE_SCAN_COND_OP action,
- tBTM_BLE_PF_COND_TYPE cond_type,
- tBTM_BLE_PF_COND_PARAM *p_cond,
- tBTM_BLE_PF_CMPL_CBACK *p_cmpl_cback);
-
#endif
#define BTM_BLE_META_READ_IRK_LEN 2
#define BTM_BLE_META_ADD_WL_ATTR_LEN 9
-#define BTM_BLE_PF_BIT_TO_MASK(x) (UINT32)(1 << (x))
#define BTM_BLE_PF_SELECT_NONE 0
#define BTM_BLE_PF_ADDR_FILTER_BIT BTM_BLE_PF_BIT_TO_MASK(BTM_BLE_PF_ADDR_FILTER)
#define BTM_BLE_PF_SRVC_DATA_BIT BTM_BLE_PF_BIT_TO_MASK(BTM_BLE_PF_SRVC_DATA)
typedef UINT8 tBTM_BLE_PF_SEL_MASK;
-#define BTM_BLE_MAX_FILTER_COUNTER (BTM_BLE_MAX_ADDR_FILTER + 1) /* per device filter + one generic filter indexed by 0 */
-
-typedef struct
-{
- BOOLEAN in_use;
- BD_ADDR bd_addr;
- UINT32 feat_mask; /* per BD_ADDR feature mask */
- UINT8 pf_counter[BTM_BLE_PF_TYPE_MAX]; /* number of filter indexed by tBTM_BLE_PF_COND_TYPE */
-}tBTM_BLE_PF_COUNT;
-
#ifndef BTM_CS_IRK_LIST_MAX
#define BTM_CS_IRK_LIST_MAX 0x20
#endif