Home | History | Annotate | Download | only in btm
      1 /******************************************************************************
      2  *
      3  *  Copyright (C) 2014  Broadcom Corporation
      4  *
      5  *  Licensed under the Apache License, Version 2.0 (the "License");
      6  *  you may not use this file except in compliance with the License.
      7  *  You may obtain a copy of the License at:
      8  *
      9  *  http://www.apache.org/licenses/LICENSE-2.0
     10  *
     11  *  Unless required by applicable law or agreed to in writing, software
     12  *  distributed under the License is distributed on an "AS IS" BASIS,
     13  *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     14  *  See the License for the specific language governing permissions and
     15  *  limitations under the License.
     16  *
     17  ******************************************************************************/
     18 
     19 #define LOG_TAG "bt_btm_ble"
     20 
     21 #include <base/bind.h>
     22 #include <string.h>
     23 #include <algorithm>
     24 #include <vector>
     25 
     26 #include "bt_target.h"
     27 
     28 #include "bt_types.h"
     29 #include "bt_utils.h"
     30 #include "btm_ble_api.h"
     31 #include "btm_int.h"
     32 #include "btu.h"
     33 #include "device/include/controller.h"
     34 #include "hcidefs.h"
     35 #include "hcimsgs.h"
     36 
     37 #define BTM_BLE_ADV_FILT_META_HDR_LENGTH 3
     38 #define BTM_BLE_ADV_FILT_FEAT_SELN_LEN 13
     39 #define BTM_BLE_ADV_FILT_TRACK_NUM 2
     40 
     41 #define BTM_BLE_PF_SELECT_NONE 0
     42 
     43 /* BLE meta vsc header: 1 bytes of sub_code, 1 byte of PCF action */
     44 #define BTM_BLE_META_HDR_LENGTH 3
     45 #define BTM_BLE_PF_FEAT_SEL_LEN 18
     46 #define BTM_BLE_PCF_ENABLE_LEN 2
     47 
     48 #define BTM_BLE_META_ADDR_LEN 7
     49 #define BTM_BLE_META_UUID_LEN 40
     50 
     51 #define BTM_BLE_PF_BIT_TO_MASK(x) (uint16_t)(1 << (x))
     52 
     53 tBTM_BLE_ADV_FILTER_CB btm_ble_adv_filt_cb;
     54 tBTM_BLE_VSC_CB cmn_ble_vsc_cb;
     55 static const BD_ADDR na_bda = {0};
     56 
     57 static uint8_t btm_ble_cs_update_pf_counter(tBTM_BLE_SCAN_COND_OP action,
     58                                             uint8_t cond_type,
     59                                             tBLE_BD_ADDR* p_bd_addr,
     60                                             uint8_t num_available);
     61 
     62 #define BTM_BLE_SET_SCAN_PF_OPCODE(x, y) (((x) << 4) | (y))
     63 #define BTM_BLE_GET_SCAN_PF_SUBCODE(x) ((x) >> 4)
     64 #define BTM_BLE_GET_SCAN_PF_ACTION(x) ((x)&0x0f)
     65 #define BTM_BLE_INVALID_COUNTER 0xff
     66 
     67 /* length of each multi adv sub command */
     68 #define BTM_BLE_ADV_FILTER_ENB_LEN 3
     69 
     70 /* length of each batch scan command */
     71 #define BTM_BLE_ADV_FILTER_CLEAR_LEN 3
     72 #define BTM_BLE_ADV_FILTER_LEN 2
     73 
     74 #define BTM_BLE_ADV_FILT_CB_EVT_MASK 0xF0
     75 #define BTM_BLE_ADV_FILT_SUBCODE_MASK 0x0F
     76 
     77 /*******************************************************************************
     78  *
     79  * Function         btm_ble_obtain_vsc_details
     80  *
     81  * Description      This function obtains the VSC details
     82  *
     83  * Parameters
     84  *
     85  * Returns          status
     86  *
     87  ******************************************************************************/
     88 tBTM_STATUS btm_ble_obtain_vsc_details() {
     89   tBTM_STATUS st = BTM_SUCCESS;
     90 
     91 #if (BLE_VND_INCLUDED == TRUE)
     92   BTM_BleGetVendorCapabilities(&cmn_ble_vsc_cb);
     93   if (cmn_ble_vsc_cb.filter_support && 0 == cmn_ble_vsc_cb.max_filter) {
     94     st = BTM_MODE_UNSUPPORTED;
     95     return st;
     96   }
     97 #else
     98   cmn_ble_vsc_cb.max_filter = BTM_BLE_MAX_FILTER_COUNTER;
     99 #endif
    100   return st;
    101 }
    102 
    103 /*******************************************************************************
    104  *
    105  * Function         btm_ble_condtype_to_ocf
    106  *
    107  * Description      Convert cond_type to OCF
    108  *
    109  * Returns          Returns ocf value
    110  *
    111  ******************************************************************************/
    112 uint8_t btm_ble_condtype_to_ocf(uint8_t cond_type) {
    113   uint8_t ocf = 0;
    114 
    115   switch (cond_type) {
    116     case BTM_BLE_PF_ADDR_FILTER:
    117       ocf = BTM_BLE_META_PF_ADDR;
    118       break;
    119     case BTM_BLE_PF_SRVC_UUID:
    120       ocf = BTM_BLE_META_PF_UUID;
    121       break;
    122     case BTM_BLE_PF_SRVC_SOL_UUID:
    123       ocf = BTM_BLE_META_PF_SOL_UUID;
    124       break;
    125     case BTM_BLE_PF_LOCAL_NAME:
    126       ocf = BTM_BLE_META_PF_LOCAL_NAME;
    127       break;
    128     case BTM_BLE_PF_MANU_DATA:
    129       ocf = BTM_BLE_META_PF_MANU_DATA;
    130       break;
    131     case BTM_BLE_PF_SRVC_DATA_PATTERN:
    132       ocf = BTM_BLE_META_PF_SRVC_DATA;
    133       break;
    134     case BTM_BLE_PF_TYPE_ALL:
    135       ocf = BTM_BLE_META_PF_ALL;
    136       break;
    137     default:
    138       ocf = BTM_BLE_PF_TYPE_MAX;
    139       break;
    140   }
    141   return ocf;
    142 }
    143 
    144 /*******************************************************************************
    145  *
    146  * Function         btm_ble_ocf_to_condtype
    147  *
    148  * Description      Convert OCF to cond type
    149  *
    150  * Returns          Returns condtype value
    151  *
    152  ******************************************************************************/
    153 uint8_t btm_ble_ocf_to_condtype(uint8_t ocf) {
    154   uint8_t cond_type = 0;
    155 
    156   switch (ocf) {
    157     case BTM_BLE_META_PF_FEAT_SEL:
    158       cond_type = BTM_BLE_META_PF_FEAT_SEL;
    159       break;
    160     case BTM_BLE_META_PF_ADDR:
    161       cond_type = BTM_BLE_PF_ADDR_FILTER;
    162       break;
    163     case BTM_BLE_META_PF_UUID:
    164       cond_type = BTM_BLE_PF_SRVC_UUID;
    165       break;
    166     case BTM_BLE_META_PF_SOL_UUID:
    167       cond_type = BTM_BLE_PF_SRVC_SOL_UUID;
    168       break;
    169     case BTM_BLE_META_PF_LOCAL_NAME:
    170       cond_type = BTM_BLE_PF_LOCAL_NAME;
    171       break;
    172     case BTM_BLE_META_PF_MANU_DATA:
    173       cond_type = BTM_BLE_PF_MANU_DATA;
    174       break;
    175     case BTM_BLE_META_PF_SRVC_DATA:
    176       cond_type = BTM_BLE_PF_SRVC_DATA_PATTERN;
    177       break;
    178     case BTM_BLE_META_PF_ALL:
    179       cond_type = BTM_BLE_PF_TYPE_ALL;
    180       break;
    181     default:
    182       cond_type = BTM_BLE_PF_TYPE_MAX;
    183       break;
    184   }
    185   return cond_type;
    186 }
    187 
    188 void btm_flt_update_cb(uint8_t expected_ocf, tBTM_BLE_PF_CFG_CBACK cb,
    189                        uint8_t* p, uint16_t evt_len) {
    190   if (evt_len != 4) {
    191     BTM_TRACE_ERROR("%s: bad length: %d", __func__, evt_len);
    192     return;
    193   }
    194 
    195   uint8_t status, op_subcode, action, num_avail;
    196   STREAM_TO_UINT8(status, p);
    197   STREAM_TO_UINT8(op_subcode, p);
    198   STREAM_TO_UINT8(action, p);
    199   STREAM_TO_UINT8(num_avail, p);
    200 
    201   if (expected_ocf != op_subcode) {
    202     BTM_TRACE_ERROR("%s: Incorrect opcode: 0x%02x, expected: 0x%02x", __func__,
    203                     expected_ocf, op_subcode);
    204     return;
    205   }
    206 
    207   if (op_subcode == BTM_BLE_META_PF_FEAT_SEL) {
    208     cb.Run(num_avail, action, status);
    209     return;
    210   }
    211 
    212   uint8_t cond_type = btm_ble_ocf_to_condtype(expected_ocf);
    213   BTM_TRACE_DEBUG("%s: Recd: %d, %d, %d, %d, %d", __func__, op_subcode,
    214                   expected_ocf, action, status, num_avail);
    215   if (HCI_SUCCESS == status) {
    216     if (memcmp(&btm_ble_adv_filt_cb.cur_filter_target.bda, &na_bda,
    217                BD_ADDR_LEN) == 0)
    218       btm_ble_cs_update_pf_counter(action, cond_type, NULL, num_avail);
    219     else
    220       btm_ble_cs_update_pf_counter(
    221           action, cond_type, &btm_ble_adv_filt_cb.cur_filter_target, num_avail);
    222   }
    223 
    224   /* send ADV PF operation complete */
    225   btm_ble_adv_filt_cb.op_type = 0;
    226 
    227   cb.Run(num_avail, action, status);
    228 }
    229 
    230 /*******************************************************************************
    231  *
    232  * Function         btm_ble_find_addr_filter_counter
    233  *
    234  * Description      find the per bd address ADV payload filter counter by
    235  *                  BD_ADDR.
    236  *
    237  * Returns          pointer to the counter if found; NULL otherwise.
    238  *
    239  ******************************************************************************/
    240 tBTM_BLE_PF_COUNT* btm_ble_find_addr_filter_counter(tBLE_BD_ADDR* p_le_bda) {
    241   uint8_t i;
    242   tBTM_BLE_PF_COUNT* p_addr_filter =
    243       &btm_ble_adv_filt_cb.p_addr_filter_count[1];
    244 
    245   if (p_le_bda == NULL) return &btm_ble_adv_filt_cb.p_addr_filter_count[0];
    246 
    247   for (i = 0; i < cmn_ble_vsc_cb.max_filter; i++, p_addr_filter++) {
    248     if (p_addr_filter->in_use &&
    249         memcmp(p_le_bda->bda, p_addr_filter->bd_addr, BD_ADDR_LEN) == 0) {
    250       return p_addr_filter;
    251     }
    252   }
    253   return NULL;
    254 }
    255 
    256 /*******************************************************************************
    257  *
    258  * Function         btm_ble_alloc_addr_filter_counter
    259  *
    260  * Description      allocate the per device adv payload filter counter.
    261  *
    262  * Returns          pointer to the counter if allocation succeed; NULL
    263  *                  otherwise.
    264  *
    265  ******************************************************************************/
    266 tBTM_BLE_PF_COUNT* btm_ble_alloc_addr_filter_counter(BD_ADDR bd_addr) {
    267   uint8_t i;
    268   tBTM_BLE_PF_COUNT* p_addr_filter =
    269       &btm_ble_adv_filt_cb.p_addr_filter_count[1];
    270 
    271   for (i = 0; i < cmn_ble_vsc_cb.max_filter; i++, p_addr_filter++) {
    272     if (memcmp(na_bda, p_addr_filter->bd_addr, BD_ADDR_LEN) == 0) {
    273       memcpy(p_addr_filter->bd_addr, bd_addr, BD_ADDR_LEN);
    274       p_addr_filter->in_use = true;
    275       return p_addr_filter;
    276     }
    277   }
    278   return NULL;
    279 }
    280 /*******************************************************************************
    281  *
    282  * Function         btm_ble_dealloc_addr_filter_counter
    283  *
    284  * Description      de-allocate the per device adv payload filter counter.
    285  *
    286  * Returns          true if deallocation succeed; false otherwise.
    287  *
    288  ******************************************************************************/
    289 bool btm_ble_dealloc_addr_filter_counter(tBLE_BD_ADDR* p_bd_addr,
    290                                          uint8_t filter_type) {
    291   uint8_t i;
    292   tBTM_BLE_PF_COUNT* p_addr_filter =
    293       &btm_ble_adv_filt_cb.p_addr_filter_count[1];
    294   bool found = false;
    295 
    296   if (BTM_BLE_PF_TYPE_ALL == filter_type && NULL == p_bd_addr)
    297     memset(&btm_ble_adv_filt_cb.p_addr_filter_count[0], 0,
    298            sizeof(tBTM_BLE_PF_COUNT));
    299 
    300   for (i = 0; i < cmn_ble_vsc_cb.max_filter; i++, p_addr_filter++) {
    301     if ((p_addr_filter->in_use) &&
    302         (NULL == p_bd_addr ||
    303          (NULL != p_bd_addr &&
    304           memcmp(p_bd_addr->bda, p_addr_filter->bd_addr, BD_ADDR_LEN) == 0))) {
    305       found = true;
    306       memset(p_addr_filter, 0, sizeof(tBTM_BLE_PF_COUNT));
    307 
    308       if (NULL != p_bd_addr) break;
    309     }
    310   }
    311   return found;
    312 }
    313 
    314 /**
    315  * This function update(add,delete or clear) the adv local name filtering
    316  * condition.
    317  */
    318 void BTM_LE_PF_local_name(tBTM_BLE_SCAN_COND_OP action,
    319                           tBTM_BLE_PF_FILT_INDEX filt_index,
    320                           std::vector<uint8_t> name, tBTM_BLE_PF_CFG_CBACK cb) {
    321   uint8_t len = BTM_BLE_ADV_FILT_META_HDR_LENGTH;
    322 
    323   uint8_t len_max = len + BTM_BLE_PF_STR_LEN_MAX;
    324   uint8_t param[len_max];
    325   memset(param, 0, len_max);
    326 
    327   uint8_t* p = param;
    328   UINT8_TO_STREAM(p, BTM_BLE_META_PF_LOCAL_NAME);
    329   UINT8_TO_STREAM(p, action);
    330   UINT8_TO_STREAM(p, filt_index);
    331 
    332   if (action != BTM_BLE_SCAN_COND_CLEAR) {
    333     int size = std::min(name.size(), (size_t)BTM_BLE_PF_STR_LEN_MAX);
    334     ARRAY_TO_STREAM(p, name.data(), size);
    335     len += size;
    336   }
    337 
    338   /* send local name filter */
    339   btu_hcif_send_cmd_with_cb(
    340       FROM_HERE, HCI_BLE_ADV_FILTER_OCF, param, len,
    341       base::Bind(&btm_flt_update_cb, BTM_BLE_META_PF_LOCAL_NAME, cb));
    342 
    343   memset(&btm_ble_adv_filt_cb.cur_filter_target, 0, sizeof(tBLE_BD_ADDR));
    344 }
    345 
    346 /**
    347  * this function update(add/remove) service data change filter.
    348  */
    349 void BTM_LE_PF_srvc_data(tBTM_BLE_SCAN_COND_OP action,
    350                          tBTM_BLE_PF_FILT_INDEX filt_index) {
    351   uint8_t num_avail = (action == BTM_BLE_SCAN_COND_ADD) ? 0 : 1;
    352 
    353   btm_ble_cs_update_pf_counter(action, BTM_BLE_PF_SRVC_DATA, nullptr,
    354                                num_avail);
    355 }
    356 
    357 /**
    358  * This function update(add,delete or clear) the adv manufacturer data filtering
    359  * condition.
    360  */
    361 void BTM_LE_PF_manu_data(tBTM_BLE_SCAN_COND_OP action,
    362                          tBTM_BLE_PF_FILT_INDEX filt_index, uint16_t company_id,
    363                          uint16_t company_id_mask, std::vector<uint8_t> data,
    364                          std::vector<uint8_t> data_mask,
    365                          tBTM_BLE_PF_CFG_CBACK cb) {
    366   uint8_t len = BTM_BLE_ADV_FILT_META_HDR_LENGTH;
    367   int len_max = len + BTM_BLE_PF_STR_LEN_MAX + BTM_BLE_PF_STR_LEN_MAX;
    368 
    369   uint8_t param[len_max];
    370   memset(param, 0, len_max);
    371 
    372   uint8_t* p = param;
    373   UINT8_TO_STREAM(p, BTM_BLE_META_PF_MANU_DATA);
    374   UINT8_TO_STREAM(p, action);
    375   UINT8_TO_STREAM(p, filt_index);
    376 
    377   if (action != BTM_BLE_SCAN_COND_CLEAR) {
    378     uint8_t size = std::min(data.size(), (size_t)(BTM_BLE_PF_STR_LEN_MAX - 2));
    379 
    380     UINT16_TO_STREAM(p, company_id);
    381     if (size > 0 && data_mask.size() != 0) {
    382       ARRAY_TO_STREAM(p, data.data(), size);
    383       len += size + 2;
    384     } else
    385       len += 2;
    386 
    387     if (company_id_mask != 0) {
    388       UINT16_TO_STREAM(p, company_id_mask);
    389     } else {
    390       UINT16_TO_STREAM(p, (uint16_t)0xFFFF);
    391     }
    392     len += 2;
    393 
    394     if (size > 0 && data_mask.size() != 0) {
    395       ARRAY_TO_STREAM(p, data_mask.data(), size);
    396       len += (size);
    397     }
    398 
    399     BTM_TRACE_DEBUG("Manuf data length: %d", len);
    400   }
    401 
    402   btu_hcif_send_cmd_with_cb(
    403       FROM_HERE, HCI_BLE_ADV_FILTER_OCF, param, len,
    404       base::Bind(&btm_flt_update_cb, BTM_BLE_META_PF_MANU_DATA, cb));
    405 
    406   memset(&btm_ble_adv_filt_cb.cur_filter_target, 0, sizeof(tBLE_BD_ADDR));
    407 }
    408 
    409 /**
    410  * This function update(add,delete or clear) the service data filtering
    411  * condition.
    412  **/
    413 void BTM_LE_PF_srvc_data_pattern(tBTM_BLE_SCAN_COND_OP action,
    414                                  tBTM_BLE_PF_FILT_INDEX filt_index,
    415                                  std::vector<uint8_t> data,
    416                                  std::vector<uint8_t> data_mask,
    417                                  tBTM_BLE_PF_CFG_CBACK cb) {
    418   uint8_t len = BTM_BLE_ADV_FILT_META_HDR_LENGTH;
    419   int len_max = len + BTM_BLE_PF_STR_LEN_MAX + BTM_BLE_PF_STR_LEN_MAX;
    420 
    421   uint8_t param[len_max];
    422   memset(param, 0, len_max);
    423 
    424   uint8_t* p = param;
    425   UINT8_TO_STREAM(p, BTM_BLE_META_PF_SRVC_DATA);
    426   UINT8_TO_STREAM(p, action);
    427   UINT8_TO_STREAM(p, filt_index);
    428 
    429   if (action != BTM_BLE_SCAN_COND_CLEAR) {
    430     uint8_t size = std::min(data.size(), (size_t)(BTM_BLE_PF_STR_LEN_MAX - 2));
    431 
    432     if (size > 0) {
    433       ARRAY_TO_STREAM(p, data.data(), size);
    434       len += size;
    435       ARRAY_TO_STREAM(p, data_mask.data(), size);
    436       len += size;
    437     }
    438   }
    439 
    440   btu_hcif_send_cmd_with_cb(
    441       FROM_HERE, HCI_BLE_ADV_FILTER_OCF, param, len,
    442       base::Bind(&btm_flt_update_cb, BTM_BLE_META_PF_SRVC_DATA, cb));
    443 
    444   memset(&btm_ble_adv_filt_cb.cur_filter_target, 0, sizeof(tBLE_BD_ADDR));
    445 }
    446 
    447 /*******************************************************************************
    448  *
    449  * Function         btm_ble_cs_update_pf_counter
    450  *
    451  * Description      this function is to update the adv data payload filter
    452  *                  counter
    453  *
    454  * Returns          current number of the counter; BTM_BLE_INVALID_COUNTER if
    455  *                  counter update failed.
    456  *
    457  ******************************************************************************/
    458 uint8_t btm_ble_cs_update_pf_counter(tBTM_BLE_SCAN_COND_OP action,
    459                                      uint8_t cond_type, tBLE_BD_ADDR* p_bd_addr,
    460                                      uint8_t num_available) {
    461   tBTM_BLE_PF_COUNT* p_addr_filter = NULL;
    462   uint8_t* p_counter = NULL;
    463 
    464   btm_ble_obtain_vsc_details();
    465 
    466   if (cond_type > BTM_BLE_PF_TYPE_ALL) {
    467     BTM_TRACE_ERROR("unknown PF filter condition type %d", cond_type);
    468     return BTM_BLE_INVALID_COUNTER;
    469   }
    470 
    471   /* for these three types of filter, always generic */
    472   if (BTM_BLE_PF_ADDR_FILTER == cond_type ||
    473       BTM_BLE_PF_MANU_DATA == cond_type || BTM_BLE_PF_LOCAL_NAME == cond_type ||
    474       BTM_BLE_PF_SRVC_DATA_PATTERN == cond_type)
    475     p_bd_addr = NULL;
    476 
    477   if ((p_addr_filter = btm_ble_find_addr_filter_counter(p_bd_addr)) == NULL &&
    478       BTM_BLE_SCAN_COND_ADD == action) {
    479     p_addr_filter = btm_ble_alloc_addr_filter_counter(p_bd_addr->bda);
    480   }
    481 
    482   if (NULL != p_addr_filter) {
    483     /* all filter just cleared */
    484     if ((BTM_BLE_PF_TYPE_ALL == cond_type &&
    485          BTM_BLE_SCAN_COND_CLEAR == action) ||
    486         /* or bd address filter been deleted */
    487         (BTM_BLE_PF_ADDR_FILTER == cond_type &&
    488          (BTM_BLE_SCAN_COND_DELETE == action ||
    489           BTM_BLE_SCAN_COND_CLEAR == action))) {
    490       btm_ble_dealloc_addr_filter_counter(p_bd_addr, cond_type);
    491     }
    492     /* if not feature selection, update new addition/reduction of the filter
    493        counter */
    494     else if (cond_type != BTM_BLE_PF_TYPE_ALL) {
    495       p_counter = p_addr_filter->pf_counter;
    496       if (num_available > 0) p_counter[cond_type] += 1;
    497 
    498       BTM_TRACE_DEBUG("counter = %d, maxfilt = %d, num_avbl=%d",
    499                       p_counter[cond_type], cmn_ble_vsc_cb.max_filter,
    500                       num_available);
    501       return p_counter[cond_type];
    502     }
    503   } else {
    504     BTM_TRACE_ERROR("no matching filter counter found");
    505   }
    506   /* no matching filter located and updated */
    507   return BTM_BLE_INVALID_COUNTER;
    508 }
    509 
    510 /**
    511  * This function updates the address filter of adv.
    512  */
    513 void BTM_LE_PF_addr_filter(tBTM_BLE_SCAN_COND_OP action,
    514                            tBTM_BLE_PF_FILT_INDEX filt_index, tBLE_BD_ADDR addr,
    515                            tBTM_BLE_PF_CFG_CBACK cb) {
    516   const uint8_t len = BTM_BLE_ADV_FILT_META_HDR_LENGTH + BTM_BLE_META_ADDR_LEN;
    517 
    518   uint8_t param[len];
    519   memset(param, 0, len);
    520 
    521   uint8_t* p = param;
    522   UINT8_TO_STREAM(p, BTM_BLE_META_PF_ADDR);
    523   UINT8_TO_STREAM(p, action);
    524   UINT8_TO_STREAM(p, filt_index);
    525 
    526   if (action != BTM_BLE_SCAN_COND_CLEAR) {
    527     BDADDR_TO_STREAM(p, addr.bda);
    528     UINT8_TO_STREAM(p, addr.type);
    529   }
    530 
    531   /* send address filter */
    532   btu_hcif_send_cmd_with_cb(
    533       FROM_HERE, HCI_BLE_ADV_FILTER_OCF, param, len,
    534       base::Bind(&btm_flt_update_cb, BTM_BLE_META_PF_ADDR, cb));
    535 
    536   memset(&btm_ble_adv_filt_cb.cur_filter_target, 0, sizeof(tBLE_BD_ADDR));
    537 }
    538 
    539 /**
    540  * This function updates(adds, deletes or clears) the service UUID filter.
    541  */
    542 void BTM_LE_PF_uuid_filter(tBTM_BLE_SCAN_COND_OP action,
    543                            tBTM_BLE_PF_FILT_INDEX filt_index,
    544                            tBTM_BLE_PF_COND_TYPE filter_type, tBT_UUID uuid,
    545                            tBTM_BLE_PF_LOGIC_TYPE cond_logic,
    546                            tBTM_BLE_PF_COND_MASK* p_uuid_mask,
    547                            tBTM_BLE_PF_CFG_CBACK cb) {
    548   uint8_t evt_type;
    549 
    550   if (BTM_BLE_PF_SRVC_UUID == filter_type) {
    551     evt_type = BTM_BLE_META_PF_UUID;
    552   } else {
    553     evt_type = BTM_BLE_META_PF_SOL_UUID;
    554   }
    555 
    556   uint8_t len = BTM_BLE_ADV_FILT_META_HDR_LENGTH;
    557   uint8_t max_len = len + BTM_BLE_META_UUID_LEN;
    558   uint8_t param[max_len];
    559   memset(param, 0, max_len);
    560   uint8_t* p = param;
    561 
    562   UINT8_TO_STREAM(p, evt_type);
    563   UINT8_TO_STREAM(p, action);
    564   UINT8_TO_STREAM(p, filt_index);
    565 
    566   if (action != BTM_BLE_SCAN_COND_CLEAR) {
    567     if (uuid.len == LEN_UUID_16) {
    568       UINT16_TO_STREAM(p, uuid.uu.uuid16);
    569       len += LEN_UUID_16;
    570     } else if (uuid.len == LEN_UUID_32) {
    571       UINT32_TO_STREAM(p, uuid.uu.uuid32);
    572       len += LEN_UUID_32;
    573     } else if (uuid.len == LEN_UUID_128) {
    574       ARRAY_TO_STREAM(p, uuid.uu.uuid128, LEN_UUID_128);
    575       len += LEN_UUID_128;
    576     } else {
    577       BTM_TRACE_ERROR("illegal UUID length: %d", uuid.len);
    578       cb.Run(0, BTM_BLE_PF_CONFIG, 1 /*BTA_FAILURE*/);
    579       return;
    580     }
    581 
    582     if (p_uuid_mask) {
    583       if (uuid.len == LEN_UUID_16) {
    584         UINT16_TO_STREAM(p, p_uuid_mask->uuid16_mask);
    585         len += LEN_UUID_16;
    586       } else if (uuid.len == LEN_UUID_32) {
    587         UINT32_TO_STREAM(p, p_uuid_mask->uuid32_mask);
    588         len += LEN_UUID_32;
    589       } else if (uuid.len == LEN_UUID_128) {
    590         ARRAY_TO_STREAM(p, p_uuid_mask->uuid128_mask, LEN_UUID_128);
    591         len += LEN_UUID_128;
    592       }
    593     } else {
    594       memset(p, 0xff, uuid.len);
    595       len += uuid.len;
    596     }
    597   }
    598 
    599   /* send UUID filter update */
    600   btu_hcif_send_cmd_with_cb(FROM_HERE, HCI_BLE_ADV_FILTER_OCF, param, len,
    601                             base::Bind(&btm_flt_update_cb, evt_type, cb));
    602   memset(&btm_ble_adv_filt_cb.cur_filter_target, 0, sizeof(tBLE_BD_ADDR));
    603 }
    604 
    605 /**
    606  * all adv payload filter by de-selecting all the adv pf feature bits
    607  */
    608 void BTM_LE_PF_clear(tBTM_BLE_PF_FILT_INDEX filt_index,
    609                      tBTM_BLE_PF_CFG_CBACK cb) {
    610   /* clear the general filter entry */
    611   {
    612     tBTM_BLE_PF_CFG_CBACK fDoNothing;
    613 
    614     /* clear manufactuer data filter */
    615     BTM_LE_PF_manu_data(BTM_BLE_SCAN_COND_CLEAR, filt_index, 0, 0, {}, {},
    616                         fDoNothing);
    617 
    618     /* clear local name filter */
    619     BTM_LE_PF_local_name(BTM_BLE_SCAN_COND_CLEAR, filt_index, {}, fDoNothing);
    620 
    621     /* update the counter for service data */
    622     BTM_LE_PF_srvc_data(BTM_BLE_SCAN_COND_CLEAR, filt_index);
    623 
    624     /* clear UUID filter */
    625     BTM_LE_PF_uuid_filter(BTM_BLE_SCAN_COND_CLEAR, filt_index,
    626                           BTM_BLE_PF_SRVC_UUID, {}, 0, nullptr, fDoNothing);
    627 
    628     BTM_LE_PF_uuid_filter(BTM_BLE_SCAN_COND_CLEAR, filt_index,
    629                           BTM_BLE_PF_SRVC_SOL_UUID, {}, 0, nullptr, fDoNothing);
    630 
    631     /* clear service data filter */
    632     BTM_LE_PF_srvc_data_pattern(BTM_BLE_SCAN_COND_CLEAR, filt_index, {}, {},
    633                                 fDoNothing);
    634   }
    635 
    636   uint8_t len = BTM_BLE_ADV_FILT_META_HDR_LENGTH + BTM_BLE_PF_FEAT_SEL_LEN;
    637   uint8_t param[len];
    638   memset(param, 0, len);
    639 
    640   uint8_t* p = param;
    641 
    642   /* select feature based on control block settings */
    643   UINT8_TO_STREAM(p, BTM_BLE_META_PF_FEAT_SEL);
    644   UINT8_TO_STREAM(p, BTM_BLE_SCAN_COND_CLEAR);
    645   UINT8_TO_STREAM(p, filt_index);
    646   /* set PCF selection */
    647   UINT32_TO_STREAM(p, BTM_BLE_PF_SELECT_NONE);
    648   /* set logic condition as OR as default */
    649   UINT8_TO_STREAM(p, BTM_BLE_PF_LOGIC_OR);
    650 
    651   btu_hcif_send_cmd_with_cb(
    652       FROM_HERE, HCI_BLE_ADV_FILTER_OCF, param, len,
    653       base::Bind(&btm_flt_update_cb, BTM_BLE_META_PF_FEAT_SEL, cb));
    654 
    655   memset(&btm_ble_adv_filt_cb.cur_filter_target, 0, sizeof(tBLE_BD_ADDR));
    656 }
    657 
    658 /*******************************************************************************
    659  *
    660  * Function         BTM_BleAdvFilterParamSetup
    661  *
    662  * Description      This function is called to setup the adv data payload filter
    663  *                  condition.
    664  *
    665  * Parameters       action - Type of action to be performed
    666  *                       filt_index - Filter index
    667  *                       p_filt_params - Filter parameters
    668  *                       cb - Callback
    669  *
    670  ******************************************************************************/
    671 void BTM_BleAdvFilterParamSetup(
    672     int action, tBTM_BLE_PF_FILT_INDEX filt_index,
    673     std::unique_ptr<btgatt_filt_param_setup_t> p_filt_params,
    674     tBTM_BLE_PF_PARAM_CB cb) {
    675   tBTM_BLE_PF_COUNT* p_bda_filter = NULL;
    676   uint8_t len = BTM_BLE_ADV_FILT_META_HDR_LENGTH +
    677                 BTM_BLE_ADV_FILT_FEAT_SELN_LEN + BTM_BLE_ADV_FILT_TRACK_NUM;
    678   uint8_t param[len], *p;
    679 
    680   if (BTM_SUCCESS != btm_ble_obtain_vsc_details()) {
    681     cb.Run(0, BTM_BLE_PF_ENABLE, 1 /* BTA_FAILURE */);
    682     return;
    683   }
    684 
    685   p = param;
    686   memset(param, 0, len);
    687   BTM_TRACE_EVENT("%s", __func__);
    688 
    689   if (BTM_BLE_SCAN_COND_ADD == action) {
    690     p_bda_filter = btm_ble_find_addr_filter_counter(nullptr);
    691     if (NULL == p_bda_filter) {
    692       BTM_TRACE_ERROR("BD Address not found!");
    693       cb.Run(0, BTM_BLE_PF_ENABLE, 1 /* BTA_FAILURE */);
    694       return;
    695     }
    696 
    697     BTM_TRACE_DEBUG("%s : Feat mask:%d", __func__, p_filt_params->feat_seln);
    698     /* select feature based on control block settings */
    699     UINT8_TO_STREAM(p, BTM_BLE_META_PF_FEAT_SEL);
    700     UINT8_TO_STREAM(p, BTM_BLE_SCAN_COND_ADD);
    701 
    702     /* Filter index */
    703     UINT8_TO_STREAM(p, filt_index);
    704 
    705     /* set PCF selection */
    706     UINT16_TO_STREAM(p, p_filt_params->feat_seln);
    707     /* set logic type */
    708     UINT16_TO_STREAM(p, p_filt_params->list_logic_type);
    709     /* set logic condition */
    710     UINT8_TO_STREAM(p, p_filt_params->filt_logic_type);
    711     /* set RSSI high threshold */
    712     UINT8_TO_STREAM(p, p_filt_params->rssi_high_thres);
    713     /* set delivery mode */
    714     UINT8_TO_STREAM(p, p_filt_params->dely_mode);
    715 
    716     if (0x01 == p_filt_params->dely_mode) {
    717       /* set onfound timeout */
    718       UINT16_TO_STREAM(p, p_filt_params->found_timeout);
    719       /* set onfound timeout count*/
    720       UINT8_TO_STREAM(p, p_filt_params->found_timeout_cnt);
    721       /* set RSSI low threshold */
    722       UINT8_TO_STREAM(p, p_filt_params->rssi_low_thres);
    723       /* set onlost timeout */
    724       UINT16_TO_STREAM(p, p_filt_params->lost_timeout);
    725       /* set num_of_track_entries for firmware greater than L-release version */
    726       if (cmn_ble_vsc_cb.version_supported > BTM_VSC_CHIP_CAPABILITY_L_VERSION)
    727         UINT16_TO_STREAM(p, p_filt_params->num_of_tracking_entries);
    728     }
    729 
    730     if (cmn_ble_vsc_cb.version_supported == BTM_VSC_CHIP_CAPABILITY_L_VERSION)
    731       len = BTM_BLE_ADV_FILT_META_HDR_LENGTH + BTM_BLE_ADV_FILT_FEAT_SELN_LEN;
    732     else
    733       len = BTM_BLE_ADV_FILT_META_HDR_LENGTH + BTM_BLE_ADV_FILT_FEAT_SELN_LEN +
    734             BTM_BLE_ADV_FILT_TRACK_NUM;
    735 
    736     btu_hcif_send_cmd_with_cb(
    737         FROM_HERE, HCI_BLE_ADV_FILTER_OCF, param, len,
    738         base::Bind(&btm_flt_update_cb, BTM_BLE_META_PF_FEAT_SEL, cb));
    739   } else if (BTM_BLE_SCAN_COND_DELETE == action) {
    740     /* select feature based on control block settings */
    741     UINT8_TO_STREAM(p, BTM_BLE_META_PF_FEAT_SEL);
    742     UINT8_TO_STREAM(p, BTM_BLE_SCAN_COND_DELETE);
    743     /* Filter index */
    744     UINT8_TO_STREAM(p, filt_index);
    745 
    746     btu_hcif_send_cmd_with_cb(
    747         FROM_HERE, HCI_BLE_ADV_FILTER_OCF, param,
    748         (uint8_t)(BTM_BLE_ADV_FILT_META_HDR_LENGTH),
    749         base::Bind(&btm_flt_update_cb, BTM_BLE_META_PF_FEAT_SEL, cb));
    750   } else if (BTM_BLE_SCAN_COND_CLEAR == action) {
    751     /* Deallocate all filters here */
    752     btm_ble_dealloc_addr_filter_counter(NULL, BTM_BLE_PF_TYPE_ALL);
    753 
    754     /* select feature based on control block settings */
    755     UINT8_TO_STREAM(p, BTM_BLE_META_PF_FEAT_SEL);
    756     UINT8_TO_STREAM(p, BTM_BLE_SCAN_COND_CLEAR);
    757 
    758     btu_hcif_send_cmd_with_cb(
    759         FROM_HERE, HCI_BLE_ADV_FILTER_OCF, param,
    760         (uint8_t)(BTM_BLE_ADV_FILT_META_HDR_LENGTH - 1),
    761         base::Bind(&btm_flt_update_cb, BTM_BLE_META_PF_FEAT_SEL, cb));
    762   }
    763 }
    764 
    765 void enable_cmpl_cback(tBTM_BLE_PF_STATUS_CBACK p_stat_cback, uint8_t* p,
    766                        uint16_t evt_len) {
    767   uint8_t status, op_subcode, action;
    768 
    769   if (evt_len != 3) {
    770     BTM_TRACE_ERROR("%s: APCF callback length = %d", __func__, evt_len);
    771     return;
    772   }
    773 
    774   STREAM_TO_UINT8(status, p);
    775   STREAM_TO_UINT8(op_subcode, p);
    776   STREAM_TO_UINT8(action, p);
    777 
    778   if (op_subcode != BTM_BLE_META_PF_ENABLE) {
    779     BTM_TRACE_ERROR("%s :bad subcode: 0x%02x", __func__, op_subcode);
    780     return;
    781   }
    782 
    783   p_stat_cback.Run(action, status);
    784 }
    785 
    786 /*******************************************************************************
    787  *
    788  * Function         BTM_BleEnableDisableFilterFeature
    789  *
    790  * Description      This function is called to enable / disable the APCF feature
    791  *
    792  * Parameters       enable: enable or disable the filter condition
    793  *                  p_stat_cback - Status callback pointer
    794  *
    795  ******************************************************************************/
    796 void BTM_BleEnableDisableFilterFeature(uint8_t enable,
    797                                        tBTM_BLE_PF_STATUS_CBACK p_stat_cback) {
    798   if (BTM_SUCCESS != btm_ble_obtain_vsc_details()) {
    799     if (p_stat_cback) p_stat_cback.Run(BTM_BLE_PF_ENABLE, 1 /* BTA_FAILURE */);
    800     return;
    801   }
    802 
    803   uint8_t param[20];
    804   memset(param, 0, 20);
    805 
    806   uint8_t* p = param;
    807   UINT8_TO_STREAM(p, BTM_BLE_META_PF_ENABLE);
    808   UINT8_TO_STREAM(p, enable);
    809 
    810   btu_hcif_send_cmd_with_cb(FROM_HERE, HCI_BLE_ADV_FILTER_OCF, param,
    811                             BTM_BLE_PCF_ENABLE_LEN,
    812                             base::Bind(&enable_cmpl_cback, p_stat_cback));
    813 }
    814 
    815 /*******************************************************************************
    816  *
    817  * Function         btm_ble_adv_filter_init
    818  *
    819  * Description      This function initializes the adv filter control block
    820  *
    821  * Parameters
    822  *
    823  * Returns          status
    824  *
    825  ******************************************************************************/
    826 void btm_ble_adv_filter_init(void) {
    827   memset(&btm_ble_adv_filt_cb, 0, sizeof(tBTM_BLE_ADV_FILTER_CB));
    828   if (BTM_SUCCESS != btm_ble_obtain_vsc_details()) return;
    829 
    830   if (cmn_ble_vsc_cb.max_filter > 0) {
    831     btm_ble_adv_filt_cb.p_addr_filter_count = (tBTM_BLE_PF_COUNT*)osi_malloc(
    832         sizeof(tBTM_BLE_PF_COUNT) * cmn_ble_vsc_cb.max_filter);
    833   }
    834 }
    835 
    836 /*******************************************************************************
    837  *
    838  * Function         btm_ble_adv_filter_cleanup
    839  *
    840  * Description      This function de-initializes the adv filter control block
    841  *
    842  * Parameters
    843  *
    844  * Returns          status
    845  *
    846  ******************************************************************************/
    847 void btm_ble_adv_filter_cleanup(void) {
    848   osi_free_and_reset((void**)&btm_ble_adv_filt_cb.p_addr_filter_count);
    849 }
    850