• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /******************************************************************************
2  *
3  *  Copyright (C) 2008-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 functions for BLE GAP.
22  *
23  ******************************************************************************/
24 
25 #include <string.h>
26 #include <stdio.h>
27 #include <stddef.h>
28 
29 #include "bt_types.h"
30 #include "btu.h"
31 #include "btm_int.h"
32 #include "hcimsgs.h"
33 #if (GAP_INCLUDED == TRUE)
34 #include "gap_api.h"
35 #endif
36 #if (BLE_INCLUDED == TRUE)
37 #include "gattdefs.h"
38 
39 #define BTM_BLE_NAME_SHORT                  0x01
40 #define BTM_BLE_NAME_CMPL                   0x02
41 
42 #define BTM_BLE_FILTER_TARGET_UNKNOWN       0xff
43 #define BTM_BLE_POLICY_UNKNOWN              0xff
44 
45 #define BTM_EXT_BLE_RMT_NAME_TIMEOUT        30
46 
47 /*******************************************************************************
48 **  Local functions
49 *******************************************************************************/
50 static void btm_ble_update_adv_flag(UINT8 flag);
51 static void btm_ble_process_adv_pkt_cont(BD_ADDR bda, UINT8 addr_type, UINT8 evt_type, UINT8 *p);
52 static UINT8 *btm_ble_build_adv_data(tBTM_BLE_AD_MASK *p_data_mask, UINT8 **p_dst, tBTM_BLE_ADV_DATA *p_data);
53 static UINT8 btm_set_conn_mode_adv_init_addr(tBTM_BLE_INQ_CB *p_cb,
54                                      BD_ADDR_PTR p_addr_ptr,
55                                      tBLE_ADDR_TYPE *p_init_addr_type,
56                                      tBLE_ADDR_TYPE *p_own_addr_type);
57 static BOOLEAN btm_ble_start_adv(void);
58 static tBTM_STATUS btm_ble_stop_adv(void);
59 
60 
61 
62 /*******************************************************************************
63 **
64 ** Function         BTM_BleReset
65 **
66 ** Description      This function is called to reset ULP controller.
67 **
68 ** Parameters       None.
69 **
70 ** Returns          void
71 **
72 *******************************************************************************/
BTM_BleReset(void)73 void BTM_BleReset(void)
74 {
75     btsnd_hcic_ble_reset();
76 }
77 /*******************************************************************************
78 **
79 ** Function         BTM_BleUpdateAdvWhitelist
80 **
81 ** Description      Add or remove device from advertising white list
82 **
83 ** Returns          void
84 **
85 *******************************************************************************/
BTM_BleUpdateAdvWhitelist(BOOLEAN add_remove,BD_ADDR remote_bda)86 BOOLEAN BTM_BleUpdateAdvWhitelist(BOOLEAN add_remove, BD_ADDR remote_bda)
87 {
88         return FALSE;
89 }
90 
91 /*******************************************************************************
92 **
93 ** Function         BTM_BleUpdateAdvFilterPolicy
94 **
95 ** Description      This function update the filter policy of advertiser.
96 **
97 ** Parameter        adv_policy: advertising filter policy
98 **
99 ** Return           void
100 *******************************************************************************/
BTM_BleUpdateAdvFilterPolicy(tBTM_BLE_AFP adv_policy)101 void BTM_BleUpdateAdvFilterPolicy(tBTM_BLE_AFP adv_policy)
102 {
103     tBTM_BLE_INQ_CB *p_cb = &btm_cb.ble_ctr_cb.inq_var;
104     tBLE_ADDR_TYPE   init_addr_type = BLE_ADDR_PUBLIC;
105     BD_ADDR          p_addr_ptr= {0};
106     UINT8            adv_mode = p_cb->adv_mode;
107 
108     BTM_TRACE_EVENT0 ("BTM_BleUpdateAdvFilterPolicy");
109 
110     if (!HCI_LE_HOST_SUPPORTED(btm_cb.devcb.local_lmp_features[HCI_EXT_FEATURES_PAGE_1]))
111         return;
112 
113     if (p_cb->afp != adv_policy)
114     {
115         p_cb->afp = adv_policy;
116 
117         /* if adv active, stop and restart */
118         btm_ble_stop_adv ();
119 
120         if (p_cb->connectable_mode & BTM_BLE_CONNECTABLE)
121             p_cb->evt_type = btm_set_conn_mode_adv_init_addr(p_cb, p_addr_ptr, &init_addr_type, &p_cb->adv_addr_type);
122 
123         btsnd_hcic_ble_write_adv_params (p_cb->adv_interval_min,
124                                          p_cb->adv_interval_max,
125                                          p_cb->evt_type,
126                                          p_cb->adv_addr_type,
127                                          init_addr_type,
128                                          p_addr_ptr,
129                                          p_cb->adv_chnl_map,
130                                          p_cb->afp);
131 
132         if (adv_mode == BTM_BLE_ADV_ENABLE)
133             btm_ble_start_adv ();
134 
135     }
136 }
137 /*******************************************************************************
138 **
139 ** Function         BTM_BleObserve
140 **
141 ** Description      This procedure keep the device listening for advertising
142 **                  events from a broadcast device.
143 **
144 ** Parameters       start: start or stop observe.
145 **                  white_list: use white list in observer mode or not.
146 **
147 ** Returns          void
148 **
149 *******************************************************************************/
BTM_BleObserve(BOOLEAN start,UINT8 duration,tBTM_INQ_RESULTS_CB * p_results_cb,tBTM_CMPL_CB * p_cmpl_cb)150 tBTM_STATUS BTM_BleObserve(BOOLEAN start, UINT8 duration,
151                            tBTM_INQ_RESULTS_CB *p_results_cb, tBTM_CMPL_CB *p_cmpl_cb)
152 {
153     tBTM_BLE_INQ_CB *p_inq = &btm_cb.ble_ctr_cb.inq_var;
154     tBTM_STATUS     status = BTM_NO_RESOURCES;
155 
156     BTM_TRACE_EVENT1 ("BTM_BleObserve : scan_type:%d",btm_cb.btm_inq_vars.scan_type);
157 
158     if (!HCI_LE_HOST_SUPPORTED(btm_cb.devcb.local_lmp_features[HCI_EXT_FEATURES_PAGE_1]))
159         return BTM_ILLEGAL_VALUE;
160 
161     if (start)
162     {
163         /* shared inquiry database, do not allow observe if any inquiry is active */
164         if (btm_cb.btm_inq_vars.inq_active || p_inq->proc_mode != BTM_BLE_INQUIRY_NONE)
165         {
166             /*check if an interleave scan is already in progress*/
167             if(btm_cb.btm_inq_vars.scan_type == INQ_GENERAL
168                 && btm_cb.btm_inq_vars.p_inq_results_cb != NULL)
169             {
170                 BTM_TRACE_EVENT0 ("BTM_BleObserve general inq in progress, redirecting the results");
171                 btm_cb.btm_inq_vars.p_inq_ble_results_cb = p_results_cb;
172                 btm_cb.btm_inq_vars.p_inq_ble_cmpl_cb = p_cmpl_cb;
173                 return BTM_SUCCESS;
174             }
175             else
176                 return BTM_BUSY;
177         }
178         btm_cb.btm_inq_vars.scan_type = INQ_LE_OBSERVE;
179         btm_cb.btm_inq_vars.p_inq_ble_results_cb = p_results_cb;
180         btm_cb.btm_inq_vars.p_inq_ble_cmpl_cb = p_cmpl_cb;
181         p_inq->scan_type = (p_inq->scan_type == BTM_BLE_SCAN_MODE_NONE) ? BTM_BLE_SCAN_MODE_ACTI: p_inq->scan_type;
182 
183         /* allow config scanning type */
184         if (btsnd_hcic_ble_set_scan_params (p_inq->scan_type,
185                                             (UINT16)(!p_inq->scan_interval ? BTM_BLE_GAP_DISC_SCAN_INT : p_inq->scan_interval),
186                                             (UINT16)(!p_inq->scan_window ? BTM_BLE_GAP_DISC_SCAN_WIN : p_inq->scan_window),
187                                             BLE_ADDR_PUBLIC,
188                                             BTM_BLE_DEFAULT_SFP)) /* assume observe always not using white list */
189         {
190             /* start scan, disable duplicate filtering */
191             if (btsnd_hcic_ble_set_scan_enable (BTM_BLE_SCAN_ENABLE, BTM_BLE_DUPLICATE_DISABLE))
192             {
193                 status = BTM_SUCCESS;
194                 p_inq->proc_mode = BTM_BLE_OBSERVE;
195                 btm_cb.btm_inq_vars.inq_active |= BTM_LE_OBSERVE_ACTIVE;
196 
197                 if (duration != 0)
198                 {
199                     /* start inquiry timer */
200                     btu_start_timer (&p_inq->inq_timer_ent, BTU_TTYPE_BLE_INQUIRY, duration);
201                 }
202             }
203         }
204     }
205     else/*start = 0*/
206     {
207         if(btm_cb.btm_inq_vars.scan_type == INQ_GENERAL)
208         {
209             //Dont stop the scan. Just nullify the cbs
210             btm_cb.btm_inq_vars.p_inq_ble_results_cb = NULL;
211             btm_cb.btm_inq_vars.p_inq_ble_cmpl_cb = NULL;
212         }
213         else if (p_inq->proc_mode == BTM_BLE_OBSERVE)
214         {
215             btm_cb.btm_inq_vars.inq_active &= ~BTM_LE_OBSERVE_ACTIVE;
216             btm_ble_stop_scan();
217         }
218     }
219 
220     return status;
221 }
222 
223 /*******************************************************************************
224 **
225 ** Function         BTM_BleBroadcast
226 **
227 ** Description      This function is to start or stop broadcasting.
228 **
229 ** Parameters       start: start or stop broadcasting.
230 **
231 ** Returns          status.
232 **
233 *******************************************************************************/
BTM_BleBroadcast(BOOLEAN start)234 tBTM_STATUS BTM_BleBroadcast(BOOLEAN start)
235 {
236     tBTM_STATUS status = BTM_NO_RESOURCES;
237     tBTM_LE_RANDOM_CB *p_addr_cb = &btm_cb.ble_ctr_cb.addr_mgnt_cb;
238     tBTM_BLE_INQ_CB *p_cb = &btm_cb.ble_ctr_cb.inq_var;
239     UINT8 evt_type = p_cb->scan_rsp ? BTM_BLE_DISCOVER_EVT: BTM_BLE_NON_CONNECT_EVT;
240 
241     if (!HCI_LE_HOST_SUPPORTED(btm_cb.devcb.local_lmp_features[HCI_EXT_FEATURES_PAGE_1]))
242         return BTM_ILLEGAL_VALUE;
243 
244 #ifdef  BTM_BLE_PC_ADV_TEST_MODE
245     if (BTM_BLE_PC_ADV_TEST_MODE)
246     {
247         evt_type = p_cb->scan_rsp ? BTM_BLE_CONNECT_EVT: BTM_BLE_NON_CONNECT_EVT;
248     }
249 #endif
250 
251     if (start && p_cb->adv_mode == BTM_BLE_ADV_DISABLE)
252     {
253         /* update adv params */
254         if (!btsnd_hcic_ble_write_adv_params ((UINT16)(p_cb->adv_interval_min ? p_cb->adv_interval_min : BTM_BLE_GAP_ADV_INT),
255                                               (UINT16)(p_cb->adv_interval_max ? p_cb->adv_interval_max : BTM_BLE_GAP_ADV_INT),
256                                               evt_type,
257                                               p_addr_cb->own_addr_type,
258                                               p_cb->direct_bda.type,
259                                               p_cb->direct_bda.bda,
260                                               p_cb->adv_chnl_map,
261                                               p_cb->afp))
262 
263             status = BTM_NO_RESOURCES;
264         else
265             p_cb->evt_type = evt_type;
266 
267         status = btm_ble_start_adv ();
268     }
269     else if (!start && p_cb->adv_mode == BTM_BLE_ADV_ENABLE)
270     {
271         status = btm_ble_stop_adv();
272     }
273     else
274     {
275         status = BTM_WRONG_MODE;
276         BTM_TRACE_ERROR2("Can not %s Broadcast, device %s in Broadcast mode",
277             (start ? "Start" : "Stop"), (start ? "alerady" :"not"));
278     }
279     return status;
280 }
281 
282 /*******************************************************************************
283 **
284 ** Function         BTM_RegisterScanReqEvt
285 **
286 ** Description      This function is called to register a scan request callback
287 **                  on the advertiser.
288 **
289 ** Parameters       p_scan_req_cback: scan request callback.  If NULL, remove the
290 **                                    registration.
291 **
292 ** Returns          void
293 **
294 *******************************************************************************/
BTM_RegisterScanReqEvt(tBTM_BLE_SCAN_REQ_CBACK * p_scan_req_cback)295 void BTM_RegisterScanReqEvt(tBTM_BLE_SCAN_REQ_CBACK   *p_scan_req_cback)
296 {
297 #ifdef BTM_BLE_PC_ADV_TEST_MODE /* For general stack code (e.g. BTInsight testing), we simply do not define it to exclude or set it to TRUE to include */
298     if (BTM_BLE_PC_ADV_TEST_MODE)   /* For stack component, it is always defined and maps to a global variable g_bDraculaAdvertisingMode */
299     {
300         tBTM_BLE_CB *p_cb = &btm_cb.ble_ctr_cb;
301         p_cb->p_scan_req_cback = p_scan_req_cback;
302     }
303 #endif
304 }
305 
306 /*******************************************************************************
307 **
308 ** Function         BTM_BleSetBgConnType
309 **
310 ** Description      This function is called to set BLE connectable mode for a
311 **                  peripheral device.
312 **
313 ** Parameters       bg_conn_type: it can be auto connection, or selective connection.
314 **                  p_select_cback: callback function when selective connection procedure
315 **                              is being used.
316 **
317 ** Returns          void
318 **
319 *******************************************************************************/
BTM_BleSetBgConnType(tBTM_BLE_CONN_TYPE bg_conn_type,tBTM_BLE_SEL_CBACK * p_select_cback)320 BOOLEAN BTM_BleSetBgConnType(tBTM_BLE_CONN_TYPE   bg_conn_type,
321                              tBTM_BLE_SEL_CBACK   *p_select_cback)
322 {
323     BOOLEAN started = TRUE;
324 
325     BTM_TRACE_EVENT0 ("BTM_BleSetBgConnType ");
326     if (!HCI_LE_HOST_SUPPORTED(btm_cb.devcb.local_lmp_features[HCI_EXT_FEATURES_PAGE_1]))
327         return FALSE;
328 
329     if (btm_cb.ble_ctr_cb.bg_conn_type != bg_conn_type)
330     {
331         switch (bg_conn_type)
332         {
333             case BTM_BLE_CONN_AUTO:
334                 btm_ble_start_auto_conn(TRUE);
335                 break;
336 
337             case BTM_BLE_CONN_SELECTIVE:
338                 if (btm_cb.ble_ctr_cb.bg_conn_type == BTM_BLE_CONN_AUTO)
339                 {
340                     btm_ble_start_auto_conn(FALSE);
341                 }
342                 started = btm_ble_start_select_conn(TRUE, p_select_cback);
343                 break;
344 
345             case BTM_BLE_CONN_NONE:
346                 if (btm_cb.ble_ctr_cb.bg_conn_type == BTM_BLE_CONN_AUTO)
347                 {
348                     btm_ble_start_auto_conn(FALSE);
349                 }
350                 else if (btm_cb.ble_ctr_cb.bg_conn_type == BTM_BLE_CONN_SELECTIVE)
351                 {
352                     btm_ble_start_select_conn(FALSE, NULL);
353                 }
354                 started = TRUE;
355                 break;
356 
357             default:
358                 BTM_TRACE_ERROR1("invalid bg connection type : %d ", bg_conn_type);
359                 started = FALSE;
360                 break;
361         }
362 
363         if (started)
364             btm_cb.ble_ctr_cb.bg_conn_type = bg_conn_type;
365     }
366     return started;
367 }
368 
369 /*******************************************************************************
370 **
371 ** Function         BTM_BleUpdateBgConnDev
372 **
373 ** Description      This function is called to add or remove a device into/from
374 **                  background connection procedure. The background connection
375 *                   procedure is decided by the background connection type, it can be
376 *                   auto connection, or selective connection.
377 **
378 ** Parameters       add_remove: TRUE to add; FALSE to remove.
379 **                  remote_bda: device address to add/remove.
380 **
381 ** Returns          void
382 **
383 *******************************************************************************/
BTM_BleUpdateBgConnDev(BOOLEAN add_remove,BD_ADDR remote_bda)384 BOOLEAN BTM_BleUpdateBgConnDev(BOOLEAN add_remove, BD_ADDR   remote_bda)
385 {
386     BOOLEAN ret = TRUE;
387     UINT8   dev_wl_type = 0;
388     BTM_TRACE_EVENT0 (" BTM_BleUpdateBgConnDev");
389 
390     /* update white list */
391     ret = btm_update_bg_conn_list(add_remove, remote_bda, &dev_wl_type);
392 
393     btm_update_dev_to_white_list(add_remove, remote_bda, dev_wl_type);
394 
395     return ret;
396 }
397 
398 /*******************************************************************************
399 **
400 ** Function         BTM_BleSetConnMode
401 **
402 ** Description      This function is called to set BLE connectable mode for a
403 **                  peripheral device.
404 **
405 ** Parameters       directed: is directed connectable mode, or non-directed.
406 **                  p_dir_bda: connectable direct initiator's LE device address
407 **
408 ** Returns          void
409 **
410 *******************************************************************************/
BTM_BleSetConnMode(BOOLEAN is_directed)411 tBTM_STATUS BTM_BleSetConnMode(BOOLEAN is_directed)
412 {
413     tBTM_BLE_INQ_CB *p_cb = &btm_cb.ble_ctr_cb.inq_var;
414 
415     BTM_TRACE_EVENT1 ("BTM_BleSetConnMode is_directed = %d ", is_directed);
416     if (!HCI_LE_HOST_SUPPORTED(btm_cb.devcb.local_lmp_features[HCI_EXT_FEATURES_PAGE_1]))
417         return BTM_ILLEGAL_VALUE;
418 
419     p_cb->directed_conn = is_directed;
420     return btm_ble_set_connectability( p_cb->connectable_mode);
421 
422 }
423 
424 /*******************************************************************************
425 **
426 ** Function         btm_set_conn_mode_adv_init_addr
427 **
428 ** Description      set initator address type and local address type based on adv
429 **                  mode.
430 **
431 **
432 *******************************************************************************/
btm_set_conn_mode_adv_init_addr(tBTM_BLE_INQ_CB * p_cb,BD_ADDR_PTR p_addr_ptr,tBLE_ADDR_TYPE * p_init_addr_type,tBLE_ADDR_TYPE * p_own_addr_type)433 static UINT8 btm_set_conn_mode_adv_init_addr(tBTM_BLE_INQ_CB *p_cb,
434                                      BD_ADDR_PTR p_addr_ptr,
435                                      tBLE_ADDR_TYPE *p_init_addr_type,
436                                      tBLE_ADDR_TYPE *p_own_addr_type)
437 {
438     UINT8 evt_type;
439 
440     if ( p_cb->directed_conn)
441     {
442         /*  direct adv mode does not have privacy if privacy
443             is not enabled or no reconn addr config */
444         *p_own_addr_type   = BLE_ADDR_PUBLIC;
445         *p_init_addr_type  = p_cb->direct_bda.type;
446          memcpy(p_addr_ptr, p_cb->direct_bda.bda, BD_ADDR_LEN);
447         evt_type = BTM_BLE_CONNECT_DIR_EVT;
448     }
449     else /* undirect adv mode */
450     {
451         evt_type = BTM_BLE_CONNECT_EVT;
452     }
453 
454     return evt_type;
455 
456 }
457 
458 /*******************************************************************************
459 **
460 ** Function         BTM_BleSetAdvParams
461 **
462 ** Description      This function is called to set advertising parameters.
463 **
464 ** Parameters       adv_int_min: minimum advertising interval
465 **                  adv_int_max: maximum advertising interval
466 **                  p_dir_bda: connectable direct initiator's LE device address
467 **                  chnl_map: advertising channel map.
468 **
469 ** Returns          void
470 **
471 *******************************************************************************/
BTM_BleSetAdvParams(UINT16 adv_int_min,UINT16 adv_int_max,tBLE_BD_ADDR * p_dir_bda,tBTM_BLE_ADV_CHNL_MAP chnl_map)472 tBTM_STATUS BTM_BleSetAdvParams(UINT16 adv_int_min, UINT16 adv_int_max,
473                                 tBLE_BD_ADDR *p_dir_bda,
474                                 tBTM_BLE_ADV_CHNL_MAP chnl_map)
475 {
476     tBTM_LE_RANDOM_CB *p_addr_cb = &btm_cb.ble_ctr_cb.addr_mgnt_cb;
477     tBTM_BLE_INQ_CB *p_cb = &btm_cb.ble_ctr_cb.inq_var;
478     tBTM_STATUS status = BTM_SUCCESS;
479     BD_ADDR     p_addr_ptr =  {0};
480     tBLE_ADDR_TYPE   init_addr_type = BLE_ADDR_PUBLIC;
481     tBLE_ADDR_TYPE   own_addr_type = p_addr_cb->own_addr_type;
482     UINT8            adv_mode = p_cb->adv_mode;
483 
484     BTM_TRACE_EVENT0 ("BTM_BleSetAdvParams");
485 
486     if (!HCI_LE_HOST_SUPPORTED(btm_cb.devcb.local_lmp_features[HCI_EXT_FEATURES_PAGE_1]))
487         return BTM_ILLEGAL_VALUE;
488 
489     if (!BTM_BLE_VALID_PRAM(adv_int_min, BTM_BLE_ADV_INT_MIN, BTM_BLE_ADV_INT_MAX) ||
490         !BTM_BLE_VALID_PRAM(adv_int_max, BTM_BLE_ADV_INT_MIN, BTM_BLE_ADV_INT_MAX))
491     {
492         return BTM_ILLEGAL_VALUE;
493     }
494 
495     p_cb->adv_interval_min = adv_int_min;
496     p_cb->adv_interval_max = adv_int_max;
497     p_cb->adv_chnl_map = chnl_map;
498 
499     if (p_dir_bda)
500     {
501         memcpy(&p_cb->direct_bda, p_dir_bda, sizeof(tBLE_BD_ADDR));
502     }
503 
504     BTM_TRACE_EVENT0 ("update params for an active adv");
505 
506     btm_ble_stop_adv();
507 
508     if (p_cb->connectable_mode & BTM_BLE_CONNECTABLE)
509         p_cb->evt_type = btm_set_conn_mode_adv_init_addr(p_cb, p_addr_ptr, &init_addr_type, &own_addr_type);
510 
511     /* update adv params */
512     btsnd_hcic_ble_write_adv_params (p_cb->adv_interval_min,
513                                      p_cb->adv_interval_max,
514                                      p_cb->evt_type,
515                                      own_addr_type,
516                                      init_addr_type,
517                                      p_addr_ptr,
518                                      p_cb->adv_chnl_map,
519                                      p_cb->afp);
520 
521     if (adv_mode == BTM_BLE_ADV_ENABLE)
522         btm_ble_start_adv();
523 
524     return status;
525 }
526 
527 /*******************************************************************************
528 **
529 ** Function         BTM_BleReadAdvParams
530 **
531 ** Description      This function is called to set advertising parameters.
532 **
533 ** Parameters       adv_int_min: minimum advertising interval
534 **                  adv_int_max: maximum advertising interval
535 **                  p_dir_bda: connectable direct initiator's LE device address
536 **                  chnl_map: advertising channel map.
537 **
538 ** Returns          void
539 **
540 *******************************************************************************/
BTM_BleReadAdvParams(UINT16 * adv_int_min,UINT16 * adv_int_max,tBLE_BD_ADDR * p_dir_bda,tBTM_BLE_ADV_CHNL_MAP * p_chnl_map)541 void BTM_BleReadAdvParams (UINT16 *adv_int_min, UINT16 *adv_int_max,
542                            tBLE_BD_ADDR *p_dir_bda, tBTM_BLE_ADV_CHNL_MAP *p_chnl_map)
543 {
544     tBTM_BLE_INQ_CB *p_cb = &btm_cb.ble_ctr_cb.inq_var;
545 
546     BTM_TRACE_EVENT0 ("BTM_BleReadAdvParams ");
547     if (!HCI_LE_HOST_SUPPORTED(btm_cb.devcb.local_lmp_features[HCI_EXT_FEATURES_PAGE_1]))
548         return ;
549 
550     *adv_int_min = p_cb->adv_interval_min;
551     *adv_int_max = p_cb->adv_interval_max;
552     *p_chnl_map = p_cb->adv_chnl_map;
553 
554     if (p_dir_bda != NULL)
555     {
556         memcpy(p_dir_bda, &p_cb->direct_bda, sizeof(tBLE_BD_ADDR));
557     }
558 }
559 
560 /*******************************************************************************
561 **
562 ** Function         BTM_BleSetScanParams
563 **
564 ** Description      This function is called to set Scan parameters.
565 **
566 ** Parameters       adv_int_min: minimum advertising interval
567 **                  adv_int_max: maximum advertising interval
568 **                  p_dir_bda: connectable direct initiator's LE device address
569 **                  chnl_map: advertising channel map.
570 **                  scan_type: active scan or passive scan
571 **
572 ** Returns          void
573 **
574 *******************************************************************************/
BTM_BleSetScanParams(UINT16 scan_interval,UINT16 scan_window,tBTM_BLE_SCAN_MODE scan_mode)575 void BTM_BleSetScanParams(UINT16 scan_interval, UINT16 scan_window, tBTM_BLE_SCAN_MODE scan_mode)
576 {
577     tBTM_BLE_INQ_CB *p_cb = &btm_cb.ble_ctr_cb.inq_var;
578 
579     BTM_TRACE_EVENT0 (" BTM_BleSetScanParams");
580     if (!HCI_LE_HOST_SUPPORTED(btm_cb.devcb.local_lmp_features[HCI_EXT_FEATURES_PAGE_1]))
581         return ;
582 
583     if (BTM_BLE_VALID_PRAM(scan_interval, BTM_BLE_SCAN_INT_MIN, BTM_BLE_SCAN_INT_MAX) &&
584         BTM_BLE_VALID_PRAM(scan_window, BTM_BLE_SCAN_WIN_MIN, BTM_BLE_SCAN_WIN_MAX) &&
585         (scan_mode == BTM_BLE_SCAN_MODE_ACTI || scan_mode == BTM_BLE_SCAN_MODE_PASS))
586     {
587         p_cb->scan_type     = scan_mode;
588 
589         if (BTM_BLE_CONN_PARAM_UNDEF != scan_interval)
590             p_cb->scan_interval = scan_interval;
591 
592         if (BTM_BLE_CONN_PARAM_UNDEF != scan_window)
593             p_cb->scan_window   = scan_window;
594     }
595     else
596     {
597         BTM_TRACE_ERROR2("Illegal params: scan_interval = %d scan_window = %d",
598                         scan_interval, scan_window);
599     }
600 
601 }
602 
603 /*******************************************************************************
604 **
605 ** Function         BTM_BleWriteScanRsp
606 **
607 ** Description      This function is called to write LE scan response.
608 **
609 ** Parameters:      p_scan_rsp: scan response information.
610 **
611 ** Returns          void
612 **
613 *******************************************************************************/
BTM_BleWriteScanRsp(tBTM_BLE_AD_MASK data_mask,tBTM_BLE_ADV_DATA * p_data)614 tBTM_STATUS BTM_BleWriteScanRsp(tBTM_BLE_AD_MASK data_mask, tBTM_BLE_ADV_DATA *p_data)
615 {
616     tBTM_STATUS     status = BTM_NO_RESOURCES;
617     UINT8   rsp_data[BTM_BLE_AD_DATA_LEN],
618             *p = rsp_data;
619 
620     BTM_TRACE_EVENT0 (" BTM_BleWriteScanRsp");
621 
622     if (!HCI_LE_HOST_SUPPORTED(btm_cb.devcb.local_lmp_features[HCI_EXT_FEATURES_PAGE_1]))
623         return BTM_ILLEGAL_VALUE;
624 
625     memset(rsp_data, 0, BTM_BLE_AD_DATA_LEN);
626     btm_ble_build_adv_data(&data_mask, &p, p_data);
627 
628     if (btsnd_hcic_ble_set_scan_rsp_data((UINT8)(p - rsp_data), rsp_data))
629     {
630         status = BTM_SUCCESS;
631 
632         if (data_mask != 0)
633             btm_cb.ble_ctr_cb.inq_var.scan_rsp = TRUE;
634         else
635             btm_cb.ble_ctr_cb.inq_var.scan_rsp = FALSE;
636     }
637     else
638         status = BTM_ILLEGAL_VALUE;
639 
640     return status;
641 }
642 
643 /*******************************************************************************
644 **
645 ** Function         BTM_BleWriteAdvData
646 **
647 ** Description      This function is called to write advertising data.
648 **
649 ** Parameters:       None.
650 **
651 ** Returns          void
652 **
653 *******************************************************************************/
BTM_BleWriteAdvData(tBTM_BLE_AD_MASK data_mask,tBTM_BLE_ADV_DATA * p_data)654 tBTM_STATUS BTM_BleWriteAdvData(tBTM_BLE_AD_MASK data_mask, tBTM_BLE_ADV_DATA *p_data)
655 {
656     tBTM_BLE_LOCAL_ADV_DATA *p_cb_data = &btm_cb.ble_ctr_cb.inq_var.adv_data;
657     UINT8  *p;
658     UINT16   mask = data_mask;
659 
660     BTM_TRACE_EVENT0 ("BTM_BleWriteAdvData ");
661 
662     if (!HCI_LE_HOST_SUPPORTED(btm_cb.devcb.local_lmp_features[HCI_EXT_FEATURES_PAGE_1]))
663         return BTM_ILLEGAL_VALUE;
664 
665     memset(p_cb_data, 0, sizeof(tBTM_BLE_LOCAL_ADV_DATA));
666     p = p_cb_data->ad_data;
667     p_cb_data->data_mask = data_mask;
668 
669     p_cb_data->p_flags = btm_ble_build_adv_data(&mask, &p, p_data);
670 
671     p_cb_data->p_pad = p;
672 
673     if (data_mask != 0)
674     {
675         BTM_TRACE_ERROR0("Partial data write into ADV");
676     }
677 
678     p_cb_data->data_mask &= ~mask;
679 
680     if (btsnd_hcic_ble_set_adv_data((UINT8)(p_cb_data->p_pad - p_cb_data->ad_data),
681                                     p_cb_data->ad_data))
682         return BTM_SUCCESS;
683     else
684         return BTM_NO_RESOURCES;
685 
686 }
687 
688 /*******************************************************************************
689 **
690 ** Function         BTM_CheckAdvData
691 **
692 ** Description      This function is called to get ADV data for a specific type.
693 **
694 ** Parameters       p_adv - pointer of ADV data
695 **                  type   - finding ADV data type
696 **                  p_length - return the length of ADV data not including type
697 **
698 ** Returns          pointer of ADV data
699 **
700 *******************************************************************************/
BTM_CheckAdvData(UINT8 * p_adv,UINT8 type,UINT8 * p_length)701 UINT8 *BTM_CheckAdvData( UINT8 *p_adv, UINT8 type, UINT8 *p_length)
702 {
703     UINT8 *p = p_adv;
704     UINT8 length;
705     UINT8 adv_type;
706     BTM_TRACE_API1("BTM_CheckAdvData type=0x%02X", type);
707 
708     STREAM_TO_UINT8(length, p);
709 
710     while ( length && (p - p_adv <= BTM_BLE_CACHE_ADV_DATA_MAX))
711     {
712         STREAM_TO_UINT8(adv_type, p);
713 
714         if ( adv_type == type )
715         {
716             /* length doesn't include itself */
717             *p_length = length - 1; /* minus the length of type */
718             return p;
719         }
720         p += length - 1; /* skip the length of data */
721         STREAM_TO_UINT8(length, p);
722     }
723 
724     *p_length = 0;
725     return NULL;
726 }
727 
728 /*******************************************************************************
729 **
730 ** Function         btm_ble_build_adv_data
731 **
732 ** Description      This function is called build the adv data and rsp data.
733 *******************************************************************************/
btm_ble_build_adv_data(tBTM_BLE_AD_MASK * p_data_mask,UINT8 ** p_dst,tBTM_BLE_ADV_DATA * p_data)734 static UINT8 *btm_ble_build_adv_data(tBTM_BLE_AD_MASK *p_data_mask, UINT8 **p_dst, tBTM_BLE_ADV_DATA *p_data)
735 {
736     UINT16 data_mask = *p_data_mask;
737     UINT8   *p = *p_dst,
738     *p_flag = NULL;
739     UINT16  len = BTM_BLE_AD_DATA_LEN, cp_len = 0;
740     UINT8   i = 0;
741     tBTM_BLE_PROP_ELEM      *p_elem;
742 
743     BTM_TRACE_EVENT0 (" btm_ble_build_adv_data");
744 
745     /* build the adv data structure and build the data string */
746     if (data_mask)
747     {
748         /* flags */
749         if (data_mask & BTM_BLE_AD_BIT_FLAGS)
750         {
751             *p++ = 2;
752             *p++ = BTM_BLE_AD_TYPE_FLAG;
753             p_flag = p;
754             if (p_data)
755                 *p++ = p_data->flag;
756             else
757                 *p++ = 0;
758 
759             len -= 3;
760 
761             data_mask &= ~BTM_BLE_AD_BIT_FLAGS;
762         }
763         /* appearance data */
764         if (len > 3 && data_mask & BTM_BLE_AD_BIT_APPEARANCE)
765         {
766             *p++ = 3; /* length */
767             *p++ = BTM_BLE_AD_TYPE_APPEARANCE;
768             UINT16_TO_STREAM(p, p_data->appearance);
769             len -= 4;
770 
771             data_mask &= ~BTM_BLE_AD_BIT_APPEARANCE;
772         }
773         /* device name */
774 #if BTM_MAX_LOC_BD_NAME_LEN > 0
775         if (len > 2 && data_mask & BTM_BLE_AD_BIT_DEV_NAME)
776         {
777             if (strlen(btm_cb.cfg.bd_name) > (UINT16)(len - 2))
778             {
779                 *p++ = len - 2 + 1;
780                 *p++ = BTM_BLE_AD_TYPE_NAME_SHORT;
781                 ARRAY_TO_STREAM(p, btm_cb.cfg.bd_name, len - 2);
782             }
783             else
784             {
785                 cp_len = (UINT16)strlen(btm_cb.cfg.bd_name);
786                 *p++ = cp_len + 1;
787                 *p++ = BTM_BLE_AD_TYPE_NAME_CMPL;
788                 ARRAY_TO_STREAM(p, btm_cb.cfg.bd_name, cp_len);
789             }
790             len -= (cp_len + 2);
791             data_mask &= ~BTM_BLE_AD_BIT_DEV_NAME;
792         }
793 #endif
794         /* manufacturer data */
795         if (len > 2 && data_mask & BTM_BLE_AD_BIT_MANU &&
796             p_data && p_data->manu.len != 0 && p_data->manu.p_val)
797         {
798             if (p_data->manu.len > (len - 2))
799                 cp_len = len - 2;
800             else
801                 cp_len = p_data->manu.len;
802 
803             *p++ = cp_len + 1;
804             *p++ = BTM_BLE_AD_TYPE_MANU;
805             ARRAY_TO_STREAM(p, p_data->manu.p_val, cp_len);
806 
807             len -= (cp_len + 2);
808             data_mask &= ~BTM_BLE_AD_BIT_MANU;
809         }
810         /* TX power */
811         if (len > 2 && data_mask & BTM_BLE_AD_BIT_TX_PWR)
812         {
813             *p++ = 2;
814             *p++ = BTM_BLE_AD_TYPE_TX_PWR;
815             *p++ = btm_cb.ble_ctr_cb.inq_var.tx_power;
816             len -= 3;
817 
818             data_mask &= ~BTM_BLE_AD_BIT_TX_PWR;
819         }
820         /* services */
821         if (len > 2 && data_mask & BTM_BLE_AD_BIT_SERVICE &&
822             p_data && p_data->services.num_service != 0 &&
823             p_data->services.p_uuid)
824         {
825             if (p_data->services.num_service * 2 > (len - 2))
826             {
827                 cp_len = (len - 2)/2;
828                 *p ++ = 1 + cp_len * 2;
829                 *p++ = BTM_BLE_AD_TYPE_16SRV_PART;
830             }
831             else
832             {
833                 cp_len = p_data->services.num_service;
834                 *p++ = 1 + cp_len * 2;
835                 *p++ = BTM_BLE_AD_TYPE_16SRV_CMPL;
836             }
837             for (i = 0; i < cp_len; i ++)
838             {
839                 UINT16_TO_STREAM(p, *(p_data->services.p_uuid + i));
840             }
841 
842             len -= (cp_len * 2 + 2);
843             data_mask &= ~BTM_BLE_AD_BIT_SERVICE;
844         }
845         if (len >= 6 && data_mask & BTM_BLE_AD_BIT_INT_RANGE &&
846             p_data)
847         {
848             *p++ = 5;
849             *p++ = BTM_BLE_AD_TYPE_INT_RANGE;
850             UINT16_TO_STREAM(p, p_data->int_range.low);
851             UINT16_TO_STREAM(p, p_data->int_range.hi);
852             len -= 6;
853             data_mask &= ~BTM_BLE_AD_BIT_INT_RANGE;
854         }
855         if (data_mask & BTM_BLE_AD_BIT_PROPRIETARY && p_data && p_data->p_proprietary)
856         {
857             for (i = 0; i < p_data->p_proprietary->num_elem ; i ++)
858             {
859                 p_elem = p_data->p_proprietary->p_elem  + i;
860 
861                 if (len >= (2 + p_elem->len))/* len byte(1) + ATTR type(1) + Uuid len(2) + value length */
862                 {
863                     *p ++ = p_elem->len + 1; /* Uuid len + value length */
864                     *p ++ = p_elem->adv_type;
865                     ARRAY_TO_STREAM(p, p_elem->p_val, p_elem->len);
866 
867                     len -= (2 + p_elem->len);
868                 }
869                 else
870                 {
871                     BTM_TRACE_WARNING0("data exceed max adv packet length");
872                     break;
873                 }
874             }
875             data_mask &= ~BTM_BLE_AD_BIT_PROPRIETARY;
876         }
877     }
878 
879     *p_data_mask = data_mask;
880     *p_dst = p;
881 
882     return p_flag;
883 }
884 
885 /*******************************************************************************
886 **
887 ** Function         btm_ble_set_discoverability
888 **
889 ** Description      This function is called to set BLE discoverable mode.
890 **
891 ** Parameters:      mode: discoverability mode.
892 **
893 ** Returns          void
894 **
895 *******************************************************************************/
btm_ble_set_discoverability(UINT16 combined_mode)896 tBTM_STATUS btm_ble_set_discoverability(UINT16 combined_mode)
897 {
898     tBTM_LE_RANDOM_CB   *p_addr_cb = &btm_cb.ble_ctr_cb.addr_mgnt_cb;
899     tBTM_BLE_INQ_CB     *p_cb = &btm_cb.ble_ctr_cb.inq_var;
900     UINT16              mode = (combined_mode &  BTM_BLE_DISCOVERABLE_MASK);
901     UINT8               flag = 0;
902     UINT8               new_mode = BTM_BLE_ADV_ENABLE;
903     UINT8               evt_type = (p_cb->connectable_mode == BTM_BLE_NON_CONNECTABLE) ? \
904                                    ((p_cb->scan_rsp) ? BTM_BLE_DISCOVER_EVT : BTM_BLE_NON_CONNECT_EVT )\
905                                    : BTM_BLE_CONNECT_EVT;
906     tBTM_STATUS         status = BTM_SUCCESS;
907     BD_ADDR             p_addr_ptr= {0};
908     tBLE_ADDR_TYPE      init_addr_type = BLE_ADDR_PUBLIC,
909                         own_addr_type = p_addr_cb->own_addr_type;;
910 
911     BTM_TRACE_EVENT2 ("btm_ble_set_discoverability mode=0x%0x combined_mode=0x%x", mode, combined_mode);
912 
913     /*** Check mode parameter ***/
914     if (mode > BTM_BLE_MAX_DISCOVERABLE)
915         return(BTM_ILLEGAL_VALUE);
916 
917     p_cb->br_edr_supported_flag |= (combined_mode & BTM_DISCOVERABLE_MASK);
918     p_cb->discoverable_mode = mode;
919 
920     if (!p_cb->br_edr_supported_flag)
921     {
922         flag = BTM_BLE_BREDR_NOT_SPT;
923         BTM_TRACE_DEBUG1("btm_ble_set_discoverability (BREDR not sup)flag=0x%x",flag);
924     }
925 
926     BTM_TRACE_DEBUG1 ("br_edr_supported=0x%x", p_cb->br_edr_supported_flag);
927 
928     if (mode == BTM_BLE_LIMITED_DISCOVERABLE || mode == BTM_BLE_GENERAL_DISCOVERABLE)
929     {
930         BTM_TRACE_EVENT0 ("mode == BTM_BLE_LIMITED_DISCOVERABLE ");
931         /* write ADV data with limited disc flag */
932         if (mode == BTM_BLE_LIMITED_DISCOVERABLE)
933             flag |= BTM_BLE_LIMIT_DISC_FLAG ;
934         else
935             flag |= BTM_BLE_GEN_DISC_FLAG;
936     }
937     else  /* non-discoverable */
938     {
939         BTM_TRACE_EVENT0 ("mode == BTM_BLE_NON_DISCOVERABLE ");
940 
941         if (p_cb->connectable_mode == BTM_BLE_NON_CONNECTABLE)
942         {
943             p_cb->br_edr_supported_flag = 0;
944 
945             BTM_TRACE_EVENT0 ("always disable adv in non-discoverable non-connectable mode if no scan rsp ");
946             if (!p_cb->scan_rsp )
947 	            new_mode = BTM_BLE_ADV_DISABLE;
948 
949         }
950         else
951         {
952             p_cb->evt_type = btm_set_conn_mode_adv_init_addr(p_cb, p_addr_ptr, &init_addr_type, &own_addr_type);
953         }
954     }
955     btm_ble_update_adv_flag(flag);
956 
957     /* update adv params if start advertising */
958     BTM_TRACE_EVENT2 ("evt_type=0x%x p-cb->evt_type=0x%x ", evt_type, p_cb->evt_type);
959     if (new_mode == BTM_BLE_ADV_ENABLE &&
960         (evt_type != p_cb->evt_type ||p_cb->adv_addr_type != own_addr_type))
961     {
962         btm_ble_stop_adv();
963 
964         /* update adv params */
965         if (!btsnd_hcic_ble_write_adv_params ((UINT16)(p_cb->adv_interval_min ? p_cb->adv_interval_min : BTM_BLE_GAP_ADV_INT),
966                                               (UINT16)(p_cb->adv_interval_max ? p_cb->adv_interval_max : BTM_BLE_GAP_ADV_INT),
967                                               evt_type,
968                                               own_addr_type,
969                                               init_addr_type,
970                                               p_addr_ptr,
971                                               p_cb->adv_chnl_map,
972                                               p_cb->afp))
973 
974             status = BTM_NO_RESOURCES;
975         else
976         {
977             p_cb->evt_type = evt_type;
978             p_cb->adv_addr_type = own_addr_type;
979         }
980 
981     }
982 
983     if (status == BTM_SUCCESS && p_cb->adv_mode != new_mode)
984     {
985         if (new_mode == BTM_BLE_ADV_ENABLE)
986             status = btm_ble_start_adv();
987         else
988             status = btm_ble_stop_adv();
989     }
990 
991     /* set up stop advertising timer */
992     if (status == BTM_SUCCESS && mode == BTM_BLE_LIMITED_DISCOVERABLE)
993     {
994         BTM_TRACE_EVENT1 ("start timer for limited disc mode duration=%d (30 secs)", BTM_BLE_GAP_LIM_TOUT);
995         /* start Tgap(lim_timeout) */
996         btu_start_timer (&p_cb->inq_timer_ent, BTU_TTYPE_BLE_GAP_LIM_DISC,
997                          BTM_BLE_GAP_LIM_TOUT);
998     }
999     return status;
1000 }
1001 
1002 /*******************************************************************************
1003 **
1004 ** Function         btm_ble_set_connectability
1005 **
1006 ** Description      This function is called to set BLE connectability mode.
1007 **
1008 ** Parameters:      mode: connectability mode.
1009 **
1010 ** Returns          void
1011 **
1012 *******************************************************************************/
btm_ble_set_connectability(UINT16 combined_mode)1013 tBTM_STATUS btm_ble_set_connectability(UINT16 combined_mode)
1014 {
1015     tBTM_LE_RANDOM_CB       *p_addr_cb = &btm_cb.ble_ctr_cb.addr_mgnt_cb;
1016     tBTM_BLE_INQ_CB         *p_cb = &btm_cb.ble_ctr_cb.inq_var;
1017     UINT16                  mode = (combined_mode & BTM_BLE_CONNECTABLE_MASK);
1018     UINT8                   cur_flag = 0;
1019     UINT8                   cur_br_edr_not_sup_flag;
1020     UINT8                   new_flag;
1021     UINT8                   new_mode = BTM_BLE_ADV_ENABLE;
1022     UINT8                   evt_type = (p_cb->scan_rsp) ? BTM_BLE_DISCOVER_EVT: BTM_BLE_NON_CONNECT_EVT;
1023     tBTM_STATUS             status = BTM_SUCCESS;
1024     BD_ADDR                 p_addr_ptr =  {0};
1025     tBLE_ADDR_TYPE          init_addr_type = BLE_ADDR_PUBLIC,
1026                             own_addr_type = p_addr_cb->own_addr_type;
1027 
1028     BTM_TRACE_EVENT2 ("btm_ble_set_connectability mode=0x%0x combined_mode=0x%x", mode, combined_mode);
1029     /*** Check mode parameter ***/
1030     if (mode > BTM_BLE_MAX_CONNECTABLE)
1031         return(BTM_ILLEGAL_VALUE);
1032     if (btm_cb.ble_ctr_cb.inq_var.adv_data.p_flags)
1033         cur_flag = *btm_cb.ble_ctr_cb.inq_var.adv_data.p_flags ;
1034     cur_br_edr_not_sup_flag = (cur_flag & ((UINT8) BTM_BLE_BREDR_NOT_SPT));
1035 
1036     p_cb->br_edr_supported_flag |= ((combined_mode & BTM_CONNECTABLE_MASK) << 4);
1037     if (p_cb->br_edr_supported_flag && cur_br_edr_not_sup_flag)
1038     {
1039         new_flag = cur_flag & ((UINT8) (~BTM_BLE_BREDR_NOT_SPT));
1040         BTM_TRACE_EVENT2 ("new flag=0x%x cur flag=0x%x",new_flag,  cur_flag);
1041         btm_ble_update_adv_flag(new_flag);
1042     }
1043     p_cb->connectable_mode = mode;
1044 
1045     if (mode == BTM_BLE_NON_CONNECTABLE)
1046     {
1047         if (p_cb->discoverable_mode == BTM_BLE_NON_DISCOVERABLE)
1048         {
1049             p_cb->br_edr_supported_flag = 0;
1050             BTM_TRACE_EVENT0 ("always disable adv in non-discoverable non-connectable mode with no scan rsp");
1051             if(!p_cb->scan_rsp)
1052 	            new_mode = BTM_BLE_ADV_DISABLE;
1053 
1054         }
1055     }
1056     else /* connectable */
1057     {
1058         evt_type = btm_set_conn_mode_adv_init_addr(p_cb, p_addr_ptr, &init_addr_type, &own_addr_type);
1059     }
1060 
1061     /* update adv params if needed */
1062     if ((p_cb->evt_type != evt_type || p_cb->adv_addr_type != p_addr_cb->own_addr_type)
1063         && new_mode == BTM_BLE_ADV_ENABLE)
1064     {
1065         btm_ble_stop_adv();
1066 
1067         if (!btsnd_hcic_ble_write_adv_params ((UINT16)(p_cb->adv_interval_min ? p_cb->adv_interval_min : BTM_BLE_GAP_ADV_INT),
1068                                               (UINT16)(p_cb->adv_interval_max ? p_cb->adv_interval_max : BTM_BLE_GAP_ADV_INT),
1069                                               evt_type,
1070                                               own_addr_type,
1071                                               init_addr_type,
1072                                               p_addr_ptr,
1073                                               p_cb->adv_chnl_map,
1074                                               p_cb->afp))
1075             status = BTM_NO_RESOURCES;
1076         else
1077         {
1078             p_cb->evt_type = evt_type;
1079             p_cb->adv_addr_type = own_addr_type;
1080         }
1081     }
1082 
1083     /* update advertising mode */
1084     if (status == BTM_SUCCESS && new_mode != p_cb->adv_mode)
1085     {
1086         if (btsnd_hcic_ble_set_adv_enable (new_mode))
1087         {
1088             status = BTM_SUCCESS;
1089 
1090             p_cb->adv_mode = new_mode;
1091 
1092             if (p_cb->adv_mode == BTM_BLE_ADV_ENABLE &&
1093                 p_cb->afp != AP_SCAN_CONN_ALL)
1094                 btm_cb.ble_ctr_cb.wl_state |= BTM_BLE_WL_ADV;
1095             else
1096                 btm_cb.ble_ctr_cb.wl_state &= ~BTM_BLE_WL_ADV;
1097 
1098         }
1099     }
1100 
1101     return status;
1102 }
1103 
1104 /*******************************************************************************
1105 **
1106 ** Function         btm_ble_start_inquiry
1107 **
1108 ** Description      This function is called to start BLE inquiry procedure.
1109 **                  If the duration is zero, the periodic inquiry mode is cancelled.
1110 **
1111 ** Parameters:      mode - GENERAL or LIMITED inquiry
1112 **                  p_inq_params - pointer to the BLE inquiry parameter.
1113 **                  p_results_cb - callback returning pointer to results (tBTM_INQ_RESULTS)
1114 **                  p_cmpl_cb - callback indicating the end of an inquiry
1115 **
1116 **
1117 **
1118 ** Returns          BTM_CMD_STARTED if successfully started
1119 **                  BTM_NO_RESOURCES if could not allocate a message buffer
1120 **                  BTM_BUSY - if an inquiry is already active
1121 **
1122 *******************************************************************************/
btm_ble_start_inquiry(UINT8 mode,UINT8 duration)1123 tBTM_STATUS btm_ble_start_inquiry (UINT8 mode, UINT8   duration)
1124 {
1125     tBTM_STATUS status = BTM_NO_RESOURCES;
1126     tBTM_BLE_INQ_CB *p_inq = &btm_cb.ble_ctr_cb.inq_var;
1127 
1128     BTM_TRACE_DEBUG2("btm_ble_start_inquiry: mode = %02x inq_active = %d", mode, btm_cb.btm_inq_vars.inq_active);
1129 
1130     if (p_inq->proc_mode != BTM_BLE_INQUIRY_NONE)
1131     {
1132         BTM_TRACE_ERROR0("LE scan is active, can not start inquiry");
1133         return(BTM_BUSY);
1134     }
1135 
1136     btm_update_scanner_filter_policy(SP_ADV_ALL);
1137 
1138     /* start scan, already enable duplicate filtering */
1139     if (btsnd_hcic_ble_set_scan_enable (BTM_BLE_SCAN_ENABLE, BTM_BLE_DUPLICATE_DISABLE))
1140     {
1141         status = BTM_CMD_STARTED;
1142         p_inq->proc_mode = mode;
1143 
1144         if (duration != 0)
1145         {
1146             /* start inquiry timer */
1147             btu_start_timer (&p_inq->inq_timer_ent, BTU_TTYPE_BLE_INQUIRY, duration);
1148         }
1149     }
1150 
1151     return status;
1152 }
1153 
1154 /*******************************************************************************
1155 **
1156 ** Function         btm_ble_read_remote_name_cmpl
1157 **
1158 ** Description      This function is called when BLE remote name is received.
1159 **
1160 ** Returns          void
1161 **
1162 *******************************************************************************/
btm_ble_read_remote_name_cmpl(BOOLEAN status,BD_ADDR bda,UINT16 length,char * p_name)1163 void btm_ble_read_remote_name_cmpl(BOOLEAN status, BD_ADDR bda, UINT16 length, char *p_name)
1164 {
1165     UINT8   hci_status = HCI_SUCCESS;
1166     BD_NAME bd_name;
1167 
1168     memset(bd_name, 0, (BD_NAME_LEN + 1));
1169     memcpy((UINT8*)bd_name, p_name, length);
1170 
1171     if ((!status) || (length==0))
1172     {
1173         hci_status = HCI_ERR_HOST_TIMEOUT;
1174     }
1175 
1176     btm_process_remote_name(bda, bd_name, length +1, hci_status);
1177     btm_sec_rmt_name_request_complete (bda, (UINT8 *)p_name, hci_status);
1178 }
1179 
1180 /*******************************************************************************
1181 **
1182 ** Function         btm_ble_read_remote_name
1183 **
1184 ** Description      This function read remote LE device name using GATT read
1185 **                  procedure.
1186 **
1187 ** Parameters:       None.
1188 **
1189 ** Returns          void
1190 **
1191 *******************************************************************************/
btm_ble_read_remote_name(BD_ADDR remote_bda,tBTM_INQ_INFO * p_cur,tBTM_CMPL_CB * p_cb)1192 tBTM_STATUS btm_ble_read_remote_name(BD_ADDR remote_bda, tBTM_INQ_INFO *p_cur, tBTM_CMPL_CB *p_cb)
1193 {
1194     tBTM_INQUIRY_VAR_ST      *p_inq = &btm_cb.btm_inq_vars;
1195 
1196     if (!HCI_LE_HOST_SUPPORTED(btm_cb.devcb.local_lmp_features[HCI_EXT_FEATURES_PAGE_1]))
1197         return BTM_ERR_PROCESSING;
1198 
1199     if (p_cur &&
1200         p_cur->results.ble_evt_type != BTM_BLE_EVT_CONN_ADV &&
1201         p_cur->results.ble_evt_type != BTM_BLE_EVT_CONN_DIR_ADV)
1202     {
1203         BTM_TRACE_DEBUG0("name request to non-connectable device failed.");
1204         return BTM_ERR_PROCESSING;
1205     }
1206 
1207     /* read remote device name using GATT procedure */
1208     if (p_inq->remname_active)
1209         return BTM_BUSY;
1210 
1211     if (!GAP_BleReadPeerDevName(remote_bda, btm_ble_read_remote_name_cmpl))
1212         return BTM_BUSY;
1213 
1214     p_inq->p_remname_cmpl_cb = p_cb;
1215     p_inq->remname_active = TRUE;
1216 
1217     memcpy(p_inq->remname_bda, remote_bda, BD_ADDR_LEN);
1218 
1219     btu_start_timer (&p_inq->rmt_name_timer_ent,
1220                      BTU_TTYPE_BTM_RMT_NAME,
1221                      BTM_EXT_BLE_RMT_NAME_TIMEOUT);
1222 
1223     return BTM_CMD_STARTED;
1224 }
1225 
1226 /*******************************************************************************
1227 **
1228 ** Function         btm_ble_cancel_remote_name
1229 **
1230 ** Description      This function cancel read remote LE device name.
1231 **
1232 ** Parameters:       None.
1233 **
1234 ** Returns          void
1235 **
1236 *******************************************************************************/
btm_ble_cancel_remote_name(BD_ADDR remote_bda)1237 BOOLEAN btm_ble_cancel_remote_name(BD_ADDR remote_bda)
1238 {
1239     tBTM_INQUIRY_VAR_ST      *p_inq = &btm_cb.btm_inq_vars;
1240     BOOLEAN     status;
1241 
1242     status = GAP_BleCancelReadPeerDevName(remote_bda);
1243 
1244     p_inq->remname_active = FALSE;
1245     memset(p_inq->remname_bda, 0, BD_ADDR_LEN);
1246     btu_stop_timer(&p_inq->rmt_name_timer_ent);
1247 
1248     return status;
1249 }
1250 
1251 /*******************************************************************************
1252 **
1253 ** Function         btm_ble_update_adv_flag
1254 **
1255 ** Description      This function update the limited discoverable flag in the adv
1256 **                  data.
1257 **
1258 ** Parameters:       None.
1259 **
1260 ** Returns          void
1261 **
1262 *******************************************************************************/
btm_ble_update_adv_flag(UINT8 flag)1263 static void btm_ble_update_adv_flag(UINT8 flag)
1264 {
1265     tBTM_BLE_LOCAL_ADV_DATA *p_adv_data = &btm_cb.ble_ctr_cb.inq_var.adv_data;
1266     UINT8   *p;
1267 
1268     BTM_TRACE_DEBUG1 ("btm_ble_update_adv_flag new=0x%x", flag);
1269 
1270     if (p_adv_data->p_flags != NULL)
1271     {
1272         BTM_TRACE_DEBUG1 ("btm_ble_update_adv_flag old=0x%x",   *p_adv_data->p_flags);
1273         *p_adv_data->p_flags = flag;
1274     }
1275     else /* no FLAGS in ADV data*/
1276     {
1277         p = (p_adv_data->p_pad == NULL) ? p_adv_data->ad_data : p_adv_data->p_pad;
1278         /* need 3 bytes space to stuff in the flags, if not */
1279         /* erase all written data, just for flags */
1280         if ((BTM_BLE_AD_DATA_LEN - (p - p_adv_data->ad_data)) < 3)
1281         {
1282             p = p_adv_data->p_pad = p_adv_data->ad_data;
1283             memset(p_adv_data->ad_data, 0, BTM_BLE_AD_DATA_LEN);
1284         }
1285 
1286         *p++ = 2;
1287         *p++ = BTM_BLE_AD_TYPE_FLAG;
1288         p_adv_data->p_flags = p;
1289         *p++ = flag;
1290         p_adv_data->p_pad = p;
1291     }
1292 
1293     if (btsnd_hcic_ble_set_adv_data((UINT8)(p_adv_data->p_pad - p_adv_data->ad_data),
1294                                     p_adv_data->ad_data))
1295         p_adv_data->data_mask |= BTM_BLE_AD_BIT_FLAGS;
1296 
1297 }
1298 
1299 #if 0
1300 /*******************************************************************************
1301 **
1302 ** Function         btm_ble_parse_adv_data
1303 **
1304 ** Description      This function parse the adv data into a structure.
1305 **
1306 ** Returns          pointer to entry, or NULL if not found
1307 **
1308 *******************************************************************************/
1309 static void btm_ble_parse_adv_data(tBTM_INQ_INFO *p_info, UINT8 *p_data,
1310                                    UINT8 len, tBTM_BLE_INQ_DATA *p_adv_data, UINT8 *p_buf)
1311 {
1312     UINT8   *p_cur = p_data;
1313     UINT8   ad_len, ad_type, ad_flag;
1314 
1315     BTM_TRACE_EVENT0 (" btm_ble_parse_adv_data");
1316 
1317     while (len > 0)
1318     {
1319         BTM_TRACE_DEBUG1("btm_ble_parse_adv_data: len = %d", len);
1320         if ((ad_len = *p_cur ++) == 0)
1321             break;
1322 
1323         ad_type = *p_cur ++;
1324 
1325         BTM_TRACE_DEBUG2("     ad_type = %02x ad_len = %d", ad_type, ad_len);
1326 
1327         switch (ad_type)
1328         {
1329             case BTM_BLE_AD_TYPE_NAME_SHORT:
1330 
1331             case BTM_BLE_AD_TYPE_NAME_CMPL:
1332                 p_adv_data->ad_mask |= BTM_BLE_AD_BIT_DEV_NAME;
1333                 if (p_info)
1334                 {
1335                     p_info->remote_name_type =(ad_type == BTM_BLE_AD_TYPE_NAME_SHORT) ?
1336                                               BTM_BLE_NAME_SHORT: BTM_BLE_NAME_CMPL;
1337                     memcpy(p_info->remote_name, p_cur, ad_len -1);
1338                     p_info->remote_name[ad_len] = 0;
1339                     p_adv_data->p_remote_name = p_info->remote_name;
1340                     p_info->remote_name_len = p_adv_data->remote_name_len = ad_len - 1;
1341                     BTM_TRACE_DEBUG1("BTM_BLE_AD_TYPE_NAME name = %s",p_adv_data->p_remote_name);
1342                 }
1343                 p_cur += (ad_len -1);
1344 
1345                 break;
1346 
1347             case BTM_BLE_AD_TYPE_FLAG:
1348                 p_adv_data->ad_mask |= BTM_BLE_AD_BIT_FLAGS;
1349                 ad_flag = *p_cur ++;
1350                 p_adv_data->flag = (UINT8)(ad_flag & BTM_BLE_ADV_FLAG_MASK) ;
1351                 BTM_TRACE_DEBUG3("BTM_BLE_AD_TYPE_FLAG flag = %s | %s | %s",
1352                                  (p_adv_data->flag & BTM_BLE_LIMIT_DISC_FLAG)? "LE_LIMIT_DISC" : "",
1353                                  (p_adv_data->flag & BTM_BLE_GEN_DISC_FLAG)? "LE_GENERAL_DISC" : "",
1354                                  (p_adv_data->flag & BTM_BLE_BREDR_NOT_SPT)? "LE Only device" : "");
1355                 break;
1356 
1357             case BTM_BLE_AD_TYPE_TX_PWR:
1358                 p_adv_data->ad_mask |= BTM_BLE_AD_BIT_TX_PWR;
1359                 p_adv_data->tx_power_level = (INT8)*p_cur ++;
1360                 BTM_TRACE_DEBUG1("BTM_BLE_AD_TYPE_TX_PWR tx_level = %d", p_adv_data->tx_power_level);
1361                 break;
1362 
1363             case BTM_BLE_AD_TYPE_MANU:
1364 
1365             case BTM_BLE_AD_TYPE_16SRV_PART:
1366             case BTM_BLE_AD_TYPE_16SRV_CMPL:
1367                 p_adv_data->ad_mask |= BTM_BLE_AD_BIT_SERVICE;
1368                 /* need allocate memory to store UUID list */
1369                 p_adv_data->service.num_service = (ad_len - 1)/2;
1370                 BTM_TRACE_DEBUG1("service UUID list, num = %d", p_adv_data->service.num_service);
1371                 p_cur += (ad_len - 1);
1372                 break;
1373 
1374             case BTM_BLE_AD_TYPE_SOL_SRV_UUID:
1375                 p_adv_data->ad_mask |= BTM_BLE_AD_BIT_SERVICE_SOL;
1376                 /* need allocate memory to store UUID list */
1377                 p_adv_data->service.num_service = (ad_len - 1)/2;
1378                 BTM_TRACE_DEBUG1("service UUID list, num = %d", p_adv_data->service.num_service);
1379                 p_cur += (ad_len - 1);
1380                 break;
1381 
1382             case BTM_BLE_AD_TYPE_128SOL_SRV_UUID:
1383                 p_adv_data->ad_mask |= BTM_BLE_AD_BIT_SERVICE_128SOL;
1384                 /* need allocate memory to store UUID list */
1385                 p_adv_data->service.num_service = (ad_len - 1)/16;
1386                 BTM_TRACE_DEBUG1("service UUID list, num = %d", p_adv_data->service.num_service);
1387                 p_cur += (ad_len - 1);
1388                 break;
1389 
1390             case BTM_BLE_AD_TYPE_APPEARANCE:
1391             case BTM_BLE_AD_TYPE_PUBLIC_TARGET:
1392             case BTM_BLE_AD_TYPE_RANDOM_TARGET:
1393             default:
1394                 break;
1395         }
1396         len -= (ad_len + 1);
1397     }
1398 }
1399 #endif
1400 
1401 /*******************************************************************************
1402 **
1403 ** Function         btm_ble_cache_adv_data
1404 **
1405 ** Description      Update advertising cache data.
1406 **
1407 ** Returns          void
1408 **
1409 *******************************************************************************/
btm_ble_cache_adv_data(tBTM_INQ_RESULTS * p_cur,UINT8 data_len,UINT8 * p,UINT8 evt_type)1410 void btm_ble_cache_adv_data(tBTM_INQ_RESULTS *p_cur, UINT8 data_len, UINT8 *p, UINT8 evt_type)
1411 {
1412     tBTM_BLE_INQ_CB     *p_le_inq_cb = &btm_cb.ble_ctr_cb.inq_var;
1413     UINT8 *p_cache;
1414     UINT8 length;
1415 
1416     /* cache adv report/scan response data */
1417     if (evt_type != BTM_BLE_SCAN_RSP_EVT)
1418     {
1419         p_le_inq_cb->adv_len = 0;
1420         memset(p_le_inq_cb->adv_data_cache, 0, BTM_BLE_CACHE_ADV_DATA_MAX);
1421     }
1422 
1423     if (data_len > 0)
1424     {
1425         p_cache = &p_le_inq_cb->adv_data_cache[p_le_inq_cb->adv_len];
1426         STREAM_TO_UINT8(length, p);
1427         while ( length && ((p_le_inq_cb->adv_len + length + 1) <= BTM_BLE_CACHE_ADV_DATA_MAX))
1428         {
1429             /* copy from the length byte & data into cache */
1430             memcpy(p_cache, p-1, length+1);
1431             /* advance the cache pointer past data */
1432             p_cache += length+1;
1433             /* increment cache length */
1434             p_le_inq_cb->adv_len += length+1;
1435             /* skip the length of data */
1436             p += length;
1437             STREAM_TO_UINT8(length, p);
1438         }
1439     }
1440 
1441     /* parse service UUID from adv packet and save it in inq db eir_uuid */
1442     /* TODO */
1443 }
1444 
1445 /*******************************************************************************
1446 **
1447 ** Function         btm_ble_is_discoverable
1448 **
1449 ** Description      check ADV flag to make sure device is discoverable and match
1450 **                  the search condition
1451 **
1452 ** Parameters
1453 **
1454 ** Returns          void
1455 **
1456 *******************************************************************************/
btm_ble_is_discoverable(BD_ADDR bda,UINT8 evt_type,UINT8 * p)1457 BOOLEAN btm_ble_is_discoverable(BD_ADDR bda, UINT8 evt_type, UINT8 *p)
1458 {
1459     BOOLEAN             is_discoverable = FALSE;
1460     UINT8               *p_flag, flag = 0;
1461     UINT8                data_len;
1462     tBTM_INQ_PARMS      *p_cond = &btm_cb.btm_inq_vars.inqparms;
1463 
1464     STREAM_TO_UINT8    (data_len, p);
1465 
1466     /* for observer, always "discoverable */
1467     if (btm_cb.ble_ctr_cb.inq_var.proc_mode == BTM_BLE_OBSERVE ||
1468         (btm_cb.ble_ctr_cb.inq_var.proc_mode == BTM_BLE_SELECT_SCAN &&
1469         btm_cb.ble_ctr_cb.bg_conn_type == BTM_BLE_CONN_SELECTIVE))
1470         return TRUE;
1471 
1472     /* does not match filter condition */
1473     if (p_cond->filter_cond_type == BTM_FILTER_COND_BD_ADDR &&
1474         memcmp(bda, p_cond->filter_cond.bdaddr_cond, BD_ADDR_LEN) != 0)
1475     {
1476         BTM_TRACE_DEBUG0("BD ADDR does not meet filter condition");
1477         return FALSE;
1478     }
1479 
1480     /* scan response does not include the flag */
1481     if (evt_type == BTM_BLE_SCAN_RSP_EVT)
1482         return FALSE;
1483 
1484     if (data_len > BTM_BLE_ADV_DATA_LEN_MAX)
1485     {
1486         BTM_TRACE_WARNING1("ADV data too long %d. discard", data_len);
1487         return FALSE;
1488     }
1489 
1490     if (data_len != 0)
1491     {
1492         if ((p_flag = BTM_CheckAdvData(p, BTM_BLE_AD_TYPE_FLAG, &data_len)) != NULL)
1493         {
1494             flag = * p_flag;
1495 
1496             if ((btm_cb.ble_ctr_cb.inq_var.proc_mode == BTM_BLE_GENERAL_INQUIRY) &&
1497                 (flag & (BTM_BLE_LIMIT_DISC_FLAG|BTM_BLE_GEN_DISC_FLAG)) != 0)
1498             {
1499                 BTM_TRACE_DEBUG0("Find Generable Discoverable device");
1500                 is_discoverable = TRUE;
1501             }
1502 
1503             else if (btm_cb.ble_ctr_cb.inq_var.proc_mode == BTM_BLE_LIMITED_INQUIRY &&
1504                      (flag & BTM_BLE_LIMIT_DISC_FLAG) != 0)
1505             {
1506                 BTM_TRACE_DEBUG0("Find limited discoverable device");
1507                 is_discoverable = TRUE;
1508             }
1509 
1510         }
1511     }
1512 
1513     if (!is_discoverable)
1514     {
1515         BTM_TRACE_ERROR1("discoverable flag not desired: %d", flag);
1516     }
1517 
1518     return is_discoverable;
1519 }
1520 
1521 /*******************************************************************************
1522 **
1523 ** Function         btm_ble_update_inq_result
1524 **
1525 ** Description      Update adv packet information into inquiry result.
1526 **
1527 ** Parameters
1528 **
1529 ** Returns          void
1530 **
1531 *******************************************************************************/
btm_ble_update_inq_result(tINQ_DB_ENT * p_i,UINT8 addr_type,UINT8 evt_type,UINT8 * p)1532 BOOLEAN btm_ble_update_inq_result(tINQ_DB_ENT *p_i, UINT8 addr_type, UINT8 evt_type, UINT8 *p)
1533 {
1534     BOOLEAN             to_report = TRUE;
1535     tBTM_INQ_RESULTS     *p_cur = &p_i->inq_info.results;
1536     UINT8               len;
1537     UINT8               *p_flag;
1538     tBTM_INQUIRY_VAR_ST  *p_inq = &btm_cb.btm_inq_vars;
1539     UINT8                data_len, rssi;
1540     tBTM_BLE_INQ_CB     *p_le_inq_cb = &btm_cb.ble_ctr_cb.inq_var;
1541     UINT8 *p1;
1542 
1543     STREAM_TO_UINT8    (data_len, p);
1544 
1545     if (data_len > BTM_BLE_ADV_DATA_LEN_MAX)
1546     {
1547         BTM_TRACE_WARNING1("EIR data too long %d. discard", data_len);
1548         return FALSE;
1549     }
1550     btm_ble_cache_adv_data(p_cur, data_len, p, evt_type);
1551 
1552     p1 = (p + data_len);
1553     STREAM_TO_UINT8 (rssi, p1);
1554 
1555     /* Save the info */
1556     p_cur->inq_result_type = BTM_INQ_RESULT_BLE;
1557     p_cur->ble_addr_type    = addr_type;
1558     p_cur->rssi = rssi;
1559 
1560     /* active scan, always wait until get scan_rsp to report the result */
1561     if ((btm_cb.ble_ctr_cb.inq_var.scan_type == BTM_BLE_SCAN_MODE_ACTI &&
1562          (evt_type == BTM_BLE_CONNECT_EVT || evt_type == BTM_BLE_DISCOVER_EVT)))
1563     {
1564         BTM_TRACE_DEBUG1("btm_ble_update_inq_result scan_rsp=false, to_report=false,\
1565                               scan_type_active=%d", btm_cb.ble_ctr_cb.inq_var.scan_type);
1566         p_i->scan_rsp = FALSE;
1567         to_report = FALSE;
1568     }
1569     else
1570         p_i->scan_rsp = TRUE;
1571 
1572     if (p_i->inq_count != p_inq->inq_counter)
1573         p_cur->device_type = BT_DEVICE_TYPE_BLE;
1574     else
1575         p_cur->device_type |= BT_DEVICE_TYPE_BLE;
1576 
1577     if (evt_type != BTM_BLE_SCAN_RSP_EVT)
1578         p_cur->ble_evt_type     = evt_type;
1579 
1580     p_i->inq_count = p_inq->inq_counter;   /* Mark entry for current inquiry */
1581 
1582     if (p_le_inq_cb->adv_len != 0)
1583     {
1584         if ((p_flag = BTM_CheckAdvData(p_le_inq_cb->adv_data_cache, BTM_BLE_AD_TYPE_FLAG, &len)) != NULL)
1585             p_cur->flag = * p_flag;
1586     }
1587 
1588     /* if BR/EDR not supported is not set, assume is a DUMO device */
1589     if ((p_cur->flag & BTM_BLE_BREDR_NOT_SPT) == 0 &&
1590          evt_type != BTM_BLE_CONNECT_DIR_EVT)
1591     {
1592         if (p_cur->ble_addr_type != BLE_ADDR_RANDOM)
1593         {
1594             BTM_TRACE_DEBUG0("BR/EDR NOT support bit not set, treat as DUMO");
1595             p_cur->device_type |= BT_DEVICE_TYPE_DUMO;
1596         } else {
1597             BTM_TRACE_DEBUG0("Random address, treating device as LE only");
1598         }
1599     }
1600     else
1601     {
1602         BTM_TRACE_DEBUG0("BR/EDR NOT SUPPORT bit set, LE only device");
1603     }
1604 
1605     return to_report;
1606 
1607 }
1608 
1609 /*******************************************************************************
1610 **
1611 ** Function         btm_send_sel_conn_callback
1612 **
1613 ** Description      send selection connection request callback.
1614 **
1615 ** Parameters
1616 **
1617 ** Returns          void
1618 **
1619 *******************************************************************************/
btm_send_sel_conn_callback(BD_ADDR remote_bda,UINT8 evt_type,UINT8 * p_data,UINT8 addr_type)1620 void btm_send_sel_conn_callback(BD_ADDR remote_bda, UINT8 evt_type, UINT8 *p_data, UINT8 addr_type)
1621 {
1622     UINT8   data_len, len;
1623     UINT8   *p_dev_name, remname[31] = {0};
1624 
1625     if (btm_cb.ble_ctr_cb.p_select_cback == NULL ||
1626         /* non-connectable device */
1627         (evt_type != BTM_BLE_EVT_CONN_ADV && evt_type != BTM_BLE_EVT_CONN_DIR_ADV))
1628         return;
1629 
1630     STREAM_TO_UINT8    (data_len, p_data);
1631 
1632     /* get the device name if exist in ADV data */
1633     if (data_len != 0)
1634     {
1635         p_dev_name = BTM_CheckAdvData(p_data, BTM_BLE_AD_TYPE_NAME_CMPL, &len);
1636 
1637         if (p_dev_name == NULL)
1638             p_dev_name = BTM_CheckAdvData(p_data, BTM_BLE_AD_TYPE_NAME_SHORT, &len);
1639 
1640         if (p_dev_name)
1641             memcpy(remname, p_dev_name, len);
1642     }
1643     /* allow connection */
1644     if ((* btm_cb.ble_ctr_cb.p_select_cback)(remote_bda, remname))
1645     {
1646         /* terminate selective connection, initiate connection */
1647         btm_ble_initiate_select_conn(remote_bda);
1648     }
1649 }
1650 
1651 /*******************************************************************************
1652 **
1653 ** Function         btm_ble_process_adv_pkt
1654 **
1655 ** Description      This function is called when adv packet report events are
1656 **                  received from the device. It updates the inquiry database.
1657 **                  If the inquiry database is full, the oldest entry is discarded.
1658 **
1659 ** Parameters
1660 **
1661 ** Returns          void
1662 **
1663 *******************************************************************************/
btm_ble_process_adv_pkt(UINT8 * p_data)1664 void btm_ble_process_adv_pkt (UINT8 *p_data)
1665 {
1666     BD_ADDR             bda;
1667     UINT8               evt_type = 0, *p = p_data;
1668     UINT8               addr_type = 0;
1669 
1670     /* always get one device at a time */
1671     p ++;
1672 
1673     /* Extract inquiry results */
1674     STREAM_TO_UINT8    (evt_type, p);
1675     STREAM_TO_UINT8    (addr_type, p);
1676     STREAM_TO_BDADDR   (bda, p);
1677 
1678 #ifdef BTM_BLE_PC_ADV_TEST_MODE /* For general stack code (e.g. BTInsight testing), we simply do not define it to exclude or set it to TRUE to include */
1679     if (BTM_BLE_PC_ADV_TEST_MODE)   /* For stack component, it is always defined and maps to a global variable g_bDraculaAdvertisingMode */
1680     {
1681         if (btm_cb.ble_ctr_cb.p_scan_req_cback)
1682             (*btm_cb.ble_ctr_cb.p_scan_req_cback)(bda, addr_type, evt_type);
1683     }
1684 #endif
1685 
1686 
1687 
1688     /* Only process the results if the inquiry is still active */
1689     if ((btm_cb.btm_inq_vars.inq_active & BTM_LE_SCAN_ACTIVE_MASK) == 0 &&
1690         (btm_cb.ble_ctr_cb.bg_conn_type != BTM_BLE_CONN_SELECTIVE ||
1691          /* or selective auto connection is active */
1692          btm_cb.ble_ctr_cb.p_select_cback == NULL))
1693         return;
1694 
1695     BTM_TRACE_DEBUG6("btm_ble_process_adv_pkt:bda= %0x:%0x:%0x:%0x:%0x:%0x",
1696                                      bda[0],bda[1],bda[2],bda[3],bda[4],bda[5]);
1697     btm_ble_process_adv_pkt_cont(bda, addr_type, evt_type, p);
1698 }
1699 
1700 /*******************************************************************************
1701 **
1702 ** Function         btm_ble_process_adv_pkt_cont
1703 **
1704 ** Description      This function is called after random address resolution is
1705 **                  done, and proceed to process adv packet.
1706 **
1707 ** Parameters
1708 **
1709 ** Returns          void
1710 **
1711 *******************************************************************************/
btm_ble_process_adv_pkt_cont(BD_ADDR bda,UINT8 addr_type,UINT8 evt_type,UINT8 * p)1712 static void btm_ble_process_adv_pkt_cont(BD_ADDR bda, UINT8 addr_type, UINT8 evt_type, UINT8 *p)
1713 {
1714     tINQ_DB_ENT          *p_i;
1715     BOOLEAN              to_report = FALSE;
1716     BOOLEAN              to_report_LE = TRUE; //var for reporting to LE observe
1717     tBTM_INQUIRY_VAR_ST  *p_inq = &btm_cb.btm_inq_vars;
1718     tBTM_INQ_RESULTS_CB  *p_inq_results_cb = p_inq->p_inq_results_cb;
1719     tBTM_INQ_RESULTS_CB  *p_inq_ble_results_cb = p_inq->p_inq_ble_results_cb;
1720     tBTM_BLE_INQ_CB      *p_le_inq_cb = &btm_cb.ble_ctr_cb.inq_var;
1721     BTM_TRACE_DEBUG2("btm_ble_process_adv_pkt_cont: addr_type: %d, evt_type: %d", addr_type, evt_type);
1722 
1723     p_i = btm_inq_db_find (bda);
1724 
1725     /* Check if this address has already been processed for this inquiry */
1726     if (btm_inq_find_bdaddr(bda))
1727     {
1728         /* never been report as an LE device */
1729         if ((p_i &&
1730             (!(p_i->inq_info.results.device_type & BT_DEVICE_TYPE_BLE) ||
1731               /* scan repsonse to be updated */
1732               (!p_i->scan_rsp)))
1733             ||
1734             btm_cb.ble_ctr_cb.inq_var.proc_mode == BTM_BLE_OBSERVE)
1735         {
1736             BTM_TRACE_DEBUG0("update new BLE information ");
1737             to_report = TRUE;
1738         }
1739         else
1740         {
1741             to_report = FALSE;
1742         }
1743     }
1744     else /* not been processed in this round */
1745     {
1746         to_report = TRUE;
1747     }
1748 
1749     /* If existing entry, use that, else get  a new one (possibly reusing the oldest) */
1750     if (p_i == NULL)
1751     {
1752         if ((p_i = btm_inq_db_new (bda)) != NULL)
1753         {
1754             p_inq->inq_cmpl_info.num_resp++;
1755         }
1756         else
1757             return;
1758 
1759         if (to_report && btm_ble_is_discoverable(bda, evt_type, p))
1760         {
1761             to_report = TRUE;
1762         }
1763         else
1764         {
1765             BTM_TRACE_ERROR0("discard adv pkt");
1766             to_report = FALSE;
1767         }
1768     }
1769     else if (p_i->inq_count != p_inq->inq_counter) /* first time seen in this inquiry */
1770     {
1771         p_inq->inq_cmpl_info.num_resp++;
1772     }
1773     /* update the LE device information in inquiry database */
1774     to_report_LE = btm_ble_update_inq_result(p_i, addr_type, evt_type, p);
1775     if (to_report)
1776         to_report = to_report_LE;
1777 #if BTM_USE_INQ_RESULTS_FILTER == TRUE
1778     /* If the number of responses found and limited, issue a cancel inquiry */
1779     if (p_inq->inqparms.max_resps &&
1780         p_inq->inq_cmpl_info.num_resp == p_inq->inqparms.max_resps)
1781     {
1782         /* new device */
1783         if (p_i == NULL ||
1784             (/* assume a DUMO device, BR/EDR inquiry is always active */
1785              p_i && p_i->inq_info.results.device_type == BT_DEVICE_TYPE_BLE && p_i->scan_rsp))
1786         {
1787             BTM_TRACE_WARNING0("INQ RES: Extra Response Received...cancelling inquiry..");
1788 
1789             /* if is non-periodic inquiry active, cancel now */
1790             if ((p_inq->inq_active & BTM_BR_INQ_ACTIVE_MASK) != 0 &&
1791                 (p_inq->inq_active & BTM_PERIODIC_INQUIRY_ACTIVE) == 0)
1792                 btsnd_hcic_inq_cancel();
1793 
1794             /* stop LE scan now */
1795             btm_ble_stop_scan();
1796 
1797 #if BTM_BUSY_LEVEL_CHANGE_INCLUDED == TRUE
1798             btm_acl_update_busy_level (BTM_BLI_INQ_DONE_EVT);
1799 #endif
1800         }
1801     }
1802 #endif
1803 
1804     BTM_TRACE_DEBUG2("btm_ble_process_adv_pkt_cont: to_report =%d, to_report_le=%d",
1805                                                                to_report, to_report_LE);
1806     /* background connection in selective connection mode */
1807     if (btm_cb.ble_ctr_cb.bg_conn_type == BTM_BLE_CONN_SELECTIVE)
1808     {
1809         if (p_i->inq_info.results.device_type == BT_DEVICE_TYPE_BLE &&
1810             (evt_type == BTM_BLE_CONNECT_EVT || evt_type == BTM_BLE_CONNECT_DIR_EVT))
1811             btm_send_sel_conn_callback(bda, evt_type, p, addr_type);
1812         else
1813         {
1814             BTM_TRACE_DEBUG0("None LE device, can not initiate selective connection");
1815         }
1816     }
1817     else if (to_report || to_report_LE)
1818     {
1819         if(p_inq_results_cb && to_report)
1820             (p_inq_results_cb)((tBTM_INQ_RESULTS *) &p_i->inq_info.results, p_le_inq_cb->adv_data_cache);
1821         if(p_inq_ble_results_cb && to_report_LE)
1822             (p_inq_ble_results_cb)((tBTM_INQ_RESULTS *) &p_i->inq_info.results,
1823                                                       p_le_inq_cb->adv_data_cache);
1824     }
1825 }
1826 
1827 /*******************************************************************************
1828 **
1829 ** Function         btm_ble_stop_scan
1830 **
1831 ** Description      Stop the BLE scan.
1832 **
1833 ** Returns          void
1834 **
1835 *******************************************************************************/
btm_ble_stop_scan(void)1836 void btm_ble_stop_scan(void)
1837 {
1838     tBTM_BLE_INQ_CB *p_cb = &btm_cb.ble_ctr_cb.inq_var;
1839     tBTM_INQUIRY_VAR_ST *p_inq = &btm_cb.btm_inq_vars;
1840 
1841     BTM_TRACE_EVENT0 ("btm_ble_stop_scan ");
1842 
1843     btu_stop_timer (&p_cb->inq_timer_ent);
1844 
1845     /* Clear the inquiry callback if set */
1846     p_cb->scan_type = BTM_BLE_SCAN_MODE_NONE;
1847     p_cb->proc_mode = BTM_BLE_INQUIRY_NONE;
1848 
1849     /* stop discovery now */
1850     btsnd_hcic_ble_set_scan_enable (BTM_BLE_SCAN_DISABLE, BTM_BLE_DUPLICATE_ENABLE);
1851 
1852     /* If we have a callback registered for inquiry complete, call it */
1853     BTM_TRACE_DEBUG2 ("BTM Inq Compl Callback: status 0x%02x, num results %d",
1854                       p_inq->inq_cmpl_info.status, p_inq->inq_cmpl_info.num_resp);
1855 
1856     btm_update_scanner_filter_policy(SP_ADV_ALL);
1857 
1858     btm_process_inq_complete(HCI_SUCCESS, (UINT8)(p_inq->inqparms.mode & BTM_BLE_INQUIRY_MASK));
1859 
1860 }
1861 
1862 /*******************************************************************************
1863 **
1864 ** Function         btm_ble_start_adv
1865 **
1866 ** Description      Stop the BLE advertising.
1867 **
1868 ** Returns          void
1869 **
1870 *******************************************************************************/
btm_ble_start_adv(void)1871 static tBTM_STATUS btm_ble_start_adv(void)
1872 {
1873     tBTM_BLE_INQ_CB *p_cb = &btm_cb.ble_ctr_cb.inq_var;
1874     tBTM_STATUS     rt = BTM_NO_RESOURCES;
1875 
1876     if (btsnd_hcic_ble_set_adv_enable (BTM_BLE_ADV_ENABLE))
1877     {
1878         if (p_cb->afp != AP_SCAN_CONN_ALL)
1879              btm_cb.ble_ctr_cb.wl_state |= BTM_BLE_WL_ADV;
1880 
1881          p_cb->adv_mode = BTM_BLE_ADV_ENABLE;
1882 
1883          rt = BTM_SUCCESS;
1884      }
1885      else
1886      {
1887          p_cb->adv_mode = BTM_BLE_ADV_DISABLE;
1888          btm_cb.ble_ctr_cb.wl_state &= ~BTM_BLE_WL_ADV;
1889      }
1890      return rt;
1891 }
1892 /*******************************************************************************
1893 **
1894 ** Function         btm_ble_stop_adv
1895 **
1896 ** Description      Stop the BLE advertising.
1897 **
1898 ** Returns          void
1899 **
1900 *******************************************************************************/
btm_ble_stop_adv(void)1901 static tBTM_STATUS btm_ble_stop_adv(void)
1902 {
1903     tBTM_BLE_INQ_CB *p_cb = &btm_cb.ble_ctr_cb.inq_var;
1904     tBTM_STATUS rt = BTM_SUCCESS;
1905 
1906     if (p_cb->adv_mode == BTM_BLE_ADV_ENABLE)
1907     {
1908         if (btsnd_hcic_ble_set_adv_enable (BTM_BLE_ADV_DISABLE))
1909         {
1910             p_cb->adv_mode = BTM_BLE_ADV_DISABLE;
1911             btm_cb.ble_ctr_cb.wl_state &= ~BTM_BLE_WL_ADV;
1912         }
1913         else
1914             rt = BTM_NO_RESOURCES;
1915     }
1916     return rt;
1917 
1918 }
1919 
1920 /*******************************************************************************
1921 **
1922 ** Function         btm_ble_timeout
1923 **
1924 ** Description      Called when BTM BLE inquiry timer expires
1925 **
1926 ** Returns          void
1927 **
1928 *******************************************************************************/
btm_ble_timeout(TIMER_LIST_ENT * p_tle)1929 void btm_ble_timeout(TIMER_LIST_ENT *p_tle)
1930 {
1931     switch (p_tle->event)
1932     {
1933         case BTU_TTYPE_BLE_INQUIRY:
1934             btm_ble_stop_scan();
1935             break;
1936 
1937         case BTU_TTYPE_BLE_GAP_LIM_DISC:
1938             /* lim_timeout expiried, limited discovery should exit now */
1939             btm_ble_update_adv_flag(BTM_BLE_NON_LIMIT_DISC_FLAG);
1940 
1941             btm_ble_stop_adv();
1942             break;
1943 
1944         case BTU_TTYPE_BLE_RANDOM_ADDR:
1945             if (btm_cb.ble_ctr_cb.addr_mgnt_cb.own_addr_type == BLE_ADDR_RANDOM)
1946             {
1947                 /* refresh the random addr */
1948                 btm_gen_resolvable_private_addr();
1949             }
1950             break;
1951 
1952     }
1953 }
1954 
1955 
1956 /*******************************************************************************
1957 **
1958 ** Function         btm_ble_read_remote_features_complete
1959 **
1960 ** Description      This function is called when the command complete message
1961 **                  is received from the HCI for the read LE remote feature supported
1962 **                  complete event.
1963 **
1964 ** Returns          void
1965 **
1966 *******************************************************************************/
btm_ble_read_remote_features_complete(UINT8 * p)1967 void btm_ble_read_remote_features_complete(UINT8 *p)
1968 {
1969     tACL_CONN        *p_acl_cb = &btm_cb.acl_db[0];
1970     UINT8             status;
1971     UINT16            handle;
1972     int               xx;
1973 
1974     BTM_TRACE_EVENT0 ("btm_ble_read_remote_features_complete ");
1975 
1976     STREAM_TO_UINT8  (status, p);
1977     STREAM_TO_UINT16 (handle, p);
1978 
1979     /* Look up the connection by handle and copy features */
1980     for (xx = 0; xx < MAX_L2CAP_LINKS; xx++, p_acl_cb++)
1981     {
1982         if ((p_acl_cb->in_use) && (p_acl_cb->hci_handle == handle))
1983         {
1984             STREAM_TO_ARRAY(p_acl_cb->peer_le_features, p, BD_FEATURES_LEN);
1985             break;
1986         }
1987     }
1988 }
1989 
1990 /*******************************************************************************
1991 **
1992 ** Function         btm_ble_write_adv_enable_complete
1993 **
1994 ** Description      This function process the write adv enable command complete.
1995 **
1996 ** Returns          void
1997 **
1998 *******************************************************************************/
btm_ble_write_adv_enable_complete(UINT8 * p)1999 void btm_ble_write_adv_enable_complete(UINT8 * p)
2000 {
2001     tBTM_BLE_INQ_CB *p_cb = &btm_cb.ble_ctr_cb.inq_var;
2002 
2003     /* if write adv enable/disbale not succeed */
2004     if (*p != HCI_SUCCESS)
2005     {
2006         /* toggle back the adv mode */
2007         p_cb->adv_mode = !p_cb->adv_mode;
2008     }
2009 
2010 
2011 }
2012 
2013 /*******************************************************************************
2014 **
2015 ** Function         btm_ble_dir_adv_tout
2016 **
2017 ** Description      when directed adv time out
2018 **
2019 ** Returns          void
2020 **
2021 *******************************************************************************/
btm_ble_dir_adv_tout(void)2022 void btm_ble_dir_adv_tout(void)
2023 {
2024     btm_cb.ble_ctr_cb.inq_var.adv_mode = BTM_BLE_ADV_DISABLE;
2025 
2026     /* make device fall back into undirected adv mode by default */
2027     btm_cb.ble_ctr_cb.inq_var.directed_conn = FALSE;
2028 }
2029 
2030 /*******************************************************************************
2031 **
2032 ** Function         btm_ble_update_mode_operation
2033 **
2034 ** Description      This function update the GAP role operation when a link status
2035 **                  is updated.
2036 **
2037 ** Returns          void
2038 **
2039 *******************************************************************************/
btm_ble_update_mode_operation(UINT8 link_role,BD_ADDR bd_addr,BOOLEAN conn_cancel)2040 void btm_ble_update_mode_operation(UINT8 link_role, BD_ADDR bd_addr, BOOLEAN conn_cancel)
2041 {
2042     tACL_CONN   *pa = &btm_cb.acl_db[0];
2043     UINT16       xx;
2044     UINT8        dev_role = link_role;
2045 
2046     BTM_TRACE_DEBUG1("btm_ble_update_mode_operation adv_mode = %d", btm_cb.ble_ctr_cb.inq_var.adv_mode );
2047 
2048     /* update periphera role operation */
2049     /* If we are LE connectable, check if we need to start advertising again */
2050     if (link_role == HCI_ROLE_UNKNOWN)
2051         /* && btm_cb.ble_ctr_cb.inq_var.connectable_mode != BTM_BLE_NON_CONNECTABLE) */
2052     {
2053         for (xx = 0; xx < MAX_L2CAP_LINKS; xx++, pa++)
2054         {
2055             /* If any other LE link is up, we are still not connectable */
2056             if (pa->in_use && pa->is_le_link)
2057             {
2058                 dev_role = pa->link_role;
2059                 break;
2060             }
2061         }
2062     }
2063 
2064     if (btm_cb.ble_ctr_cb.inq_var.connectable_mode == BTM_BLE_CONNECTABLE  &&
2065         (dev_role == HCI_ROLE_UNKNOWN )) /* when device has no connection, update adv here */
2066         /* if already in connection, no connectable adv is allowed unless scatternet is enabled */
2067     {
2068         btm_ble_set_connectability ( btm_cb.ble_ctr_cb.inq_var.connectable_mode );
2069     }
2070 
2071     if (btm_ble_get_conn_st() == BLE_CONN_IDLE)
2072     {
2073         if (!btm_send_pending_direct_conn())
2074         {
2075             btm_ble_resume_bg_conn();
2076         }
2077     }
2078 }
2079 
2080 /*******************************************************************************
2081 **
2082 ** Function         btm_ble_init
2083 **
2084 ** Description      Initialize the control block variable values.
2085 **
2086 ** Returns          void
2087 **
2088 *******************************************************************************/
btm_ble_init(void)2089 void btm_ble_init (void)
2090 {
2091     tBTM_BLE_CB *p_cb = &btm_cb.ble_ctr_cb;
2092 
2093     BTM_TRACE_EVENT0 ("btm_ble_init ");
2094 
2095     memset(p_cb, 0, sizeof(tBTM_BLE_CB));
2096 
2097     p_cb->inq_var.adv_mode = BTM_BLE_ADV_DISABLE;
2098     p_cb->inq_var.scan_type = BTM_BLE_SCAN_MODE_NONE;
2099     p_cb->inq_var.adv_chnl_map = BTM_BLE_DEFAULT_ADV_CHNL_MAP;
2100     p_cb->inq_var.afp = BTM_BLE_DEFAULT_AFP;
2101     p_cb->inq_var.sfp = BTM_BLE_DEFAULT_SFP;
2102     p_cb->inq_var.connectable_mode = BTM_BLE_NON_CONNECTABLE;
2103     p_cb->inq_var.discoverable_mode = BTM_BLE_NON_DISCOVERABLE;
2104 
2105     /* for background connection, reset connection params to be undefined */
2106     p_cb->scan_int = p_cb->scan_win = BTM_BLE_CONN_PARAM_UNDEF;
2107 
2108     p_cb->inq_var.evt_type = BTM_BLE_NON_CONNECT_EVT;
2109 }
2110 
2111 #endif  /* BLE_INCLUDED */
2112