1/******************************************************************************
2 *
3 *  Copyright (C) 1999-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 address management.
22 *
23 ******************************************************************************/
24
25#include <base/bind.h>
26#include <string.h>
27
28#include "bt_types.h"
29#include "btm_int.h"
30#include "btu.h"
31#include "device/include/controller.h"
32#include "gap_api.h"
33#include "hcimsgs.h"
34
35#include "btm_ble_int.h"
36#include "smp_api.h"
37
38/*******************************************************************************
39 *
40 * Function         btm_gen_resolve_paddr_cmpl
41 *
42 * Description      This is callback functioin when resolvable private address
43 *                  generation is complete.
44 *
45 * Returns          void
46 *
47 ******************************************************************************/
48static void btm_gen_resolve_paddr_cmpl(tSMP_ENC* p) {
49  tBTM_LE_RANDOM_CB* p_cb = &btm_cb.ble_ctr_cb.addr_mgnt_cb;
50  BTM_TRACE_EVENT("btm_gen_resolve_paddr_cmpl");
51
52  if (p) {
53    /* set hash to be LSB of rpAddress */
54    p_cb->private_addr.address[5] = p->param_buf[0];
55    p_cb->private_addr.address[4] = p->param_buf[1];
56    p_cb->private_addr.address[3] = p->param_buf[2];
57    /* set it to controller */
58    btm_ble_set_random_address(p_cb->private_addr);
59
60    p_cb->own_addr_type = BLE_ADDR_RANDOM;
61
62    /* start a periodical timer to refresh random addr */
63    period_ms_t interval_ms = BTM_BLE_PRIVATE_ADDR_INT_MS;
64#if (BTM_BLE_CONFORMANCE_TESTING == TRUE)
65    interval_ms = btm_cb.ble_ctr_cb.rpa_tout * 1000;
66#endif
67    alarm_set_on_mloop(p_cb->refresh_raddr_timer, interval_ms,
68                       btm_ble_refresh_raddr_timer_timeout, NULL);
69  } else {
70    /* random address set failure */
71    BTM_TRACE_DEBUG("set random address failed");
72  }
73}
74/*******************************************************************************
75 *
76 * Function         btm_gen_resolve_paddr_low
77 *
78 * Description      This function is called when random address has generate the
79 *                  random number base for low 3 byte bd address.
80 *
81 * Returns          void
82 *
83 ******************************************************************************/
84void btm_gen_resolve_paddr_low(BT_OCTET8 rand) {
85  tBTM_LE_RANDOM_CB* p_cb = &btm_cb.ble_ctr_cb.addr_mgnt_cb;
86  tSMP_ENC output;
87
88  BTM_TRACE_EVENT("btm_gen_resolve_paddr_low");
89  rand[2] &= (~BLE_RESOLVE_ADDR_MASK);
90  rand[2] |= BLE_RESOLVE_ADDR_MSB;
91
92  p_cb->private_addr.address[2] = rand[0];
93  p_cb->private_addr.address[1] = rand[1];
94  p_cb->private_addr.address[0] = rand[2];
95
96  /* encrypt with ur IRK */
97  if (!SMP_Encrypt(btm_cb.devcb.id_keys.irk, BT_OCTET16_LEN, rand, 3,
98                   &output)) {
99    btm_gen_resolve_paddr_cmpl(NULL);
100  } else {
101    btm_gen_resolve_paddr_cmpl(&output);
102  }
103}
104/*******************************************************************************
105 *
106 * Function         btm_gen_resolvable_private_addr
107 *
108 * Description      This function generate a resolvable private address.
109 *
110 * Returns          void
111 *
112 ******************************************************************************/
113void btm_gen_resolvable_private_addr(base::Callback<void(BT_OCTET8)> cb) {
114  BTM_TRACE_EVENT("%s", __func__);
115  /* generate 3B rand as BD LSB, SRK with it, get BD MSB */
116  btsnd_hcic_ble_rand(std::move(cb));
117}
118/*******************************************************************************
119 *
120 * Function         btm_gen_non_resolve_paddr_cmpl
121 *
122 * Description      This is the callback function when non-resolvable private
123 *                  function is generated and write to controller.
124 *
125 * Returns          void
126 *
127 ******************************************************************************/
128static void btm_gen_non_resolve_paddr_cmpl(BT_OCTET8 rand) {
129  tBTM_LE_RANDOM_CB* p_cb = &btm_cb.ble_ctr_cb.addr_mgnt_cb;
130  tBTM_BLE_ADDR_CBACK* p_cback = p_cb->p_generate_cback;
131  void* p_data = p_cb->p;
132  uint8_t* pp;
133  RawAddress static_random;
134
135  BTM_TRACE_EVENT("btm_gen_non_resolve_paddr_cmpl");
136
137  p_cb->p_generate_cback = NULL;
138  pp = rand;
139  STREAM_TO_BDADDR(static_random, pp);
140  /* mask off the 2 MSB */
141  static_random.address[0] &= BLE_STATIC_PRIVATE_MSB_MASK;
142
143  /* report complete */
144  if (p_cback) (*p_cback)(static_random, p_data);
145}
146/*******************************************************************************
147 *
148 * Function         btm_gen_non_resolvable_private_addr
149 *
150 * Description      This function generate a non-resolvable private address.
151 *
152 *
153 * Returns          void
154 *
155 ******************************************************************************/
156void btm_gen_non_resolvable_private_addr(tBTM_BLE_ADDR_CBACK* p_cback,
157                                         void* p) {
158  tBTM_LE_RANDOM_CB* p_mgnt_cb = &btm_cb.ble_ctr_cb.addr_mgnt_cb;
159
160  BTM_TRACE_EVENT("btm_gen_non_resolvable_private_addr");
161
162  if (p_mgnt_cb->p_generate_cback != NULL) return;
163
164  p_mgnt_cb->p_generate_cback = p_cback;
165  p_mgnt_cb->p = p;
166  btsnd_hcic_ble_rand(base::Bind(&btm_gen_non_resolve_paddr_cmpl));
167}
168
169/*******************************************************************************
170 *  Utility functions for Random address resolving
171 ******************************************************************************/
172/*******************************************************************************
173 *
174 * Function         btm_ble_proc_resolve_x
175 *
176 * Description      This function compares the X with random address 3 MSO bytes
177 *                  to find a match.
178 *
179 * Returns          true on match, false otherwise
180 *
181 ******************************************************************************/
182static bool btm_ble_proc_resolve_x(const tSMP_ENC& encrypt_output,
183                                   const RawAddress& random_bda) {
184  BTM_TRACE_EVENT("btm_ble_proc_resolve_x");
185
186  /* compare the hash with 3 LSB of bd address */
187  uint8_t comp[3];
188  comp[0] = random_bda.address[5];
189  comp[1] = random_bda.address[4];
190  comp[2] = random_bda.address[3];
191
192  if (!memcmp(encrypt_output.param_buf, comp, 3)) {
193    BTM_TRACE_EVENT("match is found");
194    return true;
195  }
196
197  return false;
198}
199
200/*******************************************************************************
201 *
202 * Function         btm_ble_init_pseudo_addr
203 *
204 * Description      This function is used to initialize pseudo address.
205 *                  If pseudo address is not available, use dummy address
206 *
207 * Returns          true is updated; false otherwise.
208 *
209 ******************************************************************************/
210bool btm_ble_init_pseudo_addr(tBTM_SEC_DEV_REC* p_dev_rec,
211                              const RawAddress& new_pseudo_addr) {
212  if (p_dev_rec->ble.pseudo_addr.IsEmpty()) {
213    p_dev_rec->ble.pseudo_addr = new_pseudo_addr;
214    return true;
215  }
216
217  return false;
218}
219
220/*******************************************************************************
221 *
222 * Function         btm_ble_addr_resolvable
223 *
224 * Description      This function checks if a RPA is resolvable by the device
225 *                  key.
226 *
227 * Returns          true is resolvable; false otherwise.
228 *
229 ******************************************************************************/
230bool btm_ble_addr_resolvable(const RawAddress& rpa,
231                             tBTM_SEC_DEV_REC* p_dev_rec) {
232  bool rt = false;
233
234  if (!BTM_BLE_IS_RESOLVE_BDA(rpa)) return rt;
235
236  uint8_t rand[3];
237  tSMP_ENC output;
238  if ((p_dev_rec->device_type & BT_DEVICE_TYPE_BLE) &&
239      (p_dev_rec->ble.key_type & BTM_LE_KEY_PID)) {
240    BTM_TRACE_DEBUG("%s try to resolve", __func__);
241    /* use the 3 MSB of bd address as prand */
242    rand[0] = rpa.address[2];
243    rand[1] = rpa.address[1];
244    rand[2] = rpa.address[0];
245
246    /* generate X = E irk(R0, R1, R2) and R is random address 3 LSO */
247    SMP_Encrypt(p_dev_rec->ble.keys.irk, BT_OCTET16_LEN, &rand[0], 3, &output);
248
249    rand[0] = rpa.address[5];
250    rand[1] = rpa.address[4];
251    rand[2] = rpa.address[3];
252
253    if (!memcmp(output.param_buf, &rand[0], 3)) {
254      btm_ble_init_pseudo_addr(p_dev_rec, rpa);
255      rt = true;
256    }
257  }
258  return rt;
259}
260
261/*******************************************************************************
262 *
263 * Function         btm_ble_match_random_bda
264 *
265 * Description      This function match the random address to the appointed
266 *                  device record, starting from calculating IRK. If the record
267 *                  index exceeds the maximum record number, matching failed and
268 *                  send a callback.
269 *
270 * Returns          None.
271 *
272 ******************************************************************************/
273static bool btm_ble_match_random_bda(void* data, void* context) {
274  RawAddress* random_bda = (RawAddress*)context;
275  /* use the 3 MSB of bd address as prand */
276
277  uint8_t rand[3];
278  rand[0] = random_bda->address[2];
279  rand[1] = random_bda->address[1];
280  rand[2] = random_bda->address[0];
281
282  BTM_TRACE_EVENT("%s next iteration", __func__);
283
284  tSMP_ENC output;
285  tBTM_SEC_DEV_REC* p_dev_rec = static_cast<tBTM_SEC_DEV_REC*>(data);
286
287  BTM_TRACE_DEBUG("sec_flags = %02x device_type = %d", p_dev_rec->sec_flags,
288                  p_dev_rec->device_type);
289
290  if (!(p_dev_rec->device_type & BT_DEVICE_TYPE_BLE) ||
291      !(p_dev_rec->ble.key_type & BTM_LE_KEY_PID))
292    return true;
293
294  /* generate X = E irk(R0, R1, R2) and R is random address 3 LSO */
295  SMP_Encrypt(p_dev_rec->ble.keys.irk, BT_OCTET16_LEN, &rand[0], 3, &output);
296  // if it was match, finish iteration, otherwise continue
297  return !btm_ble_proc_resolve_x(output, *random_bda);
298}
299
300/*******************************************************************************
301 *
302 * Function         btm_ble_resolve_random_addr
303 *
304 * Description      This function is called to resolve a random address.
305 *
306 * Returns          pointer to the security record of the device whom a random
307 *                  address is matched to.
308 *
309 ******************************************************************************/
310tBTM_SEC_DEV_REC* btm_ble_resolve_random_addr(const RawAddress& random_bda) {
311  BTM_TRACE_EVENT("%s", __func__);
312
313  /* start to resolve random address */
314  /* check for next security record */
315
316  list_node_t* n = list_foreach(btm_cb.sec_dev_rec, btm_ble_match_random_bda,
317                                (void*)&random_bda);
318  tBTM_SEC_DEV_REC* p_dev_rec = nullptr;
319  if (n != nullptr) p_dev_rec = static_cast<tBTM_SEC_DEV_REC*>(list_node(n));
320
321  BTM_TRACE_EVENT("%s:  %sresolved", __func__,
322                  (p_dev_rec == nullptr ? "not " : ""));
323  return p_dev_rec;
324}
325
326/*******************************************************************************
327 *  address mapping between pseudo address and real connection address
328 ******************************************************************************/
329/*******************************************************************************
330 *
331 * Function         btm_find_dev_by_identity_addr
332 *
333 * Description      find the security record whose LE static address is matching
334 *
335 ******************************************************************************/
336tBTM_SEC_DEV_REC* btm_find_dev_by_identity_addr(const RawAddress& bd_addr,
337                                                uint8_t addr_type) {
338#if (BLE_PRIVACY_SPT == TRUE)
339  list_node_t* end = list_end(btm_cb.sec_dev_rec);
340  for (list_node_t* node = list_begin(btm_cb.sec_dev_rec); node != end;
341       node = list_next(node)) {
342    tBTM_SEC_DEV_REC* p_dev_rec =
343        static_cast<tBTM_SEC_DEV_REC*>(list_node(node));
344    if (p_dev_rec->ble.static_addr == bd_addr) {
345      if ((p_dev_rec->ble.static_addr_type & (~BLE_ADDR_TYPE_ID_BIT)) !=
346          (addr_type & (~BLE_ADDR_TYPE_ID_BIT)))
347        BTM_TRACE_WARNING(
348            "%s find pseudo->random match with diff addr type: %d vs %d",
349            __func__, p_dev_rec->ble.static_addr_type, addr_type);
350
351      /* found the match */
352      return p_dev_rec;
353    }
354  }
355#endif
356
357  return NULL;
358}
359
360/*******************************************************************************
361 *
362 * Function         btm_identity_addr_to_random_pseudo
363 *
364 * Description      This function map a static BD address to a pseudo random
365 *                  address in security database.
366 *
367 ******************************************************************************/
368bool btm_identity_addr_to_random_pseudo(RawAddress* bd_addr,
369                                        uint8_t* p_addr_type, bool refresh) {
370#if (BLE_PRIVACY_SPT == TRUE)
371  tBTM_SEC_DEV_REC* p_dev_rec =
372      btm_find_dev_by_identity_addr(*bd_addr, *p_addr_type);
373
374  BTM_TRACE_EVENT("%s", __func__);
375  /* evt reported on static address, map static address to random pseudo */
376  if (p_dev_rec != NULL) {
377    /* if RPA offloading is supported, or 4.2 controller, do RPA refresh */
378    if (refresh &&
379        controller_get_interface()->get_ble_resolving_list_max_size() != 0)
380      btm_ble_read_resolving_list_entry(p_dev_rec);
381
382    /* assign the original address to be the current report address */
383    if (!btm_ble_init_pseudo_addr(p_dev_rec, *bd_addr))
384      *bd_addr = p_dev_rec->ble.pseudo_addr;
385
386    *p_addr_type = p_dev_rec->ble.ble_addr_type;
387    return true;
388  }
389#endif
390  return false;
391}
392
393/*******************************************************************************
394 *
395 * Function         btm_random_pseudo_to_identity_addr
396 *
397 * Description      This function map a random pseudo address to a public
398 *                  address. random_pseudo is input and output parameter
399 *
400 ******************************************************************************/
401bool btm_random_pseudo_to_identity_addr(RawAddress* random_pseudo,
402                                        uint8_t* p_static_addr_type) {
403#if (BLE_PRIVACY_SPT == TRUE)
404  tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(*random_pseudo);
405
406  if (p_dev_rec != NULL) {
407    if (p_dev_rec->ble.in_controller_list & BTM_RESOLVING_LIST_BIT) {
408      *p_static_addr_type = p_dev_rec->ble.static_addr_type;
409      *random_pseudo = p_dev_rec->ble.static_addr;
410      if (controller_get_interface()->supports_ble_privacy())
411        *p_static_addr_type |= BLE_ADDR_TYPE_ID_BIT;
412      return true;
413    }
414  }
415#endif
416  return false;
417}
418
419/*******************************************************************************
420 *
421 * Function         btm_ble_refresh_peer_resolvable_private_addr
422 *
423 * Description      This function refresh the currently used resolvable remote
424 *                  private address into security database and set active
425 *                  connection address.
426 *
427 ******************************************************************************/
428void btm_ble_refresh_peer_resolvable_private_addr(const RawAddress& pseudo_bda,
429                                                  const RawAddress& rpa,
430                                                  uint8_t rra_type) {
431#if (BLE_PRIVACY_SPT == TRUE)
432  uint8_t rra_dummy = false;
433  if (rpa.IsEmpty()) rra_dummy = true;
434
435  /* update security record here, in adv event or connection complete process */
436  tBTM_SEC_DEV_REC* p_sec_rec = btm_find_dev(pseudo_bda);
437  if (p_sec_rec != NULL) {
438    p_sec_rec->ble.cur_rand_addr = rpa;
439
440    /* unknown, if dummy address, set to static */
441    if (rra_type == BTM_BLE_ADDR_PSEUDO)
442      p_sec_rec->ble.active_addr_type =
443          rra_dummy ? BTM_BLE_ADDR_STATIC : BTM_BLE_ADDR_RRA;
444    else
445      p_sec_rec->ble.active_addr_type = rra_type;
446  } else {
447    BTM_TRACE_ERROR("No matching known device in record");
448    return;
449  }
450
451  BTM_TRACE_DEBUG("%s: active_addr_type: %d ", __func__,
452                  p_sec_rec->ble.active_addr_type);
453
454  /* connection refresh remote address */
455  tACL_CONN* p_acl = btm_bda_to_acl(p_sec_rec->bd_addr, BT_TRANSPORT_LE);
456  if (p_acl == NULL)
457    p_acl = btm_bda_to_acl(p_sec_rec->ble.pseudo_addr, BT_TRANSPORT_LE);
458
459  if (p_acl != NULL) {
460    if (rra_type == BTM_BLE_ADDR_PSEUDO) {
461      /* use static address, resolvable_private_addr is empty */
462      if (rra_dummy) {
463        p_acl->active_remote_addr_type = p_sec_rec->ble.static_addr_type;
464        p_acl->active_remote_addr = p_sec_rec->ble.static_addr;
465      } else {
466        p_acl->active_remote_addr_type = BLE_ADDR_RANDOM;
467        p_acl->active_remote_addr = rpa;
468      }
469    } else {
470      p_acl->active_remote_addr_type = rra_type;
471      p_acl->active_remote_addr = rpa;
472    }
473
474    BTM_TRACE_DEBUG("p_acl->active_remote_addr_type: %d ",
475                    p_acl->active_remote_addr_type);
476    VLOG(1) << __func__ << " conn_addr: " << p_acl->active_remote_addr;
477  }
478#endif
479}
480
481/*******************************************************************************
482 *
483 * Function         btm_ble_refresh_local_resolvable_private_addr
484 *
485 * Description      This function refresh the currently used resolvable private
486 *                  address for the active link to the remote device
487 *
488 ******************************************************************************/
489void btm_ble_refresh_local_resolvable_private_addr(
490    const RawAddress& pseudo_addr, const RawAddress& local_rpa) {
491#if (BLE_PRIVACY_SPT == TRUE)
492  tACL_CONN* p = btm_bda_to_acl(pseudo_addr, BT_TRANSPORT_LE);
493
494  if (p != NULL) {
495    if (btm_cb.ble_ctr_cb.privacy_mode != BTM_PRIVACY_NONE) {
496      p->conn_addr_type = BLE_ADDR_RANDOM;
497      if (!local_rpa.IsEmpty())
498        p->conn_addr = local_rpa;
499      else
500        p->conn_addr = btm_cb.ble_ctr_cb.addr_mgnt_cb.private_addr;
501    } else {
502      p->conn_addr_type = BLE_ADDR_PUBLIC;
503      p->conn_addr = *controller_get_interface()->get_address();
504    }
505  }
506#endif
507}
508