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