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 the SMP L2CAP utility functions
22  *
23  ******************************************************************************/
24 #include "common/bt_target.h"
25 
26 #if SMP_INCLUDED == TRUE
27 
28 #include "stack/bt_types.h"
29 //#include "bt_utils.h"
30 #include <string.h>
31 //#include <ctype.h>
32 #include "stack/hcidefs.h"
33 #include "stack/btm_ble_api.h"
34 #include "stack/l2c_api.h"
35 #include "l2c_int.h"
36 #include "smp_int.h"
37 #include "device/controller.h"
38 #include "btm_int.h"
39 #include "common/bte_appl.h"
40 
41 #define SMP_PAIRING_REQ_SIZE    7
42 #define SMP_CONFIRM_CMD_SIZE    (BT_OCTET16_LEN + 1)
43 #define SMP_RAND_CMD_SIZE       (BT_OCTET16_LEN + 1)
44 #define SMP_INIT_CMD_SIZE       (BT_OCTET16_LEN + 1)
45 #define SMP_ENC_INFO_SIZE       (BT_OCTET16_LEN + 1)
46 #define SMP_MASTER_ID_SIZE      (BT_OCTET8_LEN + 2 + 1)
47 #define SMP_ID_INFO_SIZE        (BT_OCTET16_LEN + 1)
48 #define SMP_ID_ADDR_SIZE        (BD_ADDR_LEN + 1 + 1)
49 #define SMP_SIGN_INFO_SIZE      (BT_OCTET16_LEN + 1)
50 #define SMP_PAIR_FAIL_SIZE      2
51 #define SMP_SECURITY_REQUEST_SIZE  2
52 #define SMP_PAIR_PUBL_KEY_SIZE  (1 /* opcode */ + (2*BT_OCTET32_LEN))
53 #define SMP_PAIR_COMMITM_SIZE           (1 /* opcode */ + BT_OCTET16_LEN /*Commitment*/)
54 #define SMP_PAIR_DHKEY_CHECK_SIZE       (1 /* opcode */ + BT_OCTET16_LEN /*DHKey Check*/)
55 #define SMP_PAIR_KEYPR_NOTIF_SIZE       (1 /* opcode */ + 1 /*Notif Type*/)
56 
57 /* SMP command sizes per spec */
58 static const UINT8 smp_cmd_size_per_spec[] = {
59     0,
60     SMP_PAIRING_REQ_SIZE,       /* 0x01: pairing request */
61     SMP_PAIRING_REQ_SIZE,       /* 0x02: pairing response */
62     SMP_CONFIRM_CMD_SIZE,       /* 0x03: pairing confirm */
63     SMP_RAND_CMD_SIZE,          /* 0x04: pairing random */
64     SMP_PAIR_FAIL_SIZE,         /* 0x05: pairing failed */
65     SMP_ENC_INFO_SIZE,          /* 0x06: encryption information */
66     SMP_MASTER_ID_SIZE,         /* 0x07: master identification */
67     SMP_ID_INFO_SIZE,           /* 0x08: identity information */
68     SMP_ID_ADDR_SIZE,           /* 0x09: identity address information */
69     SMP_SIGN_INFO_SIZE,         /* 0x0A: signing information */
70     SMP_SECURITY_REQUEST_SIZE,  /* 0x0B: security request */
71     SMP_PAIR_PUBL_KEY_SIZE,     /* 0x0C: pairing public key */
72     SMP_PAIR_DHKEY_CHECK_SIZE,  /* 0x0D: pairing dhkey check */
73     SMP_PAIR_KEYPR_NOTIF_SIZE,  /* 0x0E: pairing keypress notification */
74     SMP_PAIR_COMMITM_SIZE       /* 0x0F: pairing commitment */
75 };
76 
77 static BOOLEAN smp_parameter_unconditionally_valid(tSMP_CB *p_cb);
78 static BOOLEAN smp_parameter_unconditionally_invalid(tSMP_CB *p_cb);
79 
80 /* type for SMP command length validation functions */
81 typedef BOOLEAN (*tSMP_CMD_LEN_VALID)(tSMP_CB *p_cb);
82 
83 static BOOLEAN smp_command_has_valid_fixed_length(tSMP_CB *p_cb);
84 
85 static const tSMP_CMD_LEN_VALID smp_cmd_len_is_valid[] = {
86     smp_parameter_unconditionally_invalid,
87     smp_command_has_valid_fixed_length, /* 0x01: pairing request */
88     smp_command_has_valid_fixed_length, /* 0x02: pairing response */
89     smp_command_has_valid_fixed_length, /* 0x03: pairing confirm */
90     smp_command_has_valid_fixed_length, /* 0x04: pairing random */
91     smp_command_has_valid_fixed_length, /* 0x05: pairing failed */
92     smp_command_has_valid_fixed_length, /* 0x06: encryption information */
93     smp_command_has_valid_fixed_length, /* 0x07: master identification */
94     smp_command_has_valid_fixed_length, /* 0x08: identity information */
95     smp_command_has_valid_fixed_length, /* 0x09: identity address information */
96     smp_command_has_valid_fixed_length, /* 0x0A: signing information */
97     smp_command_has_valid_fixed_length, /* 0x0B: security request */
98     smp_command_has_valid_fixed_length, /* 0x0C: pairing public key */
99     smp_command_has_valid_fixed_length, /* 0x0D: pairing dhkey check */
100     smp_command_has_valid_fixed_length, /* 0x0E: pairing keypress notification */
101     smp_command_has_valid_fixed_length  /* 0x0F: pairing commitment */
102 };
103 
104 /* type for SMP command parameter ranges validation functions */
105 typedef BOOLEAN (*tSMP_CMD_PARAM_RANGES_VALID)(tSMP_CB *p_cb);
106 
107 static BOOLEAN smp_pairing_request_response_parameters_are_valid(tSMP_CB *p_cb);
108 static BOOLEAN smp_pairing_keypress_notification_is_valid(tSMP_CB *p_cb);
109 
110 static const tSMP_CMD_PARAM_RANGES_VALID smp_cmd_param_ranges_are_valid[] = {
111     smp_parameter_unconditionally_invalid,
112     smp_pairing_request_response_parameters_are_valid, /* 0x01: pairing request */
113     smp_pairing_request_response_parameters_are_valid, /* 0x02: pairing response */
114     smp_parameter_unconditionally_valid, /* 0x03: pairing confirm */
115     smp_parameter_unconditionally_valid, /* 0x04: pairing random */
116     smp_parameter_unconditionally_valid, /* 0x05: pairing failed */
117     smp_parameter_unconditionally_valid, /* 0x06: encryption information */
118     smp_parameter_unconditionally_valid, /* 0x07: master identification */
119     smp_parameter_unconditionally_valid, /* 0x08: identity information */
120     smp_parameter_unconditionally_valid, /* 0x09: identity address information */
121     smp_parameter_unconditionally_valid, /* 0x0A: signing information */
122     smp_parameter_unconditionally_valid, /* 0x0B: security request */
123     smp_parameter_unconditionally_valid, /* 0x0C: pairing public key */
124     smp_parameter_unconditionally_valid, /* 0x0D: pairing dhkey check */
125     smp_pairing_keypress_notification_is_valid, /* 0x0E: pairing keypress notification */
126     smp_parameter_unconditionally_valid /* 0x0F: pairing commitment */
127 };
128 
129 /* type for action functions */
130 typedef BT_HDR *(*tSMP_CMD_ACT)(UINT8 cmd_code, tSMP_CB *p_cb);
131 
132 static BT_HDR *smp_build_pairing_cmd(UINT8 cmd_code, tSMP_CB *p_cb);
133 static BT_HDR *smp_build_confirm_cmd(UINT8 cmd_code, tSMP_CB *p_cb);
134 static BT_HDR *smp_build_rand_cmd(UINT8 cmd_code, tSMP_CB *p_cb);
135 static BT_HDR *smp_build_pairing_fail(UINT8 cmd_code, tSMP_CB *p_cb);
136 static BT_HDR *smp_build_identity_info_cmd(UINT8 cmd_code, tSMP_CB *p_cb);
137 static BT_HDR *smp_build_encrypt_info_cmd(UINT8 cmd_code, tSMP_CB *p_cb);
138 static BT_HDR *smp_build_security_request(UINT8 cmd_code, tSMP_CB *p_cb);
139 static BT_HDR *smp_build_signing_info_cmd(UINT8 cmd_code, tSMP_CB *p_cb);
140 static BT_HDR *smp_build_master_id_cmd(UINT8 cmd_code, tSMP_CB *p_cb);
141 static BT_HDR *smp_build_id_addr_cmd(UINT8 cmd_code, tSMP_CB *p_cb);
142 static BT_HDR *smp_build_pair_public_key_cmd(UINT8 cmd_code, tSMP_CB *p_cb);
143 static BT_HDR *smp_build_pairing_commitment_cmd(UINT8 cmd_code, tSMP_CB *p_cb);
144 static BT_HDR *smp_build_pair_dhkey_check_cmd(UINT8 cmd_code, tSMP_CB *p_cb);
145 static BT_HDR *smp_build_pairing_keypress_notification_cmd(UINT8 cmd_code, tSMP_CB *p_cb);
146 
147 static const tSMP_CMD_ACT smp_cmd_build_act[] = {
148     NULL,
149     smp_build_pairing_cmd,          /* 0x01: pairing request */
150     smp_build_pairing_cmd,          /* 0x02: pairing response */
151     smp_build_confirm_cmd,          /* 0x03: pairing confirm */
152     smp_build_rand_cmd,             /* 0x04: pairing random */
153     smp_build_pairing_fail,         /* 0x05: pairing failure */
154     smp_build_encrypt_info_cmd,     /* 0x06: encryption information */
155     smp_build_master_id_cmd,        /* 0x07: master identification */
156     smp_build_identity_info_cmd,    /* 0x08: identity information */
157     smp_build_id_addr_cmd,          /* 0x09: identity address information */
158     smp_build_signing_info_cmd,     /* 0x0A: signing information */
159     smp_build_security_request,     /* 0x0B: security request */
160     smp_build_pair_public_key_cmd,  /* 0x0C: pairing public key */
161     smp_build_pair_dhkey_check_cmd, /* 0x0D: pairing DHKey check */
162     smp_build_pairing_keypress_notification_cmd, /* 0x0E: pairing keypress notification */
163     smp_build_pairing_commitment_cmd /* 0x0F: pairing commitment */
164 };
165 
166 static const UINT8 smp_association_table[2][SMP_IO_CAP_MAX][SMP_IO_CAP_MAX] = {
167     /* display only */    /* Display Yes/No */   /* keyboard only */
168     /* No Input/Output */ /* keyboard display */
169 
170     /* initiator */
171     /* model = tbl[peer_io_caps][loc_io_caps] */
172     /* Display Only */
173     {   {
174             SMP_MODEL_ENCRYPTION_ONLY, SMP_MODEL_ENCRYPTION_ONLY, SMP_MODEL_PASSKEY,
175             SMP_MODEL_ENCRYPTION_ONLY, SMP_MODEL_PASSKEY
176         },
177 
178         /* Display Yes/No */
179         {
180             SMP_MODEL_ENCRYPTION_ONLY, SMP_MODEL_ENCRYPTION_ONLY, SMP_MODEL_PASSKEY,
181             SMP_MODEL_ENCRYPTION_ONLY, SMP_MODEL_PASSKEY
182         },
183 
184         /* Keyboard only */
185         {
186             SMP_MODEL_KEY_NOTIF, SMP_MODEL_KEY_NOTIF, SMP_MODEL_PASSKEY,
187             SMP_MODEL_ENCRYPTION_ONLY, SMP_MODEL_KEY_NOTIF
188         },
189 
190         /* No Input No Output */
191         {
192             SMP_MODEL_ENCRYPTION_ONLY, SMP_MODEL_ENCRYPTION_ONLY, SMP_MODEL_ENCRYPTION_ONLY,
193             SMP_MODEL_ENCRYPTION_ONLY, SMP_MODEL_ENCRYPTION_ONLY
194         },
195 
196         /* keyboard display */
197         {
198             SMP_MODEL_KEY_NOTIF, SMP_MODEL_KEY_NOTIF, SMP_MODEL_PASSKEY,
199             SMP_MODEL_ENCRYPTION_ONLY, SMP_MODEL_KEY_NOTIF
200         }
201     },
202 
203     /* responder */
204     /* model = tbl[loc_io_caps][peer_io_caps] */
205     /* Display Only */
206     {   {
207             SMP_MODEL_ENCRYPTION_ONLY, SMP_MODEL_ENCRYPTION_ONLY, SMP_MODEL_KEY_NOTIF,
208             SMP_MODEL_ENCRYPTION_ONLY, SMP_MODEL_KEY_NOTIF
209         },
210 
211         /* Display Yes/No */
212         {
213             SMP_MODEL_ENCRYPTION_ONLY, SMP_MODEL_ENCRYPTION_ONLY, SMP_MODEL_KEY_NOTIF,
214             SMP_MODEL_ENCRYPTION_ONLY, SMP_MODEL_KEY_NOTIF
215         },
216 
217         /* keyboard only */
218         {
219             SMP_MODEL_PASSKEY, SMP_MODEL_PASSKEY, SMP_MODEL_PASSKEY,
220             SMP_MODEL_ENCRYPTION_ONLY, SMP_MODEL_PASSKEY
221         },
222 
223         /* No Input No Output */
224         {
225             SMP_MODEL_ENCRYPTION_ONLY, SMP_MODEL_ENCRYPTION_ONLY, SMP_MODEL_ENCRYPTION_ONLY,
226             SMP_MODEL_ENCRYPTION_ONLY, SMP_MODEL_ENCRYPTION_ONLY
227         },
228 
229         /* keyboard display */
230         {
231             SMP_MODEL_PASSKEY, SMP_MODEL_PASSKEY, SMP_MODEL_KEY_NOTIF,
232             SMP_MODEL_ENCRYPTION_ONLY, SMP_MODEL_PASSKEY
233         }
234     }
235 };
236 
237 static const UINT8 smp_association_table_sc[2][SMP_IO_CAP_MAX][SMP_IO_CAP_MAX] = {
238     /* display only */    /* Display Yes/No */   /* keyboard only */
239     /* No InputOutput */  /* keyboard display */
240 
241     /* initiator */
242     /* model = tbl[peer_io_caps][loc_io_caps] */
243 
244     /* Display Only */
245     {   {
246             SMP_MODEL_SEC_CONN_JUSTWORKS, SMP_MODEL_SEC_CONN_JUSTWORKS, SMP_MODEL_SEC_CONN_PASSKEY_ENT,
247             SMP_MODEL_SEC_CONN_JUSTWORKS, SMP_MODEL_SEC_CONN_PASSKEY_ENT
248         },
249 
250         /* Display Yes/No */
251         {
252             SMP_MODEL_SEC_CONN_JUSTWORKS, SMP_MODEL_SEC_CONN_NUM_COMP, SMP_MODEL_SEC_CONN_PASSKEY_ENT,
253             SMP_MODEL_SEC_CONN_JUSTWORKS, SMP_MODEL_SEC_CONN_NUM_COMP
254         },
255 
256         /* keyboard only */
257         {
258             SMP_MODEL_SEC_CONN_PASSKEY_DISP, SMP_MODEL_SEC_CONN_PASSKEY_DISP, SMP_MODEL_SEC_CONN_PASSKEY_ENT,
259             SMP_MODEL_SEC_CONN_JUSTWORKS, SMP_MODEL_SEC_CONN_PASSKEY_DISP
260         },
261 
262         /* No Input No Output */
263         {
264             SMP_MODEL_SEC_CONN_JUSTWORKS, SMP_MODEL_SEC_CONN_JUSTWORKS, SMP_MODEL_SEC_CONN_JUSTWORKS,
265             SMP_MODEL_SEC_CONN_JUSTWORKS, SMP_MODEL_SEC_CONN_JUSTWORKS
266         },
267 
268         /* keyboard display */
269         {
270             SMP_MODEL_SEC_CONN_PASSKEY_DISP, SMP_MODEL_SEC_CONN_NUM_COMP, SMP_MODEL_SEC_CONN_PASSKEY_ENT,
271             SMP_MODEL_SEC_CONN_JUSTWORKS, SMP_MODEL_SEC_CONN_NUM_COMP
272         }
273     },
274 
275     /* responder */
276     /* model = tbl[loc_io_caps][peer_io_caps] */
277 
278     /* Display Only */
279     {   {
280             SMP_MODEL_SEC_CONN_JUSTWORKS, SMP_MODEL_SEC_CONN_JUSTWORKS, SMP_MODEL_SEC_CONN_PASSKEY_DISP,
281             SMP_MODEL_SEC_CONN_JUSTWORKS, SMP_MODEL_SEC_CONN_PASSKEY_DISP
282         },
283 
284         /* Display Yes/No */
285         {
286             SMP_MODEL_SEC_CONN_JUSTWORKS, SMP_MODEL_SEC_CONN_NUM_COMP, SMP_MODEL_SEC_CONN_PASSKEY_DISP,
287             SMP_MODEL_SEC_CONN_JUSTWORKS, SMP_MODEL_SEC_CONN_NUM_COMP
288         },
289 
290         /* keyboard only */
291         {
292             SMP_MODEL_SEC_CONN_PASSKEY_ENT, SMP_MODEL_SEC_CONN_PASSKEY_ENT, SMP_MODEL_SEC_CONN_PASSKEY_ENT,
293             SMP_MODEL_SEC_CONN_JUSTWORKS, SMP_MODEL_SEC_CONN_PASSKEY_ENT
294         },
295 
296         /* No Input No Output */
297         {
298             SMP_MODEL_SEC_CONN_JUSTWORKS, SMP_MODEL_SEC_CONN_JUSTWORKS, SMP_MODEL_SEC_CONN_JUSTWORKS,
299             SMP_MODEL_SEC_CONN_JUSTWORKS, SMP_MODEL_SEC_CONN_JUSTWORKS
300         },
301 
302         /* keyboard display */
303         {
304             SMP_MODEL_SEC_CONN_PASSKEY_ENT, SMP_MODEL_SEC_CONN_NUM_COMP, SMP_MODEL_SEC_CONN_PASSKEY_DISP,
305             SMP_MODEL_SEC_CONN_JUSTWORKS, SMP_MODEL_SEC_CONN_NUM_COMP
306         }
307     }
308 };
309 
310 static tSMP_ASSO_MODEL smp_select_legacy_association_model(tSMP_CB *p_cb);
311 static tSMP_ASSO_MODEL smp_select_association_model_secure_connections(tSMP_CB *p_cb);
312 
313 /*******************************************************************************
314 **
315 ** Function         smp_send_msg_to_L2CAP
316 **
317 ** Description      Send message to L2CAP.
318 **
319 *******************************************************************************/
smp_send_msg_to_L2CAP(BD_ADDR rem_bda,BT_HDR * p_toL2CAP)320 BOOLEAN  smp_send_msg_to_L2CAP(BD_ADDR rem_bda, BT_HDR *p_toL2CAP)
321 {
322     UINT16 l2cap_ret;
323     UINT16 fixed_cid = L2CAP_SMP_CID;
324 
325     if (smp_cb.smp_over_br) {
326         fixed_cid = L2CAP_SMP_BR_CID;
327     }
328 
329     SMP_TRACE_EVENT("%s", __FUNCTION__);
330     smp_cb.total_tx_unacked += 1;
331 
332     if ((l2cap_ret = L2CA_SendFixedChnlData (fixed_cid, rem_bda, p_toL2CAP)) == L2CAP_DW_FAILED) {
333         smp_cb.total_tx_unacked -= 1;
334         SMP_TRACE_ERROR("SMP failed to pass msg to L2CAP");
335         return FALSE;
336     } else {
337         return TRUE;
338     }
339 }
340 
341 /*******************************************************************************
342 **
343 ** Function         smp_send_cmd
344 **
345 ** Description      send a SMP command on L2CAP channel.
346 **
347 *******************************************************************************/
smp_send_cmd(UINT8 cmd_code,tSMP_CB * p_cb)348 BOOLEAN smp_send_cmd(UINT8 cmd_code, tSMP_CB *p_cb)
349 {
350     BT_HDR *p_buf;
351     BOOLEAN sent = FALSE;
352     UINT8 failure = SMP_PAIR_INTERNAL_ERR;
353     SMP_TRACE_EVENT("smp_send_cmd on l2cap cmd_code=0x%x\n", cmd_code);
354     if ( cmd_code <= (SMP_OPCODE_MAX + 1 /* for SMP_OPCODE_PAIR_COMMITM */) &&
355             smp_cmd_build_act[cmd_code] != NULL) {
356         p_buf = (*smp_cmd_build_act[cmd_code])(cmd_code, p_cb);
357 
358         if (p_buf != NULL &&
359                 smp_send_msg_to_L2CAP(p_cb->pairing_bda, p_buf)) {
360             sent = TRUE;
361 
362             btu_stop_timer (&p_cb->rsp_timer_ent);
363             btu_start_timer (&p_cb->rsp_timer_ent, BTU_TTYPE_SMP_PAIRING_CMD,
364                              SMP_WAIT_FOR_RSP_TOUT);
365         }
366     }
367 
368     if (!sent) {
369         if (p_cb->smp_over_br) {
370 #if (CLASSIC_BT_INCLUDED == TRUE)
371             smp_br_state_machine_event(p_cb, SMP_BR_AUTH_CMPL_EVT, &failure);
372 #endif  ///CLASSIC_BT_INCLUDED == TRUE
373         } else {
374             smp_sm_event(p_cb, SMP_AUTH_CMPL_EVT, &failure);
375         }
376     }
377     return sent;
378 }
379 
380 /*******************************************************************************
381 **
382 ** Function         smp_rsp_timeout
383 **
384 ** Description      Called when SMP wait for SMP command response timer expires
385 **
386 ** Returns          void
387 **
388 *******************************************************************************/
smp_rsp_timeout(TIMER_LIST_ENT * p_tle)389 void smp_rsp_timeout(TIMER_LIST_ENT *p_tle)
390 {
391     tSMP_CB   *p_cb = &smp_cb;
392     UINT8 failure = SMP_RSP_TIMEOUT;
393     UNUSED(p_tle);
394 
395     SMP_TRACE_EVENT("%s state:%d br_state:%d", __FUNCTION__, p_cb->state, p_cb->br_state);
396 
397     if (p_cb->smp_over_br) {
398 #if (CLASSIC_BT_INCLUDED == TRUE)
399         smp_br_state_machine_event(p_cb, SMP_BR_AUTH_CMPL_EVT, &failure);
400 #endif  ///CLASSIC_BT_INCLUDED == TRUE
401     } else {
402         smp_sm_event(p_cb, SMP_AUTH_CMPL_EVT, &failure);
403     }
404 }
405 
406 /*******************************************************************************
407 **
408 ** Function         smp_build_pairing_req_cmd
409 **
410 ** Description      Build pairing request command.
411 **
412 *******************************************************************************/
smp_build_pairing_cmd(UINT8 cmd_code,tSMP_CB * p_cb)413 BT_HDR *smp_build_pairing_cmd(UINT8 cmd_code, tSMP_CB *p_cb)
414 {
415     BT_HDR      *p_buf = NULL ;
416     UINT8       *p;
417 
418     SMP_TRACE_EVENT("smp_build_pairing_cmd");
419     if ((p_buf = (BT_HDR *)osi_malloc(sizeof(BT_HDR) + SMP_PAIRING_REQ_SIZE + L2CAP_MIN_OFFSET)) != NULL) {
420         p = (UINT8 *)(p_buf + 1) + L2CAP_MIN_OFFSET;
421 
422         UINT8_TO_STREAM (p, cmd_code);
423         UINT8_TO_STREAM (p, p_cb->local_io_capability);
424         UINT8_TO_STREAM (p, p_cb->loc_oob_flag);
425         UINT8_TO_STREAM (p, p_cb->loc_auth_req);
426         UINT8_TO_STREAM (p, p_cb->loc_enc_size);
427         UINT8_TO_STREAM (p, p_cb->local_i_key);
428         UINT8_TO_STREAM (p, p_cb->local_r_key);
429 
430         p_buf->offset = L2CAP_MIN_OFFSET;
431         /* 1B ERR_RSP op code + 1B cmd_op_code + 2B handle + 1B status */
432         p_buf->len = SMP_PAIRING_REQ_SIZE;
433     }
434 
435     return p_buf;
436 }
437 
438 /*******************************************************************************
439 **
440 ** Function         smp_build_confirm_cmd
441 **
442 ** Description      Build confirm request command.
443 **
444 *******************************************************************************/
smp_build_confirm_cmd(UINT8 cmd_code,tSMP_CB * p_cb)445 static BT_HDR *smp_build_confirm_cmd(UINT8 cmd_code, tSMP_CB *p_cb)
446 {
447     BT_HDR      *p_buf = NULL ;
448     UINT8       *p;
449     UNUSED(cmd_code);
450 
451     SMP_TRACE_EVENT("smp_build_confirm_cmd\n");
452     if ((p_buf = (BT_HDR *)osi_malloc(sizeof(BT_HDR) + SMP_CONFIRM_CMD_SIZE + L2CAP_MIN_OFFSET)) != NULL) {
453         p = (UINT8 *)(p_buf + 1) + L2CAP_MIN_OFFSET;
454 
455         UINT8_TO_STREAM (p, SMP_OPCODE_CONFIRM);
456         ARRAY_TO_STREAM (p, p_cb->confirm, BT_OCTET16_LEN);
457 
458         p_buf->offset = L2CAP_MIN_OFFSET;
459         p_buf->len = SMP_CONFIRM_CMD_SIZE;
460     }
461 
462     return p_buf;
463 }
464 /*******************************************************************************
465 **
466 ** Function         smp_build_rand_cmd
467 **
468 ** Description      Build Random command.
469 **
470 *******************************************************************************/
smp_build_rand_cmd(UINT8 cmd_code,tSMP_CB * p_cb)471 static BT_HDR *smp_build_rand_cmd(UINT8 cmd_code, tSMP_CB *p_cb)
472 {
473     BT_HDR      *p_buf = NULL ;
474     UINT8       *p;
475     UNUSED(cmd_code);
476 
477     SMP_TRACE_EVENT("%s\n", __func__);
478     if ((p_buf = (BT_HDR *)osi_malloc(sizeof(BT_HDR) + SMP_RAND_CMD_SIZE + L2CAP_MIN_OFFSET))
479             != NULL) {
480         p = (UINT8 *)(p_buf + 1) + L2CAP_MIN_OFFSET;
481 
482         UINT8_TO_STREAM (p, SMP_OPCODE_RAND);
483         ARRAY_TO_STREAM (p, p_cb->rand, BT_OCTET16_LEN);
484 
485         p_buf->offset = L2CAP_MIN_OFFSET;
486         p_buf->len = SMP_RAND_CMD_SIZE;
487     }
488 
489     return p_buf;
490 }
491 /*******************************************************************************
492 **
493 ** Function         smp_build_encrypt_info_cmd
494 **
495 ** Description      Build security information command.
496 **
497 *******************************************************************************/
smp_build_encrypt_info_cmd(UINT8 cmd_code,tSMP_CB * p_cb)498 static BT_HDR *smp_build_encrypt_info_cmd(UINT8 cmd_code, tSMP_CB *p_cb)
499 {
500     BT_HDR      *p_buf = NULL ;
501     UINT8       *p;
502     UNUSED(cmd_code);
503 
504     SMP_TRACE_EVENT("smp_build_encrypt_info_cmd\n");
505     if ((p_buf = (BT_HDR *)osi_malloc(sizeof(BT_HDR) + SMP_ENC_INFO_SIZE + L2CAP_MIN_OFFSET)) != NULL) {
506         p = (UINT8 *)(p_buf + 1) + L2CAP_MIN_OFFSET;
507 
508         UINT8_TO_STREAM (p, SMP_OPCODE_ENCRYPT_INFO);
509         ARRAY_TO_STREAM (p, p_cb->ltk, BT_OCTET16_LEN);
510 
511         p_buf->offset = L2CAP_MIN_OFFSET;
512         p_buf->len = SMP_ENC_INFO_SIZE;
513     }
514 
515     return p_buf;
516 }
517 
518 /*******************************************************************************
519 **
520 ** Function         smp_build_master_id_cmd
521 **
522 ** Description      Build security information command.
523 **
524 *******************************************************************************/
smp_build_master_id_cmd(UINT8 cmd_code,tSMP_CB * p_cb)525 static BT_HDR *smp_build_master_id_cmd(UINT8 cmd_code, tSMP_CB *p_cb)
526 {
527     BT_HDR      *p_buf = NULL ;
528     UINT8       *p;
529     UNUSED(cmd_code);
530 
531     SMP_TRACE_EVENT("%s\n", __func__);
532 
533     if ((p_buf = (BT_HDR *)osi_malloc(sizeof(BT_HDR) + SMP_MASTER_ID_SIZE + L2CAP_MIN_OFFSET)) != NULL) {
534         p = (UINT8 *)(p_buf + 1) + L2CAP_MIN_OFFSET;
535 
536         UINT8_TO_STREAM (p, SMP_OPCODE_MASTER_ID);
537         UINT16_TO_STREAM (p, p_cb->ediv);
538         ARRAY_TO_STREAM (p, p_cb->enc_rand, BT_OCTET8_LEN);
539 
540         p_buf->offset = L2CAP_MIN_OFFSET;
541         p_buf->len = SMP_MASTER_ID_SIZE;
542     }
543 
544     return p_buf;
545 }
546 
547 /*******************************************************************************
548 **
549 ** Function         smp_build_identity_info_cmd
550 **
551 ** Description      Build identity information command.
552 **
553 *******************************************************************************/
smp_build_identity_info_cmd(UINT8 cmd_code,tSMP_CB * p_cb)554 static BT_HDR *smp_build_identity_info_cmd(UINT8 cmd_code, tSMP_CB *p_cb)
555 {
556     BT_HDR      *p_buf = NULL ;
557 #if (BLE_INCLUDED == TRUE)
558     UINT8       *p;
559     BT_OCTET16  irk;
560     UNUSED(cmd_code);
561     UNUSED(p_cb);
562 
563     SMP_TRACE_EVENT("smp_build_identity_info_cmd\n");
564     if ((p_buf = (BT_HDR *)osi_malloc(sizeof(BT_HDR) + SMP_ID_INFO_SIZE + L2CAP_MIN_OFFSET)) != NULL) {
565         p = (UINT8 *)(p_buf + 1) + L2CAP_MIN_OFFSET;
566 
567         BTM_GetDeviceIDRoot(irk);
568 
569         UINT8_TO_STREAM (p, SMP_OPCODE_IDENTITY_INFO);
570         ARRAY_TO_STREAM (p,  irk, BT_OCTET16_LEN);
571 
572         p_buf->offset = L2CAP_MIN_OFFSET;
573         p_buf->len = SMP_ID_INFO_SIZE;
574     }
575 
576 #endif  ///BLE_INCLUDED == TRUE
577     return p_buf;
578 }
579 
580 /*******************************************************************************
581 **
582 ** Function         smp_build_id_addr_cmd
583 **
584 ** Description      Build identity address information command.
585 **
586 *******************************************************************************/
smp_build_id_addr_cmd(UINT8 cmd_code,tSMP_CB * p_cb)587 static BT_HDR *smp_build_id_addr_cmd(UINT8 cmd_code, tSMP_CB *p_cb)
588 {
589     BT_HDR *p_buf = NULL;
590     UINT8 *p;
591 
592     UNUSED(cmd_code);
593     UNUSED(p_cb);
594     SMP_TRACE_EVENT("smp_build_id_addr_cmd\n");
595     if ((p_buf = (BT_HDR *)osi_malloc(sizeof(BT_HDR) + SMP_ID_ADDR_SIZE + L2CAP_MIN_OFFSET)) != NULL) {
596         p = (UINT8 *)(p_buf + 1) + L2CAP_MIN_OFFSET;
597 
598         UINT8_TO_STREAM (p, SMP_OPCODE_ID_ADDR);
599         /* Identity Address Information is used in the Transport Specific Key Distribution phase to distribute
600         its public device address or static random address. if slave using static random address is encrypted,
601         it should distribute its static random address */
602 #if (BLE_INCLUDED == TRUE)
603         if(btm_cb.ble_ctr_cb.addr_mgnt_cb.own_addr_type == BLE_ADDR_RANDOM && memcmp(btm_cb.ble_ctr_cb.addr_mgnt_cb.static_rand_addr, btm_cb.ble_ctr_cb.addr_mgnt_cb.private_addr,6) == 0) {
604             UINT8_TO_STREAM (p, 0x01);
605             BDADDR_TO_STREAM (p, btm_cb.ble_ctr_cb.addr_mgnt_cb.static_rand_addr);
606         } else
607 #endif  ///BLE_INCLUDED == TRUE
608         {
609             UINT8_TO_STREAM (p, 0);
610             BDADDR_TO_STREAM (p, controller_get_interface()->get_address()->address);
611         }
612 
613         p_buf->offset = L2CAP_MIN_OFFSET;
614         p_buf->len = SMP_ID_ADDR_SIZE;
615     }
616 
617     return p_buf;
618 }
619 
620 /*******************************************************************************
621 **
622 ** Function         smp_build_signing_info_cmd
623 **
624 ** Description      Build signing information command.
625 **
626 *******************************************************************************/
smp_build_signing_info_cmd(UINT8 cmd_code,tSMP_CB * p_cb)627 static BT_HDR *smp_build_signing_info_cmd(UINT8 cmd_code, tSMP_CB *p_cb)
628 {
629     BT_HDR      *p_buf = NULL ;
630     UINT8       *p;
631     UNUSED(cmd_code);
632 
633     SMP_TRACE_EVENT("smp_build_signing_info_cmd\n");
634     if ((p_buf = (BT_HDR *)osi_malloc(sizeof(BT_HDR) + SMP_SIGN_INFO_SIZE + L2CAP_MIN_OFFSET)) != NULL) {
635         p = (UINT8 *)(p_buf + 1) + L2CAP_MIN_OFFSET;
636 
637         UINT8_TO_STREAM (p, SMP_OPCODE_SIGN_INFO);
638         ARRAY_TO_STREAM (p, p_cb->csrk, BT_OCTET16_LEN);
639 
640         p_buf->offset = L2CAP_MIN_OFFSET;
641         p_buf->len = SMP_SIGN_INFO_SIZE;
642     }
643 
644     return p_buf;
645 }
646 
647 /*******************************************************************************
648 **
649 ** Function         smp_build_pairing_fail
650 **
651 ** Description      Build Pairing Fail command.
652 **
653 *******************************************************************************/
smp_build_pairing_fail(UINT8 cmd_code,tSMP_CB * p_cb)654 static BT_HDR *smp_build_pairing_fail(UINT8 cmd_code, tSMP_CB *p_cb)
655 {
656     BT_HDR      *p_buf = NULL ;
657     UINT8       *p;
658     UNUSED(cmd_code);
659 
660     SMP_TRACE_EVENT("%s\n", __func__);
661     if ((p_buf = (BT_HDR *)osi_malloc(sizeof(BT_HDR) + SMP_PAIR_FAIL_SIZE + L2CAP_MIN_OFFSET)) != NULL) {
662         p = (UINT8 *)(p_buf + 1) + L2CAP_MIN_OFFSET;
663 
664         UINT8_TO_STREAM (p, SMP_OPCODE_PAIRING_FAILED);
665         UINT8_TO_STREAM (p, p_cb->failure);
666 
667         p_buf->offset = L2CAP_MIN_OFFSET;
668         p_buf->len = SMP_PAIR_FAIL_SIZE;
669     }
670 
671     return p_buf;
672 }
673 
674 /*******************************************************************************
675 **
676 ** Function         smp_build_security_request
677 **
678 ** Description      Build security request command.
679 **
680 *******************************************************************************/
smp_build_security_request(UINT8 cmd_code,tSMP_CB * p_cb)681 static BT_HDR *smp_build_security_request(UINT8 cmd_code, tSMP_CB *p_cb)
682 {
683     BT_HDR      *p_buf = NULL ;
684     UINT8       *p;
685     UNUSED(cmd_code);
686 
687     SMP_TRACE_EVENT("%s\n", __func__);
688     if ((p_buf = (BT_HDR *)osi_malloc(sizeof(BT_HDR) + 2 + L2CAP_MIN_OFFSET)) != NULL) {
689         p = (UINT8 *)(p_buf + 1) + L2CAP_MIN_OFFSET;
690 
691         UINT8_TO_STREAM (p, SMP_OPCODE_SEC_REQ);
692         UINT8_TO_STREAM (p,  p_cb->loc_auth_req);
693 
694         p_buf->offset = L2CAP_MIN_OFFSET;
695         p_buf->len = SMP_SECURITY_REQUEST_SIZE;
696 
697         SMP_TRACE_EVENT("opcode=%d auth_req=0x%x", SMP_OPCODE_SEC_REQ,  p_cb->loc_auth_req );
698     }
699 
700     return p_buf;
701 
702 }
703 
704 /*******************************************************************************
705 **
706 ** Function         smp_build_pair_public_key_cmd
707 **
708 ** Description      Build pairing public key command.
709 **
710 *******************************************************************************/
smp_build_pair_public_key_cmd(UINT8 cmd_code,tSMP_CB * p_cb)711 static BT_HDR *smp_build_pair_public_key_cmd(UINT8 cmd_code, tSMP_CB *p_cb)
712 {
713     BT_HDR  *p_buf = NULL ;
714     UINT8   *p;
715     UINT8   publ_key[2 * BT_OCTET32_LEN];
716     UINT8   *p_publ_key = publ_key;
717     UNUSED(cmd_code);
718 
719     SMP_TRACE_EVENT("%s\n", __FUNCTION__);
720 
721     memcpy(p_publ_key, p_cb->loc_publ_key.x, BT_OCTET32_LEN);
722     memcpy(p_publ_key + BT_OCTET32_LEN, p_cb->loc_publ_key.y, BT_OCTET32_LEN);
723 
724     if ((p_buf = (BT_HDR *)osi_malloc(sizeof(BT_HDR) +
725                                       SMP_PAIR_PUBL_KEY_SIZE + L2CAP_MIN_OFFSET)) != NULL) {
726         p = (UINT8 *)(p_buf + 1) + L2CAP_MIN_OFFSET;
727 
728         UINT8_TO_STREAM (p, SMP_OPCODE_PAIR_PUBLIC_KEY);
729         ARRAY_TO_STREAM (p, p_publ_key, 2 * BT_OCTET32_LEN);
730 
731         p_buf->offset = L2CAP_MIN_OFFSET;
732         p_buf->len = SMP_PAIR_PUBL_KEY_SIZE;
733     }
734 
735     return p_buf;
736 }
737 
738 /*******************************************************************************
739 **
740 ** Function         smp_build_pairing_commitment_cmd
741 **
742 ** Description      Build pairing commitment command.
743 **
744 *******************************************************************************/
smp_build_pairing_commitment_cmd(UINT8 cmd_code,tSMP_CB * p_cb)745 static BT_HDR *smp_build_pairing_commitment_cmd(UINT8 cmd_code, tSMP_CB *p_cb)
746 {
747     BT_HDR *p_buf = NULL;
748     UINT8 *p;
749     UNUSED(cmd_code);
750 
751     SMP_TRACE_EVENT("%s\n", __func__);
752     if ((p_buf = (BT_HDR *)osi_malloc(sizeof(BT_HDR) + SMP_PAIR_COMMITM_SIZE + L2CAP_MIN_OFFSET))
753             != NULL) {
754         p = (UINT8 *)(p_buf + 1) + L2CAP_MIN_OFFSET;
755 
756         UINT8_TO_STREAM (p, SMP_OPCODE_CONFIRM);
757         ARRAY_TO_STREAM (p, p_cb->commitment, BT_OCTET16_LEN);
758 
759         p_buf->offset = L2CAP_MIN_OFFSET;
760         p_buf->len = SMP_PAIR_COMMITM_SIZE;
761     }
762 
763     return p_buf;
764 }
765 
766 /*******************************************************************************
767 **
768 ** Function         smp_build_pair_dhkey_check_cmd
769 **
770 ** Description      Build pairing DHKey check command.
771 **
772 *******************************************************************************/
smp_build_pair_dhkey_check_cmd(UINT8 cmd_code,tSMP_CB * p_cb)773 static BT_HDR *smp_build_pair_dhkey_check_cmd(UINT8 cmd_code, tSMP_CB *p_cb)
774 {
775     BT_HDR *p_buf = NULL;
776     UINT8 *p;
777     UNUSED(cmd_code);
778 
779     SMP_TRACE_EVENT("%s\n", __FUNCTION__);
780     if ((p_buf = (BT_HDR *)osi_malloc(sizeof(BT_HDR) +
781                                       SMP_PAIR_DHKEY_CHECK_SIZE + L2CAP_MIN_OFFSET)) != NULL) {
782         p = (UINT8 *)(p_buf + 1) + L2CAP_MIN_OFFSET;
783 
784         UINT8_TO_STREAM (p, SMP_OPCODE_PAIR_DHKEY_CHECK);
785         ARRAY_TO_STREAM (p, p_cb->dhkey_check, BT_OCTET16_LEN);
786 
787         p_buf->offset = L2CAP_MIN_OFFSET;
788         p_buf->len = SMP_PAIR_DHKEY_CHECK_SIZE;
789     }
790 
791     return p_buf;
792 }
793 
794 /*******************************************************************************
795 **
796 ** Function         smp_build_pairing_keypress_notification_cmd
797 **
798 ** Description      Build keypress notification command.
799 **
800 *******************************************************************************/
smp_build_pairing_keypress_notification_cmd(UINT8 cmd_code,tSMP_CB * p_cb)801 static BT_HDR *smp_build_pairing_keypress_notification_cmd(UINT8 cmd_code, tSMP_CB *p_cb)
802 {
803     BT_HDR      *p_buf = NULL ;
804     UINT8       *p;
805     UNUSED(cmd_code);
806 
807     SMP_TRACE_EVENT("%s\n", __FUNCTION__);
808     if ((p_buf = (BT_HDR *)osi_malloc(sizeof(BT_HDR)\
809                                       + SMP_PAIR_KEYPR_NOTIF_SIZE + L2CAP_MIN_OFFSET)) != NULL) {
810         p = (UINT8 *)(p_buf + 1) + L2CAP_MIN_OFFSET;
811 
812         UINT8_TO_STREAM (p, SMP_OPCODE_PAIR_KEYPR_NOTIF);
813         UINT8_TO_STREAM (p, p_cb->local_keypress_notification);
814 
815         p_buf->offset = L2CAP_MIN_OFFSET;
816         p_buf->len = SMP_PAIR_KEYPR_NOTIF_SIZE;
817     }
818 
819     return p_buf;
820 }
821 
822 /*******************************************************************************
823 **
824 ** Function         smp_convert_string_to_tk
825 **
826 ** Description      This function is called to convert a 6 to 16 digits numeric
827 **                  character string into SMP TK.
828 **
829 **
830 ** Returns          void
831 **
832 *******************************************************************************/
smp_convert_string_to_tk(BT_OCTET16 tk,UINT32 passkey)833 void smp_convert_string_to_tk(BT_OCTET16 tk, UINT32 passkey)
834 {
835     UINT8   *p = tk;
836     tSMP_KEY    key;
837     SMP_TRACE_EVENT("smp_convert_string_to_tk\n");
838     UINT32_TO_STREAM(p, passkey);
839 
840     key.key_type    = SMP_KEY_TYPE_TK;
841     key.p_data      = tk;
842 
843     smp_sm_event(&smp_cb, SMP_KEY_READY_EVT, &key);
844 }
845 
846 /*******************************************************************************
847 **
848 ** Function         smp_mask_enc_key
849 **
850 ** Description      This function is called to mask off the encryption key based
851 **                  on the maximum encryption key size.
852 **
853 **
854 ** Returns          void
855 **
856 *******************************************************************************/
smp_mask_enc_key(UINT8 loc_enc_size,UINT8 * p_data)857 void smp_mask_enc_key(UINT8 loc_enc_size, UINT8 *p_data)
858 {
859     SMP_TRACE_EVENT("smp_mask_enc_key\n");
860     if (loc_enc_size < BT_OCTET16_LEN) {
861         for (; loc_enc_size < BT_OCTET16_LEN; loc_enc_size ++) {
862             * (p_data + loc_enc_size) = 0;
863         }
864     }
865     return;
866 }
867 
868 /*******************************************************************************
869 **
870 ** Function         smp_xor_128
871 **
872 ** Description      utility function to do an biteise exclusive-OR of two bit
873 **                  strings of the length of BT_OCTET16_LEN.
874 **
875 ** Returns          void
876 **
877 *******************************************************************************/
smp_xor_128(BT_OCTET16 a,const BT_OCTET16 b)878 void smp_xor_128(BT_OCTET16 a, const BT_OCTET16 b)
879 {
880     UINT8 i, *aa = a;
881     const UINT8 *bb = b;
882 
883     SMP_TRACE_EVENT("smp_xor_128\n");
884     for (i = 0; i < BT_OCTET16_LEN; i++) {
885         aa[i] = aa[i] ^ bb[i];
886     }
887 }
888 
889 /*******************************************************************************
890 **
891 ** Function         smp_cb_cleanup
892 **
893 ** Description      Clean up SMP control block
894 **
895 ** Returns          void
896 **
897 *******************************************************************************/
smp_cb_cleanup(tSMP_CB * p_cb)898 void smp_cb_cleanup(tSMP_CB *p_cb)
899 {
900     tSMP_CALLBACK   *p_callback = p_cb->p_callback;
901     UINT8           trace_level = p_cb->trace_level;
902     UINT32          static_passkey = p_cb->static_passkey;
903     BOOLEAN         use_static_passkey = p_cb->use_static_passkey;
904     SMP_TRACE_EVENT("smp_cb_cleanup\n");
905 
906     memset(p_cb, 0, sizeof(tSMP_CB));
907     p_cb->p_callback = p_callback;
908     p_cb->trace_level = trace_level;
909     if(use_static_passkey) {
910         p_cb->use_static_passkey = use_static_passkey;
911         p_cb->static_passkey = static_passkey;
912     }
913 }
914 
915 /*******************************************************************************
916 **
917 ** Function         smp_remove_fixed_channel
918 **
919 ** Description      This function is called to remove the fixed channel
920 **
921 ** Returns          void
922 **
923 *******************************************************************************/
smp_remove_fixed_channel(tSMP_CB * p_cb)924 void smp_remove_fixed_channel(tSMP_CB *p_cb)
925 {
926     SMP_TRACE_DEBUG("%s\n", __func__);
927 
928     if (p_cb->smp_over_br) {
929         L2CA_RemoveFixedChnl (L2CAP_SMP_BR_CID, p_cb->pairing_bda);
930     } else {
931         L2CA_RemoveFixedChnl (L2CAP_SMP_CID, p_cb->pairing_bda);
932     }
933 }
934 
935 /*******************************************************************************
936 **
937 ** Function         smp_reset_control_value
938 **
939 ** Description      This function is called to reset the control block value when
940 **                  pairing procedure finished.
941 **
942 **
943 ** Returns          void
944 **
945 *******************************************************************************/
smp_reset_control_value(tSMP_CB * p_cb)946 void smp_reset_control_value(tSMP_CB *p_cb)
947 {
948     SMP_TRACE_EVENT("smp_reset_control_value\n");
949     btu_stop_timer (&p_cb->rsp_timer_ent);
950     p_cb->flags = 0;
951     /* set the link idle timer to drop the link when pairing is done
952        usually service discovery will follow authentication complete, to avoid
953        racing condition for a link down/up, set link idle timer to be
954        SMP_LINK_TOUT_MIN to guarantee SMP key exchange */
955     L2CA_SetIdleTimeoutByBdAddr(p_cb->pairing_bda, SMP_LINK_TOUT_MIN, BT_TRANSPORT_LE);
956 
957     /* We can tell L2CAP to remove the fixed channel (if it has one) */
958     smp_remove_fixed_channel(p_cb);
959     smp_cb_cleanup(p_cb);
960 }
961 
962 /*******************************************************************************
963 **
964 ** Function         smp_proc_pairing_cmpl
965 **
966 ** Description      This function is called to process pairing complete
967 **
968 **
969 ** Returns          void
970 **
971 *******************************************************************************/
smp_proc_pairing_cmpl(tSMP_CB * p_cb)972 void smp_proc_pairing_cmpl(tSMP_CB *p_cb)
973 {
974     tSMP_EVT_DATA   evt_data = {0};
975     tSMP_CALLBACK   *p_callback = p_cb->p_callback;
976     BD_ADDR         pairing_bda;
977 
978     SMP_TRACE_DEBUG ("smp_proc_pairing_cmpl \n");
979 
980     evt_data.cmplt.reason = p_cb->status;
981     evt_data.cmplt.smp_over_br = p_cb->smp_over_br;
982     evt_data.cmplt.auth_mode = 0;
983 #if (BLE_INCLUDED == TRUE)
984     tBTM_SEC_DEV_REC    *p_rec = btm_find_dev (p_cb->pairing_bda);
985     if (p_cb->status == SMP_SUCCESS) {
986         evt_data.cmplt.sec_level = p_cb->sec_level;
987         if (p_cb->auth_mode) { // the first encryption
988             evt_data.cmplt.auth_mode = p_cb->auth_mode;
989             if (p_rec) {
990                 p_rec->ble.auth_mode = p_cb->auth_mode;
991             }
992         } else if (p_rec) {
993             evt_data.cmplt.auth_mode =  p_rec->ble.auth_mode;
994         }
995     }
996 #else
997     if (p_cb->status == SMP_SUCCESS) {
998         evt_data.cmplt.sec_level = p_cb->sec_level;
999         evt_data.cmplt.auth_mode = p_cb->auth_mode;
1000     }
1001 #endif
1002 
1003     evt_data.cmplt.is_pair_cancel  = FALSE;
1004 
1005     if (p_cb->is_pair_cancel) {
1006         evt_data.cmplt.is_pair_cancel = TRUE;
1007     }
1008 
1009 
1010     SMP_TRACE_DEBUG ("send SMP_COMPLT_EVT reason=0x%0x sec_level=0x%0x\n",
1011                      evt_data.cmplt.reason,
1012                      evt_data.cmplt.sec_level );
1013 
1014     memcpy (pairing_bda, p_cb->pairing_bda, BD_ADDR_LEN);
1015 
1016 #if (BLE_INCLUDED == TRUE)
1017 #if (SMP_SLAVE_CON_PARAMS_UPD_ENABLE == TRUE)
1018     if (p_cb->role == HCI_ROLE_SLAVE) {
1019         if(p_rec && p_rec->ble.skip_update_conn_param) {
1020             //clear flag
1021             p_rec->ble.skip_update_conn_param = false;
1022         } else {
1023             #if (BT_MULTI_CONNECTION_ENBALE == FALSE)
1024             L2CA_EnableUpdateBleConnParams(p_cb->pairing_bda, TRUE);
1025             #endif
1026         }
1027     }
1028 
1029 #endif
1030 #endif  ///BLE_INCLUDED == TRUE
1031 
1032     smp_reset_control_value(p_cb);
1033     // TODO: clear local oob data when start advertising
1034     smp_clear_local_oob_data();
1035 
1036     if (p_callback) {
1037         (*p_callback) (SMP_COMPLT_EVT, pairing_bda, &evt_data);
1038     }
1039 }
1040 
1041 /*******************************************************************************
1042 **
1043 ** Function         smp_command_has_invalid_parameters
1044 **
1045 ** Description      Checks if the received SMP command has invalid parameters i.e.
1046 **                  if the command length is valid and the command parameters are
1047 **                  inside specified range.
1048 **                  It returns TRUE if the command has invalid parameters.
1049 **
1050 ** Returns          TRUE if the command has invalid parameters, FALSE otherwise.
1051 **
1052 *******************************************************************************/
smp_command_has_invalid_parameters(tSMP_CB * p_cb)1053 BOOLEAN smp_command_has_invalid_parameters(tSMP_CB *p_cb)
1054 {
1055     UINT8 cmd_code = p_cb->rcvd_cmd_code;
1056 
1057     SMP_TRACE_DEBUG("%s for cmd code 0x%02x\n", __func__, cmd_code);
1058 
1059     if ((cmd_code > (SMP_OPCODE_MAX + 1 /* for SMP_OPCODE_PAIR_COMMITM */)) ||
1060             (cmd_code < SMP_OPCODE_MIN)) {
1061         SMP_TRACE_WARNING("Somehow received command with the RESERVED code 0x%02x\n", cmd_code);
1062         return TRUE;
1063     }
1064 
1065     if (!(*smp_cmd_len_is_valid[cmd_code])(p_cb)) {
1066         return TRUE;
1067     }
1068 
1069     if (!(*smp_cmd_param_ranges_are_valid[cmd_code])(p_cb)) {
1070         return TRUE;
1071     }
1072 
1073     return FALSE;
1074 }
1075 
1076 /*******************************************************************************
1077 **
1078 ** Function         smp_command_has_valid_fixed_length
1079 **
1080 ** Description      Checks if the received command size is equal to the size
1081 **                  according to specs.
1082 **
1083 ** Returns          TRUE if the command size is as expected, FALSE otherwise.
1084 **
1085 ** Note             The command is expected to have fixed length.
1086 *******************************************************************************/
smp_command_has_valid_fixed_length(tSMP_CB * p_cb)1087 BOOLEAN smp_command_has_valid_fixed_length(tSMP_CB *p_cb)
1088 {
1089     UINT8   cmd_code = p_cb->rcvd_cmd_code;
1090 
1091     SMP_TRACE_DEBUG("%s for cmd code 0x%02x\n", __func__, cmd_code);
1092 
1093     if (p_cb->rcvd_cmd_len != smp_cmd_size_per_spec[cmd_code]) {
1094         SMP_TRACE_WARNING("Rcvd from the peer cmd 0x%02x with invalid length\
1095             0x%02x (per spec the length is 0x%02x).\n",
1096                           cmd_code, p_cb->rcvd_cmd_len, smp_cmd_size_per_spec[cmd_code]);
1097         return FALSE;
1098     }
1099 
1100     return TRUE;
1101 }
1102 
1103 /*******************************************************************************
1104 **
1105 ** Function         smp_pairing_request_response_parameters_are_valid
1106 **
1107 ** Description      Validates parameter ranges in the received SMP command
1108 **                  pairing request or pairing response.
1109 **                  The parameters to validate:
1110 **                  IO capability,
1111 **                  OOB data flag,
1112 **                  Bonding_flags in AuthReq
1113 **                  Maximum encryption key size.
1114 **                  Returns FALSE if at least one of these parameters is out of range.
1115 **
1116 *******************************************************************************/
smp_pairing_request_response_parameters_are_valid(tSMP_CB * p_cb)1117 BOOLEAN smp_pairing_request_response_parameters_are_valid(tSMP_CB *p_cb)
1118 {
1119     UINT8   io_caps = p_cb->peer_io_caps;
1120     UINT8   oob_flag = p_cb->peer_oob_flag;
1121     UINT8   bond_flag = p_cb->peer_auth_req & 0x03; //0x03 is gen bond with appropriate mask
1122     UINT8   enc_size = p_cb->peer_enc_size;
1123 
1124     SMP_TRACE_DEBUG("%s for cmd code 0x%02x\n", __func__, p_cb->rcvd_cmd_code);
1125 
1126     if (io_caps >= BTM_IO_CAP_MAX) {
1127         SMP_TRACE_WARNING("Rcvd from the peer cmd 0x%02x with IO Capability \
1128             value (0x%02x) out of range).\n",
1129                           p_cb->rcvd_cmd_code, io_caps);
1130         return FALSE;
1131     }
1132 
1133     if (!((oob_flag == SMP_OOB_NONE) || (oob_flag == SMP_OOB_PRESENT))) {
1134         SMP_TRACE_WARNING("Rcvd from the peer cmd 0x%02x with OOB data flag value \
1135             (0x%02x) out of range).\n",
1136                           p_cb->rcvd_cmd_code, oob_flag);
1137         return FALSE;
1138     }
1139 
1140     if (!((bond_flag == SMP_AUTH_NO_BOND) || (bond_flag == SMP_AUTH_BOND))) {
1141         SMP_TRACE_WARNING("Rcvd from the peer cmd 0x%02x with Bonding_Flags value (0x%02x)\
1142                            out of range).\n",
1143                           p_cb->rcvd_cmd_code, bond_flag);
1144         return FALSE;
1145     }
1146 
1147     /* `bte_appl_cfg.ble_min_enc_key_size` will be `SMP_ENCR_KEY_SIZE_MIN` by
1148      * default if not set explicitly  */
1149 #if (BLE_INCLUDED == TRUE)
1150     if (enc_size < bte_appl_cfg.ble_min_key_size) {
1151         SMP_TRACE_WARNING("Rcvd from the peer cmd 0x%02x with Maximum Encryption \
1152             Key value (0x%02x) less than minimum required key size).\n",
1153                           p_cb->rcvd_cmd_code, enc_size);
1154         return FALSE;
1155     }
1156 #else
1157     if (enc_size < SMP_ENCR_KEY_SIZE_MIN) {
1158         SMP_TRACE_WARNING("Rcvd from the peer cmd 0x%02x with Maximum Encryption \
1159             Key value (0x%02x) less than minimum required key size).\n",
1160                           p_cb->rcvd_cmd_code, enc_size);
1161         return FALSE;
1162     }
1163 #endif
1164 
1165     if (enc_size > SMP_ENCR_KEY_SIZE_MAX) {
1166         SMP_TRACE_WARNING("Rcvd from the peer cmd 0x%02x with Maximum Encryption \
1167             Key value (0x%02x) greater than supported by stack).\n",
1168                           p_cb->rcvd_cmd_code, enc_size);
1169         return FALSE;
1170     }
1171 
1172     return TRUE;
1173 }
1174 
1175 /*******************************************************************************
1176 **
1177 ** Function         smp_pairing_keypress_notification_is_valid
1178 **
1179 ** Description      Validates Notification Type parameter range in the received SMP command
1180 **                  pairing keypress notification.
1181 **                  Returns FALSE if this parameter is out of range.
1182 **
1183 *******************************************************************************/
smp_pairing_keypress_notification_is_valid(tSMP_CB * p_cb)1184 BOOLEAN smp_pairing_keypress_notification_is_valid(tSMP_CB *p_cb)
1185 {
1186     tBTM_SP_KEY_TYPE keypress_notification = p_cb->peer_keypress_notification;
1187 
1188     SMP_TRACE_DEBUG("%s for cmd code 0x%02x\n", __func__, p_cb->rcvd_cmd_code);
1189 
1190     if (keypress_notification >= BTM_SP_KEY_OUT_OF_RANGE) {
1191         SMP_TRACE_WARNING("Rcvd from the peer cmd 0x%02x with Pairing Keypress \
1192             Notification value (0x%02x) out of range).\n",
1193                           p_cb->rcvd_cmd_code, keypress_notification);
1194         return FALSE;
1195     }
1196 
1197     return TRUE;
1198 }
1199 
1200 /*******************************************************************************
1201 **
1202 ** Function         smp_parameter_unconditionally_valid
1203 **
1204 ** Description      Always returns TRUE.
1205 **
1206 *******************************************************************************/
smp_parameter_unconditionally_valid(tSMP_CB * p_cb)1207 BOOLEAN smp_parameter_unconditionally_valid(tSMP_CB *p_cb)
1208 {
1209     return TRUE;
1210 }
1211 
1212 /*******************************************************************************
1213 **
1214 ** Function         smp_parameter_unconditionally_invalid
1215 **
1216 ** Description      Always returns FALSE.
1217 **
1218 *******************************************************************************/
smp_parameter_unconditionally_invalid(tSMP_CB * p_cb)1219 BOOLEAN smp_parameter_unconditionally_invalid(tSMP_CB *p_cb)
1220 {
1221     return FALSE;
1222 }
1223 
1224 /*******************************************************************************
1225 **
1226 ** Function         smp_reject_unexpected_pairing_command
1227 **
1228 ** Description      send pairing failure to an unexpected pairing command during
1229 **                  an active pairing process.
1230 **
1231 ** Returns          void
1232 **
1233 *******************************************************************************/
smp_reject_unexpected_pairing_command(BD_ADDR bd_addr)1234 void smp_reject_unexpected_pairing_command(BD_ADDR bd_addr)
1235 {
1236     BT_HDR *p_buf;
1237     UINT8   *p;
1238 
1239     SMP_TRACE_DEBUG ("%s\n", __FUNCTION__);
1240 
1241     if ((p_buf = (BT_HDR *)osi_malloc(sizeof(BT_HDR) + \
1242                                       SMP_PAIR_FAIL_SIZE + L2CAP_MIN_OFFSET)) != NULL) {
1243         p = (UINT8 *)(p_buf + 1) + L2CAP_MIN_OFFSET;
1244 
1245         UINT8_TO_STREAM (p, SMP_OPCODE_PAIRING_FAILED);
1246         UINT8_TO_STREAM (p, SMP_PAIR_NOT_SUPPORT);
1247 
1248         p_buf->offset = L2CAP_MIN_OFFSET;
1249         p_buf->len = SMP_PAIR_FAIL_SIZE;
1250 
1251         smp_send_msg_to_L2CAP(bd_addr, p_buf);
1252     }
1253 }
1254 
1255 /*******************************************************************************
1256 ** Function         smp_select_association_model
1257 **
1258 ** Description      This function selects association model to use for STK
1259 **                  generation. Selection is based on both sides' io capability,
1260 **                  oob data flag and authentication request.
1261 **
1262 ** Note             If Secure Connections Only mode is required locally then we
1263 **                  come to this point only if both sides support Secure Connections
1264 **                  mode, i.e. if p_cb->secure_connections_only_mode_required = TRUE then we come
1265 **                  to this point only if
1266 **                      (p_cb->peer_auth_req & SMP_SC_SUPPORT_BIT) ==
1267 **                      (p_cb->loc_auth_req & SMP_SC_SUPPORT_BIT) ==
1268 **                      SMP_SC_SUPPORT_BIT
1269 **
1270 *******************************************************************************/
smp_select_association_model(tSMP_CB * p_cb)1271 tSMP_ASSO_MODEL smp_select_association_model(tSMP_CB *p_cb)
1272 {
1273     tSMP_ASSO_MODEL model = SMP_MODEL_OUT_OF_RANGE;
1274     p_cb->le_secure_connections_mode_is_used = FALSE;
1275 
1276     SMP_TRACE_EVENT("%s\n", __FUNCTION__);
1277     SMP_TRACE_DEBUG("%s p_cb->peer_io_caps = %d p_cb->local_io_capability = %d\n",
1278                     __FUNCTION__, p_cb->peer_io_caps, p_cb->local_io_capability);
1279     SMP_TRACE_DEBUG("%s p_cb->peer_oob_flag = %d p_cb->loc_oob_flag = %d\n",
1280                     __FUNCTION__, p_cb->peer_oob_flag, p_cb->loc_oob_flag);
1281     SMP_TRACE_DEBUG("%s p_cb->peer_auth_req = 0x%02x p_cb->loc_auth_req = 0x%02x\n",
1282                     __FUNCTION__, p_cb->peer_auth_req, p_cb->loc_auth_req);
1283     SMP_TRACE_DEBUG("%s p_cb->secure_connections_only_mode_required = %s\n",
1284                     __FUNCTION__, p_cb->secure_connections_only_mode_required ?
1285                     "TRUE" : "FALSE");
1286 
1287     if ((p_cb->peer_auth_req & SMP_SC_SUPPORT_BIT) && (p_cb->loc_auth_req & SMP_SC_SUPPORT_BIT)) {
1288         p_cb->le_secure_connections_mode_is_used = TRUE;
1289     }
1290 
1291     SMP_TRACE_DEBUG("use_sc_process = %d\n", p_cb->le_secure_connections_mode_is_used);
1292 
1293     if (p_cb->le_secure_connections_mode_is_used) {
1294         model = smp_select_association_model_secure_connections(p_cb);
1295     } else {
1296         model = smp_select_legacy_association_model(p_cb);
1297     }
1298     return model;
1299 }
1300 
1301 /*******************************************************************************
1302 ** Function         smp_select_legacy_association_model
1303 **
1304 ** Description      This function is called to select association mode if at least
1305 **                  one side doesn't support secure connections.
1306 **
1307 *******************************************************************************/
smp_select_legacy_association_model(tSMP_CB * p_cb)1308 tSMP_ASSO_MODEL smp_select_legacy_association_model(tSMP_CB *p_cb)
1309 {
1310     tSMP_ASSO_MODEL model = SMP_MODEL_OUT_OF_RANGE;
1311 
1312     SMP_TRACE_DEBUG("%s\n", __func__);
1313     /* if OOB data is present on both devices, then use OOB association model */
1314     if (p_cb->peer_oob_flag == SMP_OOB_PRESENT && p_cb->loc_oob_flag == SMP_OOB_PRESENT) {
1315         return SMP_MODEL_OOB;
1316     }
1317 
1318     /* else if neither device requires MITM, then use Just Works association model */
1319     if (SMP_NO_MITM_REQUIRED (p_cb->peer_auth_req) && SMP_NO_MITM_REQUIRED(p_cb->loc_auth_req)) {
1320         return SMP_MODEL_ENCRYPTION_ONLY;
1321     }
1322 
1323     /* otherwise use IO capability to select association model */
1324     if (p_cb->peer_io_caps < SMP_IO_CAP_MAX && p_cb->local_io_capability < SMP_IO_CAP_MAX) {
1325         if (p_cb->role == HCI_ROLE_MASTER) {
1326             model = smp_association_table[p_cb->role][p_cb->peer_io_caps]
1327                     [p_cb->local_io_capability];
1328         } else {
1329             model = smp_association_table[p_cb->role][p_cb->local_io_capability]
1330                     [p_cb->peer_io_caps];
1331         }
1332     }
1333 
1334     return model;
1335 }
1336 
1337 /*******************************************************************************
1338 ** Function         smp_select_association_model_secure_connections
1339 **
1340 ** Description      This function is called to select association mode if both
1341 **                  sides support secure connections.
1342 **
1343 *******************************************************************************/
smp_select_association_model_secure_connections(tSMP_CB * p_cb)1344 tSMP_ASSO_MODEL smp_select_association_model_secure_connections(tSMP_CB *p_cb)
1345 {
1346     tSMP_ASSO_MODEL model = SMP_MODEL_OUT_OF_RANGE;
1347 
1348     SMP_TRACE_DEBUG("%s\n", __func__);
1349     /* if OOB data is present on at least one device, then use OOB association model */
1350     if (p_cb->peer_oob_flag == SMP_OOB_PRESENT || p_cb->loc_oob_flag == SMP_OOB_PRESENT) {
1351         return SMP_MODEL_SEC_CONN_OOB;
1352     }
1353 
1354     /* else if neither device requires MITM, then use Just Works association model */
1355     if (SMP_NO_MITM_REQUIRED (p_cb->peer_auth_req) && SMP_NO_MITM_REQUIRED(p_cb->loc_auth_req)) {
1356         return SMP_MODEL_SEC_CONN_JUSTWORKS;
1357     }
1358 
1359     /* otherwise use IO capability to select association model */
1360     if (p_cb->peer_io_caps < SMP_IO_CAP_MAX && p_cb->local_io_capability < SMP_IO_CAP_MAX) {
1361         if (p_cb->role == HCI_ROLE_MASTER) {
1362             model = smp_association_table_sc[p_cb->role][p_cb->peer_io_caps]
1363                     [p_cb->local_io_capability];
1364         } else {
1365             model = smp_association_table_sc[p_cb->role][p_cb->local_io_capability]
1366                     [p_cb->peer_io_caps];
1367         }
1368     }
1369 
1370     return model;
1371 }
1372 
1373 /*******************************************************************************
1374 ** Function         smp_reverse_array
1375 **
1376 ** Description      This function reverses array bytes
1377 **
1378 *******************************************************************************/
smp_reverse_array(UINT8 * arr,UINT8 len)1379 void smp_reverse_array(UINT8 *arr, UINT8 len)
1380 {
1381     UINT8 i = 0, tmp;
1382 
1383     SMP_TRACE_DEBUG("smp_reverse_array\n");
1384 
1385     for (i = 0; i < len / 2; i ++) {
1386         tmp = arr[i];
1387         arr[i] = arr[len - 1 - i];
1388         arr[len - 1 - i] = tmp;
1389     }
1390 }
1391 
1392 /*******************************************************************************
1393 ** Function         smp_calculate_random_input
1394 **
1395 ** Description      This function returns random input value to be used in commitment
1396 **                  calculation for SC passkey entry association mode
1397 **                  (if bit["round"] in "random" array == 1 then returns 0x81
1398 **                   else returns 0x80).
1399 **
1400 ** Returns          ri value
1401 **
1402 *******************************************************************************/
smp_calculate_random_input(UINT8 * random,UINT8 round)1403 UINT8 smp_calculate_random_input(UINT8 *random, UINT8 round)
1404 {
1405     UINT8 i = round / 8;
1406     UINT8 j = round % 8;
1407     UINT8 ri;
1408 
1409     SMP_TRACE_DEBUG("random: 0x%02x, round: %d, i: %d, j: %d\n", random[i], round, i, j);
1410     ri = ((random[i] >> j) & 1) | 0x80;
1411     SMP_TRACE_DEBUG("%s ri=0x%02x\n", __func__, ri);
1412     return ri;
1413 }
1414 
1415 /*******************************************************************************
1416 ** Function         smp_collect_local_io_capabilities
1417 **
1418 ** Description      This function puts into IOcap array local device
1419 **                  IOCapability, OOB data, AuthReq.
1420 **
1421 ** Returns          void
1422 **
1423 *******************************************************************************/
smp_collect_local_io_capabilities(UINT8 * iocap,tSMP_CB * p_cb)1424 void smp_collect_local_io_capabilities(UINT8 *iocap, tSMP_CB *p_cb)
1425 {
1426     SMP_TRACE_DEBUG("%s\n", __func__);
1427 
1428     iocap[0] = p_cb->local_io_capability;
1429     iocap[1] = p_cb->loc_oob_flag;
1430     iocap[2] = p_cb->loc_auth_req;
1431 }
1432 
1433 /*******************************************************************************
1434 ** Function         smp_collect_peer_io_capabilities
1435 **
1436 ** Description      This function puts into IOcap array peer device
1437 **                  IOCapability, OOB data, AuthReq.
1438 **
1439 ** Returns          void
1440 **
1441 *******************************************************************************/
smp_collect_peer_io_capabilities(UINT8 * iocap,tSMP_CB * p_cb)1442 void smp_collect_peer_io_capabilities(UINT8 *iocap, tSMP_CB *p_cb)
1443 {
1444     SMP_TRACE_DEBUG("%s\n", __func__);
1445 
1446     iocap[0] = p_cb->peer_io_caps;
1447     iocap[1] = p_cb->peer_oob_flag;
1448     iocap[2] = p_cb->peer_auth_req;
1449 }
1450 #if (BLE_INCLUDED == TRUE)
1451 /*******************************************************************************
1452 ** Function         smp_collect_local_ble_address
1453 **
1454 ** Description      This function puts into le_addr array local device le address:
1455 **                  le_addr[0-5] = local BD ADDR,
1456 **                  le_addr[6] = local le address type (PUBLIC/RANDOM).
1457 **
1458 ** Returns          void
1459 **
1460 *******************************************************************************/
smp_collect_local_ble_address(UINT8 * le_addr,tSMP_CB * p_cb)1461 void smp_collect_local_ble_address(UINT8 *le_addr, tSMP_CB *p_cb)
1462 {
1463     tBLE_ADDR_TYPE  addr_type = 0;
1464     BD_ADDR         bda;
1465     UINT8           *p = le_addr;
1466 
1467     SMP_TRACE_DEBUG("%s\n", __func__);
1468 
1469     BTM_ReadConnectionAddr( p_cb->pairing_bda, bda, &addr_type);
1470     BDADDR_TO_STREAM(p, bda);
1471     UINT8_TO_STREAM(p, addr_type);
1472 }
1473 
1474 /*******************************************************************************
1475 ** Function         smp_collect_peer_ble_address
1476 **
1477 ** Description      This function puts into le_addr array peer device le address:
1478 **                  le_addr[0-5] = peer BD ADDR,
1479 **                  le_addr[6] = peer le address type (PUBLIC/RANDOM).
1480 **
1481 ** Returns          void
1482 **
1483 *******************************************************************************/
smp_collect_peer_ble_address(UINT8 * le_addr,tSMP_CB * p_cb)1484 void smp_collect_peer_ble_address(UINT8 *le_addr, tSMP_CB *p_cb)
1485 {
1486     tBLE_ADDR_TYPE  addr_type = 0;
1487     BD_ADDR         bda;
1488     UINT8           *p = le_addr;
1489 
1490     SMP_TRACE_DEBUG("%s\n", __func__);
1491 
1492     if (!BTM_ReadRemoteConnectionAddr(p_cb->pairing_bda, bda, &addr_type)) {
1493         SMP_TRACE_ERROR("can not collect peer le addr information for unknown device\n");
1494         return;
1495     }
1496 
1497     BDADDR_TO_STREAM(p, bda);
1498     UINT8_TO_STREAM(p, addr_type);
1499 }
1500 
1501 /*******************************************************************************
1502 ** Function         smp_check_commitment
1503 **
1504 ** Description      This function compares peer commitment values:
1505 **                  - expected (i.e. calculated locally),
1506 **                  - received from the peer.
1507 **
1508 ** Returns          TRUE  if the values are the same
1509 **                  FALSE otherwise
1510 **
1511 *******************************************************************************/
smp_check_commitment(tSMP_CB * p_cb)1512 BOOLEAN smp_check_commitment(tSMP_CB *p_cb)
1513 {
1514     BT_OCTET16 expected;
1515 
1516     SMP_TRACE_DEBUG("%s\n", __func__);
1517 
1518     smp_calculate_peer_commitment(p_cb, expected);
1519     print128(expected, (const UINT8 *)"calculated peer commitment");
1520     print128(p_cb->remote_commitment, (const UINT8 *)"received peer commitment");
1521 
1522     if (memcmp(p_cb->remote_commitment, expected, BT_OCTET16_LEN)) {
1523         SMP_TRACE_WARNING("Commitment check fails\n");
1524         return FALSE;
1525     }
1526 
1527     SMP_TRACE_DEBUG("Commitment check succeeds\n");
1528     return TRUE;
1529 }
1530 
1531 /*******************************************************************************
1532 **
1533 ** Function         smp_save_secure_connections_long_term_key
1534 **
1535 ** Description      The function saves SC LTK as BLE key for future use as local
1536 **                  and/or peer key.
1537 **
1538 ** Returns          void
1539 **
1540 *******************************************************************************/
smp_save_secure_connections_long_term_key(tSMP_CB * p_cb)1541 void smp_save_secure_connections_long_term_key(tSMP_CB *p_cb)
1542 {
1543     tBTM_LE_LENC_KEYS   lle_key;
1544     tBTM_LE_PENC_KEYS   ple_key;
1545 
1546     SMP_TRACE_DEBUG("%s-Save LTK as local LTK key\n", __func__);
1547     memcpy(lle_key.ltk, p_cb->ltk, BT_OCTET16_LEN);
1548     lle_key.div = 0;
1549     lle_key.key_size = p_cb->loc_enc_size;
1550     lle_key.sec_level = p_cb->sec_level;
1551     btm_sec_save_le_key(p_cb->pairing_bda, BTM_LE_KEY_LENC, (tBTM_LE_KEY_VALUE *)&lle_key, TRUE);
1552 
1553     SMP_TRACE_DEBUG("%s-Save LTK as peer LTK key\n", __func__);
1554     ple_key.ediv = 0;
1555     memset(ple_key.rand, 0, BT_OCTET8_LEN);
1556     memcpy(ple_key.ltk, p_cb->ltk, BT_OCTET16_LEN);
1557     ple_key.sec_level = p_cb->sec_level;
1558     ple_key.key_size  = p_cb->loc_enc_size;
1559     btm_sec_save_le_key(p_cb->pairing_bda, BTM_LE_KEY_PENC, (tBTM_LE_KEY_VALUE *)&ple_key, TRUE);
1560 }
1561 
1562 /*******************************************************************************
1563 **
1564 ** Function         smp_calculate_f5_mackey_and_long_term_key
1565 **
1566 ** Description      The function calculates MacKey and LTK and saves them in CB.
1567 **                  To calculate MacKey and LTK it calls smp_calc_f5(...).
1568 **                  MacKey is used in dhkey calculation, LTK is used to encrypt
1569 **                  the link.
1570 **
1571 ** Returns          FALSE if out of resources, TRUE otherwise.
1572 **
1573 *******************************************************************************/
smp_calculate_f5_mackey_and_long_term_key(tSMP_CB * p_cb)1574 BOOLEAN smp_calculate_f5_mackey_and_long_term_key(tSMP_CB *p_cb)
1575 {
1576     UINT8 a[7];
1577     UINT8 b[7];
1578     UINT8 *p_na;
1579     UINT8 *p_nb;
1580 
1581     SMP_TRACE_DEBUG("%s\n", __func__);
1582 
1583     if (p_cb->role == HCI_ROLE_MASTER) {
1584         smp_collect_local_ble_address(a, p_cb);
1585         smp_collect_peer_ble_address(b, p_cb);
1586         p_na = p_cb->rand;
1587         p_nb = p_cb->rrand;
1588     } else {
1589         smp_collect_local_ble_address(b, p_cb);
1590         smp_collect_peer_ble_address(a, p_cb);
1591         p_na = p_cb->rrand;
1592         p_nb = p_cb->rand;
1593     }
1594 
1595     if (!smp_calculate_f5(p_cb->dhkey, p_na, p_nb, a, b, p_cb->mac_key, p_cb->ltk)) {
1596         SMP_TRACE_ERROR("%s failed\n", __func__);
1597         return FALSE;
1598     }
1599 
1600     SMP_TRACE_EVENT ("%s is completed\n", __func__);
1601     return TRUE;
1602 }
1603 #endif  ///BLE_INCLUDED == TRUE
1604 /*******************************************************************************
1605 **
1606 ** Function         smp_request_oob_data
1607 **
1608 ** Description      Requests application to provide OOB data.
1609 **
1610 ** Returns          TRUE - OOB data has to be provided by application
1611 **                  FALSE - otherwise (unexpected)
1612 **
1613 *******************************************************************************/
smp_request_oob_data(tSMP_CB * p_cb)1614 BOOLEAN smp_request_oob_data(tSMP_CB *p_cb)
1615 {
1616     tSMP_OOB_DATA_TYPE req_oob_type = SMP_OOB_INVALID_TYPE;
1617 
1618     SMP_TRACE_DEBUG("%s\n", __func__);
1619 
1620     if (p_cb->peer_oob_flag == SMP_OOB_PRESENT && p_cb->loc_oob_flag == SMP_OOB_PRESENT) {
1621         /* both local and peer rcvd data OOB */
1622         req_oob_type = SMP_OOB_BOTH;
1623     } else if (p_cb->peer_oob_flag == SMP_OOB_PRESENT) {
1624         /* peer rcvd OOB local data, local didn't receive OOB peer data */
1625         req_oob_type = SMP_OOB_LOCAL;
1626     } else if (p_cb->loc_oob_flag == SMP_OOB_PRESENT) {
1627         req_oob_type = SMP_OOB_PEER;
1628     }
1629 
1630     SMP_TRACE_DEBUG("req_oob_type = %d\n", req_oob_type);
1631 
1632     if (req_oob_type == SMP_OOB_INVALID_TYPE) {
1633         return FALSE;
1634     }
1635 
1636     p_cb->req_oob_type = req_oob_type;
1637     p_cb->cb_evt = SMP_SC_OOB_REQ_EVT;
1638     smp_sm_event(p_cb, SMP_TK_REQ_EVT, &req_oob_type);
1639 
1640     return TRUE;
1641 }
1642 
1643 
1644 #endif
1645