Home | History | Annotate | Download | only in dm
      1 /******************************************************************************
      2  *
      3  *  Copyright (C) 2003-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 /******************************************************************************
     20  *
     21  *  This file contains the action functions for device manager state
     22  *  machine.
     23  *
     24  ******************************************************************************/
     25 
     26 #define LOG_TAG "bt_bta_dm"
     27 
     28 #include <assert.h>
     29 #include <string.h>
     30 
     31 #include "bt_target.h"
     32 #include "bt_types.h"
     33 #include "bta_api.h"
     34 #include "bta_dm_co.h"
     35 #include "bta_dm_int.h"
     36 #include "bta_sys.h"
     37 #include "btm_api.h"
     38 #include "btm_int.h"
     39 #include "btu.h"
     40 #include "gap_api.h"    /* For GAP_BleReadPeerPrefConnParams */
     41 #include "bt_common.h"
     42 #include "l2c_api.h"
     43 #include "osi/include/log.h"
     44 #include "osi/include/osi.h"
     45 #include "sdp_api.h"
     46 #include "utl.h"
     47 
     48 #if (GAP_INCLUDED == TRUE)
     49 #include "gap_api.h"
     50 #endif
     51 
     52 static void bta_dm_inq_results_cb (tBTM_INQ_RESULTS *p_inq, UINT8 *p_eir);
     53 static void bta_dm_inq_cmpl_cb (void * p_result);
     54 static void bta_dm_service_search_remname_cback (BD_ADDR bd_addr, DEV_CLASS dc, BD_NAME bd_name);
     55 static void bta_dm_remname_cback (tBTM_REMOTE_DEV_NAME *p_remote_name);
     56 static void bta_dm_find_services ( BD_ADDR bd_addr);
     57 static void bta_dm_discover_next_device(void);
     58 static void bta_dm_sdp_callback (UINT16 sdp_status);
     59 static UINT8 bta_dm_authorize_cback (BD_ADDR bd_addr, DEV_CLASS dev_class, BD_NAME bd_name, UINT8 *service_name, UINT8 service_id, BOOLEAN is_originator);
     60 static UINT8 bta_dm_pin_cback (BD_ADDR bd_addr, DEV_CLASS dev_class, BD_NAME bd_name, BOOLEAN min_16_digit);
     61 static UINT8 bta_dm_new_link_key_cback(BD_ADDR bd_addr, DEV_CLASS dev_class, BD_NAME bd_name, LINK_KEY key, UINT8 key_type);
     62 static UINT8 bta_dm_authentication_complete_cback(BD_ADDR bd_addr, DEV_CLASS dev_class,BD_NAME bd_name, int result);
     63 static void bta_dm_local_name_cback(BD_ADDR bd_addr);
     64 static BOOLEAN bta_dm_check_av(UINT16 event);
     65 static void bta_dm_bl_change_cback (tBTM_BL_EVENT_DATA *p_data);
     66 
     67 static void bta_dm_policy_cback(tBTA_SYS_CONN_STATUS status, UINT8 id, UINT8 app_id, BD_ADDR peer_addr);
     68 
     69 /* Extended Inquiry Response */
     70 static UINT8 bta_dm_sp_cback (tBTM_SP_EVT event, tBTM_SP_EVT_DATA *p_data);
     71 
     72 static void bta_dm_set_eir (char *local_name);
     73 
     74 static void bta_dm_eir_search_services( tBTM_INQ_RESULTS  *p_result,
     75                                         tBTA_SERVICE_MASK *p_services_to_search,
     76                                         tBTA_SERVICE_MASK *p_services_found);
     77 
     78 static void bta_dm_search_timer_cback(void *data);
     79 static void bta_dm_disable_conn_down_timer_cback(void *data);
     80 static void bta_dm_rm_cback(tBTA_SYS_CONN_STATUS status, UINT8 id, UINT8 app_id, BD_ADDR peer_addr);
     81 static void bta_dm_adjust_roles(BOOLEAN delay_role_switch);
     82 static char *bta_dm_get_remname(void);
     83 static void bta_dm_bond_cancel_complete_cback(tBTM_STATUS result);
     84 
     85 static BOOLEAN bta_dm_read_remote_device_name (BD_ADDR bd_addr,tBT_TRANSPORT transport);
     86 static void bta_dm_discover_device(BD_ADDR remote_bd_addr);
     87 
     88 static void bta_dm_sys_hw_cback( tBTA_SYS_HW_EVT status );
     89 static void bta_dm_disable_search_and_disc(void);
     90 
     91 #if ((defined BLE_INCLUDED) && (BLE_INCLUDED == TRUE))
     92     #if ((defined SMP_INCLUDED) && (SMP_INCLUDED == TRUE))
     93 static UINT8 bta_dm_ble_smp_cback (tBTM_LE_EVT event, BD_ADDR bda, tBTM_LE_EVT_DATA *p_data);
     94     #endif
     95 static void bta_dm_ble_id_key_cback (UINT8 key_type, tBTM_BLE_LOCAL_KEYS *p_key);
     96     #if ((defined BTA_GATT_INCLUDED) &&  (BTA_GATT_INCLUDED == TRUE))
     97 static void bta_dm_gattc_register(void);
     98 static void btm_dm_start_gatt_discovery(BD_ADDR bd_addr);
     99 static void bta_dm_cancel_gatt_discovery(BD_ADDR bd_addr);
    100 static void bta_dm_gattc_callback(tBTA_GATTC_EVT event, tBTA_GATTC *p_data);
    101 extern tBTA_DM_CONTRL_STATE bta_dm_pm_obtain_controller_state(void);
    102     #endif
    103 
    104 #if BLE_VND_INCLUDED == TRUE
    105 static void bta_dm_ctrl_features_rd_cmpl_cback(tBTM_STATUS result);
    106 #endif
    107 
    108 #ifndef BTA_DM_BLE_ADV_CHNL_MAP
    109 #define BTA_DM_BLE_ADV_CHNL_MAP (BTM_BLE_ADV_CHNL_37|BTM_BLE_ADV_CHNL_38|BTM_BLE_ADV_CHNL_39)
    110 #endif
    111 #endif
    112 
    113 /* Disable timer interval (in milliseconds) */
    114 #ifndef BTA_DM_DISABLE_TIMER_MS
    115 #define BTA_DM_DISABLE_TIMER_MS 5000
    116 #endif
    117 
    118 /* Disable timer retrial interval (in milliseconds) */
    119 #ifndef BTA_DM_DISABLE_TIMER_RETRIAL_MS
    120 #define BTA_DM_DISABLE_TIMER_RETRIAL_MS 1500
    121 #endif
    122 
    123 /* Disable connection down timer (in milliseconds) */
    124 #ifndef BTA_DM_DISABLE_CONN_DOWN_TIMER_MS
    125 #define BTA_DM_DISABLE_CONN_DOWN_TIMER_MS 1000
    126 #endif
    127 
    128 /* Switch delay timer (in milliseconds) */
    129 #ifndef BTA_DM_SWITCH_DELAY_TIMER_MS
    130 #define BTA_DM_SWITCH_DELAY_TIMER_MS 500
    131 #endif
    132 
    133 static void bta_dm_reset_sec_dev_pending(BD_ADDR remote_bd_addr);
    134 static void bta_dm_remove_sec_dev_entry(BD_ADDR remote_bd_addr);
    135 static void bta_dm_observe_results_cb(tBTM_INQ_RESULTS *p_inq, UINT8 *p_eir);
    136 static void bta_dm_observe_cmpl_cb(void * p_result);
    137 static void bta_dm_delay_role_switch_cback(void *data);
    138 extern void sdpu_uuid16_to_uuid128(UINT16 uuid16, UINT8* p_uuid128);
    139 static void bta_dm_disable_timer_cback(void *data);
    140 
    141 
    142 const UINT16 bta_service_id_to_uuid_lkup_tbl [BTA_MAX_SERVICE_ID] =
    143 {
    144     UUID_SERVCLASS_PNP_INFORMATION,         /* Reserved */
    145     UUID_SERVCLASS_SERIAL_PORT,             /* BTA_SPP_SERVICE_ID */
    146     UUID_SERVCLASS_DIALUP_NETWORKING,       /* BTA_DUN_SERVICE_ID */
    147     UUID_SERVCLASS_AUDIO_SOURCE,            /* BTA_A2DP_SOURCE_SERVICE_ID */
    148     UUID_SERVCLASS_LAN_ACCESS_USING_PPP,    /* BTA_LAP_SERVICE_ID */
    149     UUID_SERVCLASS_HEADSET,                 /* BTA_HSP_HS_SERVICE_ID */
    150     UUID_SERVCLASS_HF_HANDSFREE,            /* BTA_HFP_HS_SERVICE_ID */
    151     UUID_SERVCLASS_OBEX_OBJECT_PUSH,        /* BTA_OPP_SERVICE_ID */
    152     UUID_SERVCLASS_OBEX_FILE_TRANSFER,      /* BTA_FTP_SERVICE_ID */
    153     UUID_SERVCLASS_CORDLESS_TELEPHONY,      /* BTA_CTP_SERVICE_ID */
    154     UUID_SERVCLASS_INTERCOM,                /* BTA_ICP_SERVICE_ID */
    155     UUID_SERVCLASS_IRMC_SYNC,               /* BTA_SYNC_SERVICE_ID */
    156     UUID_SERVCLASS_DIRECT_PRINTING,         /* BTA_BPP_SERVICE_ID */
    157     UUID_SERVCLASS_IMAGING_RESPONDER,       /* BTA_BIP_SERVICE_ID */
    158     UUID_SERVCLASS_PANU,                    /* BTA_PANU_SERVICE_ID */
    159     UUID_SERVCLASS_NAP,                     /* BTA_NAP_SERVICE_ID */
    160     UUID_SERVCLASS_GN,                      /* BTA_GN_SERVICE_ID */
    161     UUID_SERVCLASS_SAP,                     /* BTA_SAP_SERVICE_ID */
    162     UUID_SERVCLASS_AUDIO_SINK,              /* BTA_A2DP_SERVICE_ID */
    163     UUID_SERVCLASS_AV_REMOTE_CONTROL,       /* BTA_AVRCP_SERVICE_ID */
    164     UUID_SERVCLASS_HUMAN_INTERFACE,         /* BTA_HID_SERVICE_ID */
    165     UUID_SERVCLASS_VIDEO_SINK,              /* BTA_VDP_SERVICE_ID */
    166     UUID_SERVCLASS_PBAP_PSE,                /* BTA_PBAP_SERVICE_ID */
    167     UUID_SERVCLASS_HEADSET_AUDIO_GATEWAY,   /* BTA_HSP_SERVICE_ID */
    168     UUID_SERVCLASS_AG_HANDSFREE,            /* BTA_HFP_SERVICE_ID */
    169     UUID_SERVCLASS_MESSAGE_ACCESS,          /* BTA_MAP_SERVICE_ID */
    170     UUID_SERVCLASS_MESSAGE_NOTIFICATION,    /* BTA_MN_SERVICE_ID */
    171     UUID_SERVCLASS_HDP_PROFILE,             /* BTA_HDP_SERVICE_ID */
    172     UUID_SERVCLASS_PBAP_PCE                 /* BTA_PCE_SERVICE_ID */
    173 #if BLE_INCLUDED && BTA_GATT_INCLUDED
    174     ,UUID_PROTOCOL_ATT                       /* BTA_GATT_SERVICE_ID */
    175 #endif
    176 };
    177 
    178 /*
    179  * NOTE : The number of element in bta_service_id_to_btm_srv_id_lkup_tbl should be matching with
    180  *        the value BTA_MAX_SERVICE_ID in bta_api.h
    181  *
    182  *        i.e., If you add new Service ID for BTA, the correct security ID of the new service
    183  *              from Security service definitions (btm_api.h) should be added to this lookup table.
    184  */
    185 const UINT32 bta_service_id_to_btm_srv_id_lkup_tbl [BTA_MAX_SERVICE_ID] =
    186 {
    187     0,                                      /* Reserved */
    188     BTM_SEC_SERVICE_SERIAL_PORT,            /* BTA_SPP_SERVICE_ID */
    189     BTM_SEC_SERVICE_DUN,                    /* BTA_DUN_SERVICE_ID */
    190     BTM_SEC_SERVICE_AVDTP,                  /* BTA_AUDIO_SOURCE_SERVICE_ID */
    191     BTM_SEC_SERVICE_LAN_ACCESS,             /* BTA_LAP_SERVICE_ID */
    192     BTM_SEC_SERVICE_HEADSET_AG,             /* BTA_HSP_SERVICE_ID */
    193     BTM_SEC_SERVICE_AG_HANDSFREE,           /* BTA_HFP_SERVICE_ID */
    194     BTM_SEC_SERVICE_OBEX,                   /* BTA_OPP_SERVICE_ID */
    195     BTM_SEC_SERVICE_OBEX_FTP,               /* BTA_FTP_SERVICE_ID */
    196     BTM_SEC_SERVICE_CORDLESS,               /* BTA_CTP_SERVICE_ID */
    197     BTM_SEC_SERVICE_INTERCOM,               /* BTA_ICP_SERVICE_ID */
    198     BTM_SEC_SERVICE_IRMC_SYNC,              /* BTA_SYNC_SERVICE_ID */
    199     BTM_SEC_SERVICE_BPP_JOB,                /* BTA_BPP_SERVICE_ID */
    200     BTM_SEC_SERVICE_BIP,                    /* BTA_BIP_SERVICE_ID */
    201     BTM_SEC_SERVICE_BNEP_PANU,              /* BTA_PANU_SERVICE_ID */
    202     BTM_SEC_SERVICE_BNEP_NAP,               /* BTA_NAP_SERVICE_ID */
    203     BTM_SEC_SERVICE_BNEP_GN,                /* BTA_GN_SERVICE_ID */
    204     BTM_SEC_SERVICE_SAP,                    /* BTA_SAP_SERVICE_ID */
    205     BTM_SEC_SERVICE_AVDTP,                  /* BTA_A2DP_SERVICE_ID */
    206     BTM_SEC_SERVICE_AVCTP,                  /* BTA_AVRCP_SERVICE_ID */
    207     BTM_SEC_SERVICE_HIDH_SEC_CTRL,          /* BTA_HID_SERVICE_ID */
    208     BTM_SEC_SERVICE_AVDTP,                  /* BTA_VDP_SERVICE_ID */
    209     BTM_SEC_SERVICE_PBAP,                   /* BTA_PBAP_SERVICE_ID */
    210     BTM_SEC_SERVICE_HEADSET,                /* BTA_HSP_HS_SERVICE_ID */
    211     BTM_SEC_SERVICE_HF_HANDSFREE,           /* BTA_HFP_HS_SERVICE_ID */
    212     BTM_SEC_SERVICE_MAP,                    /* BTA_MAP_SERVICE_ID */
    213     BTM_SEC_SERVICE_MAP,                    /* BTA_MN_SERVICE_ID */
    214     BTM_SEC_SERVICE_HDP_SNK,                /* BTA_HDP_SERVICE_ID */
    215     BTM_SEC_SERVICE_PBAP                    /* BTA_PCE_SERVICE_ID */
    216 #if BLE_INCLUDED && BTA_GATT_INCLUDED
    217     ,BTM_SEC_SERVICE_ATT                    /* BTA_GATT_SERVICE_ID */
    218 #endif
    219 
    220 };
    221 
    222 /* bta security callback */
    223 const tBTM_APPL_INFO bta_security =
    224 {
    225     &bta_dm_authorize_cback,
    226     &bta_dm_pin_cback,
    227     &bta_dm_new_link_key_cback,
    228     &bta_dm_authentication_complete_cback,
    229     &bta_dm_bond_cancel_complete_cback,
    230 #if (BTM_LOCAL_IO_CAPS != BTM_IO_CAP_NONE)
    231     &bta_dm_sp_cback
    232 #else
    233     NULL
    234 #endif
    235 #if BLE_INCLUDED == TRUE
    236 #if SMP_INCLUDED == TRUE
    237     ,&bta_dm_ble_smp_cback
    238 #endif
    239     ,&bta_dm_ble_id_key_cback
    240 #endif
    241 
    242 };
    243 
    244 #define MAX_DISC_RAW_DATA_BUF       (4096)
    245 UINT8 g_disc_raw_data_buf[MAX_DISC_RAW_DATA_BUF];
    246 
    247 extern DEV_CLASS local_device_default_class;
    248 extern fixed_queue_t *btu_bta_alarm_queue;
    249 
    250 /*******************************************************************************
    251 **
    252 ** Function         bta_dm_enable
    253 **
    254 ** Description      Initialises the BT device manager
    255 **
    256 **
    257 ** Returns          void
    258 **
    259 *******************************************************************************/
    260 void bta_dm_enable(tBTA_DM_MSG *p_data)
    261 {
    262     tBTA_DM_ENABLE enable_event;
    263 
    264     /* if already in use, return an error */
    265     if( bta_dm_cb.is_bta_dm_active == TRUE  )
    266     {
    267         APPL_TRACE_WARNING("%s Device already started by another application", __func__);
    268         memset(&enable_event, 0, sizeof(tBTA_DM_ENABLE));
    269         enable_event.status = BTA_FAILURE;
    270         if (p_data->enable.p_sec_cback != NULL)
    271             p_data->enable.p_sec_cback(BTA_DM_ENABLE_EVT, (tBTA_DM_SEC *)&enable_event);
    272         return;
    273     }
    274 
    275     /* first, register our callback to SYS HW manager */
    276     bta_sys_hw_register( BTA_SYS_HW_BLUETOOTH, bta_dm_sys_hw_cback );
    277 
    278     /* make sure security callback is saved - if no callback, do not erase the previous one,
    279     it could be an error recovery mechanism */
    280     if( p_data->enable.p_sec_cback != NULL  )
    281     bta_dm_cb.p_sec_cback = p_data->enable.p_sec_cback;
    282     /* notify BTA DM is now active */
    283     bta_dm_cb.is_bta_dm_active = TRUE;
    284 
    285     /* send a message to BTA SYS */
    286     tBTA_SYS_HW_MSG *sys_enable_event =
    287         (tBTA_SYS_HW_MSG *)osi_malloc(sizeof(tBTA_SYS_HW_MSG));
    288     sys_enable_event->hdr.event = BTA_SYS_API_ENABLE_EVT;
    289     sys_enable_event->hw_module = BTA_SYS_HW_BLUETOOTH;
    290 
    291     bta_sys_sendmsg(sys_enable_event);
    292 }
    293 
    294 /*******************************************************************************
    295 **
    296 ** Function         bta_dm_init_cb
    297 **
    298 ** Description      Initializes or re-initializes the bta_dm_cb control block
    299 **
    300 **
    301 ** Returns          void
    302 **
    303 *******************************************************************************/
    304 void bta_dm_init_cb(void)
    305 {
    306     /*
    307      * TODO: Should alarm_free() the bta_dm_cb timers during graceful
    308      * shutdown.
    309      */
    310     alarm_free(bta_dm_cb.disable_timer);
    311     alarm_free(bta_dm_cb.switch_delay_timer);
    312     for (size_t i = 0; i < BTA_DM_NUM_PM_TIMER; i++) {
    313         for (size_t j = 0; j < BTA_DM_PM_MODE_TIMER_MAX; j++) {
    314             alarm_free(bta_dm_cb.pm_timer[i].timer[j]);
    315         }
    316     }
    317     memset(&bta_dm_cb, 0, sizeof(bta_dm_cb));
    318     bta_dm_cb.disable_timer = alarm_new("bta_dm.disable_timer");
    319     bta_dm_cb.switch_delay_timer = alarm_new("bta_dm.switch_delay_timer");
    320     for (size_t i = 0; i < BTA_DM_NUM_PM_TIMER; i++) {
    321         for (size_t j = 0; j < BTA_DM_PM_MODE_TIMER_MAX; j++) {
    322             bta_dm_cb.pm_timer[i].timer[j] = alarm_new("bta_dm.pm_timer");
    323         }
    324     }
    325 }
    326 
    327 /*******************************************************************************
    328 **
    329 ** Function         bta_dm_sys_hw_cback
    330 **
    331 ** Description     callback register to SYS to get HW status updates
    332 **
    333 **
    334 ** Returns          void
    335 **
    336 *******************************************************************************/
    337 static void bta_dm_sys_hw_cback( tBTA_SYS_HW_EVT status )
    338 {
    339     DEV_CLASS   dev_class;
    340     tBTA_DM_SEC_CBACK           *temp_cback;
    341 #if BLE_INCLUDED == TRUE
    342     UINT8                   key_mask = 0;
    343     BT_OCTET16              er;
    344     tBTA_BLE_LOCAL_ID_KEYS  id_key;
    345 #endif
    346 
    347     APPL_TRACE_DEBUG("%s with event: %i", __func__, status);
    348 
    349     /* On H/W error evt, report to the registered DM application callback */
    350     if (status == BTA_SYS_HW_ERROR_EVT) {
    351           if( bta_dm_cb.p_sec_cback != NULL )
    352                 bta_dm_cb.p_sec_cback(BTA_DM_HW_ERROR_EVT, NULL);
    353           return;
    354     }
    355 
    356     if( status == BTA_SYS_HW_OFF_EVT )
    357     {
    358         if( bta_dm_cb.p_sec_cback != NULL )
    359             bta_dm_cb.p_sec_cback(BTA_DM_DISABLE_EVT, NULL);
    360 
    361         /* reinitialize the control block */
    362         bta_dm_init_cb();
    363 
    364         /* unregister from SYS */
    365         bta_sys_hw_unregister( BTA_SYS_HW_BLUETOOTH );
    366         /* notify BTA DM is now unactive */
    367         bta_dm_cb.is_bta_dm_active = FALSE;
    368     }
    369     else
    370     if( status == BTA_SYS_HW_ON_EVT )
    371     {
    372         /* FIXME: We should not unregister as the SYS shall invoke this callback on a H/W error.
    373         * We need to revisit when this platform has more than one BLuetooth H/W chip */
    374         //bta_sys_hw_unregister( BTA_SYS_HW_BLUETOOTH);
    375 
    376         /* save security callback */
    377         temp_cback = bta_dm_cb.p_sec_cback;
    378         /* make sure the control block is properly initialized */
    379         bta_dm_init_cb();
    380         /* and retrieve the callback */
    381         bta_dm_cb.p_sec_cback=temp_cback;
    382         bta_dm_cb.is_bta_dm_active = TRUE;
    383 
    384         /* hw is ready, go on with BTA DM initialization */
    385         alarm_free(bta_dm_search_cb.search_timer);
    386         alarm_free(bta_dm_search_cb.gatt_close_timer);
    387         memset(&bta_dm_search_cb, 0, sizeof(bta_dm_search_cb));
    388         /*
    389          * TODO: Should alarm_free() the bta_dm_search_cb timers during
    390          * graceful shutdown.
    391          */
    392         bta_dm_search_cb.search_timer =
    393           alarm_new("bta_dm_search.search_timer");
    394         bta_dm_search_cb.gatt_close_timer =
    395           alarm_new("bta_dm_search.gatt_close_timer");
    396 
    397         memset(&bta_dm_conn_srvcs, 0, sizeof(bta_dm_conn_srvcs));
    398         memset(&bta_dm_di_cb, 0, sizeof(tBTA_DM_DI_CB));
    399 
    400         memcpy(dev_class, p_bta_dm_cfg->dev_class, sizeof(dev_class));
    401         BTM_SetDeviceClass (dev_class);
    402 
    403 #if (defined(BLE_INCLUDED) && (BLE_INCLUDED == TRUE))
    404         /* load BLE local information: ID keys, ER if available */
    405         bta_dm_co_ble_load_local_keys(&key_mask, er, &id_key);
    406 
    407         if (key_mask & BTA_BLE_LOCAL_KEY_TYPE_ER)
    408         {
    409             BTM_BleLoadLocalKeys(BTA_BLE_LOCAL_KEY_TYPE_ER, (tBTM_BLE_LOCAL_KEYS *)&er);
    410         }
    411         if (key_mask & BTA_BLE_LOCAL_KEY_TYPE_ID)
    412         {
    413             BTM_BleLoadLocalKeys(BTA_BLE_LOCAL_KEY_TYPE_ID, (tBTM_BLE_LOCAL_KEYS *)&id_key);
    414         }
    415 #if (defined(BTA_GATT_INCLUDED) && (BTA_GATT_INCLUDED == TRUE))
    416         bta_dm_search_cb.conn_id = BTA_GATT_INVALID_CONN_ID;
    417 #endif  // (defined(BTA_GATT_INCLUDED) && BTA_GATT_INCLUDED)
    418 #endif  // (defined(BLE_INCLUDED) && (BLE_INCLUDED == TRUE))
    419 
    420         BTM_SecRegister((tBTM_APPL_INFO*)&bta_security);
    421         BTM_SetDefaultLinkSuperTout(p_bta_dm_cfg->link_timeout);
    422         BTM_WritePageTimeout(p_bta_dm_cfg->page_timeout);
    423         bta_dm_cb.cur_policy = p_bta_dm_cfg->policy_settings;
    424         BTM_SetDefaultLinkPolicy(bta_dm_cb.cur_policy);
    425         BTM_RegBusyLevelNotif (bta_dm_bl_change_cback, NULL, BTM_BL_UPDATE_MASK|BTM_BL_ROLE_CHG_MASK);
    426 
    427 #if BLE_VND_INCLUDED == TRUE
    428         BTM_BleReadControllerFeatures (bta_dm_ctrl_features_rd_cmpl_cback);
    429 #endif
    430 
    431         /* Earlier, we used to invoke BTM_ReadLocalAddr which was just copying the bd_addr
    432            from the control block and invoking the callback which was sending the DM_ENABLE_EVT.
    433            But then we have a few HCI commands being invoked above which were still in progress
    434            when the ENABLE_EVT was sent. So modified this to fetch the local name which forces
    435            the DM_ENABLE_EVT to be sent only after all the init steps are complete */
    436         BTM_ReadLocalDeviceNameFromController((tBTM_CMPL_CB *)bta_dm_local_name_cback);
    437 
    438         bta_sys_rm_register((tBTA_SYS_CONN_CBACK*)bta_dm_rm_cback);
    439 
    440         /* initialize bluetooth low power manager */
    441         bta_dm_init_pm();
    442 
    443         bta_sys_policy_register((tBTA_SYS_CONN_CBACK*)bta_dm_policy_cback);
    444 
    445 #if (BLE_INCLUDED == TRUE && BTA_GATT_INCLUDED == TRUE)
    446         bta_dm_gattc_register();
    447 #endif
    448 
    449     }
    450     else
    451         APPL_TRACE_DEBUG(" --- ignored event");
    452 
    453 }
    454 
    455 
    456 /*******************************************************************************
    457 **
    458 ** Function         bta_dm_disable
    459 **
    460 ** Description      Disables the BT device manager
    461 **
    462 **
    463 ** Returns          void
    464 **
    465 *******************************************************************************/
    466 void bta_dm_disable (tBTA_DM_MSG *p_data)
    467 {
    468     UNUSED(p_data);
    469 
    470     /* Set l2cap idle timeout to 0 (so BTE immediately disconnects ACL link after last channel is closed) */
    471     L2CA_SetIdleTimeoutByBdAddr((UINT8 *)BT_BD_ANY, 0, BT_TRANSPORT_BR_EDR);
    472     L2CA_SetIdleTimeoutByBdAddr((UINT8 *)BT_BD_ANY, 0, BT_TRANSPORT_LE);
    473 
    474     /* disable all active subsystems */
    475     bta_sys_disable(BTA_SYS_HW_BLUETOOTH);
    476 
    477     BTM_SetDiscoverability(BTM_NON_DISCOVERABLE, 0, 0);
    478     BTM_SetConnectability(BTM_NON_CONNECTABLE, 0, 0);
    479 
    480     bta_dm_disable_pm();
    481     bta_dm_disable_search_and_disc();
    482     bta_dm_cb.disabling = TRUE;
    483 
    484 #if BLE_INCLUDED == TRUE && BTA_GATT_INCLUDED == TRUE
    485     BTM_BleClearBgConnDev();
    486 #endif
    487 
    488     if(BTM_GetNumAclLinks()==0)
    489     {
    490 #if (defined(BTA_DISABLE_DELAY) && BTA_DISABLE_DELAY > 0)
    491         /* If BTA_DISABLE_DELAY is defined and greater than zero, then delay the shutdown by
    492          * BTA_DISABLE_DELAY milliseconds
    493          */
    494         APPL_TRACE_WARNING("%s BTA_DISABLE_DELAY set to %d ms",
    495                             __FUNCTION__, BTA_DISABLE_DELAY);
    496         alarm_set_on_queue(bta_dm_cb.disable_timer, BTA_DISABLE_DELAY,
    497                            bta_dm_disable_conn_down_timer_cback, NULL,
    498                            btu_bta_alarm_queue);
    499 #else
    500         bta_dm_disable_conn_down_timer_cback(NULL);
    501 #endif
    502     }
    503     else
    504     {
    505         alarm_set_on_queue(bta_dm_cb.disable_timer, BTA_DM_DISABLE_TIMER_MS,
    506                            bta_dm_disable_timer_cback, UINT_TO_PTR(0),
    507                            btu_bta_alarm_queue);
    508     }
    509 }
    510 
    511 /*******************************************************************************
    512 **
    513 ** Function         bta_dm_disable_timer_cback
    514 **
    515 ** Description      Called if the disable timer expires
    516 **                  Used to close ACL connections which are still active
    517 **
    518 **
    519 **
    520 ** Returns          void
    521 **
    522 *******************************************************************************/
    523 static void bta_dm_disable_timer_cback(void *data)
    524 {
    525     UINT8 i;
    526     tBT_TRANSPORT transport = BT_TRANSPORT_BR_EDR;
    527     BOOLEAN trigger_disc = FALSE;
    528     uint32_t param = PTR_TO_UINT(data);
    529 
    530     APPL_TRACE_EVENT("%s trial %u", __func__, param);
    531 
    532     if (BTM_GetNumAclLinks() && (param == 0))
    533     {
    534         for(i=0; i<bta_dm_cb.device_list.count; i++)
    535         {
    536 #if (BLE_INCLUDED == TRUE)
    537             transport = bta_dm_cb.device_list.peer_device[i].transport;
    538 #endif
    539             btm_remove_acl(bta_dm_cb.device_list.peer_device[i].peer_bdaddr, transport);
    540             trigger_disc = TRUE;
    541         }
    542 
    543         /* Retrigger disable timer in case ACL disconnect failed, DISABLE_EVT still need
    544             to be sent out to avoid jave layer disable timeout */
    545         if (trigger_disc)
    546         {
    547             alarm_set_on_queue(bta_dm_cb.disable_timer,
    548                                BTA_DM_DISABLE_TIMER_RETRIAL_MS,
    549                                bta_dm_disable_timer_cback, UINT_TO_PTR(1),
    550                                btu_bta_alarm_queue);
    551         }
    552     }
    553     else
    554     {
    555         bta_dm_cb.disabling = FALSE;
    556 
    557         bta_sys_remove_uuid(UUID_SERVCLASS_PNP_INFORMATION);
    558         bta_dm_cb.p_sec_cback(BTA_DM_DISABLE_EVT, NULL);
    559     }
    560 }
    561 
    562 
    563 
    564 
    565 /*******************************************************************************
    566 **
    567 ** Function         bta_dm_set_dev_name
    568 **
    569 ** Description      Sets local device name
    570 **
    571 **
    572 ** Returns          void
    573 **
    574 *******************************************************************************/
    575 void bta_dm_set_dev_name (tBTA_DM_MSG *p_data)
    576 {
    577 
    578     BTM_SetLocalDeviceName((char*)p_data->set_name.name);
    579     bta_dm_set_eir ((char*)p_data->set_name.name);
    580 }
    581 
    582 /*******************************************************************************
    583 **
    584 ** Function         bta_dm_set_visibility
    585 **
    586 ** Description      Sets discoverability, connectability and pairability
    587 **
    588 **
    589 ** Returns          void
    590 **
    591 *******************************************************************************/
    592 void bta_dm_set_visibility(tBTA_DM_MSG *p_data)
    593 {
    594     UINT16 window, interval;
    595 #if (defined(BTA_GATT_INCLUDED) && BTA_GATT_INCLUDED)
    596     UINT16 le_disc_mode = BTM_BleReadDiscoverability();
    597     UINT16 le_conn_mode = BTM_BleReadConnectability();
    598 #endif  // (defined(BTA_GATT_INCLUDED) && BTA_GATT_INCLUDED)
    599     UINT16 disc_mode = BTM_ReadDiscoverability(&window, &interval);
    600     UINT16 conn_mode = BTM_ReadConnectability(&window, &interval);
    601 
    602     /* set modes for Discoverability and connectability if not ignore */
    603     if (p_data->set_visibility.disc_mode != (BTA_DM_IGNORE | BTA_DM_LE_IGNORE))
    604     {
    605 #if (defined(BTA_GATT_INCLUDED) && BTA_GATT_INCLUDED)
    606         if ((p_data->set_visibility.disc_mode & BTA_DM_LE_IGNORE) == BTA_DM_LE_IGNORE)
    607             p_data->set_visibility.disc_mode =
    608                 ((p_data->set_visibility.disc_mode & ~BTA_DM_LE_IGNORE) | le_disc_mode);
    609 #endif  // (defined(BTA_GATT_INCLUDED) && BTA_GATT_INCLUDED)
    610         if ((p_data->set_visibility.disc_mode & BTA_DM_IGNORE) == BTA_DM_IGNORE)
    611             p_data->set_visibility.disc_mode =
    612                 ((p_data->set_visibility.disc_mode & ~BTA_DM_IGNORE) | disc_mode);
    613 
    614         BTM_SetDiscoverability(p_data->set_visibility.disc_mode,
    615                                 bta_dm_cb.inquiry_scan_window,
    616                                 bta_dm_cb.inquiry_scan_interval);
    617     }
    618 
    619     if (p_data->set_visibility.conn_mode != (BTA_DM_IGNORE | BTA_DM_LE_IGNORE))
    620     {
    621 #if (defined(BTA_GATT_INCLUDED) && BTA_GATT_INCLUDED)
    622         if ((p_data->set_visibility.conn_mode & BTA_DM_LE_IGNORE) == BTA_DM_LE_IGNORE)
    623             p_data->set_visibility.conn_mode =
    624                 ((p_data->set_visibility.conn_mode & ~BTA_DM_LE_IGNORE) | le_conn_mode);
    625 #endif  // (defined(BTA_GATT_INCLUDED) && BTA_GATT_INCLUDED)
    626         if ((p_data->set_visibility.conn_mode & BTA_DM_IGNORE) == BTA_DM_IGNORE)
    627             p_data->set_visibility.conn_mode =
    628                 ((p_data->set_visibility.conn_mode & ~BTA_DM_IGNORE) | conn_mode);
    629 
    630         BTM_SetConnectability(p_data->set_visibility.conn_mode,
    631                                 bta_dm_cb.page_scan_window,
    632                                 bta_dm_cb.page_scan_interval);
    633     }
    634 
    635     /* Send False or True if not ignore */
    636     if (p_data->set_visibility.pair_mode != BTA_DM_IGNORE )
    637     {
    638 
    639         if (p_data->set_visibility.pair_mode == BTA_DM_NON_PAIRABLE)
    640             bta_dm_cb.disable_pair_mode = TRUE;
    641         else
    642             bta_dm_cb.disable_pair_mode = FALSE;
    643 
    644     }
    645 
    646     /* Send False or True if not ignore */
    647     if (p_data->set_visibility.conn_paired_only != BTA_DM_IGNORE)
    648     {
    649 
    650         if (p_data->set_visibility.conn_paired_only == BTA_DM_CONN_ALL)
    651             bta_dm_cb.conn_paired_only = FALSE;
    652         else
    653             bta_dm_cb.conn_paired_only = TRUE;
    654 
    655     }
    656 
    657     /* Change mode if either mode is not ignore */
    658     if (p_data->set_visibility.pair_mode != BTA_DM_IGNORE || p_data->set_visibility.conn_paired_only != BTA_DM_IGNORE)
    659         BTM_SetPairableMode((BOOLEAN)(!(bta_dm_cb.disable_pair_mode)),bta_dm_cb.conn_paired_only);
    660 
    661 }
    662 
    663 /*******************************************************************************
    664 **
    665 ** Function         bta_dm_process_remove_device
    666 **
    667 ** Description      Removes device, Disconnects ACL link if required.
    668 ****
    669 *******************************************************************************/
    670 void bta_dm_process_remove_device(BD_ADDR bd_addr)
    671 {
    672 #if (BLE_INCLUDED == TRUE && BTA_GATT_INCLUDED == TRUE)
    673      /* need to remove all pending background connection before unpair */
    674      BTA_GATTC_CancelOpen(0, bd_addr, FALSE);
    675 #endif
    676 
    677      BTM_SecDeleteDevice(bd_addr);
    678 
    679 #if (BLE_INCLUDED == TRUE && BTA_GATT_INCLUDED == TRUE)
    680       /* remove all cached GATT information */
    681       BTA_GATTC_Refresh(bd_addr);
    682 #endif
    683 
    684       if (bta_dm_cb.p_sec_cback)
    685       {
    686          tBTA_DM_SEC sec_event;
    687          bdcpy(sec_event.link_down.bd_addr, bd_addr);
    688          /* No connection, set status to success (acl disc code not valid) */
    689          sec_event.link_down.status = HCI_SUCCESS;
    690          bta_dm_cb.p_sec_cback(BTA_DM_DEV_UNPAIRED_EVT, &sec_event);
    691       }
    692 }
    693 
    694 /*******************************************************************************
    695 **
    696 ** Function         bta_dm_remove_device
    697 **
    698 ** Description      Removes device, disconnects ACL link if required.
    699 ****
    700 *******************************************************************************/
    701 void bta_dm_remove_device(tBTA_DM_MSG *p_data)
    702 {
    703     tBTA_DM_API_REMOVE_DEVICE *p_dev = &p_data->remove_dev;
    704     BOOLEAN continue_delete_other_dev = FALSE;
    705     if (p_dev == NULL)
    706         return;
    707 
    708     BD_ADDR other_address;
    709     bdcpy(other_address, p_dev->bd_addr);
    710 
    711     /* If ACL exists for the device in the remove_bond message*/
    712     BOOLEAN continue_delete_dev = FALSE;
    713     UINT8 other_transport = BT_TRANSPORT_INVALID;
    714 
    715     if (BTM_IsAclConnectionUp(p_dev->bd_addr, BT_TRANSPORT_LE) ||
    716         BTM_IsAclConnectionUp(p_dev->bd_addr, BT_TRANSPORT_BR_EDR))
    717     {
    718         APPL_TRACE_DEBUG("%s: ACL Up count  %d", __func__, bta_dm_cb.device_list.count);
    719         continue_delete_dev = FALSE;
    720 
    721         /* Take the link down first, and mark the device for removal when disconnected */
    722         for(int i=0; i < bta_dm_cb.device_list.count; i++)
    723         {
    724             if (!bdcmp(bta_dm_cb.device_list.peer_device[i].peer_bdaddr, p_dev->bd_addr))
    725             {
    726                 UINT8 transport = BT_TRANSPORT_BR_EDR;
    727 
    728 #if (defined(BTA_GATT_INCLUDED) && BTA_GATT_INCLUDED)
    729                 transport = bta_dm_cb.device_list.peer_device[i].transport;
    730 #endif  // (defined(BTA_GATT_INCLUDED) && BTA_GATT_INCLUDED)
    731                 bta_dm_cb.device_list.peer_device[i].conn_state = BTA_DM_UNPAIRING;
    732                 btm_remove_acl(p_dev->bd_addr, transport);
    733 #if (defined(BTA_GATT_INCLUDED) && BTA_GATT_INCLUDED)
    734                 APPL_TRACE_DEBUG("%s:transport = %d", __func__,
    735                                   bta_dm_cb.device_list.peer_device[i].transport);
    736 
    737                 /* save the other transport to check if device is connected on other_transport */
    738                 if(bta_dm_cb.device_list.peer_device[i].transport == BT_TRANSPORT_LE)
    739                    other_transport = BT_TRANSPORT_BR_EDR;
    740                 else
    741                    other_transport = BT_TRANSPORT_LE;
    742 #endif  // (defined(BTA_GATT_INCLUDED) && BTA_GATT_INCLUDED)
    743 
    744                 break;
    745             }
    746         }
    747     }
    748     else
    749     {
    750         continue_delete_dev = TRUE;
    751     }
    752 #if (defined(BTA_GATT_INCLUDED) && BTA_GATT_INCLUDED)
    753     // If it is DUMO device and device is paired as different address, unpair that device
    754     // if different address
    755     if ((other_transport && (BTM_ReadConnectedTransportAddress(other_address, other_transport))) ||
    756       (!other_transport && (BTM_ReadConnectedTransportAddress(other_address, BT_TRANSPORT_BR_EDR) ||
    757        BTM_ReadConnectedTransportAddress(other_address, BT_TRANSPORT_LE))))
    758     {
    759         continue_delete_other_dev = FALSE;
    760         /* Take the link down first, and mark the device for removal when disconnected */
    761         for(int i=0; i < bta_dm_cb.device_list.count; i++)
    762         {
    763             if (!bdcmp(bta_dm_cb.device_list.peer_device[i].peer_bdaddr, other_address))
    764             {
    765                 bta_dm_cb.device_list.peer_device[i].conn_state = BTA_DM_UNPAIRING;
    766                 btm_remove_acl(other_address,bta_dm_cb.device_list.peer_device[i].transport);
    767                 break;
    768             }
    769         }
    770     }
    771     else
    772     {
    773         APPL_TRACE_DEBUG("%s: continue to delete the other dev ", __func__);
    774         continue_delete_other_dev = TRUE;
    775     }
    776 #endif
    777     /* Delete the device mentioned in the msg */
    778     if (continue_delete_dev)
    779         bta_dm_process_remove_device(p_dev->bd_addr);
    780 
    781     /* Delete the other paired device too */
    782     BD_ADDR dummy_bda = {0};
    783     if (continue_delete_other_dev && (bdcmp(other_address, dummy_bda) != 0))
    784         bta_dm_process_remove_device(other_address);
    785 }
    786 
    787 /*******************************************************************************
    788 **
    789 ** Function         bta_dm_add_device
    790 **
    791 ** Description      This function adds a Link Key to an security database entry.
    792 **                  It is normally called during host startup to restore all required information
    793 **                  stored in the NVRAM.
    794 ****
    795 *******************************************************************************/
    796 void bta_dm_add_device (tBTA_DM_MSG *p_data)
    797 {
    798     tBTA_DM_API_ADD_DEVICE *p_dev = &p_data->add_dev;
    799     UINT8   *p_dc = NULL;
    800     UINT8   *p_lc = NULL;
    801     UINT32  trusted_services_mask[BTM_SEC_SERVICE_ARRAY_SIZE];
    802     UINT8   index = 0;
    803     UINT8   btm_mask_index = 0;
    804 
    805     memset (trusted_services_mask, 0, sizeof(trusted_services_mask));
    806 
    807     /* If not all zeros, the device class has been specified */
    808     if (p_dev->dc_known)
    809         p_dc = (UINT8 *)p_dev->dc;
    810 
    811     if (p_dev->link_key_known)
    812         p_lc = (UINT8 *)p_dev->link_key;
    813 
    814     if (p_dev->is_trusted)
    815     {
    816         /* covert BTA service mask to BTM mask */
    817         while (p_dev->tm && (index < BTA_MAX_SERVICE_ID))
    818         {
    819             if (p_dev->tm & (UINT32)(1<<index))
    820             {
    821 
    822                 btm_mask_index =  bta_service_id_to_btm_srv_id_lkup_tbl[index] / BTM_SEC_ARRAY_BITS;
    823                 trusted_services_mask[btm_mask_index] |= (UINT32)(1 << (bta_service_id_to_btm_srv_id_lkup_tbl[index] - (UINT32)(btm_mask_index * 32)));
    824 
    825                 p_dev->tm &= (UINT32)(~(1<<index));
    826 
    827             }
    828             index++;
    829         }
    830     }
    831 
    832     if (!BTM_SecAddDevice (p_dev->bd_addr, p_dc, p_dev->bd_name, p_dev->features,
    833                            trusted_services_mask, p_lc, p_dev->key_type, p_dev->io_cap,
    834                            p_dev->pin_length))
    835     {
    836         APPL_TRACE_ERROR ("BTA_DM: Error adding device %08x%04x",
    837                 (p_dev->bd_addr[0]<<24)+(p_dev->bd_addr[1]<<16)+(p_dev->bd_addr[2]<<8)+p_dev->bd_addr[3],
    838                 (p_dev->bd_addr[4]<<8)+p_dev->bd_addr[5]);
    839     }
    840 }
    841 
    842 /*******************************************************************************
    843 **
    844 ** Function         bta_dm_close_acl
    845 **
    846 ** Description      This function forces to close the connection to a remote device
    847 **                  and optionaly remove the device from security database if
    848 **                  required.
    849 ****
    850 *******************************************************************************/
    851 void bta_dm_close_acl(tBTA_DM_MSG *p_data)
    852 {
    853     tBTA_DM_API_REMOVE_ACL *p_remove_acl = &p_data->remove_acl;
    854     UINT8   index;
    855 
    856     APPL_TRACE_DEBUG("bta_dm_close_acl");
    857 
    858     if (BTM_IsAclConnectionUp(p_remove_acl->bd_addr, p_remove_acl->transport))
    859     {
    860         for (index = 0; index < bta_dm_cb.device_list.count; index ++)
    861         {
    862             if (!bdcmp( bta_dm_cb.device_list.peer_device[index].peer_bdaddr, p_remove_acl->bd_addr))
    863                 break;
    864             }
    865         if (index != bta_dm_cb.device_list.count)
    866         {
    867             if (p_remove_acl->remove_dev)
    868                 bta_dm_cb.device_list.peer_device[index].remove_dev_pending = TRUE;
    869         }
    870         else
    871         {
    872             APPL_TRACE_ERROR("unknown device, remove ACL failed");
    873         }
    874         /* Disconnect the ACL link */
    875         btm_remove_acl(p_remove_acl->bd_addr, p_remove_acl->transport);
    876     }
    877     /* if to remove the device from security database ? do it now */
    878     else if (p_remove_acl->remove_dev)
    879     {
    880         if (!BTM_SecDeleteDevice(p_remove_acl->bd_addr))
    881         {
    882             APPL_TRACE_ERROR("delete device from security database failed.");
    883         }
    884 #if (BLE_INCLUDED == TRUE && BTA_GATT_INCLUDED == TRUE)
    885         /* need to remove all pending background connection if any */
    886         BTA_GATTC_CancelOpen(0, p_remove_acl->bd_addr, FALSE);
    887         /* remove all cached GATT information */
    888         BTA_GATTC_Refresh(p_remove_acl->bd_addr);
    889 #endif
    890     }
    891     /* otherwise, no action needed */
    892 
    893 }
    894 
    895 /*******************************************************************************
    896 **
    897 ** Function         bta_dm_remove_all_acl
    898 **
    899 ** Description      This function forces to close all the ACL links specified by link type
    900 ****
    901 *******************************************************************************/
    902 void bta_dm_remove_all_acl(tBTA_DM_MSG *p_data)
    903 {
    904     const tBTA_DM_LINK_TYPE link_type = p_data->remove_all_acl.link_type;
    905     tBT_TRANSPORT transport = BT_TRANSPORT_BR_EDR;
    906 
    907     APPL_TRACE_DEBUG("%s link type = %d", __func__, link_type);
    908 
    909     for (UINT8 i=0; i < bta_dm_cb.device_list.count; i++)
    910     {
    911         BD_ADDR addr = {0};
    912         bdcpy(addr, bta_dm_cb.device_list.peer_device[i].peer_bdaddr);
    913 #if defined (BLE_INCLUDED) && (BLE_INCLUDED == TRUE)
    914         transport = bta_dm_cb.device_list.peer_device[i].transport;
    915 #endif
    916         if ((link_type == BTA_DM_LINK_TYPE_ALL) ||
    917             ((link_type == BTA_DM_LINK_TYPE_LE) && (transport == BT_TRANSPORT_LE)) ||
    918             ((link_type == BTA_DM_LINK_TYPE_BR_EDR) && (transport == BT_TRANSPORT_BR_EDR)))
    919         {
    920             /* Disconnect the ACL link */
    921             btm_remove_acl(addr, transport);
    922         }
    923     }
    924 }
    925 
    926 
    927 /*******************************************************************************
    928 **
    929 ** Function         bta_dm_bond
    930 **
    931 ** Description      Bonds with peer device
    932 **
    933 **
    934 ** Returns          void
    935 **
    936 *******************************************************************************/
    937 void bta_dm_bond (tBTA_DM_MSG *p_data)
    938 {
    939     tBTM_STATUS status;
    940     tBTA_DM_SEC sec_event;
    941     char        *p_name;
    942 
    943     if (p_data->bond.transport == BTA_TRANSPORT_UNKNOWN)
    944         status = BTM_SecBond ( p_data->bond.bd_addr, 0, NULL, 0 );
    945     else
    946         status = BTM_SecBondByTransport ( p_data->bond.bd_addr, p_data->bond.transport, 0, NULL, 0 );
    947 
    948 
    949     if (bta_dm_cb.p_sec_cback && (status != BTM_CMD_STARTED))
    950     {
    951 
    952         memset(&sec_event, 0, sizeof(tBTA_DM_SEC));
    953         bdcpy(sec_event.auth_cmpl.bd_addr, p_data->bond.bd_addr);
    954         p_name = BTM_SecReadDevName(p_data->bond.bd_addr);
    955         if (p_name != NULL)
    956         {
    957             memcpy(sec_event.auth_cmpl.bd_name, p_name, (BD_NAME_LEN-1));
    958             sec_event.auth_cmpl.bd_name[BD_NAME_LEN-1] = 0;
    959         }
    960 
    961 /*      taken care of by memset [above]
    962         sec_event.auth_cmpl.key_present = FALSE;
    963         sec_event.auth_cmpl.success = FALSE;
    964 */
    965         sec_event.auth_cmpl.fail_reason = HCI_ERR_ILLEGAL_COMMAND;
    966         if (status == BTM_SUCCESS)
    967         {
    968             sec_event.auth_cmpl.success = TRUE;
    969         }
    970         else
    971         {
    972             /* delete this device entry from Sec Dev DB */
    973             bta_dm_remove_sec_dev_entry(p_data->bond.bd_addr);
    974         }
    975         bta_dm_cb.p_sec_cback(BTA_DM_AUTH_CMPL_EVT, &sec_event);
    976     }
    977 
    978 }
    979 
    980 /*******************************************************************************
    981 **
    982 ** Function         bta_dm_bond_cancel
    983 **
    984 ** Description      Cancels bonding with a peer device
    985 **
    986 **
    987 ** Returns          void
    988 **
    989 *******************************************************************************/
    990 void bta_dm_bond_cancel (tBTA_DM_MSG *p_data)
    991 {
    992     tBTM_STATUS status;
    993     tBTA_DM_SEC sec_event;
    994 
    995     APPL_TRACE_EVENT(" bta_dm_bond_cancel ");
    996     status = BTM_SecBondCancel ( p_data->bond_cancel.bd_addr );
    997 
    998     if (bta_dm_cb.p_sec_cback && (status != BTM_CMD_STARTED && status != BTM_SUCCESS))
    999     {
   1000         sec_event.bond_cancel_cmpl.result = BTA_FAILURE;
   1001 
   1002         bta_dm_cb.p_sec_cback(BTA_DM_BOND_CANCEL_CMPL_EVT, &sec_event);
   1003     }
   1004 
   1005 }
   1006 
   1007 /*******************************************************************************
   1008 **
   1009 ** Function         bta_dm_pin_reply
   1010 **
   1011 ** Description      Send the pin_reply to a request from BTM
   1012 **
   1013 **
   1014 ** Returns          void
   1015 **
   1016 *******************************************************************************/
   1017 void bta_dm_pin_reply (tBTA_DM_MSG *p_data)
   1018 {
   1019     UINT32  trusted_mask[BTM_SEC_SERVICE_ARRAY_SIZE];
   1020     UINT32  * current_trusted_mask;
   1021 
   1022     current_trusted_mask = BTM_ReadTrustedMask(p_data->pin_reply.bd_addr);
   1023 
   1024     if(current_trusted_mask)
   1025     {
   1026         memcpy(trusted_mask, current_trusted_mask, sizeof(trusted_mask));
   1027     }
   1028     else
   1029     {
   1030         memset(trusted_mask, 0, sizeof(trusted_mask));
   1031     }
   1032 
   1033     if(p_data->pin_reply.accept)
   1034     {
   1035 
   1036         BTM_PINCodeReply(p_data->pin_reply.bd_addr, BTM_SUCCESS, p_data->pin_reply.pin_len, p_data->pin_reply.p_pin, trusted_mask );
   1037     }
   1038     else
   1039     {
   1040         BTM_PINCodeReply(p_data->pin_reply.bd_addr, BTM_NOT_AUTHORIZED, 0, NULL, trusted_mask );
   1041     }
   1042 
   1043 }
   1044 
   1045 /*******************************************************************************
   1046 **
   1047 ** Function         bta_dm_policy_cback
   1048 **
   1049 ** Description      process the link policy changes
   1050 **
   1051 ** Returns          void
   1052 **
   1053 *******************************************************************************/
   1054 static void bta_dm_policy_cback(tBTA_SYS_CONN_STATUS status, UINT8 id, UINT8 app_id, BD_ADDR peer_addr)
   1055 {
   1056     tBTA_DM_PEER_DEVICE *p_dev = NULL;
   1057     UINT16  policy = app_id;
   1058     UINT32  mask = (UINT32)(1 << id);
   1059 
   1060     if(peer_addr)
   1061         p_dev = bta_dm_find_peer_device(peer_addr);
   1062 
   1063     APPL_TRACE_DEBUG(" bta_dm_policy_cback cmd:%d, policy:0x%x",
   1064         status, policy);
   1065     switch(status)
   1066     {
   1067     case BTA_SYS_PLCY_SET:
   1068         if(!p_dev)
   1069             return;
   1070         /* restore the default link policy */
   1071         p_dev->link_policy |= policy;
   1072         BTM_SetLinkPolicy(p_dev->peer_bdaddr, &(p_dev->link_policy));
   1073         break;
   1074 
   1075     case BTA_SYS_PLCY_CLR:
   1076         if(!p_dev)
   1077             return;
   1078         /* clear the policy from the default link policy */
   1079         p_dev->link_policy &= (~policy);
   1080         BTM_SetLinkPolicy(p_dev->peer_bdaddr, &(p_dev->link_policy));
   1081 
   1082         if(policy & (HCI_ENABLE_SNIFF_MODE | HCI_ENABLE_PARK_MODE))
   1083         {
   1084             /* if clearing sniff/park, wake the link */
   1085             bta_dm_pm_active(p_dev->peer_bdaddr);
   1086         }
   1087         break;
   1088 
   1089     case BTA_SYS_PLCY_DEF_SET:
   1090         /* want to restore/set the role switch policy */
   1091         bta_dm_cb.role_policy_mask &= ~mask;
   1092         if(0 == bta_dm_cb.role_policy_mask)
   1093         {
   1094             /* if nobody wants to insist on the role */
   1095             bta_dm_cb.cur_policy |= HCI_ENABLE_MASTER_SLAVE_SWITCH;
   1096             BTM_SetDefaultLinkPolicy(bta_dm_cb.cur_policy);
   1097         }
   1098         break;
   1099 
   1100     case BTA_SYS_PLCY_DEF_CLR:
   1101         /* want to remove the role switch policy */
   1102         bta_dm_cb.role_policy_mask |= mask;
   1103         bta_dm_cb.cur_policy &= ~HCI_ENABLE_MASTER_SLAVE_SWITCH;
   1104         BTM_SetDefaultLinkPolicy(bta_dm_cb.cur_policy);
   1105         break;
   1106     }
   1107 }
   1108 
   1109 /*******************************************************************************
   1110 **
   1111 ** Function         bta_dm_confirm
   1112 **
   1113 ** Description      Send the user confirm request reply in response to a
   1114 **                  request from BTM
   1115 **
   1116 ** Returns          void
   1117 **
   1118 *******************************************************************************/
   1119 void bta_dm_confirm(tBTA_DM_MSG *p_data)
   1120 {
   1121     tBTM_STATUS res = BTM_NOT_AUTHORIZED;
   1122 
   1123     if(p_data->confirm.accept == TRUE)
   1124         res = BTM_SUCCESS;
   1125     BTM_ConfirmReqReply(res, p_data->confirm.bd_addr);
   1126 }
   1127 
   1128 /*******************************************************************************
   1129 **
   1130 ** Function         bta_dm_loc_oob
   1131 **
   1132 ** Description      Retrieve the OOB data from the local LM
   1133 **
   1134 ** Returns          void
   1135 **
   1136 *******************************************************************************/
   1137 void bta_dm_loc_oob(tBTA_DM_MSG *p_data)
   1138 {
   1139     UNUSED(p_data);
   1140     BTM_ReadLocalOobData();
   1141 }
   1142 
   1143 /*******************************************************************************
   1144 **
   1145 ** Function         bta_dm_ci_io_req_act
   1146 **
   1147 ** Description      respond to the IO capabilities request from BTM
   1148 **
   1149 ** Returns          void
   1150 **
   1151 *******************************************************************************/
   1152 void bta_dm_ci_io_req_act(tBTA_DM_MSG *p_data)
   1153 {
   1154     tBTM_AUTH_REQ   auth_req = BTM_AUTH_AP_NO;
   1155     if(p_data->ci_io_req.auth_req)
   1156         auth_req = BTM_AUTH_AP_YES;
   1157     BTM_IoCapRsp(p_data->ci_io_req.bd_addr, p_data->ci_io_req.io_cap,
   1158         p_data->ci_io_req.oob_data, auth_req);
   1159 }
   1160 
   1161 /*******************************************************************************
   1162 **
   1163 ** Function         bta_dm_ci_rmt_oob_act
   1164 **
   1165 ** Description      respond to the OOB data request for the remote device from BTM
   1166 **
   1167 **
   1168 ** Returns          void
   1169 **
   1170 *******************************************************************************/
   1171 void bta_dm_ci_rmt_oob_act(tBTA_DM_MSG *p_data)
   1172 {
   1173     tBTM_STATUS res = BTM_NOT_AUTHORIZED;
   1174 
   1175     if(p_data->ci_rmt_oob.accept == TRUE)
   1176         res = BTM_SUCCESS;
   1177     BTM_RemoteOobDataReply(res, p_data->ci_rmt_oob.bd_addr,
   1178         p_data->ci_rmt_oob.c, p_data->ci_rmt_oob.r );
   1179 }
   1180 
   1181 /*******************************************************************************
   1182 **
   1183 ** Function         bta_dm_search_start
   1184 **
   1185 ** Description      Starts an inquiry
   1186 **
   1187 **
   1188 ** Returns          void
   1189 **
   1190 *******************************************************************************/
   1191 void bta_dm_search_start (tBTA_DM_MSG *p_data)
   1192 {
   1193     tBTM_INQUIRY_CMPL result;
   1194 
   1195 #if (BLE_INCLUDED == TRUE && BTA_GATT_INCLUDED == TRUE)
   1196     size_t len = sizeof(tBT_UUID) * p_data->search.num_uuid;
   1197     bta_dm_gattc_register();
   1198 #endif
   1199 
   1200     APPL_TRACE_DEBUG("%s avoid_scatter=%d", __func__, p_bta_dm_cfg->avoid_scatter);
   1201 
   1202     if (p_bta_dm_cfg->avoid_scatter &&
   1203         (p_data->search.rs_res == BTA_DM_RS_NONE) && bta_dm_check_av(BTA_DM_API_SEARCH_EVT))
   1204     {
   1205         memcpy(&bta_dm_cb.search_msg, &p_data->search, sizeof(tBTA_DM_API_SEARCH));
   1206         return;
   1207     }
   1208 
   1209     BTM_ClearInqDb(NULL);
   1210     /* save search params */
   1211     bta_dm_search_cb.p_search_cback = p_data->search.p_cback;
   1212     bta_dm_search_cb.services = p_data->search.services;
   1213 
   1214 #if (BLE_INCLUDED == TRUE && BTA_GATT_INCLUDED == TRUE)
   1215     osi_free_and_reset((void **)&bta_dm_search_cb.p_srvc_uuid);
   1216 
   1217     if ((bta_dm_search_cb.num_uuid = p_data->search.num_uuid) != 0 &&
   1218          p_data->search.p_uuid != NULL) {
   1219         bta_dm_search_cb.p_srvc_uuid = (tBT_UUID *)osi_malloc(len);
   1220         memcpy(bta_dm_search_cb.p_srvc_uuid, p_data->search.p_uuid, len);
   1221     }
   1222 #endif
   1223     result.status = BTM_StartInquiry(   (tBTM_INQ_PARMS*)&p_data->search.inq_params,
   1224                         bta_dm_inq_results_cb,
   1225                         (tBTM_CMPL_CB*) bta_dm_inq_cmpl_cb);
   1226 
   1227     APPL_TRACE_EVENT("%s status=%d", __func__, result.status);
   1228     if (result.status != BTM_CMD_STARTED)
   1229     {
   1230         result.num_resp = 0;
   1231         bta_dm_inq_cmpl_cb ((void *)&result);
   1232     }
   1233 }
   1234 
   1235 /*******************************************************************************
   1236 **
   1237 ** Function         bta_dm_search_cancel
   1238 **
   1239 ** Description      Cancels an ongoing search for devices
   1240 **
   1241 **
   1242 ** Returns          void
   1243 **
   1244 *******************************************************************************/
   1245 void bta_dm_search_cancel (tBTA_DM_MSG *p_data)
   1246 {
   1247     UNUSED(p_data);
   1248     tBTA_DM_MSG *p_msg;
   1249 
   1250     if (BTM_IsInquiryActive())
   1251     {
   1252         if (BTM_CancelInquiry() == BTM_SUCCESS)
   1253         {
   1254             bta_dm_search_cancel_notify(NULL);
   1255             p_msg = (tBTA_DM_MSG *)osi_malloc(sizeof(tBTA_DM_MSG));
   1256             p_msg->hdr.event = BTA_DM_SEARCH_CMPL_EVT;
   1257             p_msg->hdr.layer_specific = BTA_DM_API_DISCOVER_EVT;
   1258             bta_sys_sendmsg(p_msg);
   1259         } else {
   1260             /* flag a search cancel is pending */
   1261             bta_dm_search_cb.cancel_pending = TRUE;
   1262         }
   1263     }
   1264     /* If no Service Search going on then issue cancel remote name in case it is active */
   1265     else if (!bta_dm_search_cb.name_discover_done)
   1266     {
   1267         BTM_CancelRemoteDeviceName();
   1268 
   1269         p_msg = (tBTA_DM_MSG *)osi_malloc(sizeof(tBTA_DM_MSG));
   1270         p_msg->hdr.event = BTA_DM_SEARCH_CMPL_EVT;
   1271         p_msg->hdr.layer_specific = BTA_DM_API_DISCOVER_EVT;
   1272         bta_sys_sendmsg(p_msg);
   1273     } else {
   1274         p_msg = (tBTA_DM_MSG *)osi_malloc(sizeof(tBTA_DM_MSG));
   1275         p_msg->hdr.event = BTA_DM_INQUIRY_CMPL_EVT;
   1276         p_msg->hdr.layer_specific = BTA_DM_API_DISCOVER_EVT;
   1277         bta_sys_sendmsg(p_msg);
   1278     }
   1279 
   1280 #if BLE_INCLUDED == TRUE && BTA_GATT_INCLUDED == TRUE
   1281     if (bta_dm_search_cb.gatt_disc_active)
   1282     {
   1283         bta_dm_cancel_gatt_discovery(bta_dm_search_cb.peer_bdaddr);
   1284     }
   1285 #endif
   1286 }
   1287 
   1288 /*******************************************************************************
   1289 **
   1290 ** Function         bta_dm_discover
   1291 **
   1292 ** Description      Discovers services on a remote device
   1293 **
   1294 **
   1295 ** Returns          void
   1296 **
   1297 *******************************************************************************/
   1298 void bta_dm_discover (tBTA_DM_MSG *p_data)
   1299 {
   1300 #if BLE_INCLUDED == TRUE && BTA_GATT_INCLUDED == TRUE
   1301     size_t len = sizeof(tBT_UUID) * p_data->discover.num_uuid;
   1302 #endif
   1303     APPL_TRACE_EVENT("%s services_to_search=0x%04X, sdp_search=%d", __func__,
   1304                       p_data->discover.services, p_data->discover.sdp_search);
   1305 
   1306     /* save the search condition */
   1307     bta_dm_search_cb.services = p_data->discover.services;
   1308 
   1309 #if BLE_INCLUDED == TRUE && BTA_GATT_INCLUDED == TRUE
   1310     bta_dm_gattc_register();
   1311     osi_free_and_reset((void **)&bta_dm_search_cb.p_srvc_uuid);
   1312     if ((bta_dm_search_cb.num_uuid = p_data->discover.num_uuid) != 0 &&
   1313         p_data->discover.p_uuid != NULL) {
   1314         bta_dm_search_cb.p_srvc_uuid = (tBT_UUID *)osi_malloc(len);
   1315         memcpy(bta_dm_search_cb.p_srvc_uuid, p_data->discover.p_uuid, len);
   1316     }
   1317     bta_dm_search_cb.uuid_to_search = bta_dm_search_cb.num_uuid;
   1318 #endif
   1319 
   1320     bta_dm_search_cb.p_search_cback = p_data->discover.p_cback;
   1321     bta_dm_search_cb.sdp_search = p_data->discover.sdp_search;
   1322     bta_dm_search_cb.services_to_search = bta_dm_search_cb.services;
   1323     bta_dm_search_cb.service_index = 0;
   1324     bta_dm_search_cb.services_found = 0;
   1325     bta_dm_search_cb.peer_name[0] = 0;
   1326     bta_dm_search_cb.sdp_search = p_data->discover.sdp_search;
   1327     bta_dm_search_cb.p_btm_inq_info = BTM_InqDbRead (p_data->discover.bd_addr);
   1328     bta_dm_search_cb.transport = p_data->discover.transport;
   1329 
   1330     bta_dm_search_cb.name_discover_done = FALSE;
   1331     memcpy(&bta_dm_search_cb.uuid, &p_data->discover.uuid, sizeof(tSDP_UUID));
   1332     bta_dm_discover_device(p_data->discover.bd_addr);
   1333 }
   1334 
   1335 /*******************************************************************************
   1336 **
   1337 ** Function         bta_dm_di_disc_cmpl
   1338 **
   1339 ** Description      Sends event to application when DI discovery complete
   1340 **
   1341 ** Returns          void
   1342 **
   1343 *******************************************************************************/
   1344 void bta_dm_di_disc_cmpl(tBTA_DM_MSG *p_data)
   1345 {
   1346     tBTA_DM_DI_DISC_CMPL    di_disc;
   1347 
   1348     memset(&di_disc, 0, sizeof(tBTA_DM_DI_DISC_CMPL));
   1349     bdcpy(di_disc.bd_addr, bta_dm_search_cb.peer_bdaddr);
   1350 
   1351     if((p_data->hdr.offset == SDP_SUCCESS)
   1352         || (p_data->hdr.offset == SDP_DB_FULL))
   1353     {
   1354         di_disc.num_record  = SDP_GetNumDiRecords(bta_dm_di_cb.p_di_db);
   1355     }
   1356     else
   1357         di_disc.result      = BTA_FAILURE;
   1358 
   1359     bta_dm_di_cb.p_di_db = NULL;
   1360     bta_dm_search_cb.p_search_cback(BTA_DM_DI_DISC_CMPL_EVT, (tBTA_DM_SEARCH *) &di_disc);
   1361 }
   1362 
   1363 /*******************************************************************************
   1364 **
   1365 ** Function         bta_dm_di_disc_callback
   1366 **
   1367 ** Description      This function queries a remote device for DI information.
   1368 **
   1369 **
   1370 ** Returns          void
   1371 **
   1372 *******************************************************************************/
   1373 static void bta_dm_di_disc_callback(UINT16 result)
   1374 {
   1375     tBTA_DM_MSG *p_msg = (tBTA_DM_MSG *)osi_malloc(sizeof(tBTA_DM_MSG));
   1376 
   1377     p_msg->hdr.event = BTA_DM_SEARCH_CMPL_EVT;
   1378     p_msg->hdr.layer_specific = BTA_DM_API_DI_DISCOVER_EVT;
   1379     p_msg->hdr.offset = result;
   1380 
   1381     bta_sys_sendmsg(p_msg);
   1382 }
   1383 
   1384 /*******************************************************************************
   1385 **
   1386 ** Function         bta_dm_disable_search_and_disc
   1387 **
   1388 ** Description      Cancels an ongoing search or discovery for devices in case of
   1389 **                  a Bluetooth disable
   1390 **
   1391 **
   1392 ** Returns          void
   1393 **
   1394 *******************************************************************************/
   1395 static void bta_dm_disable_search_and_disc (void)
   1396 {
   1397     tBTA_DM_DI_DISC_CMPL    di_disc;
   1398 
   1399     if (bta_dm_search_cb.state != BTA_DM_SEARCH_IDLE)
   1400         bta_dm_search_cancel(NULL);
   1401 
   1402     if (bta_dm_di_cb.p_di_db != NULL)
   1403     {
   1404         memset(&di_disc, 0, sizeof(tBTA_DM_DI_DISC_CMPL));
   1405         bdcpy(di_disc.bd_addr, bta_dm_search_cb.peer_bdaddr);
   1406         di_disc.result      = BTA_FAILURE;
   1407 
   1408         bta_dm_di_cb.p_di_db = NULL;
   1409         bta_dm_search_cb.p_search_cback(BTA_DM_DI_DISC_CMPL_EVT, NULL);
   1410     }
   1411 }
   1412 
   1413 /*******************************************************************************
   1414 **
   1415 ** Function         bta_dm_di_disc
   1416 **
   1417 ** Description      This function queries a remote device for DI information.
   1418 **
   1419 **
   1420 ** Returns          void
   1421 **
   1422 *******************************************************************************/
   1423 void bta_dm_di_disc (tBTA_DM_MSG *p_data)
   1424 {
   1425     UINT16  result = BTA_FAILURE;
   1426 
   1427     bta_dm_search_cb.p_search_cback = p_data->di_disc.p_cback;
   1428     bdcpy(bta_dm_search_cb.peer_bdaddr, p_data->di_disc.bd_addr);
   1429     bta_dm_di_cb.p_di_db = p_data->di_disc.p_sdp_db;
   1430 
   1431     bta_dm_search_cb.p_sdp_db = (tSDP_DISCOVERY_DB *)osi_malloc(BTA_DM_SDP_DB_SIZE);
   1432     if (SDP_DiDiscover(bta_dm_search_cb.peer_bdaddr, p_data->di_disc.p_sdp_db,
   1433                        p_data->di_disc.len,
   1434                        bta_dm_di_disc_callback) == SDP_SUCCESS) {
   1435         result = BTA_SUCCESS;
   1436     }
   1437 
   1438     if (result == BTA_FAILURE) {
   1439         tBTA_DM_MSG *p_msg = (tBTA_DM_MSG *)osi_malloc(sizeof(tBTA_DM_MSG));
   1440 
   1441         p_msg->hdr.event = BTA_DM_SEARCH_CMPL_EVT;
   1442         p_msg->hdr.layer_specific = BTA_DM_API_DI_DISCOVER_EVT;
   1443         p_data->hdr.offset = result;
   1444         bta_sys_sendmsg(p_msg);
   1445     }
   1446 }
   1447 
   1448 /*******************************************************************************
   1449 **
   1450 ** Function         bta_dm_read_remote_device_name
   1451 **
   1452 ** Description      Initiate to get remote device name
   1453 **
   1454 ** Returns          TRUE if started to get remote name
   1455 **
   1456 *******************************************************************************/
   1457 static BOOLEAN bta_dm_read_remote_device_name (BD_ADDR bd_addr,tBT_TRANSPORT transport)
   1458 {
   1459     tBTM_STATUS  btm_status;
   1460 
   1461     APPL_TRACE_DEBUG("bta_dm_read_remote_device_name");
   1462 
   1463     bdcpy(bta_dm_search_cb.peer_bdaddr, bd_addr);
   1464     bta_dm_search_cb.peer_name[0] = 0;
   1465 
   1466     btm_status = BTM_ReadRemoteDeviceName (bta_dm_search_cb.peer_bdaddr,
   1467                                            (tBTM_CMPL_CB *) bta_dm_remname_cback,
   1468                                            transport);
   1469 
   1470     if ( btm_status == BTM_CMD_STARTED )
   1471     {
   1472         APPL_TRACE_DEBUG("bta_dm_read_remote_device_name: BTM_ReadRemoteDeviceName is started");
   1473 
   1474         return (TRUE);
   1475     }
   1476     else if ( btm_status == BTM_BUSY )
   1477     {
   1478         APPL_TRACE_DEBUG("bta_dm_read_remote_device_name: BTM_ReadRemoteDeviceName is busy");
   1479 
   1480         /* Remote name discovery is on going now so BTM cannot notify through "bta_dm_remname_cback" */
   1481         /* adding callback to get notified that current reading remore name done */
   1482         BTM_SecAddRmtNameNotifyCallback(&bta_dm_service_search_remname_cback);
   1483 
   1484         return (TRUE);
   1485     }
   1486     else
   1487     {
   1488         APPL_TRACE_WARNING("bta_dm_read_remote_device_name: BTM_ReadRemoteDeviceName returns 0x%02X", btm_status);
   1489 
   1490         return (FALSE);
   1491     }
   1492 }
   1493 
   1494 /*******************************************************************************
   1495 **
   1496 ** Function         bta_dm_inq_cmpl
   1497 **
   1498 ** Description      Process the inquiry complete event from BTM
   1499 **
   1500 ** Returns          void
   1501 **
   1502 *******************************************************************************/
   1503 void bta_dm_inq_cmpl (tBTA_DM_MSG *p_data)
   1504 {
   1505     tBTA_DM_SEARCH  data;
   1506 
   1507     APPL_TRACE_DEBUG("bta_dm_inq_cmpl");
   1508 
   1509     data.inq_cmpl.num_resps = p_data->inq_cmpl.num;
   1510     bta_dm_search_cb.p_search_cback(BTA_DM_INQ_CMPL_EVT, &data);
   1511 
   1512     if((bta_dm_search_cb.p_btm_inq_info = BTM_InqDbFirst()) != NULL)
   1513     {
   1514         /* start name and service discovery from the first device on inquiry result */
   1515         bta_dm_search_cb.name_discover_done = FALSE;
   1516         bta_dm_search_cb.peer_name[0]       = 0;
   1517         bta_dm_discover_device(bta_dm_search_cb.p_btm_inq_info->results.remote_bd_addr);
   1518     } else {
   1519         tBTA_DM_MSG *p_msg = (tBTA_DM_MSG *)osi_malloc(sizeof(tBTA_DM_MSG));
   1520 
   1521         /* no devices, search complete */
   1522         bta_dm_search_cb.services = 0;
   1523 
   1524         p_msg->hdr.event = BTA_DM_SEARCH_CMPL_EVT;
   1525         p_msg->hdr.layer_specific = BTA_DM_API_DISCOVER_EVT;
   1526         bta_sys_sendmsg(p_msg);
   1527     }
   1528 }
   1529 
   1530 /*******************************************************************************
   1531 **
   1532 ** Function         bta_dm_rmt_name
   1533 **
   1534 ** Description      Process the remote name result from BTM
   1535 **
   1536 ** Returns          void
   1537 **
   1538 *******************************************************************************/
   1539 void bta_dm_rmt_name (tBTA_DM_MSG *p_data)
   1540 {
   1541     APPL_TRACE_DEBUG("bta_dm_rmt_name");
   1542 
   1543     if( p_data->rem_name.result.disc_res.bd_name[0] && bta_dm_search_cb.p_btm_inq_info)
   1544     {
   1545         bta_dm_search_cb.p_btm_inq_info->appl_knows_rem_name = TRUE;
   1546     }
   1547 
   1548     bta_dm_discover_device(bta_dm_search_cb.peer_bdaddr);
   1549 }
   1550 
   1551 /*******************************************************************************
   1552 **
   1553 ** Function         bta_dm_disc_rmt_name
   1554 **
   1555 ** Description      Process the remote name result from BTM when application
   1556 **                  wants to find the name for a bdaddr
   1557 **
   1558 ** Returns          void
   1559 **
   1560 *******************************************************************************/
   1561 void bta_dm_disc_rmt_name (tBTA_DM_MSG *p_data)
   1562 {
   1563     tBTM_INQ_INFO *p_btm_inq_info;
   1564 
   1565     APPL_TRACE_DEBUG("bta_dm_disc_rmt_name");
   1566 
   1567     p_btm_inq_info = BTM_InqDbRead (p_data->rem_name.result.disc_res.bd_addr);
   1568     if( p_btm_inq_info )
   1569     {
   1570         if( p_data->rem_name.result.disc_res.bd_name[0] )
   1571         {
   1572             p_btm_inq_info->appl_knows_rem_name = TRUE;
   1573         }
   1574     }
   1575 
   1576     bta_dm_discover_device(p_data->rem_name.result.disc_res.bd_addr);
   1577 }
   1578 
   1579 /*******************************************************************************
   1580 **
   1581 ** Function         bta_dm_sdp_result
   1582 **
   1583 ** Description      Process the discovery result from sdp
   1584 **
   1585 ** Returns          void
   1586 **
   1587 *******************************************************************************/
   1588 void bta_dm_sdp_result (tBTA_DM_MSG *p_data)
   1589 {
   1590 
   1591     tSDP_DISC_REC   *p_sdp_rec = NULL;
   1592     tBTA_DM_MSG     *p_msg;
   1593     BOOLEAN          scn_found = FALSE;
   1594     UINT16           service = 0xFFFF;
   1595     tSDP_PROTOCOL_ELEM  pe;
   1596 
   1597 #if BLE_INCLUDED == TRUE && BTA_GATT_INCLUDED == TRUE
   1598     tBT_UUID           *p_uuid = bta_dm_search_cb.p_srvc_uuid;
   1599     tBTA_DM_SEARCH      result;
   1600     tBT_UUID            service_uuid;
   1601 #endif
   1602 
   1603     UINT32 num_uuids = 0;
   1604     UINT8  uuid_list[32][MAX_UUID_SIZE]; // assuming a max of 32 services
   1605 
   1606     if((p_data->sdp_event.sdp_result == SDP_SUCCESS)
   1607         || (p_data->sdp_event.sdp_result == SDP_NO_RECS_MATCH)
   1608         || (p_data->sdp_event.sdp_result == SDP_DB_FULL))
   1609     {
   1610         APPL_TRACE_DEBUG("sdp_result::0x%x", p_data->sdp_event.sdp_result);
   1611         do
   1612         {
   1613 
   1614             p_sdp_rec = NULL;
   1615             if( bta_dm_search_cb.service_index == (BTA_USER_SERVICE_ID+1) )
   1616             {
   1617                 p_sdp_rec = SDP_FindServiceUUIDInDb(bta_dm_search_cb.p_sdp_db, &bta_dm_search_cb.uuid, p_sdp_rec);
   1618 
   1619                 if (p_sdp_rec && SDP_FindProtocolListElemInRec(p_sdp_rec, UUID_PROTOCOL_RFCOMM, &pe))
   1620                 {
   1621                     bta_dm_search_cb.peer_scn = (UINT8) pe.params[0];
   1622                     scn_found = TRUE;
   1623                 }
   1624             }
   1625             else
   1626             {
   1627                 service = bta_service_id_to_uuid_lkup_tbl[bta_dm_search_cb.service_index-1];
   1628                 p_sdp_rec = SDP_FindServiceInDb(bta_dm_search_cb.p_sdp_db, service, p_sdp_rec);
   1629             }
   1630 #if BLE_INCLUDED == TRUE && BTA_GATT_INCLUDED == TRUE
   1631             /* finished with BR/EDR services, now we check the result for GATT based service UUID */
   1632             if (bta_dm_search_cb.service_index == BTA_MAX_SERVICE_ID)
   1633             {
   1634                 if (bta_dm_search_cb.uuid_to_search != 0 && p_uuid != NULL)
   1635                 {
   1636                     p_uuid +=  (bta_dm_search_cb.num_uuid - bta_dm_search_cb.uuid_to_search);
   1637                     /* only support 16 bits UUID for now */
   1638                     service = p_uuid->uu.uuid16;
   1639 
   1640                 }
   1641                 /* all GATT based services */
   1642                 do
   1643                 {
   1644                     /* find a service record, report it */
   1645                     p_sdp_rec = SDP_FindServiceInDb(bta_dm_search_cb.p_sdp_db,
   1646                                                 0, p_sdp_rec);
   1647                     if (p_sdp_rec)
   1648                     {
   1649                         if (SDP_FindServiceUUIDInRec(p_sdp_rec, &service_uuid))
   1650                         {
   1651                             /* send result back to app now, one by one */
   1652                             bdcpy (result.disc_ble_res.bd_addr, bta_dm_search_cb.peer_bdaddr);
   1653                             strlcpy((char*)result.disc_ble_res.bd_name, bta_dm_get_remname(), BD_NAME_LEN);
   1654                             result.disc_ble_res.service.len = service_uuid.len;
   1655                             result.disc_ble_res.service.uu.uuid16 = service_uuid.uu.uuid16;
   1656 
   1657                             bta_dm_search_cb.p_search_cback(BTA_DM_DISC_BLE_RES_EVT, &result);
   1658                         }
   1659                     }
   1660 
   1661                     if (bta_dm_search_cb.uuid_to_search > 0)
   1662                         break;
   1663 
   1664                 } while (p_sdp_rec);
   1665             }
   1666             else
   1667 #endif
   1668             {
   1669                 /* SDP_DB_FULL means some records with the
   1670                    required attributes were received */
   1671                 if (((p_data->sdp_event.sdp_result == SDP_DB_FULL) &&
   1672                         bta_dm_search_cb.services != BTA_ALL_SERVICE_MASK) ||
   1673                         (p_sdp_rec != NULL))
   1674                 {
   1675                     if (service != UUID_SERVCLASS_PNP_INFORMATION)
   1676                     {
   1677                         UINT16 tmp_svc = 0xFFFF;
   1678                         bta_dm_search_cb.services_found |=
   1679                             (tBTA_SERVICE_MASK)(BTA_SERVICE_ID_TO_SERVICE_MASK(bta_dm_search_cb.service_index-1));
   1680                         tmp_svc = bta_service_id_to_uuid_lkup_tbl[bta_dm_search_cb.service_index-1];
   1681                         /* Add to the list of UUIDs */
   1682                         sdpu_uuid16_to_uuid128(tmp_svc, uuid_list[num_uuids]);
   1683                         num_uuids++;
   1684                     }
   1685                 }
   1686             }
   1687 
   1688             if(bta_dm_search_cb.services == BTA_ALL_SERVICE_MASK &&
   1689                 bta_dm_search_cb.services_to_search == 0)
   1690             {
   1691 #if BLE_INCLUDED == TRUE && BTA_GATT_INCLUDED == TRUE
   1692                 if ( bta_dm_search_cb.service_index == BTA_BLE_SERVICE_ID &&
   1693                     bta_dm_search_cb.uuid_to_search > 0)
   1694                     bta_dm_search_cb.uuid_to_search --;
   1695 
   1696                 if (bta_dm_search_cb.uuid_to_search == 0 ||
   1697                     bta_dm_search_cb.service_index != BTA_BLE_SERVICE_ID)
   1698 #endif
   1699                     bta_dm_search_cb.service_index++;
   1700             }
   1701             else /* regular one service per search or PNP search */
   1702                 break;
   1703 
   1704         } while (bta_dm_search_cb.service_index <= BTA_MAX_SERVICE_ID);
   1705 
   1706         APPL_TRACE_DEBUG("%s services_found = %04x", __FUNCTION__,
   1707                          bta_dm_search_cb.services_found);
   1708 
   1709         /* Collect the 128-bit services here and put them into the list */
   1710         if(bta_dm_search_cb.services == BTA_ALL_SERVICE_MASK)
   1711         {
   1712             p_sdp_rec = NULL;
   1713             do
   1714             {
   1715                 tBT_UUID temp_uuid;
   1716                 /* find a service record, report it */
   1717                 p_sdp_rec = SDP_FindServiceInDb_128bit(bta_dm_search_cb.p_sdp_db, p_sdp_rec);
   1718                 if (p_sdp_rec)
   1719                 {
   1720                     if (SDP_FindServiceUUIDInRec_128bit(p_sdp_rec, &temp_uuid))
   1721                     {
   1722                         memcpy(uuid_list[num_uuids], temp_uuid.uu.uuid128, MAX_UUID_SIZE);
   1723                         num_uuids++;
   1724                     }
   1725                 }
   1726             } while (p_sdp_rec);
   1727         }
   1728         /* if there are more services to search for */
   1729         if(bta_dm_search_cb.services_to_search)
   1730         {
   1731             /* Free up the p_sdp_db before checking the next one */
   1732             bta_dm_free_sdp_db(NULL);
   1733             bta_dm_find_services(bta_dm_search_cb.peer_bdaddr);
   1734         }
   1735         else
   1736         {
   1737             /* callbacks */
   1738             /* start next bd_addr if necessary */
   1739 
   1740             BTM_SecDeleteRmtNameNotifyCallback(&bta_dm_service_search_remname_cback);
   1741 
   1742             p_msg = (tBTA_DM_MSG *)osi_malloc(sizeof(tBTA_DM_MSG));
   1743             p_msg->hdr.event = BTA_DM_DISCOVERY_RESULT_EVT;
   1744             p_msg->disc_result.result.disc_res.result = BTA_SUCCESS;
   1745             p_msg->disc_result.result.disc_res.p_raw_data = NULL;
   1746             p_msg->disc_result.result.disc_res.raw_data_size = 0;
   1747             p_msg->disc_result.result.disc_res.num_uuids = num_uuids;
   1748             p_msg->disc_result.result.disc_res.p_uuid_list = NULL;
   1749             if (num_uuids > 0) {
   1750                 p_msg->disc_result.result.disc_res.p_uuid_list =
   1751                     (UINT8 *)osi_malloc(num_uuids * MAX_UUID_SIZE);
   1752                 memcpy(p_msg->disc_result.result.disc_res.p_uuid_list,
   1753                        uuid_list, num_uuids * MAX_UUID_SIZE);
   1754             }
   1755             // Copy the raw_data to the discovery result structure
   1756             if (bta_dm_search_cb.p_sdp_db != NULL &&
   1757                 bta_dm_search_cb.p_sdp_db->raw_used != 0 &&
   1758                 bta_dm_search_cb.p_sdp_db->raw_data != NULL) {
   1759                 APPL_TRACE_DEBUG("%s raw_data used = 0x%x raw_data_ptr = 0x%x",
   1760                                  __func__,
   1761                                  bta_dm_search_cb.p_sdp_db->raw_used,
   1762                                  bta_dm_search_cb.p_sdp_db->raw_data);
   1763 
   1764                 p_msg->disc_result.result.disc_res.p_raw_data =
   1765                     osi_malloc(bta_dm_search_cb.p_sdp_db->raw_used);
   1766                 memcpy(p_msg->disc_result.result.disc_res.p_raw_data,
   1767                        bta_dm_search_cb.p_sdp_db->raw_data,
   1768                        bta_dm_search_cb.p_sdp_db->raw_used);
   1769 
   1770                 p_msg->disc_result.result.disc_res.raw_data_size =
   1771                     bta_dm_search_cb.p_sdp_db->raw_used;
   1772 
   1773                 bta_dm_search_cb.p_sdp_db->raw_data = NULL;     //no need to free this - it is a global assigned.
   1774                 bta_dm_search_cb.p_sdp_db->raw_used = 0;
   1775                 bta_dm_search_cb.p_sdp_db->raw_size = 0;
   1776             } else {
   1777                 APPL_TRACE_DEBUG("%s raw data size is 0 or raw_data is null!!",
   1778                                  __func__);
   1779             }
   1780             /* Done with p_sdp_db. Free it */
   1781             bta_dm_free_sdp_db(NULL);
   1782             p_msg->disc_result.result.disc_res.services = bta_dm_search_cb.services_found;
   1783 
   1784             // Piggy back the SCN over result field
   1785             if (scn_found) {
   1786                 p_msg->disc_result.result.disc_res.result = (3 + bta_dm_search_cb.peer_scn);
   1787                 p_msg->disc_result.result.disc_res.services |= BTA_USER_SERVICE_MASK;
   1788 
   1789                 APPL_TRACE_EVENT(" Piggy back the SCN over result field  SCN=%d", bta_dm_search_cb.peer_scn);
   1790 
   1791             }
   1792             bdcpy(p_msg->disc_result.result.disc_res.bd_addr,
   1793                   bta_dm_search_cb.peer_bdaddr);
   1794             strlcpy((char*)p_msg->disc_result.result.disc_res.bd_name,
   1795                       bta_dm_get_remname(), BD_NAME_LEN);
   1796 
   1797             bta_sys_sendmsg(p_msg);
   1798         }
   1799     } else {
   1800         /* conn failed. No need for timer */
   1801         if(p_data->sdp_event.sdp_result == SDP_CONN_FAILED || p_data->sdp_event.sdp_result == SDP_CONN_REJECTED
   1802            || p_data->sdp_event.sdp_result == SDP_SECURITY_ERR)
   1803             bta_dm_search_cb.wait_disc = FALSE;
   1804 
   1805         /* not able to connect go to next device */
   1806         if (bta_dm_search_cb.p_sdp_db)
   1807             osi_free_and_reset((void **)&bta_dm_search_cb.p_sdp_db);
   1808 
   1809         BTM_SecDeleteRmtNameNotifyCallback(&bta_dm_service_search_remname_cback);
   1810 
   1811         p_msg = (tBTA_DM_MSG *)osi_malloc(sizeof(tBTA_DM_MSG));
   1812         p_msg->hdr.event = BTA_DM_DISCOVERY_RESULT_EVT;
   1813         p_msg->disc_result.result.disc_res.result = BTA_FAILURE;
   1814         p_msg->disc_result.result.disc_res.services = bta_dm_search_cb.services_found;
   1815         bdcpy(p_msg->disc_result.result.disc_res.bd_addr,
   1816               bta_dm_search_cb.peer_bdaddr);
   1817         strlcpy((char*)p_msg->disc_result.result.disc_res.bd_name,
   1818                 bta_dm_get_remname(), BD_NAME_LEN);
   1819 
   1820         bta_sys_sendmsg(p_msg);
   1821     }
   1822 }
   1823 
   1824 /*******************************************************************************
   1825 **
   1826 ** Function         bta_dm_search_cmpl
   1827 **
   1828 ** Description      Sends event to application
   1829 **
   1830 ** Returns          void
   1831 **
   1832 *******************************************************************************/
   1833 void bta_dm_search_cmpl(tBTA_DM_MSG *p_data)
   1834 {
   1835     APPL_TRACE_EVENT("%s", __func__);
   1836 
   1837 #if (BLE_INCLUDED == TRUE && BTA_GATT_INCLUDED == TRUE)
   1838     osi_free_and_reset((void **)&bta_dm_search_cb.p_srvc_uuid);
   1839 #endif
   1840 
   1841     if (p_data->hdr.layer_specific == BTA_DM_API_DI_DISCOVER_EVT)
   1842         bta_dm_di_disc_cmpl(p_data);
   1843     else
   1844         bta_dm_search_cb.p_search_cback(BTA_DM_DISC_CMPL_EVT, NULL);
   1845 }
   1846 
   1847 /*******************************************************************************
   1848 **
   1849 ** Function         bta_dm_disc_result
   1850 **
   1851 ** Description      Service discovery result when discovering services on a device
   1852 **
   1853 ** Returns          void
   1854 **
   1855 *******************************************************************************/
   1856 void bta_dm_disc_result (tBTA_DM_MSG *p_data)
   1857 {
   1858     APPL_TRACE_EVENT("%s", __func__);
   1859 
   1860 #if BLE_INCLUDED == TRUE && BTA_GATT_INCLUDED == TRUE
   1861     /* if any BR/EDR service discovery has been done, report the event */
   1862     if ((bta_dm_search_cb.services & ((BTA_ALL_SERVICE_MASK | BTA_USER_SERVICE_MASK ) & ~BTA_BLE_SERVICE_MASK)))
   1863 #endif
   1864     bta_dm_search_cb.p_search_cback(BTA_DM_DISC_RES_EVT, &p_data->disc_result.result);
   1865 
   1866     tBTA_DM_MSG *p_msg = (tBTA_DM_MSG *)osi_malloc(sizeof(tBTA_DM_MSG));
   1867 
   1868     /* send a message to change state */
   1869     p_msg->hdr.event = BTA_DM_SEARCH_CMPL_EVT;
   1870     p_msg->hdr.layer_specific = BTA_DM_API_DISCOVER_EVT;
   1871     bta_sys_sendmsg(p_msg);
   1872 }
   1873 
   1874 /*******************************************************************************
   1875 **
   1876 ** Function         bta_dm_search_result
   1877 **
   1878 ** Description      Service discovery result while searching for devices
   1879 **
   1880 ** Returns          void
   1881 **
   1882 *******************************************************************************/
   1883 void bta_dm_search_result (tBTA_DM_MSG *p_data)
   1884 {
   1885     APPL_TRACE_DEBUG("%s searching:0x%04x, result:0x%04x", __func__,
   1886                        bta_dm_search_cb.services,
   1887                        p_data->disc_result.result.disc_res.services);
   1888 
   1889     /* call back if application wants name discovery or found services that application is searching */
   1890     if (( !bta_dm_search_cb.services )
   1891       ||(( bta_dm_search_cb.services ) && ( p_data->disc_result.result.disc_res.services )))
   1892     {
   1893         bta_dm_search_cb.p_search_cback(BTA_DM_DISC_RES_EVT, &p_data->disc_result.result);
   1894     }
   1895 
   1896     /* if searching did not initiate to create link */
   1897     if(!bta_dm_search_cb.wait_disc )
   1898     {
   1899         /* if service searching is done with EIR, don't search next device */
   1900         if( bta_dm_search_cb.p_btm_inq_info )
   1901         bta_dm_discover_next_device();
   1902     }
   1903     else
   1904     {
   1905         /* wait until link is disconnected or timeout */
   1906         bta_dm_search_cb.sdp_results = TRUE;
   1907         alarm_set_on_queue(bta_dm_search_cb.search_timer,
   1908                            1000 * (L2CAP_LINK_INACTIVITY_TOUT + 1),
   1909                            bta_dm_search_timer_cback, NULL,
   1910                            btu_bta_alarm_queue);
   1911     }
   1912 }
   1913 
   1914 /*******************************************************************************
   1915 **
   1916 ** Function         bta_dm_search_timer_cback
   1917 **
   1918 ** Description      Called when ACL disconnect time is over
   1919 **
   1920 **
   1921 ** Returns          void
   1922 **
   1923 *******************************************************************************/
   1924 static void bta_dm_search_timer_cback(UNUSED_ATTR void *data)
   1925 {
   1926     APPL_TRACE_EVENT("%s", __func__);
   1927     bta_dm_search_cb.wait_disc = FALSE;
   1928 
   1929     /* proceed with next device */
   1930     bta_dm_discover_next_device();
   1931 
   1932 }
   1933 
   1934 
   1935 /*******************************************************************************
   1936 **
   1937 ** Function         bta_dm_free_sdp_db
   1938 **
   1939 ** Description      Frees SDP data base
   1940 **
   1941 ** Returns          void
   1942 **
   1943 *******************************************************************************/
   1944 void bta_dm_free_sdp_db (tBTA_DM_MSG *p_data)
   1945 {
   1946     UNUSED(p_data);
   1947     osi_free_and_reset((void **)&bta_dm_search_cb.p_sdp_db);
   1948 }
   1949 
   1950 /*******************************************************************************
   1951 **
   1952 ** Function         bta_dm_queue_search
   1953 **
   1954 ** Description      Queues search command while search is being cancelled
   1955 **
   1956 ** Returns          void
   1957 **
   1958 *******************************************************************************/
   1959 void bta_dm_queue_search(tBTA_DM_MSG *p_data)
   1960 {
   1961     osi_free(bta_dm_search_cb.p_search_queue);
   1962     bta_dm_search_cb.p_search_queue =
   1963       (tBTA_DM_MSG *)osi_malloc(sizeof(tBTA_DM_API_SEARCH));
   1964     memcpy(bta_dm_search_cb.p_search_queue, p_data,
   1965            sizeof(tBTA_DM_API_SEARCH));
   1966 }
   1967 
   1968 /*******************************************************************************
   1969 **
   1970 ** Function         bta_dm_queue_disc
   1971 **
   1972 ** Description      Queues discovery command while search is being cancelled
   1973 **
   1974 ** Returns          void
   1975 **
   1976 *******************************************************************************/
   1977 void bta_dm_queue_disc(tBTA_DM_MSG *p_data)
   1978 {
   1979     osi_free(bta_dm_search_cb.p_search_queue);
   1980     bta_dm_search_cb.p_search_queue =
   1981         (tBTA_DM_MSG *)osi_malloc(sizeof(tBTA_DM_API_DISCOVER));
   1982     memcpy(bta_dm_search_cb.p_search_queue, p_data,
   1983            sizeof(tBTA_DM_API_DISCOVER));
   1984 }
   1985 
   1986 /*******************************************************************************
   1987 **
   1988 ** Function         bta_dm_search_clear_queue
   1989 **
   1990 ** Description      Clears the queue if API search cancel is called
   1991 **
   1992 ** Returns          void
   1993 **
   1994 *******************************************************************************/
   1995 void bta_dm_search_clear_queue(tBTA_DM_MSG *p_data)
   1996 {
   1997     UNUSED(p_data);
   1998     osi_free_and_reset((void **)&bta_dm_search_cb.p_search_queue);
   1999 }
   2000 
   2001 /*******************************************************************************
   2002 **
   2003 ** Function         bta_dm_search_cancel_cmpl
   2004 **
   2005 ** Description      Search cancel is complete
   2006 **
   2007 ** Returns          void
   2008 **
   2009 *******************************************************************************/
   2010 void bta_dm_search_cancel_cmpl (tBTA_DM_MSG *p_data)
   2011 {
   2012     UNUSED(p_data);
   2013     if(bta_dm_search_cb.p_search_queue)
   2014     {
   2015         bta_sys_sendmsg(bta_dm_search_cb.p_search_queue);
   2016         bta_dm_search_cb.p_search_queue = NULL;
   2017     }
   2018 
   2019 }
   2020 
   2021 /*******************************************************************************
   2022 **
   2023 ** Function         bta_dm_search_cancel_transac_cmpl
   2024 **
   2025 ** Description      Current Service Discovery or remote name procedure is
   2026 **                  completed after search cancellation
   2027 **
   2028 ** Returns          void
   2029 **
   2030 *******************************************************************************/
   2031 void bta_dm_search_cancel_transac_cmpl(tBTA_DM_MSG *p_data)
   2032 {
   2033     UNUSED(p_data);
   2034 
   2035     osi_free_and_reset((void **)&bta_dm_search_cb.p_sdp_db);
   2036     bta_dm_search_cancel_notify(NULL);
   2037 }
   2038 
   2039 
   2040 /*******************************************************************************
   2041 **
   2042 ** Function         bta_dm_search_cancel_notify
   2043 **
   2044 ** Description      Notify application that search has been cancelled
   2045 **
   2046 ** Returns          void
   2047 **
   2048 *******************************************************************************/
   2049 void bta_dm_search_cancel_notify (tBTA_DM_MSG *p_data)
   2050 {
   2051     UNUSED(p_data);
   2052     if (bta_dm_search_cb.p_search_cback)
   2053     {
   2054         bta_dm_search_cb.p_search_cback(BTA_DM_SEARCH_CANCEL_CMPL_EVT, NULL);
   2055     }
   2056     if (!bta_dm_search_cb.name_discover_done)
   2057     {
   2058         BTM_CancelRemoteDeviceName();
   2059     }
   2060 #if (BLE_INCLUDED == TRUE) && (BTA_GATT_INCLUDED == TRUE)
   2061     if (bta_dm_search_cb.gatt_disc_active)
   2062     {
   2063         bta_dm_cancel_gatt_discovery(bta_dm_search_cb.peer_bdaddr);
   2064     }
   2065 #endif
   2066 
   2067 }
   2068 
   2069 /*******************************************************************************
   2070 **
   2071 ** Function         bta_dm_find_services
   2072 **
   2073 ** Description      Starts discovery on a device
   2074 **
   2075 ** Returns          void
   2076 **
   2077 *******************************************************************************/
   2078 static void bta_dm_find_services ( BD_ADDR bd_addr)
   2079 {
   2080 
   2081     tSDP_UUID    uuid;
   2082 
   2083     memset(&uuid, 0, sizeof(tSDP_UUID));
   2084 
   2085     while(bta_dm_search_cb.service_index < BTA_MAX_SERVICE_ID)
   2086     {
   2087         if( bta_dm_search_cb.services_to_search
   2088             & (tBTA_SERVICE_MASK)(BTA_SERVICE_ID_TO_SERVICE_MASK(bta_dm_search_cb.service_index)))
   2089         {
   2090             bta_dm_search_cb.p_sdp_db = (tSDP_DISCOVERY_DB *)osi_malloc(BTA_DM_SDP_DB_SIZE);
   2091             APPL_TRACE_DEBUG("bta_dm_search_cb.services = %04x***********", bta_dm_search_cb.services);
   2092             /* try to search all services by search based on L2CAP UUID */
   2093             if (bta_dm_search_cb.services == BTA_ALL_SERVICE_MASK) {
   2094                 LOG_INFO(LOG_TAG, "%s services_to_search=%08x", __func__,
   2095                          bta_dm_search_cb.services_to_search);
   2096                 if (bta_dm_search_cb.services_to_search & BTA_RES_SERVICE_MASK) {
   2097                     uuid.uu.uuid16 = bta_service_id_to_uuid_lkup_tbl[0];
   2098                     bta_dm_search_cb.services_to_search &= ~BTA_RES_SERVICE_MASK;
   2099                 } else {
   2100                     uuid.uu.uuid16 = UUID_PROTOCOL_L2CAP;
   2101                     bta_dm_search_cb.services_to_search = 0;
   2102                 }
   2103             } else {
   2104 #if BLE_INCLUDED == TRUE && BTA_GATT_INCLUDED == TRUE
   2105                 /* for LE only profile */
   2106                 if (bta_dm_search_cb.service_index == BTA_BLE_SERVICE_ID) {
   2107                     if (bta_dm_search_cb.uuid_to_search > 0 &&
   2108                         bta_dm_search_cb.p_srvc_uuid) {
   2109                         memcpy(&uuid,
   2110                                (const void *)(bta_dm_search_cb.p_srvc_uuid +
   2111                                               bta_dm_search_cb.num_uuid -
   2112                                               bta_dm_search_cb.uuid_to_search),
   2113                                sizeof(tBT_UUID));
   2114 
   2115                         bta_dm_search_cb.uuid_to_search--;
   2116                     } else {
   2117                         uuid.uu.uuid16 = bta_service_id_to_uuid_lkup_tbl[bta_dm_search_cb.service_index];
   2118                     }
   2119 
   2120                     /* last one? clear the BLE service bit if all discovery has been done */
   2121                     if (bta_dm_search_cb.uuid_to_search == 0)
   2122                       bta_dm_search_cb.services_to_search &=
   2123                         (tBTA_SERVICE_MASK)(~(BTA_SERVICE_ID_TO_SERVICE_MASK(bta_dm_search_cb.service_index)));
   2124 
   2125                 } else
   2126 #endif
   2127                 {
   2128                     /* remove the service from services to be searched  */
   2129                     bta_dm_search_cb.services_to_search &=
   2130                         (tBTA_SERVICE_MASK)(~(BTA_SERVICE_ID_TO_SERVICE_MASK(bta_dm_search_cb.service_index)));
   2131                     uuid.uu.uuid16 = bta_service_id_to_uuid_lkup_tbl[bta_dm_search_cb.service_index];
   2132                 }
   2133             }
   2134 
   2135             if (uuid.len == 0)
   2136                 uuid.len = LEN_UUID_16;
   2137 
   2138             if (bta_dm_search_cb.service_index == BTA_USER_SERVICE_ID) {
   2139                 memcpy(&uuid, &bta_dm_search_cb.uuid, sizeof(tSDP_UUID));
   2140             }
   2141 
   2142             LOG_INFO(LOG_TAG, "%s search UUID = %04x", __func__,
   2143                      uuid.uu.uuid16);
   2144             SDP_InitDiscoveryDb(bta_dm_search_cb.p_sdp_db, BTA_DM_SDP_DB_SIZE,
   2145                                 1, &uuid, 0, NULL);
   2146 
   2147             memset(g_disc_raw_data_buf, 0, sizeof(g_disc_raw_data_buf));
   2148             bta_dm_search_cb.p_sdp_db->raw_data = g_disc_raw_data_buf;
   2149 
   2150             bta_dm_search_cb.p_sdp_db->raw_size = MAX_DISC_RAW_DATA_BUF;
   2151 
   2152             if (!SDP_ServiceSearchAttributeRequest(bd_addr, bta_dm_search_cb.p_sdp_db, &bta_dm_sdp_callback)) {
   2153               /*
   2154                * If discovery is not successful with this device, then
   2155                * proceed with the next one.
   2156                */
   2157               osi_free_and_reset((void **)&bta_dm_search_cb.p_sdp_db);
   2158               bta_dm_search_cb.service_index = BTA_MAX_SERVICE_ID;
   2159 
   2160             } else {
   2161 #if BLE_INCLUDED == TRUE && BTA_GATT_INCLUDED == TRUE
   2162                 if ((bta_dm_search_cb.service_index == BTA_BLE_SERVICE_ID &&
   2163                      bta_dm_search_cb.uuid_to_search == 0) ||
   2164                     bta_dm_search_cb.service_index != BTA_BLE_SERVICE_ID)
   2165 #endif
   2166                     bta_dm_search_cb.service_index++;
   2167                 return;
   2168             }
   2169         }
   2170 
   2171         bta_dm_search_cb.service_index++;
   2172     }
   2173 
   2174     /* no more services to be discovered */
   2175     if (bta_dm_search_cb.service_index >= BTA_MAX_SERVICE_ID) {
   2176         tBTA_DM_MSG *p_msg = (tBTA_DM_MSG *)osi_malloc(sizeof(tBTA_DM_MSG));
   2177         p_msg->hdr.event = BTA_DM_DISCOVERY_RESULT_EVT;
   2178         p_msg->disc_result.result.disc_res.services = bta_dm_search_cb.services_found;
   2179         bdcpy(p_msg->disc_result.result.disc_res.bd_addr, bta_dm_search_cb.peer_bdaddr);
   2180         strlcpy((char*)p_msg->disc_result.result.disc_res.bd_name,
   2181                 bta_dm_get_remname(), BD_NAME_LEN);
   2182 
   2183         bta_sys_sendmsg(p_msg);
   2184     }
   2185 }
   2186 
   2187 /*******************************************************************************
   2188 **
   2189 ** Function         bta_dm_discover_next_device
   2190 **
   2191 ** Description      Starts discovery on the next device in Inquiry data base
   2192 **
   2193 ** Returns          void
   2194 **
   2195 *******************************************************************************/
   2196 static void bta_dm_discover_next_device(void)
   2197 {
   2198     APPL_TRACE_DEBUG("bta_dm_discover_next_device");
   2199 
   2200     /* searching next device on inquiry result */
   2201     if((bta_dm_search_cb.p_btm_inq_info = BTM_InqDbNext(bta_dm_search_cb.p_btm_inq_info)) != NULL) {
   2202         bta_dm_search_cb.name_discover_done = FALSE;
   2203         bta_dm_search_cb.peer_name[0]       = 0;
   2204         bta_dm_discover_device(bta_dm_search_cb.p_btm_inq_info->results.remote_bd_addr);
   2205     } else {
   2206         tBTA_DM_MSG *p_msg =
   2207             (tBTA_DM_MSG *)osi_malloc(sizeof(tBTA_DM_MSG));
   2208 
   2209         /* no devices, search complete */
   2210         bta_dm_search_cb.services = 0;
   2211 
   2212         p_msg->hdr.event = BTA_DM_SEARCH_CMPL_EVT;
   2213         p_msg->hdr.layer_specific = BTA_DM_API_DISCOVER_EVT;
   2214 
   2215         bta_sys_sendmsg(p_msg);
   2216     }
   2217 }
   2218 
   2219 /*******************************************************************************
   2220 **
   2221 ** Function         bta_dm_discover_device
   2222 **
   2223 ** Description      Starts name and service discovery on the device
   2224 **
   2225 ** Returns          void
   2226 **
   2227 *******************************************************************************/
   2228 static void bta_dm_discover_device(BD_ADDR remote_bd_addr)
   2229 {
   2230     tBT_TRANSPORT transport = BT_TRANSPORT_BR_EDR;
   2231 
   2232 #if BLE_INCLUDED == TRUE
   2233     if (bta_dm_search_cb.transport == BTA_TRANSPORT_UNKNOWN)
   2234     {
   2235         tBT_DEVICE_TYPE dev_type;
   2236         tBLE_ADDR_TYPE  addr_type;
   2237 
   2238         BTM_ReadDevInfo(remote_bd_addr, &dev_type, &addr_type);
   2239         if (dev_type == BT_DEVICE_TYPE_BLE || addr_type == BLE_ADDR_RANDOM)
   2240             transport = BT_TRANSPORT_LE;
   2241     } else {
   2242         transport = bta_dm_search_cb.transport;
   2243     }
   2244 #endif
   2245 
   2246     /* Reset transport state for next discovery */
   2247     bta_dm_search_cb.transport = BTA_TRANSPORT_UNKNOWN;
   2248 
   2249     APPL_TRACE_DEBUG("%s BDA:0x%02X%02X%02X%02X%02X%02X", __func__,
   2250                         remote_bd_addr[0],remote_bd_addr[1],
   2251                         remote_bd_addr[2],remote_bd_addr[3],
   2252                         remote_bd_addr[4],remote_bd_addr[5]);
   2253 
   2254     bdcpy(bta_dm_search_cb.peer_bdaddr, remote_bd_addr);
   2255 
   2256     APPL_TRACE_DEBUG("%s name_discover_done = %d p_btm_inq_info 0x%x state = %d, transport=%d",
   2257                         __func__,
   2258                         bta_dm_search_cb.name_discover_done,
   2259                         bta_dm_search_cb.p_btm_inq_info,
   2260                         bta_dm_search_cb.state,
   2261                         transport);
   2262 
   2263     if (bta_dm_search_cb.p_btm_inq_info)
   2264     {
   2265         APPL_TRACE_DEBUG("%s appl_knows_rem_name %d", __func__,
   2266                             bta_dm_search_cb.p_btm_inq_info->appl_knows_rem_name);
   2267     }
   2268 #if (defined(BLE_INCLUDED) && BLE_INCLUDED == TRUE)
   2269     if((bta_dm_search_cb.p_btm_inq_info)
   2270        && (bta_dm_search_cb.p_btm_inq_info->results.device_type == BT_DEVICE_TYPE_BLE)
   2271        && (bta_dm_search_cb.state == BTA_DM_SEARCH_ACTIVE))
   2272     {
   2273         /* Do not perform RNR for LE devices at inquiry complete*/
   2274         bta_dm_search_cb.name_discover_done = TRUE;
   2275     }
   2276 #endif
   2277     /* if name discovery is not done and application needs remote name */
   2278     if ((!bta_dm_search_cb.name_discover_done)
   2279        && (( bta_dm_search_cb.p_btm_inq_info == NULL )
   2280             ||(bta_dm_search_cb.p_btm_inq_info && (!bta_dm_search_cb.p_btm_inq_info->appl_knows_rem_name))))
   2281     {
   2282         if (bta_dm_read_remote_device_name(bta_dm_search_cb.peer_bdaddr, transport) == TRUE)
   2283             return;
   2284 
   2285         /* starting name discovery failed */
   2286         bta_dm_search_cb.name_discover_done = TRUE;
   2287     }
   2288 
   2289     /* if application wants to discover service */
   2290     if ( bta_dm_search_cb.services )
   2291     {
   2292         /* initialize variables */
   2293         bta_dm_search_cb.service_index      = 0;
   2294         bta_dm_search_cb.services_found     = 0;
   2295         bta_dm_search_cb.services_to_search = bta_dm_search_cb.services;
   2296 #if BLE_INCLUDED == TRUE && BTA_GATT_INCLUDED == TRUE
   2297         bta_dm_search_cb.uuid_to_search     = bta_dm_search_cb.num_uuid;
   2298 #endif
   2299         if ((bta_dm_search_cb.p_btm_inq_info != NULL) &&
   2300             bta_dm_search_cb.services != BTA_USER_SERVICE_MASK
   2301             &&(bta_dm_search_cb.sdp_search == FALSE))
   2302         {
   2303             /* check if EIR provides the information of supported services */
   2304             bta_dm_eir_search_services( &bta_dm_search_cb.p_btm_inq_info->results,
   2305                                         &bta_dm_search_cb.services_to_search,
   2306                                         &bta_dm_search_cb.services_found );
   2307         }
   2308 
   2309         /* if seaching with EIR is not completed */
   2310         if(bta_dm_search_cb.services_to_search)
   2311         {
   2312             /* check whether connection already exists to the device
   2313                if connection exists, we don't have to wait for ACL
   2314                link to go down to start search on next device */
   2315             if (BTM_IsAclConnectionUp(bta_dm_search_cb.peer_bdaddr, BT_TRANSPORT_BR_EDR))
   2316                 bta_dm_search_cb.wait_disc = FALSE;
   2317             else
   2318                 bta_dm_search_cb.wait_disc = TRUE;
   2319 
   2320 #if (BLE_INCLUDED == TRUE && (defined BTA_GATT_INCLUDED) && (BTA_GATT_INCLUDED == TRUE))
   2321             if ( bta_dm_search_cb.p_btm_inq_info )
   2322             {
   2323                 APPL_TRACE_DEBUG("%s p_btm_inq_info 0x%x results.device_type 0x%x services_to_search 0x%x",
   2324                                     __func__,
   2325                                     bta_dm_search_cb.p_btm_inq_info,
   2326                                     bta_dm_search_cb.p_btm_inq_info->results.device_type,
   2327                                     bta_dm_search_cb.services_to_search);
   2328             }
   2329 
   2330             if (transport == BT_TRANSPORT_LE)
   2331             {
   2332                 if (bta_dm_search_cb.services_to_search & BTA_BLE_SERVICE_MASK)
   2333                 {
   2334                     //set the raw data buffer here
   2335                     memset(g_disc_raw_data_buf, 0, sizeof(g_disc_raw_data_buf));
   2336                     bta_dm_search_cb.p_ble_rawdata = g_disc_raw_data_buf;
   2337 
   2338                     bta_dm_search_cb.ble_raw_size = MAX_DISC_RAW_DATA_BUF;
   2339                     bta_dm_search_cb.ble_raw_used = 0;
   2340 
   2341                     /* start GATT for service discovery */
   2342                     btm_dm_start_gatt_discovery(bta_dm_search_cb.peer_bdaddr);
   2343                     return;
   2344                 }
   2345             }
   2346             else
   2347 #endif
   2348             {
   2349                 bta_dm_search_cb.sdp_results = FALSE;
   2350                 bta_dm_find_services(bta_dm_search_cb.peer_bdaddr);
   2351                 return;
   2352             }
   2353         }
   2354     }
   2355 
   2356     /* name discovery and service discovery are done for this device */
   2357     tBTA_DM_MSG *p_msg = (tBTA_DM_MSG *)osi_malloc(sizeof(tBTA_DM_MSG));
   2358     p_msg->hdr.event = BTA_DM_DISCOVERY_RESULT_EVT;
   2359     /* initialize the data structure - includes p_raw_data and raw_data_size */
   2360     memset(&(p_msg->disc_result.result), 0, sizeof(tBTA_DM_DISC_RES));
   2361     p_msg->disc_result.result.disc_res.result = BTA_SUCCESS;
   2362     p_msg->disc_result.result.disc_res.services = bta_dm_search_cb.services_found;
   2363     bdcpy(p_msg->disc_result.result.disc_res.bd_addr, bta_dm_search_cb.peer_bdaddr);
   2364     strlcpy((char*)p_msg->disc_result.result.disc_res.bd_name,
   2365             (char*)bta_dm_search_cb.peer_name, BD_NAME_LEN);
   2366 
   2367     bta_sys_sendmsg(p_msg);
   2368 }
   2369 
   2370 /*******************************************************************************
   2371 **
   2372 ** Function         bta_dm_sdp_callback
   2373 **
   2374 ** Description      Callback from sdp with discovery status
   2375 **
   2376 ** Returns          void
   2377 **
   2378 *******************************************************************************/
   2379 static void bta_dm_sdp_callback (UINT16 sdp_status)
   2380 {
   2381 
   2382     tBTA_DM_SDP_RESULT *p_msg =
   2383         (tBTA_DM_SDP_RESULT *)osi_malloc(sizeof(tBTA_DM_SDP_RESULT));
   2384 
   2385     p_msg->hdr.event = BTA_DM_SDP_RESULT_EVT;
   2386     p_msg->sdp_result = sdp_status;
   2387 
   2388     bta_sys_sendmsg(p_msg);
   2389 }
   2390 
   2391 /*******************************************************************************
   2392 **
   2393 ** Function         bta_dm_inq_results_cb
   2394 **
   2395 ** Description      Inquiry results callback from BTM
   2396 **
   2397 ** Returns          void
   2398 **
   2399 *******************************************************************************/
   2400 static void bta_dm_inq_results_cb (tBTM_INQ_RESULTS *p_inq, UINT8 *p_eir)
   2401 {
   2402 
   2403     tBTA_DM_SEARCH     result;
   2404     tBTM_INQ_INFO      *p_inq_info;
   2405     UINT16             service_class;
   2406 
   2407     bdcpy(result.inq_res.bd_addr, p_inq->remote_bd_addr);
   2408     memcpy(result.inq_res.dev_class, p_inq->dev_class, DEV_CLASS_LEN);
   2409     BTM_COD_SERVICE_CLASS(service_class, p_inq->dev_class);
   2410     result.inq_res.is_limited = (service_class & BTM_COD_SERVICE_LMTD_DISCOVER)?TRUE:FALSE;
   2411     result.inq_res.rssi = p_inq->rssi;
   2412 
   2413 #if (BLE_INCLUDED == TRUE)
   2414     result.inq_res.ble_addr_type    = p_inq->ble_addr_type;
   2415     result.inq_res.inq_result_type  = p_inq->inq_result_type;
   2416     result.inq_res.device_type      = p_inq->device_type;
   2417     result.inq_res.flag             = p_inq->flag;
   2418 #endif
   2419 
   2420     /* application will parse EIR to find out remote device name */
   2421     result.inq_res.p_eir = p_eir;
   2422 
   2423     if((p_inq_info = BTM_InqDbRead(p_inq->remote_bd_addr)) != NULL)
   2424     {
   2425         /* initialize remt_name_not_required to FALSE so that we get the name by default */
   2426         result.inq_res.remt_name_not_required = FALSE;
   2427 
   2428     }
   2429 
   2430     if(bta_dm_search_cb.p_search_cback)
   2431         bta_dm_search_cb.p_search_cback(BTA_DM_INQ_RES_EVT, &result);
   2432 
   2433     if(p_inq_info)
   2434     {
   2435         /* application indicates if it knows the remote name, inside the callback
   2436          copy that to the inquiry data base*/
   2437         if(result.inq_res.remt_name_not_required)
   2438             p_inq_info->appl_knows_rem_name = TRUE;
   2439 
   2440     }
   2441 
   2442 
   2443 }
   2444 
   2445 
   2446 /*******************************************************************************
   2447 **
   2448 ** Function         bta_dm_inq_cmpl_cb
   2449 **
   2450 ** Description      Inquiry complete callback from BTM
   2451 **
   2452 ** Returns          void
   2453 **
   2454 *******************************************************************************/
   2455 static void bta_dm_inq_cmpl_cb (void * p_result)
   2456 {
   2457     tBTA_DM_MSG *p_msg = (tBTA_DM_MSG *)osi_malloc(sizeof(tBTA_DM_MSG));
   2458 
   2459     APPL_TRACE_DEBUG("%s", __func__);
   2460 
   2461     if (bta_dm_search_cb.cancel_pending == FALSE) {
   2462         p_msg->inq_cmpl.hdr.event = BTA_DM_INQUIRY_CMPL_EVT;
   2463         p_msg->inq_cmpl.num = ((tBTM_INQUIRY_CMPL *)p_result)->num_resp;
   2464     } else {
   2465         bta_dm_search_cb.cancel_pending = FALSE;
   2466         bta_dm_search_cancel_notify(NULL);
   2467         p_msg->hdr.event = BTA_DM_SEARCH_CMPL_EVT;
   2468         p_msg->hdr.layer_specific = BTA_DM_API_DISCOVER_EVT;
   2469     }
   2470 
   2471     bta_sys_sendmsg(p_msg);
   2472 }
   2473 
   2474 /*******************************************************************************
   2475 **
   2476 ** Function         bta_dm_service_search_remname_cback
   2477 **
   2478 ** Description      Remote name call back from BTM during service discovery
   2479 **
   2480 ** Returns          void
   2481 **
   2482 *******************************************************************************/
   2483 static void bta_dm_service_search_remname_cback (BD_ADDR bd_addr, DEV_CLASS dc, BD_NAME bd_name)
   2484 {
   2485     tBTM_REMOTE_DEV_NAME    rem_name;
   2486     tBTM_STATUS             btm_status;
   2487     UNUSED(dc);
   2488 
   2489     APPL_TRACE_DEBUG("bta_dm_service_search_remname_cback name=<%s>", bd_name);
   2490 
   2491     /* if this is what we are looking for */
   2492     if (!bdcmp( bta_dm_search_cb.peer_bdaddr, bd_addr))
   2493     {
   2494         rem_name.length = strlen((char*)bd_name);
   2495         if (rem_name.length > (BD_NAME_LEN-1))
   2496         {
   2497             rem_name.length = (BD_NAME_LEN-1);
   2498             rem_name.remote_bd_name[(BD_NAME_LEN-1)] = 0;
   2499         }
   2500         strlcpy((char*)rem_name.remote_bd_name, (char*)bd_name, BD_NAME_LEN);
   2501         rem_name.status = BTM_SUCCESS;
   2502 
   2503         bta_dm_remname_cback(&rem_name);
   2504     }
   2505     else
   2506     {
   2507         /* get name of device */
   2508         btm_status = BTM_ReadRemoteDeviceName (bta_dm_search_cb.peer_bdaddr,
   2509                                                 (tBTM_CMPL_CB *) bta_dm_remname_cback,
   2510                                                 BT_TRANSPORT_BR_EDR);
   2511         if ( btm_status == BTM_BUSY )
   2512         {
   2513             /* wait for next chance(notification of remote name discovery done) */
   2514             APPL_TRACE_DEBUG("bta_dm_service_search_remname_cback: BTM_ReadRemoteDeviceName is busy");
   2515         }
   2516         else if ( btm_status != BTM_CMD_STARTED )
   2517         {
   2518             /* if failed to start getting remote name then continue */
   2519             APPL_TRACE_WARNING("bta_dm_service_search_remname_cback: BTM_ReadRemoteDeviceName returns 0x%02X", btm_status);
   2520 
   2521             rem_name.length = 0;
   2522             rem_name.remote_bd_name[0] = 0;
   2523             rem_name.status = btm_status;
   2524             bta_dm_remname_cback(&rem_name);
   2525         }
   2526     }
   2527 }
   2528 
   2529 
   2530 /*******************************************************************************
   2531 **
   2532 ** Function         bta_dm_remname_cback
   2533 **
   2534 ** Description      Remote name complete call back from BTM
   2535 **
   2536 ** Returns          void
   2537 **
   2538 *******************************************************************************/
   2539 static void bta_dm_remname_cback (tBTM_REMOTE_DEV_NAME *p_remote_name)
   2540 {
   2541     APPL_TRACE_DEBUG("bta_dm_remname_cback len = %d name=<%s>", p_remote_name->length,
   2542                       p_remote_name->remote_bd_name);
   2543 
   2544     /* remote name discovery is done but it could be failed */
   2545     bta_dm_search_cb.name_discover_done = TRUE;
   2546     strlcpy((char*)bta_dm_search_cb.peer_name,
   2547             (char*)p_remote_name->remote_bd_name, BD_NAME_LEN);
   2548 
   2549     BTM_SecDeleteRmtNameNotifyCallback(&bta_dm_service_search_remname_cback);
   2550 
   2551 #if BLE_INCLUDED == TRUE
   2552     if (bta_dm_search_cb.transport == BT_TRANSPORT_LE )
   2553     {
   2554         GAP_BleReadPeerPrefConnParams (bta_dm_search_cb.peer_bdaddr);
   2555     }
   2556 #endif
   2557 
   2558     tBTA_DM_REM_NAME *p_msg =
   2559         (tBTA_DM_REM_NAME *)osi_malloc(sizeof(tBTA_DM_REM_NAME));
   2560     bdcpy(p_msg->result.disc_res.bd_addr, bta_dm_search_cb.peer_bdaddr);
   2561     strlcpy((char*)p_msg->result.disc_res.bd_name,
   2562             (char*)p_remote_name->remote_bd_name, BD_NAME_LEN);
   2563     p_msg->hdr.event = BTA_DM_REMT_NAME_EVT;
   2564 
   2565     bta_sys_sendmsg(p_msg);
   2566 }
   2567 
   2568 /*******************************************************************************
   2569 **
   2570 ** Function         bta_dm_authorize_cback
   2571 **
   2572 ** Description      cback requesting authorization
   2573 **
   2574 ** Returns          void
   2575 **
   2576 *******************************************************************************/
   2577 static UINT8 bta_dm_authorize_cback (BD_ADDR bd_addr, DEV_CLASS dev_class, BD_NAME bd_name,
   2578                                      UINT8 *service_name, UINT8 service_id, BOOLEAN is_originator)
   2579 {
   2580     tBTA_DM_SEC sec_event;
   2581     UINT8       index = 1;
   2582     UNUSED(service_name);
   2583     UNUSED(is_originator);
   2584 
   2585     bdcpy(sec_event.authorize.bd_addr, bd_addr);
   2586     memcpy(sec_event.authorize.dev_class, dev_class, DEV_CLASS_LEN);
   2587     strlcpy((char*)sec_event.authorize.bd_name, (char*)bd_name, BD_NAME_LEN);
   2588 
   2589 #if ( defined(BTA_JV_INCLUDED) && BTA_JV_INCLUDED == TRUE )
   2590     sec_event.authorize.service = service_id;
   2591 #endif
   2592 
   2593     while(index < BTA_MAX_SERVICE_ID)
   2594     {
   2595         /* get the BTA service id corresponding to BTM id */
   2596         if(bta_service_id_to_btm_srv_id_lkup_tbl[index] == service_id)
   2597         {
   2598             sec_event.authorize.service = index;
   2599             break;
   2600         }
   2601         index++;
   2602     }
   2603 
   2604 
   2605     /* if supported service callback otherwise not authorized */
   2606     if(bta_dm_cb.p_sec_cback && (index < BTA_MAX_SERVICE_ID
   2607 #if ( defined(BTA_JV_INCLUDED) && BTA_JV_INCLUDED == TRUE )
   2608         /* pass through JV service ID */
   2609         || (service_id >= BTA_FIRST_JV_SERVICE_ID && service_id <= BTA_LAST_JV_SERVICE_ID)
   2610 #endif
   2611         ))
   2612     {
   2613         bta_dm_cb.p_sec_cback(BTA_DM_AUTHORIZE_EVT, &sec_event);
   2614         return BTM_CMD_STARTED;
   2615     }
   2616     else
   2617     {
   2618         return BTM_NOT_AUTHORIZED;
   2619     }
   2620 }
   2621 
   2622 
   2623 
   2624 
   2625 
   2626 /*******************************************************************************
   2627 **
   2628 ** Function         bta_dm_pinname_cback
   2629 **
   2630 ** Description      Callback requesting pin_key
   2631 **
   2632 ** Returns          void
   2633 **
   2634 *******************************************************************************/
   2635 static void bta_dm_pinname_cback (void *p_data)
   2636 {
   2637     tBTM_REMOTE_DEV_NAME *p_result = (tBTM_REMOTE_DEV_NAME *)p_data;
   2638     tBTA_DM_SEC           sec_event;
   2639     UINT32                bytes_to_copy;
   2640     tBTA_DM_SEC_EVT       event = bta_dm_cb.pin_evt;
   2641 
   2642     if (BTA_DM_SP_CFM_REQ_EVT == event)
   2643     {
   2644         /* Retrieved saved device class and bd_addr */
   2645         bdcpy(sec_event.cfm_req.bd_addr, bta_dm_cb.pin_bd_addr);
   2646         BTA_COPY_DEVICE_CLASS(sec_event.cfm_req.dev_class, bta_dm_cb.pin_dev_class);
   2647 
   2648         if (p_result && p_result->status == BTM_SUCCESS)
   2649         {
   2650             bytes_to_copy = (p_result->length < (BD_NAME_LEN-1))
   2651             ? p_result->length : (BD_NAME_LEN-1);
   2652             memcpy(sec_event.cfm_req.bd_name, p_result->remote_bd_name, bytes_to_copy);
   2653             sec_event.pin_req.bd_name[BD_NAME_LEN-1] = 0;
   2654         }
   2655         else    /* No name found */
   2656             sec_event.cfm_req.bd_name[0] = 0;
   2657 
   2658         sec_event.key_notif.passkey    = bta_dm_cb.num_val; /* get PIN code numeric number */
   2659 
   2660         /* 1 additional event data fields for this event */
   2661         sec_event.cfm_req.just_works = bta_dm_cb.just_works;
   2662     }
   2663     else
   2664     {
   2665         /* Retrieved saved device class and bd_addr */
   2666         bdcpy(sec_event.pin_req.bd_addr, bta_dm_cb.pin_bd_addr);
   2667         BTA_COPY_DEVICE_CLASS(sec_event.pin_req.dev_class, bta_dm_cb.pin_dev_class);
   2668 
   2669         if (p_result && p_result->status == BTM_SUCCESS)
   2670         {
   2671             bytes_to_copy = (p_result->length < (BD_NAME_LEN-1))
   2672             ? p_result->length : (BD_NAME_LEN-1);
   2673             memcpy(sec_event.pin_req.bd_name, p_result->remote_bd_name, bytes_to_copy);
   2674             sec_event.pin_req.bd_name[BD_NAME_LEN-1] = 0;
   2675         }
   2676         else    /* No name found */
   2677             sec_event.pin_req.bd_name[0] = 0;
   2678 
   2679         event = bta_dm_cb.pin_evt;
   2680         sec_event.key_notif.passkey    = bta_dm_cb.num_val; /* get PIN code numeric number */
   2681     }
   2682 
   2683     if( bta_dm_cb.p_sec_cback )
   2684         bta_dm_cb.p_sec_cback(event, &sec_event);
   2685 }
   2686 
   2687 /*******************************************************************************
   2688 **
   2689 ** Function         bta_dm_pin_cback
   2690 **
   2691 ** Description      Callback requesting pin_key
   2692 **
   2693 ** Returns          void
   2694 **
   2695 *******************************************************************************/
   2696 static UINT8 bta_dm_pin_cback (BD_ADDR bd_addr, DEV_CLASS dev_class, BD_NAME bd_name,
   2697         BOOLEAN min_16_digit)
   2698 {
   2699     tBTA_DM_SEC sec_event;
   2700 
   2701     if (!bta_dm_cb.p_sec_cback)
   2702         return BTM_NOT_AUTHORIZED;
   2703 
   2704     /* If the device name is not known, save bdaddr and devclass and initiate a name request */
   2705     if (bd_name[0] == 0)
   2706     {
   2707         bta_dm_cb.pin_evt = BTA_DM_PIN_REQ_EVT;
   2708         bdcpy(bta_dm_cb.pin_bd_addr, bd_addr);
   2709         BTA_COPY_DEVICE_CLASS(bta_dm_cb.pin_dev_class, dev_class);
   2710         if ((BTM_ReadRemoteDeviceName(bd_addr, bta_dm_pinname_cback, BT_TRANSPORT_BR_EDR)) == BTM_CMD_STARTED)
   2711             return BTM_CMD_STARTED;
   2712 
   2713         APPL_TRACE_WARNING(" bta_dm_pin_cback() -> Failed to start Remote Name Request  ");
   2714     }
   2715 
   2716     bdcpy(sec_event.pin_req.bd_addr, bd_addr);
   2717     BTA_COPY_DEVICE_CLASS(sec_event.pin_req.dev_class, dev_class);
   2718     strlcpy((char*)sec_event.pin_req.bd_name, (char*)bd_name, BD_NAME_LEN);
   2719     sec_event.pin_req.min_16_digit = min_16_digit;
   2720 
   2721     bta_dm_cb.p_sec_cback(BTA_DM_PIN_REQ_EVT, &sec_event);
   2722     return BTM_CMD_STARTED;
   2723 }
   2724 
   2725 /*******************************************************************************
   2726 **
   2727 ** Function         bta_dm_new_link_key_cback
   2728 **
   2729 ** Description      Callback from BTM to notify new link key
   2730 **
   2731 ** Returns          void
   2732 **
   2733 *******************************************************************************/
   2734 static UINT8  bta_dm_new_link_key_cback(BD_ADDR bd_addr, DEV_CLASS dev_class,
   2735                                         BD_NAME bd_name, LINK_KEY key, UINT8 key_type)
   2736 {
   2737     tBTA_DM_SEC sec_event;
   2738     tBTA_DM_AUTH_CMPL *p_auth_cmpl;
   2739     UINT8             event;
   2740     UNUSED(dev_class);
   2741 
   2742     memset (&sec_event, 0, sizeof(tBTA_DM_SEC));
   2743 
   2744     /* Not AMP Key type */
   2745     if (key_type != HCI_LKEY_TYPE_AMP_WIFI && key_type != HCI_LKEY_TYPE_AMP_UWB)
   2746     {
   2747         event = BTA_DM_AUTH_CMPL_EVT;
   2748         p_auth_cmpl = &sec_event.auth_cmpl;
   2749 
   2750         bdcpy(p_auth_cmpl->bd_addr, bd_addr);
   2751 
   2752         memcpy(p_auth_cmpl->bd_name, bd_name, (BD_NAME_LEN-1));
   2753         p_auth_cmpl->bd_name[BD_NAME_LEN-1] = 0;
   2754 
   2755         p_auth_cmpl->key_present = TRUE;
   2756         p_auth_cmpl->key_type = key_type;
   2757         p_auth_cmpl->success = TRUE;
   2758 
   2759         memcpy(p_auth_cmpl->key, key, LINK_KEY_LEN);
   2760         sec_event.auth_cmpl.fail_reason = HCI_SUCCESS;
   2761 
   2762 #if BLE_INCLUDED == TRUE
   2763         // Report the BR link key based on the BR/EDR address and type
   2764         BTM_ReadDevInfo(bd_addr, &sec_event.auth_cmpl.dev_type, &sec_event.auth_cmpl.addr_type);
   2765 #endif
   2766         if(bta_dm_cb.p_sec_cback)
   2767             bta_dm_cb.p_sec_cback(event, &sec_event);
   2768 
   2769         // Setting remove_dev_pending flag to FALSE, where it will avoid deleting the
   2770         // security device record when the ACL connection link goes down in case of
   2771         // reconnection.
   2772         if (bta_dm_cb.device_list.count)
   2773             bta_dm_reset_sec_dev_pending(p_auth_cmpl->bd_addr);
   2774     }
   2775     else
   2776     {
   2777         APPL_TRACE_WARNING("%s() Received AMP Key", __func__);
   2778     }
   2779 
   2780     return BTM_CMD_STARTED;
   2781 }
   2782 
   2783 
   2784 /*******************************************************************************
   2785 **
   2786 ** Function         bta_dm_authentication_complete_cback
   2787 **
   2788 ** Description      Authentication complete callback from BTM
   2789 **
   2790 ** Returns          void
   2791 **
   2792 *******************************************************************************/
   2793 static UINT8 bta_dm_authentication_complete_cback(BD_ADDR bd_addr, DEV_CLASS dev_class,BD_NAME bd_name, int result)
   2794 {
   2795     tBTA_DM_SEC sec_event;
   2796     UNUSED(dev_class);
   2797 
   2798     if(result != BTM_SUCCESS)
   2799     {
   2800         memset(&sec_event, 0, sizeof(tBTA_DM_SEC));
   2801         bdcpy(sec_event.auth_cmpl.bd_addr, bd_addr);
   2802 
   2803         memcpy(sec_event.auth_cmpl.bd_name, bd_name, (BD_NAME_LEN-1));
   2804         sec_event.auth_cmpl.bd_name[BD_NAME_LEN-1] = 0;
   2805 
   2806 #if BLE_INCLUDED == TRUE
   2807         // Report the BR link key based on the BR/EDR address and type
   2808         BTM_ReadDevInfo(bd_addr, &sec_event.auth_cmpl.dev_type, &sec_event.auth_cmpl.addr_type);
   2809 #endif
   2810         sec_event.auth_cmpl.fail_reason = (UINT8)result;
   2811 
   2812         if(bta_dm_cb.p_sec_cback)
   2813             bta_dm_cb.p_sec_cback(BTA_DM_AUTH_CMPL_EVT, &sec_event);
   2814 
   2815         bta_dm_remove_sec_dev_entry(bd_addr);
   2816     }
   2817 
   2818     return BTM_SUCCESS;
   2819 }
   2820 
   2821 /*******************************************************************************
   2822 **
   2823 ** Function         bta_dm_sp_cback
   2824 **
   2825 ** Description      simple pairing callback from BTM
   2826 **
   2827 ** Returns          void
   2828 **
   2829 *******************************************************************************/
   2830 static UINT8 bta_dm_sp_cback (tBTM_SP_EVT event, tBTM_SP_EVT_DATA *p_data)
   2831 {
   2832     tBTM_STATUS status = BTM_CMD_STARTED;
   2833     tBTA_DM_SEC sec_event;
   2834     tBTA_DM_SEC_EVT pin_evt = BTA_DM_SP_KEY_NOTIF_EVT;
   2835 
   2836     APPL_TRACE_EVENT("bta_dm_sp_cback: %d", event);
   2837     if (!bta_dm_cb.p_sec_cback)
   2838         return BTM_NOT_AUTHORIZED;
   2839 
   2840     /* TODO_SP */
   2841     switch(event)
   2842     {
   2843     case BTM_SP_IO_REQ_EVT:
   2844 #if (BTM_LOCAL_IO_CAPS != BTM_IO_CAP_NONE)
   2845         /* translate auth_req */
   2846         bta_dm_co_io_req(p_data->io_req.bd_addr, &p_data->io_req.io_cap,
   2847             &p_data->io_req.oob_data, &p_data->io_req.auth_req, p_data->io_req.is_orig);
   2848 #endif
   2849         APPL_TRACE_EVENT("io mitm: %d oob_data:%d", p_data->io_req.auth_req, p_data->io_req.oob_data);
   2850         break;
   2851     case BTM_SP_IO_RSP_EVT:
   2852 #if (BTM_LOCAL_IO_CAPS != BTM_IO_CAP_NONE)
   2853         bta_dm_co_io_rsp(p_data->io_rsp.bd_addr, p_data->io_rsp.io_cap,
   2854                          p_data->io_rsp.oob_data, p_data->io_rsp.auth_req );
   2855 #endif
   2856         break;
   2857 
   2858     case BTM_SP_CFM_REQ_EVT:
   2859         pin_evt = BTA_DM_SP_CFM_REQ_EVT;
   2860         bta_dm_cb.just_works = sec_event.cfm_req.just_works = p_data->cfm_req.just_works;
   2861         sec_event.cfm_req.loc_auth_req = p_data->cfm_req.loc_auth_req;
   2862         sec_event.cfm_req.rmt_auth_req = p_data->cfm_req.rmt_auth_req;
   2863         sec_event.cfm_req.loc_io_caps = p_data->cfm_req.loc_io_caps;
   2864         sec_event.cfm_req.rmt_io_caps = p_data->cfm_req.rmt_io_caps;
   2865 
   2866         /* continue to next case */
   2867 #if (BTM_LOCAL_IO_CAPS != BTM_IO_CAP_NONE)
   2868     /* Passkey entry mode, mobile device with output capability is very
   2869         unlikely to receive key request, so skip this event */
   2870     /*case BTM_SP_KEY_REQ_EVT: */
   2871     case BTM_SP_KEY_NOTIF_EVT:
   2872 #endif
   2873         if(BTM_SP_CFM_REQ_EVT == event)
   2874         {
   2875           /* Due to the switch case falling through below to BTM_SP_KEY_NOTIF_EVT,
   2876              call remote name request using values from cfm_req */
   2877           if(p_data->cfm_req.bd_name[0] == 0)
   2878           {
   2879               bta_dm_cb.pin_evt = pin_evt;
   2880               bdcpy(bta_dm_cb.pin_bd_addr, p_data->cfm_req.bd_addr);
   2881               BTA_COPY_DEVICE_CLASS(bta_dm_cb.pin_dev_class, p_data->cfm_req.dev_class);
   2882               if ((BTM_ReadRemoteDeviceName(p_data->cfm_req.bd_addr, bta_dm_pinname_cback,
   2883                          BT_TRANSPORT_BR_EDR)) == BTM_CMD_STARTED)
   2884                   return BTM_CMD_STARTED;
   2885               APPL_TRACE_WARNING(" bta_dm_sp_cback() -> Failed to start Remote Name Request  ");
   2886           }
   2887           else
   2888           {
   2889               /* Due to the switch case falling through below to BTM_SP_KEY_NOTIF_EVT,
   2890                  copy these values into key_notif from cfm_req */
   2891               bdcpy(sec_event.key_notif.bd_addr, p_data->cfm_req.bd_addr);
   2892               BTA_COPY_DEVICE_CLASS(sec_event.key_notif.dev_class, p_data->cfm_req.dev_class);
   2893               strlcpy((char*)sec_event.key_notif.bd_name,
   2894                       (char*)p_data->cfm_req.bd_name, BD_NAME_LEN);
   2895            }
   2896         }
   2897 
   2898         bta_dm_cb.num_val = sec_event.key_notif.passkey = p_data->key_notif.passkey;
   2899         if (BTM_SP_KEY_NOTIF_EVT == event)
   2900         {
   2901             /* If the device name is not known, save bdaddr and devclass
   2902                and initiate a name request with values from key_notif */
   2903             if(p_data->key_notif.bd_name[0] == 0)
   2904             {
   2905                 bta_dm_cb.pin_evt = pin_evt;
   2906                 bdcpy(bta_dm_cb.pin_bd_addr, p_data->key_notif.bd_addr);
   2907                 BTA_COPY_DEVICE_CLASS(bta_dm_cb.pin_dev_class, p_data->key_notif.dev_class);
   2908                 if ((BTM_ReadRemoteDeviceName(p_data->key_notif.bd_addr, bta_dm_pinname_cback,
   2909                          BT_TRANSPORT_BR_EDR)) == BTM_CMD_STARTED)
   2910                 return BTM_CMD_STARTED;
   2911                 APPL_TRACE_WARNING(" bta_dm_sp_cback() -> Failed to start Remote Name Request  ");
   2912             }
   2913             else
   2914             {
   2915                 bdcpy(sec_event.key_notif.bd_addr, p_data->key_notif.bd_addr);
   2916                 BTA_COPY_DEVICE_CLASS(sec_event.key_notif.dev_class, p_data->key_notif.dev_class);
   2917                 strlcpy((char*)sec_event.key_notif.bd_name,
   2918                         (char*)p_data->key_notif.bd_name, BD_NAME_LEN);
   2919                 sec_event.key_notif.bd_name[BD_NAME_LEN-1] = 0;
   2920             }
   2921         }
   2922 
   2923         bta_dm_cb.p_sec_cback(pin_evt, &sec_event);
   2924 
   2925         break;
   2926 
   2927     case BTM_SP_LOC_OOB_EVT:
   2928         bta_dm_co_loc_oob((BOOLEAN)(p_data->loc_oob.status == BTM_SUCCESS),
   2929             p_data->loc_oob.c, p_data->loc_oob.r);
   2930         break;
   2931 
   2932     case BTM_SP_RMT_OOB_EVT:
   2933         /* If the device name is not known, save bdaddr and devclass and initiate a name request */
   2934         if (p_data->rmt_oob.bd_name[0] == 0)
   2935         {
   2936              bta_dm_cb.pin_evt = BTA_DM_SP_RMT_OOB_EVT;
   2937              bdcpy(bta_dm_cb.pin_bd_addr, p_data->rmt_oob.bd_addr);
   2938              BTA_COPY_DEVICE_CLASS(bta_dm_cb.pin_dev_class, p_data->rmt_oob.dev_class);
   2939              if ((BTM_ReadRemoteDeviceName(p_data->rmt_oob.bd_addr, bta_dm_pinname_cback,
   2940                       BT_TRANSPORT_BR_EDR)) == BTM_CMD_STARTED)
   2941              return BTM_CMD_STARTED;
   2942              APPL_TRACE_WARNING(" bta_dm_sp_cback() -> Failed to start Remote Name Request  ");
   2943         }
   2944 
   2945         bdcpy(sec_event.rmt_oob.bd_addr, p_data->rmt_oob.bd_addr);
   2946         BTA_COPY_DEVICE_CLASS(sec_event.rmt_oob.dev_class, p_data->rmt_oob.dev_class);
   2947         strlcpy((char*)sec_event.rmt_oob.bd_name, (char*)p_data->rmt_oob.bd_name, BD_NAME_LEN);
   2948 
   2949         bta_dm_cb.p_sec_cback(BTA_DM_SP_RMT_OOB_EVT, &sec_event);
   2950 
   2951         bta_dm_co_rmt_oob(p_data->rmt_oob.bd_addr);
   2952         break;
   2953 
   2954     case BTM_SP_COMPLT_EVT:
   2955         /* do not report this event - handled by link_key_callback or auth_complete_callback */
   2956         break;
   2957 
   2958     case BTM_SP_KEYPRESS_EVT:
   2959         memcpy(&sec_event.key_press, &p_data->key_press, sizeof(tBTM_SP_KEYPRESS));
   2960         bta_dm_cb.p_sec_cback(BTA_DM_SP_KEYPRESS_EVT, &sec_event);
   2961         break;
   2962 
   2963     case BTM_SP_UPGRADE_EVT:
   2964         bta_dm_co_lk_upgrade(p_data->upgrade.bd_addr, &p_data->upgrade.upgrade );
   2965         break;
   2966 
   2967     default:
   2968         status = BTM_NOT_AUTHORIZED;
   2969         break;
   2970     }
   2971     APPL_TRACE_EVENT("dm status: %d", status);
   2972     return status;
   2973 }
   2974 
   2975 /*******************************************************************************
   2976 **
   2977 ** Function         bta_dm_local_name_cback
   2978 **
   2979 ** Description      Callback from btm after local name is read
   2980 **
   2981 **
   2982 ** Returns          void
   2983 **
   2984 *******************************************************************************/
   2985 static void bta_dm_local_name_cback(UINT8 *p_name)
   2986 {
   2987     tBTA_DM_SEC sec_event;
   2988     UNUSED(p_name);
   2989 
   2990     sec_event.enable.status = BTA_SUCCESS;
   2991 
   2992     if(bta_dm_cb.p_sec_cback)
   2993         bta_dm_cb.p_sec_cback(BTA_DM_ENABLE_EVT, &sec_event);
   2994 
   2995 }
   2996 
   2997 /*******************************************************************************
   2998 **
   2999 ** Function         bta_dm_bl_change_cback
   3000 **
   3001 ** Description      Callback from btm when acl connection goes up or down
   3002 **
   3003 **
   3004 ** Returns          void
   3005 **
   3006 *******************************************************************************/
   3007 static void bta_dm_bl_change_cback (tBTM_BL_EVENT_DATA *p_data)
   3008 {
   3009     tBTA_DM_ACL_CHANGE *p_msg =
   3010         (tBTA_DM_ACL_CHANGE *)osi_malloc(sizeof(tBTA_DM_ACL_CHANGE));
   3011 
   3012     p_msg->event = p_data->event;
   3013     p_msg->is_new = FALSE;
   3014 
   3015     switch (p_msg->event) {
   3016     case BTM_BL_CONN_EVT:
   3017         p_msg->is_new = TRUE;
   3018         bdcpy(p_msg->bd_addr, p_data->conn.p_bda);
   3019 #if BLE_INCLUDED == TRUE
   3020         p_msg->transport = p_data->conn.transport;
   3021         p_msg->handle = p_data->conn.handle;
   3022 #endif
   3023         break;
   3024     case BTM_BL_DISCN_EVT:
   3025         bdcpy(p_msg->bd_addr, p_data->discn.p_bda);
   3026 #if BLE_INCLUDED == TRUE
   3027         p_msg->transport = p_data->discn.transport;
   3028         p_msg->handle = p_data->discn.handle;
   3029 #endif
   3030         break;
   3031     case BTM_BL_UPDATE_EVT:
   3032         p_msg->busy_level = p_data->update.busy_level;
   3033         p_msg->busy_level_flags = p_data->update.busy_level_flags;
   3034         break;
   3035     case BTM_BL_ROLE_CHG_EVT:
   3036         p_msg->new_role = p_data->role_chg.new_role;
   3037         p_msg->hci_status = p_data->role_chg.hci_status;
   3038         bdcpy(p_msg->bd_addr, p_data->role_chg.p_bda);
   3039         break;
   3040     case BTM_BL_COLLISION_EVT:
   3041         bdcpy(p_msg->bd_addr, p_data->conn.p_bda);
   3042         break;
   3043     }
   3044 
   3045     p_msg->hdr.event = BTA_DM_ACL_CHANGE_EVT;
   3046     bta_sys_sendmsg(p_msg);
   3047 }
   3048 
   3049 /*******************************************************************************
   3050 **
   3051 ** Function         bta_dm_rs_cback
   3052 **
   3053 ** Description      Receives the role switch complete event
   3054 **
   3055 ** Returns
   3056 **
   3057 *******************************************************************************/
   3058 static void bta_dm_rs_cback (tBTM_ROLE_SWITCH_CMPL *p1)
   3059 {
   3060     UNUSED(p1);
   3061     APPL_TRACE_WARNING("bta_dm_rs_cback:%d", bta_dm_cb.rs_event);
   3062     if(bta_dm_cb.rs_event == BTA_DM_API_SEARCH_EVT)
   3063     {
   3064         bta_dm_cb.search_msg.rs_res = BTA_DM_RS_OK; /* do not care about the result for now */
   3065         bta_dm_cb.rs_event = 0;
   3066         bta_dm_search_start((tBTA_DM_MSG *)&bta_dm_cb.search_msg);
   3067     }
   3068 }
   3069 
   3070 /*******************************************************************************
   3071 **
   3072 ** Function         bta_dm_check_av
   3073 **
   3074 ** Description      This function checks if AV is active
   3075 **                  if yes, make sure the AV link is master
   3076 **
   3077 ** Returns          BOOLEAN - TRUE, if switch is in progress
   3078 **
   3079 *******************************************************************************/
   3080 static BOOLEAN bta_dm_check_av(UINT16 event)
   3081 {
   3082     BOOLEAN avoid_roleswitch = FALSE;
   3083     BOOLEAN switching = FALSE;
   3084     UINT8 i;
   3085     tBTA_DM_PEER_DEVICE *p_dev;
   3086 
   3087 #if defined(BTA_DM_AVOID_A2DP_ROLESWITCH_ON_INQUIRY) && (BTA_DM_AVOID_A2DP_ROLESWITCH_ON_INQUIRY == TRUE)
   3088 
   3089     /* avoid role switch upon inquiry if a2dp is actively streaming as it
   3090        introduces an audioglitch due to FW scheduling delays (unavoidable) */
   3091     if (event == BTA_DM_API_SEARCH_EVT)
   3092     {
   3093         avoid_roleswitch = TRUE;
   3094     }
   3095 #endif
   3096 
   3097     APPL_TRACE_WARNING("bta_dm_check_av:%d", bta_dm_cb.cur_av_count);
   3098     if(bta_dm_cb.cur_av_count)
   3099     {
   3100         for(i=0; i<bta_dm_cb.device_list.count; i++)
   3101         {
   3102             p_dev = &bta_dm_cb.device_list.peer_device[i];
   3103             APPL_TRACE_WARNING("[%d]: state:%d, info:x%x, avoid_rs %d",
   3104                                 i, p_dev->conn_state, p_dev->info, avoid_roleswitch);
   3105             if((p_dev->conn_state == BTA_DM_CONNECTED) && (p_dev->info & BTA_DM_DI_AV_ACTIVE) &&
   3106                (avoid_roleswitch == FALSE))
   3107             {
   3108                 /* make master and take away the role switch policy */
   3109                 if(BTM_CMD_STARTED == BTM_SwitchRole (p_dev->peer_bdaddr, HCI_ROLE_MASTER, (tBTM_CMPL_CB *)bta_dm_rs_cback))
   3110                 {
   3111                     /* the role switch command is actually sent */
   3112                     bta_dm_cb.rs_event = event;
   3113                     switching = TRUE;
   3114                 }
   3115                 /* else either already master or can not switch for some reasons */
   3116                 bta_dm_policy_cback(BTA_SYS_PLCY_CLR, 0, HCI_ENABLE_MASTER_SLAVE_SWITCH, p_dev->peer_bdaddr);
   3117                 break;
   3118             }
   3119         }
   3120     }
   3121     return switching;
   3122 }
   3123 
   3124 /*******************************************************************************
   3125 **
   3126 ** Function         bta_dm_acl_change
   3127 **
   3128 ** Description      Process BTA_DM_ACL_CHANGE_EVT
   3129 **
   3130 **
   3131 ** Returns          void
   3132 **
   3133 *******************************************************************************/
   3134 void bta_dm_acl_change(tBTA_DM_MSG *p_data)
   3135 {
   3136 
   3137     UINT8 i;
   3138     UINT8 *p;
   3139     tBTA_DM_SEC conn;
   3140     BOOLEAN is_new = p_data->acl_change.is_new;
   3141     BD_ADDR_PTR     p_bda = p_data->acl_change.bd_addr;
   3142     BOOLEAN         need_policy_change = FALSE;
   3143     BOOLEAN         issue_unpair_cb = FALSE;
   3144 
   3145     tBTA_DM_PEER_DEVICE *p_dev;
   3146     memset(&conn, 0, sizeof(tBTA_DM_SEC));
   3147 
   3148     switch(p_data->acl_change.event)
   3149     {
   3150     case BTM_BL_UPDATE_EVT:     /* busy level update */
   3151         if( bta_dm_cb.p_sec_cback )
   3152         {
   3153             conn.busy_level.level = p_data->acl_change.busy_level;
   3154             conn.busy_level.level_flags = p_data->acl_change.busy_level_flags;
   3155             bta_dm_cb.p_sec_cback(BTA_DM_BUSY_LEVEL_EVT, &conn);
   3156         }
   3157         return;
   3158 
   3159     case BTM_BL_ROLE_CHG_EVT:   /* role change event */
   3160         p_dev = bta_dm_find_peer_device(p_bda);
   3161         if(p_dev)
   3162         {
   3163             APPL_TRACE_DEBUG("bta_dm_acl_change role chg info:x%x new_role:%d dev count:%d",
   3164                 p_dev->info, p_data->acl_change.new_role, bta_dm_cb.device_list.count);
   3165             if(p_dev->info & BTA_DM_DI_AV_ACTIVE)
   3166             {
   3167                 /* there's AV activity on this link */
   3168                 if(p_data->acl_change.new_role == HCI_ROLE_SLAVE && bta_dm_cb.device_list.count > 1
   3169                     && p_data->acl_change.hci_status == HCI_SUCCESS)
   3170                 {
   3171                     /* more than one connections and the AV connection is role switched to slave
   3172                      * switch it back to master and remove the switch policy */
   3173                     BTM_SwitchRole(p_bda, BTM_ROLE_MASTER, NULL);
   3174                     need_policy_change = TRUE;
   3175                 }
   3176                 else if (p_bta_dm_cfg->avoid_scatter && (p_data->acl_change.new_role == HCI_ROLE_MASTER))
   3177                 {
   3178                     /* if the link updated to be master include AV activities, remove the switch policy */
   3179                     need_policy_change = TRUE;
   3180                 }
   3181 
   3182                 if(need_policy_change)
   3183                 {
   3184                     bta_dm_policy_cback(BTA_SYS_PLCY_CLR, 0, HCI_ENABLE_MASTER_SLAVE_SWITCH, p_dev->peer_bdaddr);
   3185                 }
   3186             }
   3187             else
   3188             {
   3189                 /* there's AV no activity on this link and role switch happened
   3190                  * check if AV is active
   3191                  * if so, make sure the AV link is master */
   3192                 bta_dm_check_av(0);
   3193             }
   3194             bta_sys_notify_role_chg(p_data->acl_change.bd_addr, p_data->acl_change.new_role, p_data->acl_change.hci_status);
   3195             bdcpy(conn.role_chg.bd_addr, p_bda);
   3196             conn.role_chg.new_role = (UINT8) p_data->acl_change.new_role;
   3197             if( bta_dm_cb.p_sec_cback )
   3198                 bta_dm_cb.p_sec_cback(BTA_DM_ROLE_CHG_EVT, (tBTA_DM_SEC *)&conn);
   3199         }
   3200         return;
   3201     }
   3202 
   3203     /* Collision report from Stack: Notify profiles */
   3204     if (p_data->acl_change.event == BTM_BL_COLLISION_EVT)
   3205     {
   3206         bta_sys_notify_collision (p_bda);
   3207         return;
   3208     }
   3209 
   3210     if(is_new)
   3211     {
   3212         for(i=0; i<bta_dm_cb.device_list.count; i++)
   3213         {
   3214             if (!bdcmp( bta_dm_cb.device_list.peer_device[i].peer_bdaddr, p_bda)
   3215 #if BLE_INCLUDED == TRUE
   3216                  && bta_dm_cb.device_list.peer_device[i].conn_handle == p_data->acl_change.handle
   3217 #endif
   3218                  )
   3219                 break;
   3220 
   3221         }
   3222 
   3223         if(i == bta_dm_cb.device_list.count)
   3224         {
   3225             if (bta_dm_cb.device_list.count < BTA_DM_NUM_PEER_DEVICE)
   3226             {
   3227                 bdcpy(bta_dm_cb.device_list.peer_device[bta_dm_cb.device_list.count].peer_bdaddr, p_bda);
   3228                 bta_dm_cb.device_list.peer_device[bta_dm_cb.device_list.count].link_policy = bta_dm_cb.cur_policy;
   3229                 bta_dm_cb.device_list.count++;
   3230 #if BLE_INCLUDED == TRUE
   3231                 bta_dm_cb.device_list.peer_device[i].conn_handle = p_data->acl_change.handle;
   3232                 if (p_data->acl_change.transport == BT_TRANSPORT_LE)
   3233                     bta_dm_cb.device_list.le_count++;
   3234 #endif
   3235             } else {
   3236                 APPL_TRACE_ERROR("%s max active connection reached, no resources", __func__);
   3237                 return;
   3238             }
   3239         }
   3240 
   3241         bta_dm_cb.device_list.peer_device[i].conn_state = BTA_DM_CONNECTED;
   3242         bta_dm_cb.device_list.peer_device[i].pref_role = BTA_ANY_ROLE;
   3243         bdcpy(conn.link_up.bd_addr, p_bda);
   3244         bta_dm_cb.device_list.peer_device[i].info = BTA_DM_DI_NONE;
   3245 #if BLE_INCLUDED == TRUE
   3246         conn.link_up.link_type = p_data->acl_change.transport;
   3247         bta_dm_cb.device_list.peer_device[i].transport = p_data->acl_change.transport;
   3248 #endif
   3249 
   3250         if (((NULL != (p = BTM_ReadLocalFeatures ())) && HCI_SNIFF_SUB_RATE_SUPPORTED(p)) &&
   3251             ((NULL != (p = BTM_ReadRemoteFeatures (p_bda))) && HCI_SNIFF_SUB_RATE_SUPPORTED(p)))
   3252         {
   3253             /* both local and remote devices support SSR */
   3254             bta_dm_cb.device_list.peer_device[i].info = BTA_DM_DI_USE_SSR;
   3255         }
   3256         APPL_TRACE_WARNING("%s info: 0x%x", __func__, bta_dm_cb.device_list.peer_device[i].info);
   3257 
   3258         if (bta_dm_cb.p_sec_cback)
   3259             bta_dm_cb.p_sec_cback(BTA_DM_LINK_UP_EVT, (tBTA_DM_SEC *)&conn);
   3260     } else {
   3261         for(i=0; i<bta_dm_cb.device_list.count; i++)
   3262         {
   3263             if (bdcmp( bta_dm_cb.device_list.peer_device[i].peer_bdaddr, p_bda)
   3264 #if BLE_INCLUDED == TRUE
   3265                  ||bta_dm_cb.device_list.peer_device[i].transport != p_data->acl_change.transport
   3266 #endif
   3267                )
   3268                 continue;
   3269 
   3270             if( bta_dm_cb.device_list.peer_device[i].conn_state == BTA_DM_UNPAIRING )
   3271             {
   3272                 if (BTM_SecDeleteDevice(bta_dm_cb.device_list.peer_device[i].peer_bdaddr))
   3273                     issue_unpair_cb = TRUE;
   3274 
   3275                 APPL_TRACE_DEBUG("%s: Unpairing: issue unpair CB = %d ",__FUNCTION__, issue_unpair_cb);
   3276             }
   3277 
   3278             conn.link_down.is_removed = bta_dm_cb.device_list.peer_device[i].remove_dev_pending;
   3279 
   3280             for(; i<bta_dm_cb.device_list.count ; i++)
   3281             {
   3282                 memcpy(&bta_dm_cb.device_list.peer_device[i], &bta_dm_cb.device_list.peer_device[i+1], sizeof(bta_dm_cb.device_list.peer_device[i]));
   3283             }
   3284             break;
   3285         }
   3286         if(bta_dm_cb.device_list.count)
   3287             bta_dm_cb.device_list.count--;
   3288 #if BLE_INCLUDED == TRUE
   3289         if ((p_data->acl_change.transport == BT_TRANSPORT_LE) &&
   3290              (bta_dm_cb.device_list.le_count))
   3291             bta_dm_cb.device_list.le_count--;
   3292         conn.link_down.link_type = p_data->acl_change.transport;
   3293 #endif
   3294 
   3295         if(bta_dm_search_cb.wait_disc && !bdcmp(bta_dm_search_cb.peer_bdaddr, p_bda))
   3296         {
   3297             bta_dm_search_cb.wait_disc = FALSE;
   3298 
   3299             if(bta_dm_search_cb.sdp_results)
   3300             {
   3301                 APPL_TRACE_EVENT(" timer stopped  ");
   3302                 alarm_cancel(bta_dm_search_cb.search_timer);
   3303                 bta_dm_discover_next_device();
   3304             }
   3305 
   3306         }
   3307 
   3308         if(bta_dm_cb.disabling)
   3309         {
   3310             if(!BTM_GetNumAclLinks())
   3311             {
   3312                 /*
   3313                  * Start a timer to make sure that the profiles
   3314                  * get the disconnect event.
   3315                  */
   3316                 alarm_set_on_queue(bta_dm_cb.disable_timer,
   3317                                    BTA_DM_DISABLE_CONN_DOWN_TIMER_MS,
   3318                                    bta_dm_disable_conn_down_timer_cback, NULL,
   3319                                    btu_bta_alarm_queue);
   3320             }
   3321         }
   3322         if (conn.link_down.is_removed)
   3323         {
   3324             BTM_SecDeleteDevice(p_bda);
   3325 #if (BLE_INCLUDED == TRUE && BTA_GATT_INCLUDED == TRUE)
   3326             /* need to remove all pending background connection */
   3327             BTA_GATTC_CancelOpen(0, p_bda, FALSE);
   3328             /* remove all cached GATT information */
   3329             BTA_GATTC_Refresh(p_bda);
   3330 #endif
   3331          }
   3332 
   3333         bdcpy(conn.link_down.bd_addr, p_bda);
   3334         conn.link_down.status = (UINT8) btm_get_acl_disc_reason_code();
   3335         if( bta_dm_cb.p_sec_cback )
   3336         {
   3337             bta_dm_cb.p_sec_cback(BTA_DM_LINK_DOWN_EVT, &conn);
   3338             if( issue_unpair_cb )
   3339                 bta_dm_cb.p_sec_cback(BTA_DM_DEV_UNPAIRED_EVT, &conn);
   3340         }
   3341     }
   3342 
   3343     bta_dm_adjust_roles(TRUE);
   3344 }
   3345 
   3346 /*******************************************************************************
   3347 **
   3348 ** Function         bta_dm_disable_conn_down_timer_cback
   3349 **
   3350 ** Description      Sends disable event to application
   3351 **
   3352 **
   3353 ** Returns          void
   3354 **
   3355 *******************************************************************************/
   3356 static void bta_dm_disable_conn_down_timer_cback(UNUSED_ATTR void *data)
   3357 {
   3358     tBTA_SYS_HW_MSG *sys_enable_event =
   3359         (tBTA_SYS_HW_MSG *)osi_malloc(sizeof(tBTA_SYS_HW_MSG));
   3360 
   3361     /* disable the power managment module */
   3362     bta_dm_disable_pm();
   3363 
   3364     /* register our callback to SYS HW manager */
   3365     bta_sys_hw_register(BTA_SYS_HW_BLUETOOTH, bta_dm_sys_hw_cback );
   3366 
   3367     /* send a message to BTA SYS */
   3368     sys_enable_event->hdr.event = BTA_SYS_API_DISABLE_EVT;
   3369     sys_enable_event->hw_module = BTA_SYS_HW_BLUETOOTH;
   3370     bta_sys_sendmsg(sys_enable_event);
   3371 
   3372     bta_dm_cb.disabling = FALSE;
   3373 }
   3374 
   3375 /*******************************************************************************
   3376 **
   3377 ** Function         bta_dm_rm_cback
   3378 **
   3379 ** Description      Role management callback from sys
   3380 **
   3381 **
   3382 ** Returns          void
   3383 **
   3384 *******************************************************************************/
   3385 static void bta_dm_rm_cback(tBTA_SYS_CONN_STATUS status, UINT8 id, UINT8 app_id, BD_ADDR peer_addr)
   3386 {
   3387     UINT8 j;
   3388     tBTA_PREF_ROLES role;
   3389     tBTA_DM_PEER_DEVICE *p_dev;
   3390 
   3391     p_dev = bta_dm_find_peer_device(peer_addr);
   3392     if( status == BTA_SYS_CONN_OPEN)
   3393     {
   3394         if(p_dev)
   3395         {
   3396             /* Do not set to connected if we are in the middle of unpairing. When AV stream is
   3397              * started it fakes out a SYS_CONN_OPEN to potentially trigger a role switch command.
   3398              * But this should not be done if we are in the middle of unpairing.
   3399              */
   3400             if (p_dev->conn_state != BTA_DM_UNPAIRING)
   3401                 p_dev->conn_state = BTA_DM_CONNECTED;
   3402 
   3403             for(j=1; j<= p_bta_dm_rm_cfg[0].app_id; j++)
   3404             {
   3405                 if(((p_bta_dm_rm_cfg[j].app_id == app_id) || (p_bta_dm_rm_cfg[j].app_id == BTA_ALL_APP_ID))
   3406                     && (p_bta_dm_rm_cfg[j].id == id))
   3407                 {
   3408                     role = p_bta_dm_rm_cfg[j].cfg;
   3409 
   3410                     if(role > p_dev->pref_role )
   3411                         p_dev->pref_role = role;
   3412                     break;
   3413                 }
   3414             }
   3415         }
   3416     }
   3417 
   3418     if((BTA_ID_AV == id)||(BTA_ID_AVK ==id))
   3419     {
   3420         if( status == BTA_SYS_CONN_BUSY)
   3421         {
   3422             if(p_dev)
   3423                 p_dev->info |= BTA_DM_DI_AV_ACTIVE;
   3424             /* AV calls bta_sys_conn_open with the A2DP stream count as app_id */
   3425             if(BTA_ID_AV == id)
   3426                 bta_dm_cb.cur_av_count = bta_dm_get_av_count();
   3427         }
   3428         else if( status == BTA_SYS_CONN_IDLE)
   3429         {
   3430             if(p_dev)
   3431                 p_dev->info &= ~BTA_DM_DI_AV_ACTIVE;
   3432 
   3433             /* get cur_av_count from connected services */
   3434             if(BTA_ID_AV == id)
   3435                 bta_dm_cb.cur_av_count = bta_dm_get_av_count();
   3436         }
   3437         APPL_TRACE_WARNING("bta_dm_rm_cback:%d, status:%d", bta_dm_cb.cur_av_count, status);
   3438     }
   3439 
   3440     /* Don't adjust roles for each busy/idle state transition to avoid
   3441        excessive switch requests when individual profile busy/idle status
   3442        changes */
   3443     if ((status != BTA_SYS_CONN_BUSY) && (status != BTA_SYS_CONN_IDLE))
   3444         bta_dm_adjust_roles(FALSE);
   3445 }
   3446 
   3447 /*******************************************************************************
   3448 **
   3449 ** Function         bta_dm_delay_role_switch_cback
   3450 **
   3451 ** Description      Callback from btm to delay a role switch
   3452 **
   3453 ** Returns          void
   3454 **
   3455 *******************************************************************************/
   3456 static void bta_dm_delay_role_switch_cback(UNUSED_ATTR void *data)
   3457 {
   3458     APPL_TRACE_EVENT("%s: initiating Delayed RS", __func__);
   3459     bta_dm_adjust_roles(FALSE);
   3460 }
   3461 
   3462 /*******************************************************************************
   3463 **
   3464 ** Function         bta_dm_reset_sec_dev_pending
   3465 **
   3466 ** Description      Setting the remove device pending status to FALSE from
   3467 **                  security device DB, when the link key notification
   3468 **                  event comes.
   3469 **
   3470 ** Returns          void
   3471 **
   3472 *******************************************************************************/
   3473 static void bta_dm_reset_sec_dev_pending(BD_ADDR remote_bd_addr)
   3474 {
   3475     for (size_t i = 0; i < bta_dm_cb.device_list.count; i++)
   3476     {
   3477         if (bdcmp(bta_dm_cb.device_list.peer_device[i].peer_bdaddr, remote_bd_addr) == 0)
   3478         {
   3479             bta_dm_cb.device_list.peer_device[i].remove_dev_pending = FALSE;
   3480             return;
   3481         }
   3482     }
   3483 }
   3484 
   3485 /*******************************************************************************
   3486 **
   3487 ** Function         bta_dm_remove_sec_dev_entry
   3488 **
   3489 ** Description      Removes device entry from Security device DB if ACL connection with
   3490 **                  remtoe device does not exist, else schedule for dev entry removal upon
   3491                      ACL close
   3492 **
   3493 ** Returns          void
   3494 **
   3495 *******************************************************************************/
   3496 static void bta_dm_remove_sec_dev_entry(BD_ADDR remote_bd_addr)
   3497 {
   3498     UINT16 index = 0;
   3499     if ( BTM_IsAclConnectionUp(remote_bd_addr, BT_TRANSPORT_LE) ||
   3500          BTM_IsAclConnectionUp(remote_bd_addr, BT_TRANSPORT_BR_EDR))
   3501     {
   3502          APPL_TRACE_DEBUG("%s ACL is not down. Schedule for  Dev Removal when ACL closes",
   3503                             __FUNCTION__);
   3504         for (index = 0; index < bta_dm_cb.device_list.count; index ++)
   3505         {
   3506             if (!bdcmp( bta_dm_cb.device_list.peer_device[index].peer_bdaddr, remote_bd_addr))
   3507                 break;
   3508         }
   3509         if (index != bta_dm_cb.device_list.count)
   3510         {
   3511             bta_dm_cb.device_list.peer_device[index].remove_dev_pending = TRUE;
   3512         }
   3513         else
   3514         {
   3515             APPL_TRACE_ERROR(" %s Device does not exist in DB", __FUNCTION__);
   3516         }
   3517     }
   3518     else
   3519     {
   3520         BTM_SecDeleteDevice (remote_bd_addr);
   3521 #if (BLE_INCLUDED == TRUE && BTA_GATT_INCLUDED == TRUE)
   3522         /* need to remove all pending background connection */
   3523         BTA_GATTC_CancelOpen(0, remote_bd_addr, FALSE);
   3524         /* remove all cached GATT information */
   3525         BTA_GATTC_Refresh(remote_bd_addr);
   3526 #endif
   3527     }
   3528 }
   3529 
   3530 
   3531 /*******************************************************************************
   3532 **
   3533 ** Function         bta_dm_adjust_roles
   3534 **
   3535 ** Description      Adjust roles
   3536 **
   3537 **
   3538 ** Returns          void
   3539 **
   3540 *******************************************************************************/
   3541 static void bta_dm_adjust_roles(BOOLEAN delay_role_switch)
   3542 {
   3543 
   3544     UINT8 i;
   3545     BOOLEAN set_master_role = FALSE;
   3546 #if BLE_INCLUDED == TRUE
   3547     UINT8 br_count = bta_dm_cb.device_list.count - bta_dm_cb.device_list.le_count;
   3548 #else
   3549     UINT8 br_count = bta_dm_cb.device_list.count;
   3550 #endif
   3551     if (br_count)
   3552     {
   3553 
   3554         /* the configuration is no scatternet
   3555          * or AV connection exists and there are more than one ACL link */
   3556         if ( (p_bta_dm_rm_cfg[0].cfg == BTA_DM_NO_SCATTERNET) ||
   3557              (bta_dm_cb.cur_av_count && br_count > 1) )
   3558         {
   3559 
   3560             L2CA_SetDesireRole (HCI_ROLE_MASTER);
   3561             set_master_role = TRUE;
   3562 
   3563         }
   3564 
   3565         for(i=0; i<bta_dm_cb.device_list.count; i++)
   3566         {
   3567             if (bta_dm_cb.device_list.peer_device[i].conn_state == BTA_DM_CONNECTED
   3568 #if BLE_INCLUDED == TRUE
   3569                 && bta_dm_cb.device_list.peer_device[i].transport == BT_TRANSPORT_BR_EDR
   3570 #endif
   3571                 )
   3572             {
   3573                 if(!set_master_role && (bta_dm_cb.device_list.peer_device[i].pref_role != BTA_ANY_ROLE)
   3574                     && (p_bta_dm_rm_cfg[0].cfg == BTA_DM_PARTIAL_SCATTERNET))
   3575                 {
   3576                     L2CA_SetDesireRole (HCI_ROLE_MASTER);
   3577                     set_master_role = TRUE;
   3578                 }
   3579 
   3580                 if((bta_dm_cb.device_list.peer_device[i].pref_role == BTA_MASTER_ROLE_ONLY)
   3581                     || (br_count > 1))
   3582                 {
   3583 
   3584                 /* Initiating immediate role switch with certain remote devices
   3585                   has caused issues due to role  switch colliding with link encryption setup and
   3586                   causing encryption (and in turn the link) to fail .  These device . Firmware
   3587                   versions are stored in a blacklist and role switch with these devices are
   3588                   delayed to avoid the collision with link encryption setup */
   3589 
   3590                     if (bta_dm_cb.device_list.peer_device[i].pref_role != BTA_SLAVE_ROLE_ONLY &&
   3591                             delay_role_switch == FALSE)
   3592                     {
   3593                         BTM_SwitchRole (bta_dm_cb.device_list.peer_device[i].peer_bdaddr,
   3594                                         HCI_ROLE_MASTER, NULL);
   3595                     }
   3596                     else
   3597                     {
   3598                         alarm_set_on_queue(bta_dm_cb.switch_delay_timer,
   3599                                            BTA_DM_SWITCH_DELAY_TIMER_MS,
   3600                                            bta_dm_delay_role_switch_cback,
   3601                                            NULL, btu_bta_alarm_queue);
   3602                     }
   3603                 }
   3604             }
   3605         }
   3606 
   3607 
   3608         if(!set_master_role)
   3609         {
   3610 
   3611             L2CA_SetDesireRole (L2CAP_DESIRED_LINK_ROLE);
   3612 
   3613         }
   3614 
   3615     }
   3616     else
   3617     {
   3618         L2CA_SetDesireRole (L2CAP_DESIRED_LINK_ROLE);
   3619     }
   3620 
   3621 
   3622 }
   3623 
   3624 /*******************************************************************************
   3625 **
   3626 ** Function         bta_dm_get_remname
   3627 **
   3628 ** Description      Returns a pointer to the remote name stored in the DM control
   3629 **                  block if it exists, or from the BTM memory.
   3630 **
   3631 ** Returns          char * - Pointer to the remote device name
   3632 *******************************************************************************/
   3633 static char *bta_dm_get_remname(void)
   3634 {
   3635     char *p_name = (char *)bta_dm_search_cb.peer_name;
   3636     char *p_temp;
   3637 
   3638     /* If the name isn't already stored, try retrieving from BTM */
   3639     if (*p_name == '\0')
   3640         if ((p_temp = BTM_SecReadDevName(bta_dm_search_cb.peer_bdaddr)) != NULL)
   3641             p_name = p_temp;
   3642 
   3643     return p_name;
   3644 }
   3645 
   3646 /*******************************************************************************
   3647 **
   3648 ** Function         bta_dm_bond_cancel_complete_cback
   3649 **
   3650 ** Description      Authentication complete callback from BTM
   3651 **
   3652 ** Returns          void
   3653 **
   3654 *******************************************************************************/
   3655 static void bta_dm_bond_cancel_complete_cback(tBTM_STATUS result)
   3656 {
   3657 
   3658     tBTA_DM_SEC sec_event;
   3659 
   3660     if (result == BTM_SUCCESS)
   3661         sec_event.bond_cancel_cmpl.result = BTA_SUCCESS;
   3662     else
   3663         sec_event.bond_cancel_cmpl.result = BTA_FAILURE;
   3664 
   3665     if(bta_dm_cb.p_sec_cback)
   3666     {
   3667         bta_dm_cb.p_sec_cback(BTA_DM_BOND_CANCEL_CMPL_EVT, &sec_event);
   3668     }
   3669 }
   3670 
   3671 /*******************************************************************************
   3672 **
   3673 ** Function         find_utf8_char_boundary
   3674 **
   3675 ** Description      This function checks a UTF8 string |utf8str| starting at
   3676 **                  |offset|, moving backwards and returns the offset of the
   3677 **                  next valid UTF8 character boundary found.
   3678 **
   3679 ** Returns          Offset of UTF8 character boundary
   3680 **
   3681 *******************************************************************************/
   3682 static size_t find_utf8_char_boundary(const char *utf8str, size_t offset)
   3683 {
   3684     assert(utf8str);
   3685     assert(offset > 0);
   3686 
   3687     while (--offset)
   3688     {
   3689         uint8_t ch = (uint8_t)utf8str[offset];
   3690         if ((ch & 0x80) == 0x00) // ASCII
   3691             return offset + 1;
   3692         if ((ch & 0xC0) == 0xC0) // Multi-byte sequence start
   3693             return offset;
   3694     }
   3695 
   3696     return 0;
   3697 }
   3698 
   3699 /*******************************************************************************
   3700 **
   3701 ** Function         bta_dm_set_eir
   3702 **
   3703 ** Description      This function creates EIR tagged data and writes it to controller.
   3704 **
   3705 ** Returns          None
   3706 **
   3707 *******************************************************************************/
   3708 static void bta_dm_set_eir (char *local_name)
   3709 {
   3710     UINT8    *p;
   3711     UINT8    *p_length;
   3712 #if (BTA_EIR_CANNED_UUID_LIST != TRUE)
   3713     UINT8    *p_type;
   3714     UINT8    max_num_uuid;
   3715 #if (BTA_EIR_SERVER_NUM_CUSTOM_UUID > 0)
   3716     UINT8    custom_uuid_idx;
   3717 #endif  // BTA_EIR_SERVER_NUM_CUSTOM_UUID
   3718 #endif  // BTA_EIR_CANNED_UUID_LIST
   3719 #if (BTM_EIR_DEFAULT_FEC_REQUIRED == FALSE)
   3720     UINT8    free_eir_length = HCI_EXT_INQ_RESPONSE_LEN;
   3721 #else  // BTM_EIR_DEFAULT_FEC_REQUIRED
   3722     UINT8    free_eir_length = HCI_DM5_PACKET_SIZE;
   3723 #endif  // BTM_EIR_DEFAULT_FEC_REQUIRED
   3724     UINT8    num_uuid;
   3725     UINT8    data_type;
   3726     UINT8    local_name_len;
   3727 
   3728     /* wait until complete to disable */
   3729     if (alarm_is_scheduled(bta_dm_cb.disable_timer))
   3730         return;
   3731 
   3732 #if ( BTA_EIR_CANNED_UUID_LIST != TRUE )
   3733     /* if local name is not provided, get it from controller */
   3734     if( local_name == NULL )
   3735     {
   3736         if( BTM_ReadLocalDeviceName( &local_name ) != BTM_SUCCESS )
   3737         {
   3738             APPL_TRACE_ERROR("Fail to read local device name for EIR");
   3739         }
   3740     }
   3741 #endif  // BTA_EIR_CANNED_UUID_LIST
   3742 
   3743     /* Allocate a buffer to hold HCI command */
   3744     BT_HDR *p_buf = (BT_HDR *)osi_malloc(BTM_CMD_BUF_SIZE);
   3745     p = (UINT8 *)p_buf + BTM_HCI_EIR_OFFSET;
   3746 
   3747     memset(p, 0x00, HCI_EXT_INQ_RESPONSE_LEN );
   3748 
   3749     APPL_TRACE_DEBUG("BTA is generating EIR");
   3750 
   3751     if( local_name )
   3752         local_name_len = strlen( local_name );
   3753     else
   3754         local_name_len = 0;
   3755 
   3756     data_type = BTM_EIR_COMPLETE_LOCAL_NAME_TYPE;
   3757     /* if local name is longer than minimum length of shortened name */
   3758     /* check whether it needs to be shortened or not */
   3759     if( local_name_len > p_bta_dm_eir_cfg->bta_dm_eir_min_name_len )
   3760     {
   3761         /* get number of UUID 16-bit list */
   3762 #if (BTA_EIR_CANNED_UUID_LIST == TRUE)
   3763         num_uuid = p_bta_dm_eir_cfg->bta_dm_eir_uuid16_len/LEN_UUID_16;
   3764 #else  // BTA_EIR_CANNED_UUID_LIST
   3765         max_num_uuid = (free_eir_length - 2)/LEN_UUID_16;
   3766         data_type = BTM_GetEirSupportedServices( bta_dm_cb.eir_uuid, &p,
   3767                                                  max_num_uuid, &num_uuid );
   3768         p = (UINT8 *)p_buf + BTM_HCI_EIR_OFFSET; /* reset p */
   3769 #endif  // BTA_EIR_CANNED_UUID_LIST
   3770 
   3771         /* if UUID doesn't fit remaing space, shorten local name */
   3772         if (local_name_len > (free_eir_length - 4 - num_uuid*LEN_UUID_16))
   3773         {
   3774             local_name_len = find_utf8_char_boundary(local_name,
   3775                 p_bta_dm_eir_cfg->bta_dm_eir_min_name_len);
   3776             APPL_TRACE_WARNING("%s local name is shortened (%d)", __func__, local_name_len);
   3777             data_type = BTM_EIR_SHORTENED_LOCAL_NAME_TYPE;
   3778         } else {
   3779             data_type = BTM_EIR_COMPLETE_LOCAL_NAME_TYPE;
   3780         }
   3781     }
   3782 
   3783     UINT8_TO_STREAM(p, local_name_len + 1);
   3784     UINT8_TO_STREAM(p, data_type);
   3785 
   3786     if (local_name != NULL)
   3787     {
   3788         memcpy(p, local_name, local_name_len);
   3789         p += local_name_len;
   3790     }
   3791     free_eir_length -= local_name_len + 2;
   3792 
   3793 #if (BTA_EIR_CANNED_UUID_LIST == TRUE)
   3794     /* if UUID list is provided as static data in configuration */
   3795     if(( p_bta_dm_eir_cfg->bta_dm_eir_uuid16_len > 0 )
   3796         &&(p_bta_dm_eir_cfg->bta_dm_eir_uuid16))
   3797     {
   3798         if( free_eir_length > LEN_UUID_16 + 2)
   3799         {
   3800             free_eir_length -= 2;
   3801 
   3802             if( free_eir_length >= p_bta_dm_eir_cfg->bta_dm_eir_uuid16_len)
   3803             {
   3804                 num_uuid = p_bta_dm_eir_cfg->bta_dm_eir_uuid16_len / LEN_UUID_16;
   3805                 data_type = BTM_EIR_COMPLETE_16BITS_UUID_TYPE;
   3806             }
   3807             else /* not enough room for all UUIDs */
   3808             {
   3809                 APPL_TRACE_WARNING("BTA EIR: UUID 16-bit list is truncated");
   3810                 num_uuid = free_eir_length / LEN_UUID_16;
   3811                 data_type = BTM_EIR_MORE_16BITS_UUID_TYPE;
   3812             }
   3813             UINT8_TO_STREAM(p, num_uuid * LEN_UUID_16 + 1);
   3814             UINT8_TO_STREAM(p, data_type);
   3815             memcpy(p, p_bta_dm_eir_cfg->bta_dm_eir_uuid16, num_uuid * LEN_UUID_16 );
   3816             p += num_uuid * LEN_UUID_16;
   3817             free_eir_length -= num_uuid * LEN_UUID_16;
   3818         }
   3819     }
   3820 #else /* (BTA_EIR_CANNED_UUID_LIST == TRUE) */
   3821     /* if UUID list is dynamic */
   3822     if ( free_eir_length >= 2)
   3823     {
   3824         p_length = p++;
   3825         p_type   = p++;
   3826         num_uuid = 0;
   3827 
   3828         max_num_uuid = (free_eir_length - 2)/LEN_UUID_16;
   3829         data_type = BTM_GetEirSupportedServices( bta_dm_cb.eir_uuid, &p, max_num_uuid, &num_uuid );
   3830 
   3831         if( data_type == BTM_EIR_MORE_16BITS_UUID_TYPE )
   3832         {
   3833             APPL_TRACE_WARNING("BTA EIR: UUID 16-bit list is truncated");
   3834         }
   3835 #if (BTA_EIR_SERVER_NUM_CUSTOM_UUID > 0)
   3836         else
   3837         {
   3838             for (custom_uuid_idx = 0; custom_uuid_idx < BTA_EIR_SERVER_NUM_CUSTOM_UUID; custom_uuid_idx++)
   3839             {
   3840                 if (bta_dm_cb.custom_uuid[custom_uuid_idx].len == LEN_UUID_16)
   3841                 {
   3842                     if ( num_uuid < max_num_uuid )
   3843                     {
   3844                         UINT16_TO_STREAM(p, bta_dm_cb.custom_uuid[custom_uuid_idx].uu.uuid16);
   3845                         num_uuid++;
   3846                     }
   3847                     else
   3848                     {
   3849                         data_type = BTM_EIR_MORE_16BITS_UUID_TYPE;
   3850                         APPL_TRACE_WARNING("BTA EIR: UUID 16-bit list is truncated");
   3851                         break;
   3852                     }
   3853                 }
   3854             }
   3855         }
   3856 #endif /* (BTA_EIR_SERVER_NUM_CUSTOM_UUID > 0) */
   3857 
   3858         UINT8_TO_STREAM(p_length, num_uuid * LEN_UUID_16 + 1);
   3859         UINT8_TO_STREAM(p_type, data_type);
   3860         free_eir_length -= num_uuid * LEN_UUID_16 + 2;
   3861     }
   3862 #endif /* (BTA_EIR_CANNED_UUID_LIST == TRUE) */
   3863 
   3864 #if ( BTA_EIR_CANNED_UUID_LIST != TRUE )&&(BTA_EIR_SERVER_NUM_CUSTOM_UUID > 0)
   3865     /* Adding 32-bit UUID list */
   3866     if ( free_eir_length >= 2)
   3867     {
   3868         p_length = p++;
   3869         p_type   = p++;
   3870         num_uuid = 0;
   3871         data_type = BTM_EIR_COMPLETE_32BITS_UUID_TYPE;
   3872 
   3873         max_num_uuid = (free_eir_length - 2)/LEN_UUID_32;
   3874 
   3875         for (custom_uuid_idx = 0; custom_uuid_idx < BTA_EIR_SERVER_NUM_CUSTOM_UUID; custom_uuid_idx++)
   3876         {
   3877             if (bta_dm_cb.custom_uuid[custom_uuid_idx].len == LEN_UUID_32)
   3878             {
   3879                 if ( num_uuid < max_num_uuid )
   3880                 {
   3881                     UINT32_TO_STREAM(p, bta_dm_cb.custom_uuid[custom_uuid_idx].uu.uuid32);
   3882                     num_uuid++;
   3883                 }
   3884                 else
   3885                 {
   3886                     data_type = BTM_EIR_MORE_32BITS_UUID_TYPE;
   3887                     APPL_TRACE_WARNING("BTA EIR: UUID 32-bit list is truncated");
   3888                     break;
   3889                 }
   3890             }
   3891         }
   3892 
   3893         UINT8_TO_STREAM(p_length, num_uuid * LEN_UUID_32 + 1);
   3894         UINT8_TO_STREAM(p_type, data_type);
   3895         free_eir_length -= num_uuid * LEN_UUID_32 + 2;
   3896     }
   3897 
   3898     /* Adding 128-bit UUID list */
   3899     if ( free_eir_length >= 2)
   3900     {
   3901         p_length = p++;
   3902         p_type   = p++;
   3903         num_uuid = 0;
   3904         data_type = BTM_EIR_COMPLETE_128BITS_UUID_TYPE;
   3905 
   3906         max_num_uuid = (free_eir_length - 2)/LEN_UUID_128;
   3907 
   3908         for (custom_uuid_idx = 0; custom_uuid_idx < BTA_EIR_SERVER_NUM_CUSTOM_UUID; custom_uuid_idx++)
   3909         {
   3910             if (bta_dm_cb.custom_uuid[custom_uuid_idx].len == LEN_UUID_128)
   3911             {
   3912                 if ( num_uuid < max_num_uuid )
   3913                 {
   3914                     ARRAY16_TO_STREAM(p, bta_dm_cb.custom_uuid[custom_uuid_idx].uu.uuid128);
   3915                     num_uuid++;
   3916                 }
   3917                 else
   3918                 {
   3919                     data_type = BTM_EIR_MORE_128BITS_UUID_TYPE;
   3920                     APPL_TRACE_WARNING("BTA EIR: UUID 128-bit list is truncated");
   3921                     break;
   3922                 }
   3923             }
   3924         }
   3925 
   3926         UINT8_TO_STREAM(p_length, num_uuid * LEN_UUID_128 + 1);
   3927         UINT8_TO_STREAM(p_type, data_type);
   3928         free_eir_length -= num_uuid * LEN_UUID_128 + 2;
   3929     }
   3930 #endif /* ( BTA_EIR_CANNED_UUID_LIST != TRUE )&&(BTA_EIR_SERVER_NUM_CUSTOM_UUID > 0) */
   3931 
   3932     /* if Flags are provided in configuration */
   3933     if(( p_bta_dm_eir_cfg->bta_dm_eir_flag_len > 0 )
   3934      &&( p_bta_dm_eir_cfg->bta_dm_eir_flags )
   3935      &&( free_eir_length >= p_bta_dm_eir_cfg->bta_dm_eir_flag_len + 2 ))
   3936     {
   3937         UINT8_TO_STREAM(p, p_bta_dm_eir_cfg->bta_dm_eir_flag_len + 1);
   3938         UINT8_TO_STREAM(p, BTM_EIR_FLAGS_TYPE);
   3939         memcpy(p, p_bta_dm_eir_cfg->bta_dm_eir_flags,
   3940                p_bta_dm_eir_cfg->bta_dm_eir_flag_len);
   3941         p += p_bta_dm_eir_cfg->bta_dm_eir_flag_len;
   3942         free_eir_length -= p_bta_dm_eir_cfg->bta_dm_eir_flag_len + 2;
   3943     }
   3944 
   3945     /* if Manufacturer Specific are provided in configuration */
   3946     if(( p_bta_dm_eir_cfg->bta_dm_eir_manufac_spec_len > 0 )
   3947      &&( p_bta_dm_eir_cfg->bta_dm_eir_manufac_spec )
   3948      &&( free_eir_length >= p_bta_dm_eir_cfg->bta_dm_eir_manufac_spec_len + 2 ))
   3949     {
   3950         p_length = p;
   3951 
   3952         UINT8_TO_STREAM(p, p_bta_dm_eir_cfg->bta_dm_eir_manufac_spec_len + 1);
   3953         UINT8_TO_STREAM(p, BTM_EIR_MANUFACTURER_SPECIFIC_TYPE);
   3954         memcpy(p, p_bta_dm_eir_cfg->bta_dm_eir_manufac_spec,
   3955                p_bta_dm_eir_cfg->bta_dm_eir_manufac_spec_len);
   3956         p += p_bta_dm_eir_cfg->bta_dm_eir_manufac_spec_len;
   3957         free_eir_length -= p_bta_dm_eir_cfg->bta_dm_eir_manufac_spec_len + 2;
   3958 
   3959     }
   3960     else
   3961     {
   3962         p_length = NULL;
   3963     }
   3964 
   3965     /* if Inquiry Tx Resp Power compiled */
   3966     if ((p_bta_dm_eir_cfg->bta_dm_eir_inq_tx_power) &&
   3967         (free_eir_length >= 3))
   3968     {
   3969         UINT8_TO_STREAM(p, 2);      /* Length field */
   3970         UINT8_TO_STREAM(p, BTM_EIR_TX_POWER_LEVEL_TYPE);
   3971         UINT8_TO_STREAM(p, *(p_bta_dm_eir_cfg->bta_dm_eir_inq_tx_power));
   3972         free_eir_length -= 3;
   3973     }
   3974 
   3975     if( free_eir_length )
   3976         UINT8_TO_STREAM(p, 0); /* terminator of significant part */
   3977 
   3978     BTM_WriteEIR( p_buf );
   3979 
   3980 }
   3981 
   3982 /*******************************************************************************
   3983 **
   3984 ** Function         bta_dm_eir_search_services
   3985 **
   3986 ** Description      This function searches services in received EIR
   3987 **
   3988 ** Returns          None
   3989 **
   3990 *******************************************************************************/
   3991 static void bta_dm_eir_search_services( tBTM_INQ_RESULTS  *p_result,
   3992                                         tBTA_SERVICE_MASK *p_services_to_search,
   3993                                         tBTA_SERVICE_MASK *p_services_found)
   3994 {
   3995     tBTA_SERVICE_MASK       service_index = 0;
   3996     tBTM_EIR_SEARCH_RESULT  result;
   3997 
   3998     APPL_TRACE_DEBUG("BTA searching services in EIR of BDA:0x%02X%02X%02X%02X%02X%02X",
   3999                         p_result->remote_bd_addr[0],p_result->remote_bd_addr[1],
   4000                         p_result->remote_bd_addr[2],p_result->remote_bd_addr[3],
   4001                         p_result->remote_bd_addr[4],p_result->remote_bd_addr[5]);
   4002 
   4003     APPL_TRACE_DEBUG("    with services_to_search=0x%08X", *p_services_to_search);
   4004 
   4005 #if BLE_INCLUDED == TRUE && BTA_GATT_INCLUDED == TRUE
   4006     /* always do GATT based service discovery by SDP instead of from EIR    */
   4007     /* if GATT based service is also to be put in EIR, need to modify this  */
   4008     while (service_index < (BTA_MAX_SERVICE_ID - 1))
   4009 #else
   4010     while(service_index < BTA_MAX_SERVICE_ID)
   4011 #endif
   4012     {
   4013         if( *p_services_to_search
   4014            & (tBTA_SERVICE_MASK)(BTA_SERVICE_ID_TO_SERVICE_MASK(service_index)))
   4015         {
   4016             result = BTM_HasInquiryEirService( p_result,
   4017                                                bta_service_id_to_uuid_lkup_tbl[service_index] );
   4018 
   4019             /* Searching for HSP v1.2 only device */
   4020             if ((result != BTM_EIR_FOUND) &&
   4021                 (bta_service_id_to_uuid_lkup_tbl[service_index] == UUID_SERVCLASS_HEADSET))
   4022             {
   4023                 result = BTM_HasInquiryEirService (p_result, UUID_SERVCLASS_HEADSET_HS);
   4024             }
   4025 
   4026             if( result == BTM_EIR_FOUND )
   4027             {
   4028                 /* If Plug and Play service record, need to check to see if Broadcom stack */
   4029                 /* However, EIR data doesn't have EXT_BRCM_VERSION so just skip it */
   4030                 if( bta_service_id_to_uuid_lkup_tbl[service_index]
   4031                     != UUID_SERVCLASS_PNP_INFORMATION )
   4032                 {
   4033 
   4034                     *p_services_found |=
   4035                        (tBTA_SERVICE_MASK)(BTA_SERVICE_ID_TO_SERVICE_MASK(service_index));
   4036                     /* remove the service from services to be searched  */
   4037                     *p_services_to_search &=
   4038                        (tBTA_SERVICE_MASK)(~(BTA_SERVICE_ID_TO_SERVICE_MASK(service_index)));
   4039                 }
   4040             }
   4041             else if( result == BTM_EIR_NOT_FOUND )
   4042             {
   4043                 /* remove the service from services to be searched  */
   4044                 *p_services_to_search &=
   4045                        (tBTA_SERVICE_MASK)(~(BTA_SERVICE_ID_TO_SERVICE_MASK(service_index)));
   4046             }
   4047         }
   4048 
   4049         service_index++;
   4050     }
   4051 
   4052     APPL_TRACE_ERROR("BTA EIR search result, services_to_search=0x%08X, services_found=0x%08X",
   4053                         *p_services_to_search, *p_services_found);
   4054 }
   4055 
   4056 #if (BTA_EIR_CANNED_UUID_LIST != TRUE)
   4057 /*******************************************************************************
   4058 **
   4059 ** Function         bta_dm_eir_update_uuid
   4060 **
   4061 ** Description      This function adds or removes service UUID in EIR database.
   4062 **
   4063 ** Returns          None
   4064 **
   4065 *******************************************************************************/
   4066 void bta_dm_eir_update_uuid(UINT16 uuid16, BOOLEAN adding)
   4067 {
   4068     /* if this UUID is not advertised in EIR */
   4069     if( !BTM_HasEirService( p_bta_dm_eir_cfg->uuid_mask, uuid16 ))
   4070         return;
   4071 
   4072     if( adding )
   4073     {
   4074         APPL_TRACE_EVENT("Adding UUID=0x%04X into EIR", uuid16);
   4075 
   4076         BTM_AddEirService( bta_dm_cb.eir_uuid, uuid16 );
   4077     }
   4078     else
   4079     {
   4080         APPL_TRACE_EVENT("Removing UUID=0x%04X from EIR", uuid16);
   4081 
   4082         BTM_RemoveEirService( bta_dm_cb.eir_uuid, uuid16 );
   4083     }
   4084 
   4085     bta_dm_set_eir (NULL);
   4086 
   4087     APPL_TRACE_EVENT("bta_dm_eir_update_uuid UUID bit mask=0x%08X %08X",
   4088                        bta_dm_cb.eir_uuid[1], bta_dm_cb.eir_uuid[0] );
   4089 }
   4090 #endif
   4091 
   4092 /*******************************************************************************
   4093 **
   4094 ** Function         bta_dm_enable_test_mode
   4095 **
   4096 ** Description      enable test mode
   4097 **
   4098 **
   4099 ** Returns          void
   4100 **
   4101 *******************************************************************************/
   4102 void bta_dm_enable_test_mode(tBTA_DM_MSG *p_data)
   4103 {
   4104     UNUSED(p_data);
   4105     BTM_EnableTestMode();
   4106 }
   4107 
   4108 /*******************************************************************************
   4109 **
   4110 ** Function         bta_dm_disable_test_mode
   4111 **
   4112 ** Description      disable test mode
   4113 **
   4114 **
   4115 ** Returns          void
   4116 **
   4117 *******************************************************************************/
   4118 void bta_dm_disable_test_mode(tBTA_DM_MSG *p_data)
   4119 {
   4120     UNUSED(p_data);
   4121     BTM_DeviceReset(NULL);
   4122 }
   4123 
   4124 /*******************************************************************************
   4125 **
   4126 ** Function         bta_dm_execute_callback
   4127 **
   4128 ** Description      Just execute a generic call back in the context of the BTU/BTA tack
   4129 **
   4130 **
   4131 ** Returns          void
   4132 **
   4133 *******************************************************************************/
   4134 void bta_dm_execute_callback(tBTA_DM_MSG *p_data)
   4135 {
   4136     /* sanity check */
   4137     if(p_data->exec_cback.p_exec_cback == NULL)
   4138     {
   4139         return;
   4140     }
   4141 
   4142     p_data->exec_cback.p_exec_cback(p_data->exec_cback.p_param);
   4143 }
   4144 
   4145 /*******************************************************************************
   4146 **
   4147 ** Function         bta_dm_encrypt_cback
   4148 **
   4149 ** Description      link encryption complete callback.
   4150 **
   4151 ** Returns         None
   4152 **
   4153 *******************************************************************************/
   4154 void bta_dm_encrypt_cback(BD_ADDR bd_addr, tBT_TRANSPORT transport, void *p_ref_data, tBTM_STATUS result)
   4155 {
   4156     tBTA_STATUS   bta_status = BTA_SUCCESS;
   4157     tBTA_DM_ENCRYPT_CBACK *p_callback = NULL;
   4158     UINT8   i ;
   4159     UNUSED(p_ref_data);
   4160 
   4161     for (i=0; i<bta_dm_cb.device_list.count; i++)
   4162     {
   4163         if (bdcmp( bta_dm_cb.device_list.peer_device[i].peer_bdaddr, bd_addr) == 0 &&
   4164             bta_dm_cb.device_list.peer_device[i].conn_state == BTA_DM_CONNECTED)
   4165             break;
   4166     }
   4167 
   4168     if (i < bta_dm_cb.device_list.count)
   4169     {
   4170         p_callback = bta_dm_cb.device_list.peer_device[i].p_encrypt_cback;
   4171         bta_dm_cb.device_list.peer_device[i].p_encrypt_cback = NULL;
   4172     }
   4173 
   4174     switch (result)
   4175     {
   4176         case BTM_SUCCESS:
   4177             break;
   4178         case BTM_WRONG_MODE:
   4179             bta_status = BTA_WRONG_MODE;
   4180             break;
   4181         case BTM_NO_RESOURCES:
   4182             bta_status = BTA_NO_RESOURCES;
   4183             break;
   4184         case BTM_BUSY:
   4185             bta_status = BTA_BUSY;
   4186             break;
   4187         default:
   4188             bta_status = BTA_FAILURE;
   4189             break;
   4190     }
   4191 
   4192     APPL_TRACE_DEBUG("bta_dm_encrypt_cback status =%d p_callback=0x%x", bta_status, p_callback);
   4193 
   4194     if (p_callback)
   4195     {
   4196         (*p_callback)(bd_addr, transport, bta_status);
   4197     }
   4198 }
   4199 
   4200 /*******************************************************************************
   4201 **
   4202 ** Function         bta_dm_set_encryption
   4203 **
   4204 ** Description      This function to encrypt the link
   4205 **
   4206 ** Returns          None
   4207 **
   4208 *******************************************************************************/
   4209 void bta_dm_set_encryption (tBTA_DM_MSG *p_data)
   4210 {
   4211     UINT8 i ;
   4212 
   4213     APPL_TRACE_DEBUG("bta_dm_set_encryption"); //todo
   4214     if (!p_data->set_encryption.p_callback)
   4215     {
   4216         APPL_TRACE_ERROR("bta_dm_set_encryption callback is not provided");
   4217         return;
   4218     }
   4219     for (i=0; i<bta_dm_cb.device_list.count; i++)
   4220     {
   4221         if (bdcmp( bta_dm_cb.device_list.peer_device[i].peer_bdaddr, p_data->set_encryption.bd_addr) == 0 &&
   4222             bta_dm_cb.device_list.peer_device[i].conn_state == BTA_DM_CONNECTED)
   4223             break;
   4224     }
   4225     if (i < bta_dm_cb.device_list.count)
   4226     {
   4227         if (bta_dm_cb.device_list.peer_device[i].p_encrypt_cback)
   4228         {
   4229             APPL_TRACE_ERROR("earlier enc was not done for same device");
   4230             (*p_data->set_encryption.p_callback)(p_data->set_encryption.bd_addr,
   4231                                              p_data->set_encryption.transport,
   4232                                              BTA_BUSY);
   4233             return;
   4234         }
   4235 
   4236         if (BTM_SetEncryption(p_data->set_encryption.bd_addr, p_data->set_encryption.transport,
   4237                               bta_dm_encrypt_cback, NULL, p_data->set_encryption.sec_act)
   4238                               == BTM_CMD_STARTED)
   4239         {
   4240             bta_dm_cb.device_list.peer_device[i].p_encrypt_cback = p_data->set_encryption.p_callback;
   4241         }
   4242     }
   4243 }
   4244 
   4245 #if (BLE_INCLUDED == TRUE)
   4246 /*******************************************************************************
   4247 **
   4248 ** Function         bta_dm_observe_results_cb
   4249 **
   4250 ** Description      Callback for BLE Observe result
   4251 **
   4252 **
   4253 ** Returns          void
   4254 **
   4255 *******************************************************************************/
   4256 static void bta_dm_observe_results_cb (tBTM_INQ_RESULTS *p_inq, UINT8 *p_eir)
   4257 {
   4258 ;
   4259     tBTA_DM_SEARCH     result;
   4260     tBTM_INQ_INFO      *p_inq_info;
   4261     APPL_TRACE_DEBUG("bta_dm_observe_results_cb")
   4262 
   4263     bdcpy(result.inq_res.bd_addr, p_inq->remote_bd_addr);
   4264     result.inq_res.rssi = p_inq->rssi;
   4265     result.inq_res.ble_addr_type    = p_inq->ble_addr_type;
   4266     result.inq_res.inq_result_type  = p_inq->inq_result_type;
   4267     result.inq_res.device_type      = p_inq->device_type;
   4268     result.inq_res.flag             = p_inq->flag;
   4269 
   4270     /* application will parse EIR to find out remote device name */
   4271     result.inq_res.p_eir = p_eir;
   4272 
   4273     if((p_inq_info = BTM_InqDbRead(p_inq->remote_bd_addr)) != NULL)
   4274     {
   4275         /* initialize remt_name_not_required to FALSE so that we get the name by default */
   4276         result.inq_res.remt_name_not_required = FALSE;
   4277     }
   4278 
   4279     if(bta_dm_search_cb.p_scan_cback)
   4280         bta_dm_search_cb.p_scan_cback(BTA_DM_INQ_RES_EVT, &result);
   4281 
   4282     if(p_inq_info)
   4283     {
   4284         /* application indicates if it knows the remote name, inside the callback
   4285          copy that to the inquiry data base*/
   4286         if(result.inq_res.remt_name_not_required)
   4287             p_inq_info->appl_knows_rem_name = TRUE;
   4288     }
   4289 }
   4290 
   4291 /*******************************************************************************
   4292 **
   4293 ** Function         bta_dm_observe_cmpl_cb
   4294 **
   4295 ** Description      Callback for BLE Observe complete
   4296 **
   4297 **
   4298 ** Returns          void
   4299 **
   4300 *******************************************************************************/
   4301 static void bta_dm_observe_cmpl_cb (void * p_result)
   4302 {
   4303     tBTA_DM_SEARCH  data;
   4304 
   4305     APPL_TRACE_DEBUG("bta_dm_observe_cmpl_cb");
   4306 
   4307     data.inq_cmpl.num_resps = ((tBTM_INQUIRY_CMPL *)p_result)->num_resp;
   4308     if (bta_dm_search_cb.p_scan_cback)
   4309     {
   4310         bta_dm_search_cb.p_scan_cback(BTA_DM_INQ_CMPL_EVT, &data);
   4311     }
   4312 }
   4313 
   4314 #if (SMP_INCLUDED == TRUE)
   4315 /*******************************************************************************
   4316 **
   4317 ** Function         bta_dm_ble_smp_cback
   4318 **
   4319 ** Description      Callback for BLE SMP
   4320 **
   4321 **
   4322 ** Returns          void
   4323 **
   4324 *******************************************************************************/
   4325 static UINT8 bta_dm_ble_smp_cback (tBTM_LE_EVT event, BD_ADDR bda, tBTM_LE_EVT_DATA *p_data)
   4326 {
   4327     tBTM_STATUS status = BTM_SUCCESS;
   4328     tBTA_DM_SEC sec_event;
   4329     char *p_name = NULL;
   4330 
   4331     if (!bta_dm_cb.p_sec_cback)
   4332         return BTM_NOT_AUTHORIZED;
   4333 
   4334     memset(&sec_event, 0, sizeof(tBTA_DM_SEC));
   4335     switch (event)
   4336     {
   4337         case BTM_LE_IO_REQ_EVT:
   4338 #if (BTM_LOCAL_IO_CAPS != BTM_IO_CAP_NONE)
   4339 
   4340             bta_dm_co_ble_io_req(bda,
   4341                                  &p_data->io_req.io_cap,
   4342                                  &p_data->io_req.oob_data,
   4343                                  &p_data->io_req.auth_req,
   4344                                  &p_data->io_req.max_key_size,
   4345                                  &p_data->io_req.init_keys,
   4346                                  &p_data->io_req.resp_keys);
   4347 #endif
   4348             APPL_TRACE_EVENT("io mitm: %d oob_data:%d", p_data->io_req.auth_req, p_data->io_req.oob_data);
   4349 
   4350             break;
   4351 
   4352         case BTM_LE_SEC_REQUEST_EVT:
   4353             bdcpy(sec_event.ble_req.bd_addr, bda);
   4354             p_name = BTM_SecReadDevName(bda);
   4355             if (p_name != NULL)
   4356                 strlcpy((char*)sec_event.ble_req.bd_name, p_name, BD_NAME_LEN);
   4357             else
   4358                 sec_event.ble_req.bd_name[0] = 0;
   4359             bta_dm_cb.p_sec_cback(BTA_DM_BLE_SEC_REQ_EVT, &sec_event);
   4360             break;
   4361 
   4362         case BTM_LE_KEY_NOTIF_EVT:
   4363             bdcpy(sec_event.key_notif.bd_addr, bda);
   4364             p_name = BTM_SecReadDevName(bda);
   4365             if (p_name != NULL)
   4366                 strlcpy((char*)sec_event.key_notif.bd_name, p_name, BD_NAME_LEN);
   4367             else
   4368                 sec_event.key_notif.bd_name[0] = 0;
   4369             sec_event.key_notif.passkey = p_data->key_notif;
   4370             bta_dm_cb.p_sec_cback(BTA_DM_BLE_PASSKEY_NOTIF_EVT, &sec_event);
   4371             break;
   4372 
   4373         case BTM_LE_KEY_REQ_EVT:
   4374             bdcpy(sec_event.ble_req.bd_addr, bda);
   4375             bta_dm_cb.p_sec_cback(BTA_DM_BLE_PASSKEY_REQ_EVT, &sec_event);
   4376             break;
   4377 
   4378         case BTM_LE_OOB_REQ_EVT:
   4379             bdcpy(sec_event.ble_req.bd_addr, bda);
   4380             bta_dm_cb.p_sec_cback(BTA_DM_BLE_OOB_REQ_EVT, &sec_event);
   4381             break;
   4382 
   4383         case BTM_LE_NC_REQ_EVT:
   4384             bdcpy(sec_event.key_notif.bd_addr, bda);
   4385             strlcpy((char*)sec_event.key_notif.bd_name, bta_dm_get_remname(), (BD_NAME_LEN));
   4386             sec_event.key_notif.passkey = p_data->key_notif;
   4387             bta_dm_cb.p_sec_cback(BTA_DM_BLE_NC_REQ_EVT, &sec_event);
   4388             break;
   4389 
   4390         case BTM_LE_KEY_EVT:
   4391             bdcpy(sec_event.ble_key.bd_addr, bda);
   4392             sec_event.ble_key.key_type = p_data->key.key_type;
   4393             sec_event.ble_key.p_key_value = p_data->key.p_key_value;
   4394             bta_dm_cb.p_sec_cback(BTA_DM_BLE_KEY_EVT, &sec_event);
   4395             break;
   4396 
   4397         case BTM_LE_COMPLT_EVT:
   4398             bdcpy(sec_event.auth_cmpl.bd_addr, bda);
   4399 #if BLE_INCLUDED == TRUE
   4400             BTM_ReadDevInfo(bda, &sec_event.auth_cmpl.dev_type, &sec_event.auth_cmpl.addr_type);
   4401 #endif
   4402             p_name = BTM_SecReadDevName(bda);
   4403             if (p_name != NULL)
   4404                 strlcpy((char*)sec_event.auth_cmpl.bd_name, p_name, (BD_NAME_LEN));
   4405             else
   4406                 sec_event.auth_cmpl.bd_name[0] = 0;
   4407 
   4408             if (p_data->complt.reason != 0)
   4409             {
   4410                 sec_event.auth_cmpl.fail_reason = BTA_DM_AUTH_CONVERT_SMP_CODE(((UINT8)p_data->complt.reason));
   4411                 /* delete this device entry from Sec Dev DB */
   4412                 bta_dm_remove_sec_dev_entry (bda);
   4413             }
   4414             else
   4415             {
   4416                 sec_event.auth_cmpl.success = TRUE;
   4417                 /* We also register for Service Changed right after connect. */
   4418                 if (!p_data->complt.smp_over_br)
   4419                     GATT_ConfigServiceChangeCCC(bda, TRUE, BT_TRANSPORT_LE);
   4420             }
   4421 
   4422             if (bta_dm_cb.p_sec_cback)
   4423             {
   4424                 //bta_dm_cb.p_sec_cback(BTA_DM_AUTH_CMPL_EVT, &sec_event);
   4425                 bta_dm_cb.p_sec_cback(BTA_DM_BLE_AUTH_CMPL_EVT, &sec_event);
   4426             }
   4427             break;
   4428 
   4429         default:
   4430             status = BTM_NOT_AUTHORIZED;
   4431             break;
   4432     }
   4433     return status;
   4434 }
   4435 #endif  /* SMP_INCLUDED == TRUE */
   4436 
   4437 /*******************************************************************************
   4438 **
   4439 ** Function         bta_dm_ble_id_key_cback
   4440 **
   4441 ** Description      Callback for BLE local ID keys
   4442 **
   4443 **
   4444 ** Returns          void
   4445 **
   4446 *******************************************************************************/
   4447 static void bta_dm_ble_id_key_cback (UINT8 key_type, tBTM_BLE_LOCAL_KEYS *p_key)
   4448 {
   4449     UINT8   evt;
   4450     tBTA_DM_SEC dm_key;
   4451 
   4452     switch (key_type)
   4453     {
   4454         case BTM_BLE_KEY_TYPE_ID:
   4455         case BTM_BLE_KEY_TYPE_ER:
   4456             if (bta_dm_cb.p_sec_cback)
   4457             {
   4458                 memcpy(&dm_key.ble_id_keys, p_key, sizeof(tBTM_BLE_LOCAL_KEYS));
   4459 
   4460                 evt = (key_type == BTM_BLE_KEY_TYPE_ID) ? BTA_DM_BLE_LOCAL_IR_EVT :\
   4461                       BTA_DM_BLE_LOCAL_ER_EVT;
   4462                 bta_dm_cb.p_sec_cback(evt, &dm_key);
   4463             }
   4464             break;
   4465 
   4466         default:
   4467             APPL_TRACE_DEBUG("Unknown key type %d", key_type);
   4468             break;
   4469     }
   4470     return;
   4471 
   4472 }
   4473 
   4474 /*******************************************************************************
   4475 **
   4476 ** Function         bta_dm_add_blekey
   4477 **
   4478 ** Description      This function adds an BLE Key to an security database entry.
   4479 **                  This function shall only be called AFTER BTA_DmAddBleDevice has been called.
   4480 **                  It is normally called during host startup to restore all required information
   4481 **                  stored in the NVRAM.
   4482 **
   4483 ** Parameters:
   4484 **
   4485 *******************************************************************************/
   4486 void bta_dm_add_blekey (tBTA_DM_MSG *p_data)
   4487 {
   4488     if (!BTM_SecAddBleKey (p_data->add_ble_key.bd_addr,
   4489                            (tBTM_LE_KEY_VALUE *)&p_data->add_ble_key.blekey,
   4490                            p_data->add_ble_key.key_type))
   4491     {
   4492         APPL_TRACE_ERROR ("BTA_DM: Error adding BLE Key for device %08x%04x",
   4493                            (p_data->add_ble_key.bd_addr[0]<<24)+(p_data->add_ble_key.bd_addr[1]<<16)+\
   4494                            (p_data->add_ble_key.bd_addr[2]<<8)+p_data->add_ble_key.bd_addr[3],
   4495                            (p_data->add_ble_key.bd_addr[4]<<8)+p_data->add_ble_key.bd_addr[5]);
   4496     }
   4497 }
   4498 
   4499 /*******************************************************************************
   4500 **
   4501 ** Function         bta_dm_add_ble_device
   4502 **
   4503 ** Description      This function adds an BLE device to an security database entry.
   4504 **                  It is normally called during host startup to restore all required information
   4505 **                  stored in the NVRAM.
   4506 **
   4507 ** Parameters:
   4508 **
   4509 *******************************************************************************/
   4510 void bta_dm_add_ble_device (tBTA_DM_MSG *p_data)
   4511 {
   4512     if (!BTM_SecAddBleDevice (p_data->add_ble_device.bd_addr, NULL,
   4513                               p_data->add_ble_device.dev_type  ,
   4514                               p_data->add_ble_device.addr_type))
   4515     {
   4516         APPL_TRACE_ERROR ("BTA_DM: Error adding BLE Device for device %08x%04x",
   4517                            (p_data->add_ble_device.bd_addr[0]<<24)+(p_data->add_ble_device.bd_addr[1]<<16)+ \
   4518                            (p_data->add_ble_device.bd_addr[2]<<8)+p_data->add_ble_device.bd_addr[3],
   4519                            (p_data->add_ble_device.bd_addr[4]<<8)+p_data->add_ble_device.bd_addr[5]);
   4520     }
   4521 }
   4522 
   4523 /*******************************************************************************
   4524 **
   4525 ** Function         bta_dm_add_ble_device
   4526 **
   4527 ** Description      This function adds an BLE device to an security database entry.
   4528 **                  It is normally called during host startup to restore all required information
   4529 **                  stored in the NVRAM.
   4530 **
   4531 ** Parameters:
   4532 **
   4533 *******************************************************************************/
   4534 void bta_dm_ble_passkey_reply (tBTA_DM_MSG *p_data)
   4535 {
   4536     if (p_data->pin_reply.accept)
   4537     {
   4538         BTM_BlePasskeyReply(p_data->ble_passkey_reply.bd_addr, BTM_SUCCESS, p_data->ble_passkey_reply.passkey);
   4539     }
   4540     else
   4541     {
   4542         BTM_BlePasskeyReply(p_data->ble_passkey_reply.bd_addr, BTM_NOT_AUTHORIZED, p_data->ble_passkey_reply.passkey);
   4543     }
   4544 
   4545 }
   4546 
   4547 /*******************************************************************************
   4548 **
   4549 ** Function         bta_dm_ble_confirm_reply
   4550 **
   4551 ** Description      This is response to SM numeric comparison request submitted
   4552 **                  to application.
   4553 **
   4554 ** Parameters:
   4555 **
   4556 *******************************************************************************/
   4557 void bta_dm_ble_confirm_reply (tBTA_DM_MSG *p_data)
   4558 {
   4559     if (p_data->confirm.accept)
   4560     {
   4561         BTM_BleConfirmReply(p_data->confirm.bd_addr, BTM_SUCCESS);
   4562     }
   4563     else
   4564     {
   4565         BTM_BleConfirmReply(p_data->ble_passkey_reply.bd_addr, BTM_NOT_AUTHORIZED);
   4566     }
   4567 }
   4568 
   4569 /*******************************************************************************
   4570 **
   4571 ** Function         bta_dm_security_grant
   4572 **
   4573 ** Description      This function grant SMP security request access.
   4574 **
   4575 ** Parameters:
   4576 **
   4577 *******************************************************************************/
   4578 void bta_dm_security_grant (tBTA_DM_MSG *p_data)
   4579 {
   4580     BTM_SecurityGrant(p_data->ble_sec_grant.bd_addr, p_data->ble_sec_grant.res);
   4581 }
   4582 
   4583 /*******************************************************************************
   4584 **
   4585 ** Function         bta_dm_ble_set_bg_conn_type
   4586 **
   4587 ** Description      This function set the BLE background connection type
   4588 **
   4589 ** Parameters:
   4590 **
   4591 *******************************************************************************/
   4592 void bta_dm_ble_set_bg_conn_type (tBTA_DM_MSG *p_data)
   4593 {
   4594     BTM_BleSetBgConnType(p_data->ble_set_bd_conn_type.bg_conn_type,
   4595                          p_data->ble_set_bd_conn_type.p_select_cback);
   4596 }
   4597 
   4598 /*******************************************************************************
   4599 **
   4600 ** Function         bta_dm_ble_set_conn_params
   4601 **
   4602 ** Description      This function set the preferred connection parameters.
   4603 **
   4604 ** Parameters:
   4605 **
   4606 *******************************************************************************/
   4607 void bta_dm_ble_set_conn_params (tBTA_DM_MSG *p_data)
   4608 {
   4609     BTM_BleSetPrefConnParams(p_data->ble_set_conn_params.peer_bda,
   4610                              p_data->ble_set_conn_params.conn_int_min,
   4611                              p_data->ble_set_conn_params.conn_int_max,
   4612                              p_data->ble_set_conn_params.slave_latency,
   4613                              p_data->ble_set_conn_params.supervision_tout);
   4614 }
   4615 
   4616 /*******************************************************************************
   4617 **
   4618 ** Function         bta_dm_ble_set_conn_scan_params
   4619 **
   4620 ** Description      This function sets BLE scan parameters.
   4621 **
   4622 ** Parameters:
   4623 **
   4624 *******************************************************************************/
   4625 void bta_dm_ble_set_scan_params(tBTA_DM_MSG *p_data)
   4626 {
   4627     BTM_BleSetScanParams(p_data->ble_set_scan_params.client_if,
   4628                          p_data->ble_set_scan_params.scan_int,
   4629                          p_data->ble_set_scan_params.scan_window,
   4630                          p_data->ble_set_scan_params.scan_mode,
   4631                          p_data->ble_set_scan_params.scan_param_setup_cback);
   4632 }
   4633 
   4634 /*******************************************************************************
   4635 **
   4636 ** Function         bta_dm_ble_set_conn_scan_params
   4637 **
   4638 ** Description      This function set the preferred connection scan parameters.
   4639 **
   4640 ** Parameters:
   4641 **
   4642 *******************************************************************************/
   4643 void bta_dm_ble_set_conn_scan_params (tBTA_DM_MSG *p_data)
   4644 {
   4645     BTM_BleSetConnScanParams(p_data->ble_set_conn_scan_params.scan_int,
   4646                              p_data->ble_set_conn_scan_params.scan_window);
   4647 }
   4648 /*******************************************************************************
   4649 **
   4650 ** Function         bta_dm_ble_update_conn_params
   4651 **
   4652 ** Description      This function update LE connection parameters.
   4653 **
   4654 ** Parameters:
   4655 **
   4656 *******************************************************************************/
   4657 void bta_dm_ble_update_conn_params (tBTA_DM_MSG *p_data)
   4658 {
   4659     if (!L2CA_UpdateBleConnParams(p_data->ble_update_conn_params.bd_addr,
   4660                                  p_data->ble_update_conn_params.min_int,
   4661                                  p_data->ble_update_conn_params.max_int,
   4662                                  p_data->ble_update_conn_params.latency,
   4663                                  p_data->ble_update_conn_params.timeout))
   4664     {
   4665         APPL_TRACE_ERROR("Update connection parameters failed!");
   4666     }
   4667 }
   4668 
   4669 #if BLE_PRIVACY_SPT == TRUE
   4670 /*******************************************************************************
   4671 **
   4672 ** Function         bta_dm_ble_config_local_privacy
   4673 **
   4674 ** Description      This function set the local device LE privacy settings.
   4675 **
   4676 ** Parameters:
   4677 **
   4678 *******************************************************************************/
   4679 void bta_dm_ble_config_local_privacy (tBTA_DM_MSG *p_data)
   4680 {
   4681     BTM_BleConfigPrivacy (p_data->ble_local_privacy.privacy_enable);
   4682 }
   4683 #endif
   4684 
   4685 /*******************************************************************************
   4686 **
   4687 ** Function         bta_dm_ble_observe
   4688 **
   4689 ** Description      This function set the preferred connection scan parameters.
   4690 **
   4691 ** Parameters:
   4692 **
   4693 *******************************************************************************/
   4694 void bta_dm_ble_observe (tBTA_DM_MSG *p_data)
   4695 {
   4696     tBTM_STATUS status;
   4697     if (p_data->ble_observe.start)
   4698     {
   4699         /*Save the  callback to be called when a scan results are available */
   4700         bta_dm_search_cb.p_scan_cback = p_data->ble_observe.p_cback;
   4701         if ((status = BTM_BleObserve(TRUE, p_data->ble_observe.duration,
   4702                             bta_dm_observe_results_cb, bta_dm_observe_cmpl_cb))!= BTM_CMD_STARTED)
   4703         {
   4704             tBTA_DM_SEARCH  data;
   4705             APPL_TRACE_WARNING(" %s BTM_BleObserve  failed. status %d",__FUNCTION__,status);
   4706             data.inq_cmpl.num_resps = 0;
   4707             if (bta_dm_search_cb.p_scan_cback)
   4708             {
   4709                 bta_dm_search_cb.p_scan_cback(BTA_DM_INQ_CMPL_EVT, &data);
   4710             }
   4711         }
   4712     }
   4713     else
   4714     {
   4715         bta_dm_search_cb.p_scan_cback = NULL;
   4716         BTM_BleObserve(FALSE, 0, NULL,NULL );
   4717     }
   4718 }
   4719 /*******************************************************************************
   4720 **
   4721 ** Function         bta_dm_ble_set_adv_params
   4722 **
   4723 ** Description      This function set the adv parameters.
   4724 **
   4725 ** Parameters:
   4726 **
   4727 *******************************************************************************/
   4728 void bta_dm_ble_set_adv_params (tBTA_DM_MSG *p_data)
   4729 {
   4730     BTM_BleSetAdvParams(p_data->ble_set_adv_params.adv_int_min,
   4731                         p_data->ble_set_adv_params.adv_int_max,
   4732                         p_data->ble_set_adv_params.p_dir_bda,
   4733                         BTA_DM_BLE_ADV_CHNL_MAP);
   4734 }
   4735 
   4736 /*******************************************************************************
   4737 **
   4738 ** Function         bta_dm_ble_set_adv_config
   4739 **
   4740 ** Description      This function set the customized ADV data configuration
   4741 **
   4742 ** Parameters:
   4743 **
   4744 *******************************************************************************/
   4745 void bta_dm_ble_set_adv_config (tBTA_DM_MSG *p_data)
   4746 {
   4747     tBTA_STATUS status = BTA_FAILURE;
   4748 
   4749     if (BTM_BleWriteAdvData(p_data->ble_set_adv_data.data_mask,
   4750                         (tBTM_BLE_ADV_DATA *)&p_data->ble_set_adv_data.adv_cfg) == BTM_SUCCESS)
   4751     {
   4752         status = BTA_SUCCESS;
   4753     }
   4754 
   4755     if (p_data->ble_set_adv_data.p_adv_data_cback)
   4756         (*p_data->ble_set_adv_data.p_adv_data_cback)(status);
   4757 }
   4758 
   4759 /*******************************************************************************
   4760 **
   4761 ** Function         bta_dm_ble_set_scan_rsp
   4762 **
   4763 ** Description      This function set the customized ADV scan resp. configuration
   4764 **
   4765 ** Parameters:
   4766 **
   4767 *******************************************************************************/
   4768 void bta_dm_ble_set_scan_rsp (tBTA_DM_MSG *p_data)
   4769 {
   4770     tBTA_STATUS status = BTA_FAILURE;
   4771 
   4772     if(BTM_BleWriteScanRsp(p_data->ble_set_adv_data.data_mask,
   4773                         (tBTM_BLE_ADV_DATA *)&p_data->ble_set_adv_data.adv_cfg) == BTM_SUCCESS)
   4774     {
   4775         status = BTA_SUCCESS;
   4776     }
   4777 
   4778     if (p_data->ble_set_adv_data.p_adv_data_cback)
   4779         (*p_data->ble_set_adv_data.p_adv_data_cback)(status);
   4780 }
   4781 
   4782 /*******************************************************************************
   4783 **
   4784 ** Function         bta_dm_ble_set_data_length
   4785 **
   4786 ** Description      This function set the maximum transmission packet size
   4787 **
   4788 ** Parameters
   4789 **
   4790 *******************************************************************************/
   4791 void bta_dm_ble_set_data_length(tBTA_DM_MSG *p_data)
   4792 {
   4793     if (BTM_SetBleDataLength(p_data->ble_set_data_length.remote_bda,
   4794                         p_data->ble_set_data_length.tx_data_length) != BTM_SUCCESS)
   4795     {
   4796         APPL_TRACE_ERROR("%s failed", __FUNCTION__);
   4797     }
   4798 }
   4799 
   4800 /*******************************************************************************
   4801 **
   4802 ** Function         bta_dm_ble_broadcast
   4803 **
   4804 ** Description      Starts or stops LE broadcasts
   4805 **
   4806 ** Parameters:
   4807 **
   4808 *******************************************************************************/
   4809 void bta_dm_ble_broadcast (tBTA_DM_MSG *p_data)
   4810 {
   4811     BTM_BleBroadcast(p_data->ble_observe.start);
   4812 }
   4813 
   4814 /*******************************************************************************
   4815 **
   4816 ** Function         bta_dm_ble_multi_adv_enb
   4817 **
   4818 ** Description      This function enables a single advertising instance
   4819 **
   4820 ** Parameters:
   4821 **
   4822 *******************************************************************************/
   4823 void bta_dm_ble_multi_adv_enb(tBTA_DM_MSG *p_data)
   4824 {
   4825     tBTM_STATUS btm_status = 0;
   4826 
   4827     bta_dm_cb.p_multi_adv_cback = p_data->ble_multi_adv_enb.p_cback;
   4828     if(BTM_BleMaxMultiAdvInstanceCount() > 0 && NULL != p_data->ble_multi_adv_enb.p_ref)
   4829     {
   4830         btm_status = BTM_BleEnableAdvInstance((tBTM_BLE_ADV_PARAMS*)
   4831                                             p_data->ble_multi_adv_enb.p_params,
   4832                                             p_data->ble_multi_adv_enb.p_cback,
   4833                                             p_data->ble_multi_adv_enb.p_ref);
   4834     }
   4835 
   4836     if(BTM_CMD_STARTED != btm_status)
   4837     {
   4838         bta_dm_cb.p_multi_adv_cback(BTA_BLE_MULTI_ADV_ENB_EVT, 0xFF,
   4839                                     p_data->ble_multi_adv_enb.p_ref, BTA_FAILURE);
   4840     }
   4841 }
   4842 /*******************************************************************************
   4843 **
   4844 ** Function         bta_dm_ble_multi_adv_param_upd
   4845 **
   4846 ** Description      This function updates multiple advertising instance parameters
   4847 **
   4848 ** Parameters:
   4849 **
   4850 *******************************************************************************/
   4851 void bta_dm_ble_multi_adv_upd_param(tBTA_DM_MSG *p_data)
   4852 {
   4853     tBTM_STATUS btm_status = 0;
   4854     void *p_ref = NULL;
   4855 
   4856     if(BTM_BleMaxMultiAdvInstanceCount() > 0 && p_data->ble_multi_adv_param.inst_id > 0
   4857         && p_data->ble_multi_adv_param.inst_id < BTM_BleMaxMultiAdvInstanceCount())
   4858     {
   4859         btm_status = BTM_BleUpdateAdvInstParam(p_data->ble_multi_adv_param.inst_id,
   4860                          (tBTM_BLE_ADV_PARAMS*)p_data->ble_multi_adv_param.p_params);
   4861     }
   4862 
   4863     if(BTM_CMD_STARTED != btm_status)
   4864     {
   4865        p_ref = btm_ble_multi_adv_get_ref(p_data->ble_multi_adv_param.inst_id);
   4866        bta_dm_cb.p_multi_adv_cback(BTA_BLE_MULTI_ADV_PARAM_EVT,
   4867                                    p_data->ble_multi_adv_param.inst_id, p_ref, BTA_FAILURE);
   4868     }
   4869 }
   4870 /*******************************************************************************
   4871 **
   4872 ** Function         bta_dm_ble_multi_adv_data
   4873 **
   4874 ** Description      This function write multiple advertising instance adv data
   4875 **                  or scan response data
   4876 **
   4877 ** Parameters:
   4878 **
   4879 *******************************************************************************/
   4880 void bta_dm_ble_multi_adv_data(tBTA_DM_MSG *p_data)
   4881 {
   4882     tBTM_STATUS btm_status = 0;
   4883     void *p_ref = NULL;
   4884 
   4885     if(BTM_BleMaxMultiAdvInstanceCount() > 0 && p_data->ble_multi_adv_data.inst_id > 0
   4886         && p_data->ble_multi_adv_data.inst_id < BTM_BleMaxMultiAdvInstanceCount())
   4887     {
   4888         btm_status = BTM_BleCfgAdvInstData(p_data->ble_multi_adv_data.inst_id,
   4889                         p_data->ble_multi_adv_data.is_scan_rsp,
   4890                         p_data->ble_multi_adv_data.data_mask,
   4891                         (tBTM_BLE_ADV_DATA*)&p_data->ble_multi_adv_data.data);
   4892     }
   4893 
   4894     if(BTM_CMD_STARTED != btm_status)
   4895     {
   4896        p_ref = btm_ble_multi_adv_get_ref(p_data->ble_multi_adv_data.inst_id);
   4897        bta_dm_cb.p_multi_adv_cback(BTA_BLE_MULTI_ADV_DATA_EVT,
   4898                                    p_data->ble_multi_adv_data.inst_id, p_ref, BTA_FAILURE);
   4899     }
   4900 
   4901 }
   4902 /*******************************************************************************
   4903 **
   4904 ** Function         btm_dm_ble_multi_adv_disable
   4905 **
   4906 ** Description      This function disable a single adv instance
   4907 **
   4908 ** Parameters:
   4909 **
   4910 *******************************************************************************/
   4911 void btm_dm_ble_multi_adv_disable(tBTA_DM_MSG *p_data)
   4912 {
   4913     tBTM_STATUS btm_status = 0;
   4914     void *p_ref = NULL;
   4915 
   4916     if(BTM_BleMaxMultiAdvInstanceCount() > 0 && p_data->ble_multi_adv_disable.inst_id > 0
   4917         && p_data->ble_multi_adv_disable.inst_id < BTM_BleMaxMultiAdvInstanceCount())
   4918     {
   4919         btm_status = BTM_BleDisableAdvInstance(p_data->ble_multi_adv_disable.inst_id);
   4920     }
   4921 
   4922     if(BTM_CMD_STARTED != btm_status)
   4923     {
   4924        p_ref = btm_ble_multi_adv_get_ref(p_data->ble_multi_adv_disable.inst_id);
   4925        bta_dm_cb.p_multi_adv_cback(BTA_BLE_MULTI_ADV_DISABLE_EVT,
   4926                                    p_data->ble_multi_adv_disable.inst_id, p_ref, BTA_FAILURE);
   4927     }
   4928 }
   4929 
   4930 /*******************************************************************************
   4931 **
   4932 ** Function         bta_dm_ble_setup_storage
   4933 **
   4934 ** Description      This function configures up the storage parameters for ADV batch scanning
   4935 **
   4936 ** Parameters:
   4937 **
   4938 *******************************************************************************/
   4939 void bta_dm_ble_setup_storage (tBTA_DM_MSG *p_data)
   4940 {
   4941     tBTM_STATUS btm_status = 0;
   4942     tBTM_BLE_VSC_CB cmn_ble_vsc_cb;
   4943 
   4944     BTM_BleGetVendorCapabilities(&cmn_ble_vsc_cb);
   4945 
   4946     if (0 != cmn_ble_vsc_cb.tot_scan_results_strg)
   4947     {
   4948         btm_status = BTM_BleSetStorageConfig(p_data->ble_set_storage.batch_scan_full_max,
   4949                                              p_data->ble_set_storage.batch_scan_trunc_max,
   4950                                              p_data->ble_set_storage.batch_scan_notify_threshold,
   4951                                              p_data->ble_set_storage.p_setup_cback,
   4952                                              p_data->ble_set_storage.p_thres_cback,
   4953                                              p_data->ble_set_storage.p_read_rep_cback,
   4954                                              p_data->ble_set_storage.ref_value);
   4955     }
   4956 
   4957     if(BTM_CMD_STARTED != btm_status)
   4958        bta_ble_scan_setup_cb(BTM_BLE_BATCH_SCAN_CFG_STRG_EVT, p_data->ble_set_storage.ref_value,
   4959                              btm_status);
   4960 }
   4961 
   4962 /*******************************************************************************
   4963 **
   4964 ** Function         bta_dm_ble_enable_batch_scan
   4965 **
   4966 ** Description      This function sets up the parameters and enables batch scan
   4967 **
   4968 ** Parameters:
   4969 **
   4970 *******************************************************************************/
   4971 void bta_dm_ble_enable_batch_scan (tBTA_DM_MSG *p_data)
   4972 {
   4973     tBTM_STATUS btm_status = 0;
   4974     tBTM_BLE_VSC_CB cmn_ble_vsc_cb;
   4975 
   4976     BTM_BleGetVendorCapabilities(&cmn_ble_vsc_cb);
   4977 
   4978     if (0 != cmn_ble_vsc_cb.tot_scan_results_strg)
   4979     {
   4980         btm_status = BTM_BleEnableBatchScan(p_data->ble_enable_scan.scan_mode,
   4981                                             p_data->ble_enable_scan.scan_int,
   4982                                             p_data->ble_enable_scan.scan_window,
   4983                                             p_data->ble_enable_scan.discard_rule,
   4984                                             p_data->ble_enable_scan.addr_type,
   4985                                             p_data->ble_enable_scan.ref_value);
   4986     }
   4987 
   4988     if(BTM_CMD_STARTED != btm_status)
   4989        bta_ble_scan_setup_cb(BTM_BLE_BATCH_SCAN_ENABLE_EVT, p_data->ble_enable_scan.ref_value,
   4990                              btm_status);
   4991 }
   4992 
   4993 /*******************************************************************************
   4994 **
   4995 ** Function         bta_dm_ble_disable_batch_scan
   4996 **
   4997 ** Description      This function disables the batch scan
   4998 **
   4999 ** Parameters:
   5000 **
   5001 *******************************************************************************/
   5002 void bta_dm_ble_disable_batch_scan (tBTA_DM_MSG *p_data)
   5003 {
   5004     UNUSED(p_data);
   5005     tBTM_STATUS btm_status = 0;
   5006     tBTM_BLE_VSC_CB cmn_ble_vsc_cb;
   5007 
   5008     BTM_BleGetVendorCapabilities(&cmn_ble_vsc_cb);
   5009 
   5010     if (0 != cmn_ble_vsc_cb.tot_scan_results_strg)
   5011     {
   5012         btm_status = BTM_BleDisableBatchScan(p_data->ble_disable_scan.ref_value);
   5013     }
   5014 
   5015     if(BTM_CMD_STARTED != btm_status)
   5016        bta_ble_scan_setup_cb(BTM_BLE_BATCH_SCAN_DISABLE_EVT, p_data->ble_enable_scan.ref_value,
   5017                              btm_status);
   5018 }
   5019 
   5020 /*******************************************************************************
   5021 **
   5022 ** Function         bta_dm_ble_read_scan_reports
   5023 **
   5024 ** Description      This function reads the batch scan reports
   5025 **
   5026 ** Parameters:
   5027 **
   5028 *******************************************************************************/
   5029 void bta_dm_ble_read_scan_reports(tBTA_DM_MSG *p_data)
   5030 {
   5031     tBTM_STATUS btm_status = 0;
   5032     tBTM_BLE_VSC_CB cmn_ble_vsc_cb;
   5033 
   5034     BTM_BleGetVendorCapabilities(&cmn_ble_vsc_cb);
   5035 
   5036     if (0 != cmn_ble_vsc_cb.tot_scan_results_strg)
   5037     {
   5038         btm_status = BTM_BleReadScanReports(p_data->ble_read_reports.scan_type,
   5039                                             p_data->ble_read_reports.ref_value);
   5040     }
   5041 
   5042     if(BTM_CMD_STARTED != btm_status)
   5043        bta_ble_scan_setup_cb(BTM_BLE_BATCH_SCAN_READ_REPTS_EVT, p_data->ble_enable_scan.ref_value,
   5044                              btm_status);
   5045 }
   5046 
   5047 /*******************************************************************************
   5048 **
   5049 ** Function         bta_dm_ble_track_advertiser
   5050 **
   5051 ** Description      This function tracks the specific advertiser
   5052 **
   5053 ** Parameters:
   5054 **
   5055 *******************************************************************************/
   5056 void bta_dm_ble_track_advertiser(tBTA_DM_MSG *p_data)
   5057 {
   5058     tBTM_STATUS btm_status = 0;
   5059     BD_ADDR bda;
   5060     memset(&bda, 0 , sizeof(BD_ADDR));
   5061     tBTM_BLE_VSC_CB cmn_ble_vsc_cb;
   5062     tBTA_DM_BLE_TRACK_ADV_DATA track_adv_data;
   5063 
   5064     BTM_BleGetVendorCapabilities(&cmn_ble_vsc_cb);
   5065 
   5066     if (0 != cmn_ble_vsc_cb.tot_scan_results_strg)
   5067     {
   5068         btm_status = BTM_BleTrackAdvertiser((tBTM_BLE_TRACK_ADV_CBACK *)
   5069                                             p_data->ble_track_advert.p_track_adv_cback,
   5070                                             p_data->ble_track_advert.ref_value);
   5071     }
   5072 
   5073     if(BTM_CMD_STARTED != btm_status)
   5074     {
   5075         memset(&track_adv_data, 0, sizeof(tBTA_DM_BLE_TRACK_ADV_DATA));
   5076         track_adv_data.advertiser_info_present = NO_ADV_INFO_PRESENT; /* Indicates failure */
   5077         track_adv_data.client_if = (UINT8)p_data->ble_track_advert.ref_value;
   5078         p_data->ble_track_advert.p_track_adv_cback(&track_adv_data);
   5079     }
   5080 }
   5081 
   5082 /*******************************************************************************
   5083 **
   5084 ** Function         bta_ble_scan_setup_cb
   5085 **
   5086 ** Description      Handle the setup callback from BTM layer and forward it to app layer
   5087 **
   5088 ** Parameters:
   5089 **
   5090 *******************************************************************************/
   5091 void bta_ble_scan_setup_cb(tBTM_BLE_BATCH_SCAN_EVT evt, tBTM_BLE_REF_VALUE ref_value,
   5092                                   tBTM_STATUS status)
   5093 {
   5094     tBTA_BLE_BATCH_SCAN_EVT bta_evt = 0;
   5095 
   5096     APPL_TRACE_DEBUG("bta_ble_scan_setup_cb : evt: %d, ref_value: %d, status:%d", evt,
   5097                       ref_value, status);
   5098 
   5099     switch(evt)
   5100     {
   5101         case BTM_BLE_BATCH_SCAN_ENABLE_EVT:
   5102            bta_evt = BTA_BLE_BATCH_SCAN_ENB_EVT;
   5103            break;
   5104         case BTM_BLE_BATCH_SCAN_CFG_STRG_EVT:
   5105            bta_evt = BTA_BLE_BATCH_SCAN_CFG_STRG_EVT;
   5106            break;
   5107         case BTM_BLE_BATCH_SCAN_DISABLE_EVT:
   5108             bta_evt = BTA_BLE_BATCH_SCAN_DIS_EVT;
   5109             break;
   5110         case BTM_BLE_BATCH_SCAN_PARAM_EVT:
   5111             bta_evt = BTA_BLE_BATCH_SCAN_PARAM_EVT;
   5112             break;
   5113         default:
   5114             break;
   5115     }
   5116 
   5117     if(NULL != bta_dm_cb.p_setup_cback)
   5118        bta_dm_cb.p_setup_cback(bta_evt, ref_value, status);
   5119 }
   5120 
   5121 
   5122 #if BLE_ANDROID_CONTROLLER_SCAN_FILTER == TRUE
   5123 /*******************************************************************************
   5124 **
   5125 ** Function         bta_ble_scan_pf_cmpl
   5126 **
   5127 ** Description      ADV payload filtering operation complete callback
   5128 **
   5129 **
   5130 ** Returns         TRUE if handled, otherwise FALSE.
   5131 **
   5132 *******************************************************************************/
   5133 static void bta_ble_scan_cfg_cmpl(tBTM_BLE_PF_ACTION action, tBTM_BLE_SCAN_COND_OP cfg_op,
   5134                                  tBTM_BLE_PF_AVBL_SPACE avbl_space, tBTM_STATUS status,
   5135                                  tBTM_BLE_REF_VALUE ref_value)
   5136 {
   5137     tBTA_STATUS st = (status == BTM_SUCCESS) ? BTA_SUCCESS: BTA_FAILURE;
   5138 
   5139     APPL_TRACE_DEBUG("bta_ble_scan_cfg_cmpl: %d, %d, %d, %d", action, cfg_op, avbl_space, status);
   5140 
   5141     if(bta_dm_cb.p_scan_filt_cfg_cback)
   5142        bta_dm_cb.p_scan_filt_cfg_cback(action, cfg_op, avbl_space, st, ref_value);
   5143 }
   5144 
   5145 /*******************************************************************************
   5146 **
   5147 ** Function         bta_dm_cfg_filter_cond
   5148 **
   5149 ** Description      This function configure adv payload filtering condition
   5150 **
   5151 ** Parameters:
   5152 **
   5153 *******************************************************************************/
   5154 void bta_dm_cfg_filter_cond (tBTA_DM_MSG *p_data)
   5155 {
   5156     tBTM_STATUS st = BTM_MODE_UNSUPPORTED;
   5157     tBTA_STATUS status = BTA_FAILURE;
   5158 
   5159     tBTM_BLE_VSC_CB cmn_vsc_cb;
   5160 
   5161     APPL_TRACE_DEBUG("bta_dm_cfg_filter_cond");
   5162     BTM_BleGetVendorCapabilities(&cmn_vsc_cb);
   5163     if(0 != cmn_vsc_cb.filter_support)
   5164     {
   5165         if ((st = BTM_BleCfgFilterCondition(p_data->ble_cfg_filter_cond.action,
   5166                             p_data->ble_cfg_filter_cond.cond_type,
   5167                             (tBTM_BLE_PF_FILT_INDEX)p_data->ble_cfg_filter_cond.filt_index,
   5168                             (tBTM_BLE_PF_COND_PARAM *)p_data->ble_cfg_filter_cond.p_cond_param,
   5169                             bta_ble_scan_cfg_cmpl, p_data->ble_cfg_filter_cond.ref_value))
   5170                 == BTM_CMD_STARTED)
   5171         {
   5172             bta_dm_cb.p_scan_filt_cfg_cback = p_data->ble_cfg_filter_cond.p_filt_cfg_cback;
   5173             return;
   5174         }
   5175     }
   5176 
   5177     if (p_data->ble_cfg_filter_cond.p_filt_cfg_cback)
   5178         p_data->ble_cfg_filter_cond.p_filt_cfg_cback(BTA_DM_BLE_PF_CONFIG_EVT,
   5179                                             p_data->ble_cfg_filter_cond.cond_type, 0, status,
   5180                                             p_data->ble_cfg_filter_cond.ref_value);
   5181     return;
   5182 }
   5183 
   5184 /*******************************************************************************
   5185 **
   5186 ** Function         bta_dm_enable_scan_filter
   5187 **
   5188 ** Description      This function enable/disable adv payload filtering condition
   5189 **
   5190 ** Parameters:
   5191 **
   5192 *******************************************************************************/
   5193 void bta_dm_enable_scan_filter(tBTA_DM_MSG *p_data)
   5194 {
   5195     tBTM_STATUS st = BTM_MODE_UNSUPPORTED;
   5196     tBTA_STATUS status = BTA_FAILURE;
   5197 
   5198     tBTM_BLE_VSC_CB cmn_vsc_cb;
   5199     APPL_TRACE_DEBUG("bta_dm_enable_scan_filter");
   5200     BTM_BleGetVendorCapabilities(&cmn_vsc_cb);
   5201 
   5202     if(0 != cmn_vsc_cb.filter_support)
   5203     {
   5204         if((st = BTM_BleEnableDisableFilterFeature(p_data->ble_enable_scan_filt.action,
   5205                    p_data->ble_enable_scan_filt.p_filt_status_cback,
   5206                    (tBTM_BLE_REF_VALUE)p_data->ble_enable_scan_filt.ref_value)) == BTM_CMD_STARTED)
   5207         bta_dm_cb.p_scan_filt_status_cback = p_data->ble_enable_scan_filt.p_filt_status_cback;
   5208         return;
   5209     }
   5210 
   5211     if (p_data->ble_enable_scan_filt.p_filt_status_cback)
   5212         p_data->ble_enable_scan_filt.p_filt_status_cback (BTA_DM_BLE_PF_ENABLE_EVT,
   5213                                             p_data->ble_enable_scan_filt.ref_value, status);
   5214 
   5215 }
   5216 
   5217 /*******************************************************************************
   5218 **
   5219 ** Function         bta_dm_scan_filter_param_setup
   5220 **
   5221 ** Description      This function sets up scan filter params
   5222 **
   5223 ** Parameters:
   5224 **
   5225 *******************************************************************************/
   5226 void bta_dm_scan_filter_param_setup (tBTA_DM_MSG *p_data)
   5227 {
   5228     tBTM_STATUS st = BTM_MODE_UNSUPPORTED;
   5229     tBTA_STATUS status = BTA_FAILURE;
   5230 
   5231     tBTM_BLE_VSC_CB cmn_vsc_cb;
   5232 
   5233     APPL_TRACE_DEBUG("bta_dm_scan_filter_param_setup");
   5234     BTM_BleGetVendorCapabilities(&cmn_vsc_cb);
   5235     if(0 != cmn_vsc_cb.filter_support)
   5236     {
   5237         if ((st = BTM_BleAdvFilterParamSetup(p_data->ble_scan_filt_param_setup.action,
   5238                    p_data->ble_scan_filt_param_setup.filt_index,
   5239                   (tBTM_BLE_PF_FILT_PARAMS *)&p_data->ble_scan_filt_param_setup.filt_params,
   5240                    p_data->ble_scan_filt_param_setup.p_target,
   5241                    p_data->ble_scan_filt_param_setup.p_filt_param_cback,
   5242                    p_data->ble_scan_filt_param_setup.ref_value)) == BTM_CMD_STARTED)
   5243         {
   5244             bta_dm_cb.p_scan_filt_param_cback = p_data->ble_scan_filt_param_setup.p_filt_param_cback;
   5245             return;
   5246         }
   5247     }
   5248 
   5249     if (p_data->ble_scan_filt_param_setup.p_filt_param_cback)
   5250         p_data->ble_scan_filt_param_setup.p_filt_param_cback (BTA_DM_BLE_PF_ENABLE_EVT, 0,
   5251                                         p_data->ble_scan_filt_param_setup.ref_value, status);
   5252 
   5253     return;
   5254 }
   5255 #endif
   5256 
   5257 /*******************************************************************************
   5258 **
   5259 ** Function         bta_ble_enable_scan_cmpl
   5260 **
   5261 ** Description      ADV payload filtering enable / disable complete callback
   5262 **
   5263 **
   5264 ** Returns          None
   5265 **
   5266 *******************************************************************************/
   5267 static void bta_ble_energy_info_cmpl(tBTM_BLE_TX_TIME_MS tx_time,
   5268                                         tBTM_BLE_RX_TIME_MS rx_time,
   5269                                         tBTM_BLE_IDLE_TIME_MS idle_time,
   5270                                         tBTM_BLE_ENERGY_USED  energy_used,
   5271                                         tBTM_STATUS status)
   5272 {
   5273     tBTA_STATUS st = (status == BTM_SUCCESS) ? BTA_SUCCESS: BTA_FAILURE;
   5274     tBTA_DM_CONTRL_STATE ctrl_state = 0;
   5275 
   5276     if (BTA_SUCCESS == st)
   5277        ctrl_state = bta_dm_pm_obtain_controller_state();
   5278 
   5279     if (bta_dm_cb.p_energy_info_cback)
   5280         bta_dm_cb.p_energy_info_cback(tx_time, rx_time, idle_time, energy_used, ctrl_state, st);
   5281 }
   5282 
   5283 /*******************************************************************************
   5284 **
   5285 ** Function         bta_dm_ble_get_energy_info
   5286 **
   5287 ** Description      This function obtains the energy info
   5288 **
   5289 ** Parameters:
   5290 **
   5291 *******************************************************************************/
   5292 void bta_dm_ble_get_energy_info(tBTA_DM_MSG *p_data)
   5293 {
   5294     tBTM_STATUS btm_status = 0;
   5295 
   5296     bta_dm_cb.p_energy_info_cback = p_data->ble_energy_info.p_energy_info_cback;
   5297     btm_status = BTM_BleGetEnergyInfo(bta_ble_energy_info_cmpl);
   5298     if (BTM_CMD_STARTED != btm_status)
   5299         bta_ble_energy_info_cmpl(0, 0, 0, 0, btm_status);
   5300 }
   5301 
   5302 #if ((defined BTA_GATT_INCLUDED) &&  (BTA_GATT_INCLUDED == TRUE))
   5303 #ifndef BTA_DM_GATT_CLOSE_DELAY_TOUT
   5304 #define BTA_DM_GATT_CLOSE_DELAY_TOUT    1000
   5305 #endif
   5306 
   5307 /*******************************************************************************
   5308 **
   5309 ** Function         bta_dm_gattc_register
   5310 **
   5311 ** Description      Register with GATTC in DM if BLE is needed.
   5312 **
   5313 **
   5314 ** Returns          void
   5315 **
   5316 *******************************************************************************/
   5317 static void bta_dm_gattc_register(void)
   5318 {
   5319     tBT_UUID                app_uuid = {LEN_UUID_128,{0}};
   5320 
   5321     if (bta_dm_search_cb.client_if == BTA_GATTS_INVALID_IF)
   5322     {
   5323         memset (&app_uuid.uu.uuid128, 0x87, LEN_UUID_128);
   5324         BTA_GATTC_AppRegister(&app_uuid, bta_dm_gattc_callback);
   5325     }
   5326 }
   5327 
   5328 /*******************************************************************************
   5329 **
   5330 ** Function         btm_dm_start_disc_gatt_services
   5331 **
   5332 ** Description      This function starts a GATT service search request.
   5333 **
   5334 ** Parameters:
   5335 **
   5336 *******************************************************************************/
   5337 static void btm_dm_start_disc_gatt_services (UINT16 conn_id)
   5338 {
   5339     tBT_UUID    *p_uuid = bta_dm_search_cb.p_srvc_uuid +
   5340                           bta_dm_search_cb.num_uuid - bta_dm_search_cb.uuid_to_search;
   5341 
   5342     p_uuid = bta_dm_search_cb.p_srvc_uuid +
   5343              bta_dm_search_cb.num_uuid - bta_dm_search_cb.uuid_to_search;
   5344 
   5345     /* always search for all services */
   5346     BTA_GATTC_ServiceSearchRequest(conn_id, p_uuid);
   5347 }
   5348 
   5349 /*******************************************************************************
   5350 **
   5351 ** Function         bta_dm_gatt_disc_result
   5352 **
   5353 ** Description      This function process the GATT service search result.
   5354 **
   5355 ** Parameters:
   5356 **
   5357 *******************************************************************************/
   5358 static void bta_dm_gatt_disc_result(tBTA_GATT_ID service_id)
   5359 {
   5360     tBTA_DM_SEARCH   result;
   5361 
   5362     /*
   5363         * This logic will not work for gatt case.  We are checking against the bluetooth profiles here
   5364         * just copy the GATTID in raw data field and send it across.
   5365         */
   5366 
   5367 
   5368     if ( bta_dm_search_cb.ble_raw_used + sizeof(tBTA_GATT_ID) < bta_dm_search_cb.ble_raw_size )
   5369     {
   5370         APPL_TRACE_DEBUG("ADDING BLE SERVICE uuid=0x%x, ble_ptr = 0x%x, ble_raw_used = 0x%x",
   5371             service_id.uuid.uu.uuid16,bta_dm_search_cb.p_ble_rawdata,bta_dm_search_cb.ble_raw_used);
   5372 
   5373         if(bta_dm_search_cb.p_ble_rawdata)
   5374         {
   5375             memcpy((bta_dm_search_cb.p_ble_rawdata + bta_dm_search_cb.ble_raw_used), &service_id,
   5376                    sizeof(service_id) );
   5377 
   5378             bta_dm_search_cb.ble_raw_used += sizeof(service_id);
   5379         }
   5380         else
   5381         {
   5382             APPL_TRACE_ERROR("p_ble_rawdata is NULL");
   5383         }
   5384 
   5385     }
   5386     else
   5387     {
   5388         APPL_TRACE_ERROR("%s out of room to accomodate more service ids ble_raw_size = %d ble_raw_used = %d", __FUNCTION__,bta_dm_search_cb.ble_raw_size, bta_dm_search_cb.ble_raw_used );
   5389     }
   5390 
   5391     LOG_INFO(LOG_TAG, "%s service_id_uuid_len=%d ", __func__, service_id.uuid.len);
   5392     if ( bta_dm_search_cb.state != BTA_DM_SEARCH_IDLE)
   5393     {
   5394 
   5395         /* send result back to app now, one by one */
   5396         bdcpy (result.disc_ble_res.bd_addr, bta_dm_search_cb.peer_bdaddr);
   5397         strlcpy((char*)result.disc_ble_res.bd_name, bta_dm_get_remname(), BD_NAME_LEN);
   5398         memcpy(&result.disc_ble_res.service, &service_id.uuid, sizeof(tBT_UUID));
   5399 
   5400         bta_dm_search_cb.p_search_cback(BTA_DM_DISC_BLE_RES_EVT, &result);
   5401     }
   5402 }
   5403 
   5404 /*******************************************************************************
   5405 **
   5406 ** Function         bta_dm_gatt_disc_complete
   5407 **
   5408 ** Description      This function process the GATT service search complete.
   5409 **
   5410 ** Parameters:
   5411 **
   5412 *******************************************************************************/
   5413 static void bta_dm_gatt_disc_complete(UINT16 conn_id, tBTA_GATT_STATUS status)
   5414 {
   5415     APPL_TRACE_DEBUG("%s conn_id = %d", __func__, conn_id);
   5416 
   5417     if (bta_dm_search_cb.uuid_to_search > 0)
   5418         bta_dm_search_cb.uuid_to_search --;
   5419 
   5420     if (status == BTA_GATT_OK && bta_dm_search_cb.uuid_to_search > 0) {
   5421         btm_dm_start_disc_gatt_services(conn_id);
   5422     } else {
   5423         tBTA_DM_MSG *p_msg = (tBTA_DM_MSG *)osi_malloc(sizeof(tBTA_DM_MSG));
   5424 
   5425         bta_dm_search_cb.uuid_to_search = 0;
   5426 
   5427         /* no more services to be discovered */
   5428         p_msg->hdr.event = BTA_DM_DISCOVERY_RESULT_EVT;
   5429         p_msg->disc_result.result.disc_res.result = (status == BTA_GATT_OK) ? BTA_SUCCESS :BTA_FAILURE;
   5430         APPL_TRACE_DEBUG("%s service found: 0x%08x", __func__,
   5431                          bta_dm_search_cb.services_found);
   5432         p_msg->disc_result.result.disc_res.services = bta_dm_search_cb.services_found;
   5433         p_msg->disc_result.result.disc_res.num_uuids = 0;
   5434         p_msg->disc_result.result.disc_res.p_uuid_list = NULL;
   5435         bdcpy(p_msg->disc_result.result.disc_res.bd_addr,
   5436               bta_dm_search_cb.peer_bdaddr);
   5437         strlcpy((char*)p_msg->disc_result.result.disc_res.bd_name,
   5438                 bta_dm_get_remname(), BD_NAME_LEN);
   5439 
   5440         p_msg->disc_result.result.disc_res.device_type |= BT_DEVICE_TYPE_BLE;
   5441         if (bta_dm_search_cb.ble_raw_used > 0) {
   5442             p_msg->disc_result.result.disc_res.p_raw_data =
   5443                 osi_malloc(bta_dm_search_cb.ble_raw_used);
   5444 
   5445             memcpy(p_msg->disc_result.result.disc_res.p_raw_data,
   5446                    bta_dm_search_cb.p_ble_rawdata,
   5447                    bta_dm_search_cb.ble_raw_used);
   5448 
   5449             p_msg->disc_result.result.disc_res.raw_data_size =
   5450                 bta_dm_search_cb.ble_raw_used;
   5451         } else {
   5452             p_msg->disc_result.result.disc_res.p_raw_data = NULL;
   5453             bta_dm_search_cb.p_ble_rawdata = 0;
   5454         }
   5455 
   5456         bta_sys_sendmsg(p_msg);
   5457 
   5458         if (conn_id != BTA_GATT_INVALID_CONN_ID)
   5459         {
   5460             /* start a GATT channel close delay timer */
   5461             bta_sys_start_timer(bta_dm_search_cb.gatt_close_timer,
   5462                                 BTA_DM_GATT_CLOSE_DELAY_TOUT,
   5463                                 BTA_DM_DISC_CLOSE_TOUT_EVT, 0);
   5464             bdcpy(bta_dm_search_cb.pending_close_bda,
   5465                   bta_dm_search_cb.peer_bdaddr);
   5466         }
   5467         bta_dm_search_cb.gatt_disc_active = FALSE;
   5468     }
   5469 }
   5470 
   5471 /*******************************************************************************
   5472 **
   5473 ** Function         bta_dm_close_gatt_conn
   5474 **
   5475 ** Description      This function close the GATT connection after delay timeout.
   5476 **
   5477 ** Parameters:
   5478 **
   5479 *******************************************************************************/
   5480 void bta_dm_close_gatt_conn(tBTA_DM_MSG *p_data)
   5481 {
   5482     UNUSED(p_data);
   5483 
   5484     if (bta_dm_search_cb.conn_id != BTA_GATT_INVALID_CONN_ID)
   5485         BTA_GATTC_Close(bta_dm_search_cb.conn_id);
   5486 
   5487     memset(bta_dm_search_cb.pending_close_bda, 0, BD_ADDR_LEN);
   5488     bta_dm_search_cb.conn_id = BTA_GATT_INVALID_CONN_ID;
   5489 }
   5490 /*******************************************************************************
   5491 **
   5492 ** Function         btm_dm_start_gatt_discovery
   5493 **
   5494 ** Description      This is GATT initiate the service search by open a GATT connection
   5495 **                  first.
   5496 **
   5497 ** Parameters:
   5498 **
   5499 *******************************************************************************/
   5500 void btm_dm_start_gatt_discovery (BD_ADDR bd_addr)
   5501 {
   5502     bta_dm_search_cb.gatt_disc_active = TRUE;
   5503 
   5504     /* connection is already open */
   5505     if (bdcmp(bta_dm_search_cb.pending_close_bda, bd_addr) == 0 &&
   5506         bta_dm_search_cb.conn_id != BTA_GATT_INVALID_CONN_ID)
   5507     {
   5508         memset(bta_dm_search_cb.pending_close_bda, 0, BD_ADDR_LEN);
   5509         alarm_cancel(bta_dm_search_cb.gatt_close_timer);
   5510         btm_dm_start_disc_gatt_services(bta_dm_search_cb.conn_id);
   5511     }
   5512     else
   5513         BTA_GATTC_Open(bta_dm_search_cb.client_if, bd_addr, TRUE, BTA_GATT_TRANSPORT_LE);
   5514 }
   5515 
   5516 /*******************************************************************************
   5517 **
   5518 ** Function         bta_dm_cancel_gatt_discovery
   5519 **
   5520 ** Description      This is GATT cancel the GATT service search.
   5521 **
   5522 ** Parameters:
   5523 **
   5524 *******************************************************************************/
   5525 static void bta_dm_cancel_gatt_discovery(BD_ADDR bd_addr)
   5526 {
   5527     if (bta_dm_search_cb.conn_id == BTA_GATT_INVALID_CONN_ID)
   5528     {
   5529         BTA_GATTC_CancelOpen(bta_dm_search_cb.client_if, bd_addr, TRUE);
   5530     }
   5531 
   5532     bta_dm_gatt_disc_complete(bta_dm_search_cb.conn_id, (tBTA_GATT_STATUS) BTA_GATT_ERROR);
   5533 }
   5534 
   5535 /*******************************************************************************
   5536 **
   5537 ** Function         bta_dm_proc_open_evt
   5538 **
   5539 ** Description      process BTA_GATTC_OPEN_EVT in DM.
   5540 **
   5541 ** Parameters:
   5542 **
   5543 *******************************************************************************/
   5544 void bta_dm_proc_open_evt(tBTA_GATTC_OPEN *p_data)
   5545 {
   5546     UINT8           *p1;
   5547     UINT8           *p2;
   5548 
   5549     p1 = bta_dm_search_cb.peer_bdaddr;
   5550     p2 = p_data->remote_bda;
   5551 
   5552     APPL_TRACE_DEBUG("DM Search state= %d search_cb.peer_dbaddr: [%08x%04x] connected_bda= [%08x%04x] ",
   5553                       bta_dm_search_cb.state,
   5554                       ((p1[0])<<24)+((p1[1])<<16)+((p1[2])<<8)+(p1[3]),
   5555                       ((p1[4])<<8)+ p1[5],
   5556                       ((p2[0])<<24)+((p2[1])<<16)+((p2[2])<<8)+(p2[3]),
   5557                       ((p2[4])<<8)+ p2[5]);
   5558 
   5559     APPL_TRACE_DEBUG("BTA_GATTC_OPEN_EVT conn_id = %d client_if=%d status = %d" ,
   5560                       p_data->conn_id,
   5561                       p_data->client_if,
   5562                       p_data->status);
   5563 
   5564     bta_dm_search_cb.conn_id = p_data->conn_id;
   5565 
   5566     if (p_data->status == BTA_GATT_OK)
   5567     {
   5568         btm_dm_start_disc_gatt_services(p_data->conn_id);
   5569     }
   5570     else
   5571     {
   5572         bta_dm_gatt_disc_complete(BTA_GATT_INVALID_CONN_ID, p_data->status);
   5573     }
   5574 }
   5575 
   5576 /*******************************************************************************
   5577 **
   5578 ** Function         bta_dm_gattc_callback
   5579 **
   5580 ** Description      This is GATT client callback function used in DM.
   5581 **
   5582 ** Parameters:
   5583 **
   5584 *******************************************************************************/
   5585 static void bta_dm_gattc_callback(tBTA_GATTC_EVT event, tBTA_GATTC *p_data)
   5586 {
   5587     APPL_TRACE_DEBUG("bta_dm_gattc_callback event = %d", event);
   5588 
   5589     switch (event)
   5590     {
   5591         case BTA_GATTC_REG_EVT:
   5592             APPL_TRACE_DEBUG("BTA_GATTC_REG_EVT client_if = %d",  p_data->reg_oper.client_if);
   5593             if (p_data->reg_oper.status == BTA_GATT_OK)
   5594                 bta_dm_search_cb.client_if = p_data->reg_oper.client_if;
   5595             else
   5596                 bta_dm_search_cb.client_if = BTA_GATTS_INVALID_IF;
   5597             break;
   5598 
   5599         case BTA_GATTC_OPEN_EVT:
   5600             bta_dm_proc_open_evt(&p_data->open);
   5601             break;
   5602 
   5603         case BTA_GATTC_SEARCH_RES_EVT:
   5604             bta_dm_gatt_disc_result(p_data->srvc_res.service_uuid);
   5605             break;
   5606 
   5607         case BTA_GATTC_SEARCH_CMPL_EVT:
   5608             if ( bta_dm_search_cb.state != BTA_DM_SEARCH_IDLE)
   5609                 bta_dm_gatt_disc_complete(p_data->search_cmpl.conn_id, p_data->search_cmpl.status);
   5610             break;
   5611 
   5612         case BTA_GATTC_CLOSE_EVT:
   5613             APPL_TRACE_DEBUG("BTA_GATTC_CLOSE_EVT reason = %d", p_data->close.reason);
   5614             /* in case of disconnect before search is completed */
   5615             if ( (bta_dm_search_cb.state != BTA_DM_SEARCH_IDLE) &&
   5616                  (bta_dm_search_cb.state != BTA_DM_SEARCH_ACTIVE) &&
   5617                  !memcmp(p_data->close.remote_bda, bta_dm_search_cb.peer_bdaddr, BD_ADDR_LEN))
   5618             {
   5619                 bta_dm_gatt_disc_complete((UINT16)BTA_GATT_INVALID_CONN_ID,  (tBTA_GATT_STATUS) BTA_GATT_ERROR);
   5620             }
   5621             break;
   5622 
   5623         default:
   5624             break;
   5625     }
   5626 }
   5627 
   5628 #endif /* BTA_GATT_INCLUDED */
   5629 
   5630 #if BLE_VND_INCLUDED == TRUE
   5631 /*******************************************************************************
   5632 **
   5633 ** Function         bta_dm_ctrl_features_rd_cmpl_cback
   5634 **
   5635 ** Description      callback to handle controller feature read complete
   5636 **
   5637 ** Parameters:
   5638 **
   5639 *******************************************************************************/
   5640 static void bta_dm_ctrl_features_rd_cmpl_cback(tBTM_STATUS result)
   5641 {
   5642     APPL_TRACE_DEBUG("%s  status = %d ", __FUNCTION__, result);
   5643     if (result == BTM_SUCCESS)
   5644     {
   5645         if(bta_dm_cb.p_sec_cback)
   5646             bta_dm_cb.p_sec_cback(BTA_DM_LE_FEATURES_READ, NULL);
   5647     }
   5648     else
   5649     {
   5650         APPL_TRACE_ERROR("%s Ctrl BLE feature read failed: status :%d",__FUNCTION__, result);
   5651     }
   5652 
   5653 }
   5654 #endif /* BLE_VND_INCLUDED */
   5655 
   5656 #endif  /* BLE_INCLUDED */
   5657