Home | History | Annotate | Download | only in btm
      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 Bluetooth Security Manager
     22  *
     23  ******************************************************************************/
     24 
     25 #include <string.h>
     26 #include "bt_types.h"
     27 #include "hcimsgs.h"
     28 #include "btu.h"
     29 #include "btm_int.h"
     30 #include "l2c_int.h"
     31 
     32 #if (BT_USE_TRACES == TRUE && BT_TRACE_VERBOSE == FALSE)
     33 /* needed for sprintf() */
     34 #include <stdio.h>
     35 #endif
     36 
     37 #if BLE_INCLUDED == TRUE
     38     #include "gatt_int.h"
     39 #endif
     40 
     41 #define BTM_SEC_MAX_COLLISION_DELAY     (GKI_SECS_TO_TICKS(5))
     42 
     43 #ifdef APPL_AUTH_WRITE_EXCEPTION
     44 BOOLEAN (APPL_AUTH_WRITE_EXCEPTION)(BD_ADDR bd_addr);
     45 #endif
     46 
     47 /********************************************************************************/
     48 /*              L O C A L    F U N C T I O N     P R O T O T Y P E S            */
     49 /********************************************************************************/
     50 static tBTM_SEC_SERV_REC *btm_sec_find_first_serv (BOOLEAN is_originator, UINT16 psm);
     51 static tBTM_SEC_SERV_REC *btm_sec_find_next_serv (tBTM_SEC_SERV_REC *p_cur);
     52 static tBTM_SEC_SERV_REC *btm_sec_find_mx_serv (UINT8 is_originator, UINT16 psm,
     53                                                 UINT32 mx_proto_id,
     54                                                 UINT32 mx_chan_id);
     55 
     56 static tBTM_STATUS btm_sec_execute_procedure (tBTM_SEC_DEV_REC *p_dev_rec);
     57 static BOOLEAN  btm_sec_start_get_name (tBTM_SEC_DEV_REC *p_dev_rec);
     58 static BOOLEAN  btm_sec_start_authentication (tBTM_SEC_DEV_REC *p_dev_rec);
     59 static BOOLEAN  btm_sec_start_encryption (tBTM_SEC_DEV_REC *p_dev_rec);
     60 static void     btm_sec_collision_timeout (TIMER_LIST_ENT *p_tle);
     61 static void     btm_restore_mode(void);
     62 static void     btm_sec_pairing_timeout (TIMER_LIST_ENT *p_tle);
     63 static tBTM_STATUS btm_sec_dd_create_conn (tBTM_SEC_DEV_REC *p_dev_rec);
     64 static void     btm_sec_change_pairing_state (tBTM_PAIRING_STATE new_state);
     65 
     66 #if (BT_USE_TRACES == TRUE)
     67 static char     *btm_pair_state_descr (tBTM_PAIRING_STATE state);
     68 #endif
     69 
     70 static void     btm_sec_check_pending_reqs(void);
     71 static BOOLEAN  btm_sec_queue_mx_request (BD_ADDR bd_addr,  UINT16 psm,  BOOLEAN is_orig,
     72                                           UINT32 mx_proto_id, UINT32 mx_chan_id,
     73                                           tBTM_SEC_CALLBACK *p_callback, void *p_ref_data);
     74 static void     btm_sec_bond_cancel_complete (void);
     75 static void     btm_send_link_key_notif (tBTM_SEC_DEV_REC *p_dev_rec);
     76 static BOOLEAN  btm_sec_check_prefetch_pin (tBTM_SEC_DEV_REC  *p_dev_rec);
     77 
     78 static UINT8    btm_sec_start_authorization (tBTM_SEC_DEV_REC *p_dev_rec);
     79 BOOLEAN         btm_sec_are_all_trusted(UINT32 p_mask[]);
     80 
     81 static tBTM_STATUS btm_sec_send_hci_disconnect (tBTM_SEC_DEV_REC *p_dev_rec, UINT8 reason);
     82 tBTM_SEC_DEV_REC *btm_sec_find_dev_by_sec_state (UINT8 state);
     83 
     84 static BOOLEAN  btm_sec_set_security_level ( CONNECTION_TYPE conn_type, char *p_name, UINT8 service_id,
     85                                             UINT16 sec_level, UINT16 psm, UINT32 mx_proto_id,
     86                                             UINT32 mx_chan_id);
     87 
     88 /* TRUE - authenticated link key is possible */
     89 static const BOOLEAN btm_sec_io_map [BTM_IO_CAP_MAX][BTM_IO_CAP_MAX] =
     90 {
     91     /*   OUT,    IO,     IN,     NONE */
     92 /* OUT  */ {FALSE,  FALSE,  TRUE,   FALSE},
     93 /* IO   */ {FALSE,  TRUE,   TRUE,   FALSE},
     94 /* IN   */ {TRUE,   TRUE,   TRUE,   FALSE},
     95 /* NONE */ {FALSE,  FALSE,  FALSE,  FALSE}
     96 };
     97 /*  BTM_IO_CAP_OUT      0   DisplayOnly */
     98 /*  BTM_IO_CAP_IO       1   DisplayYesNo */
     99 /*  BTM_IO_CAP_IN       2   KeyboardOnly */
    100 /*  BTM_IO_CAP_NONE     3   NoInputNoOutput */
    101 
    102 /*******************************************************************************
    103 **
    104 ** Function         BTM_SecRegister
    105 **
    106 ** Description      Application manager calls this function to register for
    107 **                  security services.  There can be one and only one application
    108 **                  saving link keys.  BTM allows only first registration.
    109 **
    110 ** Returns          TRUE if registered OK, else FALSE
    111 **
    112 *******************************************************************************/
    113 BOOLEAN  BTM_SecRegister (tBTM_APPL_INFO *p_cb_info)
    114 {
    115 #if BLE_INCLUDED == TRUE
    116     BT_OCTET16      temp_value = {0};
    117 #endif
    118 
    119     BTM_TRACE_EVENT0 ("BTM_Sec: application registered");
    120 
    121 #if BLE_INCLUDED == TRUE && SMP_INCLUDED == TRUE
    122     BTM_TRACE_ERROR1 ("BTM_SecRegister:p_cb_info->p_le_callback == 0x%x ", p_cb_info->p_le_callback);
    123 
    124     if (p_cb_info->p_le_callback)
    125     {
    126 #if SMP_INCLUDED == TRUE
    127         BTM_TRACE_EVENT0 ("BTM_Sec: SMP_Register( btm_proc_smp_cback )");
    128         SMP_Register(btm_proc_smp_cback);
    129 #endif
    130         /* if no IR is loaded, need to regenerate all the keys */
    131         if (memcmp(btm_cb.devcb.id_keys.ir, &temp_value, sizeof(BT_OCTET16)) == 0)
    132         {
    133             btm_ble_reset_id();
    134         }
    135     }
    136     else
    137     {
    138         BTM_TRACE_ERROR0 ("BTM_SecRegister:p_cb_info->p_le_callback == NULL ");
    139     }
    140 #endif
    141 
    142 
    143 
    144     btm_cb.api = *p_cb_info;
    145 #if BLE_INCLUDED == TRUE && SMP_INCLUDED == TRUE
    146      BTM_TRACE_ERROR1 ("BTM_SecRegister: btm_cb.api.p_le_callback = 0x%x ", btm_cb.api.p_le_callback);
    147 #endif
    148     BTM_TRACE_EVENT0 ("BTM_Sec: application registered");
    149     return(TRUE);
    150 }
    151 
    152 
    153 /*******************************************************************************
    154 **
    155 ** Function         BTM_SecRegisterLinkKeyNotificationCallback
    156 **
    157 ** Description      Application manager calls this function to register for
    158 **                  link key notification.  When there is nobody registered
    159 **                  we should avoid changing link key
    160 **
    161 ** Returns          TRUE if registered OK, else FALSE
    162 **
    163 *******************************************************************************/
    164 BOOLEAN BTM_SecRegisterLinkKeyNotificationCallback (tBTM_LINK_KEY_CALLBACK *p_callback)
    165 {
    166     btm_cb.api.p_link_key_callback = p_callback;
    167     return(TRUE);
    168 }
    169 
    170 
    171 /*******************************************************************************
    172 **
    173 ** Function         BTM_SecAddRmtNameNotifyCallback
    174 **
    175 ** Description      Any profile can register to be notified when name of the
    176 **                  remote device is resolved.
    177 **
    178 ** Returns          TRUE if registered OK, else FALSE
    179 **
    180 *******************************************************************************/
    181 BOOLEAN  BTM_SecAddRmtNameNotifyCallback (tBTM_RMT_NAME_CALLBACK *p_callback)
    182 {
    183     int i;
    184 
    185     for (i = 0; i < BTM_SEC_MAX_RMT_NAME_CALLBACKS; i++)
    186     {
    187         if (btm_cb.p_rmt_name_callback[i] == NULL)
    188         {
    189             btm_cb.p_rmt_name_callback[i] = p_callback;
    190             return(TRUE);
    191         }
    192     }
    193 
    194     return(FALSE);
    195 }
    196 
    197 
    198 /*******************************************************************************
    199 **
    200 ** Function         BTM_SecDeleteRmtNameNotifyCallback
    201 **
    202 ** Description      Any profile can deregister notification when a new Link Key
    203 **                  is generated per connection.
    204 **
    205 ** Returns          TRUE if OK, else FALSE
    206 **
    207 *******************************************************************************/
    208 BOOLEAN  BTM_SecDeleteRmtNameNotifyCallback (tBTM_RMT_NAME_CALLBACK *p_callback)
    209 {
    210     int i;
    211 
    212     for (i = 0; i < BTM_SEC_MAX_RMT_NAME_CALLBACKS; i++)
    213     {
    214         if (btm_cb.p_rmt_name_callback[i] == p_callback)
    215         {
    216             btm_cb.p_rmt_name_callback[i] = NULL;
    217             return(TRUE);
    218         }
    219     }
    220 
    221     return(FALSE);
    222 }
    223 
    224 
    225 /*******************************************************************************
    226 **
    227 ** Function         BTM_SecSetConnectFilterCallback
    228 **
    229 ** Description      Host can register to be asked whenever a HCI connection
    230 **                  request is received.  In the registered function host
    231 **                  suppose to check connectibility filters.  Yes/No result
    232 **                  should be returned syncronously
    233 **
    234 ** Returns          void
    235 **
    236 *******************************************************************************/
    237 void BTM_SecSetConnectFilterCallback (tBTM_FILTER_CB *p_callback)
    238 {
    239     btm_cb.p_conn_filter_cb = p_callback;
    240 }
    241 
    242 /*******************************************************************************
    243 **
    244 ** Function         BTM_GetSecurityMode
    245 **
    246 ** Description      Get security mode for the device
    247 **
    248 ** Returns          void
    249 **
    250 *******************************************************************************/
    251 UINT8 BTM_GetSecurityMode (void)
    252 {
    253     return(btm_cb.security_mode);
    254 }
    255 
    256 /*******************************************************************************
    257 **
    258 ** Function         BTM_GetSecurityFlags
    259 **
    260 ** Description      Get security flags for the device
    261 **
    262 ** Returns          BOOLEAN TRUE or FALSE is device found
    263 **
    264 *******************************************************************************/
    265 BOOLEAN BTM_GetSecurityFlags (BD_ADDR bd_addr, UINT8 * p_sec_flags)
    266 {
    267     tBTM_SEC_DEV_REC *p_dev_rec;
    268 
    269     if ((p_dev_rec = btm_find_dev (bd_addr)) != NULL)
    270     {
    271         *p_sec_flags = p_dev_rec->sec_flags;
    272         return(TRUE);
    273     }
    274     BTM_TRACE_ERROR0 ("BTM_GetSecurityFlags false");
    275     return(FALSE);
    276 }
    277 
    278 /*******************************************************************************
    279 **
    280 ** Function         BTM_SetSecurityMode
    281 **
    282 ** Description      Set security mode for the device
    283 **
    284 ** Returns          void
    285 **
    286 *******************************************************************************/
    287 void BTM_SetSecurityMode (UINT8 security_mode)
    288 {
    289     UINT8   old_mode = btm_cb.security_mode;
    290 
    291     UINT8   sp_mode = HCI_SP_MODE_ENABLED;
    292     UINT8   sp_debug_mode = HCI_SPD_MODE_DISABLED;
    293 
    294     switch (security_mode)
    295     {
    296 #if (BTM_PRE_LISBON_INCLUDED == TRUE)
    297         case BTM_SEC_MODE_NONE:
    298         case BTM_SEC_MODE_SERVICE:
    299         case BTM_SEC_MODE_LINK:
    300             break;
    301 #endif
    302 
    303         case BTM_SEC_MODE_SP_DEBUG:
    304             sp_debug_mode = HCI_SPD_MODE_ENABLED;
    305             break;
    306         case BTM_SEC_MODE_SP:
    307             /* the default is enabled */
    308             break;
    309         default:
    310             BTM_TRACE_ERROR1 ("BTM_SetSecurityMode: unknown mode:%d", security_mode);
    311             return;
    312     }
    313     btm_cb.security_mode = security_mode;
    314 
    315     if (HCI_SIMPLE_PAIRING_SUPPORTED(btm_cb.devcb.local_lmp_features[HCI_EXT_FEATURES_PAGE_0]))
    316     {
    317         /* Lisbon devices and only use BTM_SEC_MODE_SP */
    318         btm_cb.security_mode = BTM_SEC_MODE_SP;
    319         BTM_TRACE_DEBUG2("BTM_SetSecurityMode: SP:%d, debug:%d", sp_mode, sp_debug_mode);
    320         btsnd_hcic_write_simple_pairing_mode(sp_mode);
    321         btsnd_hcic_write_simp_pair_debug_mode(sp_debug_mode);
    322         return;
    323     }
    324 
    325     /* must be a pre-Lisbon device */
    326 #if (BTM_PRE_LISBON_INCLUDED == TRUE)
    327     /* If previously security mode was Link Level and now lesser notify */
    328     /* controller not to perform authentication, encryption on startup  */
    329     if ((old_mode == BTM_SEC_MODE_LINK)
    330         && (       security_mode != BTM_SEC_MODE_LINK))
    331     {
    332         BTM_TRACE_DEBUG0("BTM_SetSecurityMode: Authen Enable -> FALSE");
    333         btsnd_hcic_write_auth_enable (FALSE);
    334         btsnd_hcic_write_encr_mode (HCI_ENCRYPT_MODE_DISABLED);
    335     }
    336 
    337     /* If previously security is increased to Link Level notify */
    338     /* controller to perform authentication, encryption on startup  */
    339     if ((old_mode != BTM_SEC_MODE_LINK)
    340         && (       security_mode == BTM_SEC_MODE_LINK))
    341     {
    342         BTM_TRACE_DEBUG0("BTM_SetSecurityMode: Authen Enable -> TRUE");
    343         btsnd_hcic_write_auth_enable (TRUE);
    344         btsnd_hcic_write_encr_mode (HCI_ENCRYPT_MODE_POINT_TO_POINT);
    345     }
    346 #endif  /* BTM_PRE_LISBON_INCLUDED == TRUE */
    347 }
    348 
    349 /*******************************************************************************
    350 **
    351 ** Function         BTM_SetPinType
    352 **
    353 ** Description      Set PIN type for the device.
    354 **
    355 ** Returns          void
    356 **
    357 *******************************************************************************/
    358 void BTM_SetPinType (UINT8 pin_type, PIN_CODE pin_code, UINT8 pin_code_len)
    359 {
    360     BTM_TRACE_API3 ("BTM_SetPinType: pin type %d [variable-0, fixed-1], code %s, length %d",
    361                     pin_type, (char *) pin_code, pin_code_len);
    362 
    363     /* If device is not up security mode will be set as a part of startup */
    364     if ( (btm_cb.cfg.pin_type != pin_type)
    365          && (btm_cb.devcb.state > BTM_DEV_STATE_WAIT_AFTER_RESET) )
    366     {
    367         btsnd_hcic_write_pin_type (pin_type);
    368     }
    369 
    370     btm_cb.cfg.pin_type     = pin_type;
    371     btm_cb.cfg.pin_code_len = pin_code_len;
    372     memcpy (btm_cb.cfg.pin_code, pin_code, pin_code_len);
    373 }
    374 
    375 /*******************************************************************************
    376 **
    377 ** Function         BTM_SetPairableMode
    378 **
    379 ** Description      Enable or disable pairing
    380 **
    381 ** Parameters       allow_pairing - (TRUE or FALSE) whether or not the device
    382 **                      allows pairing.
    383 **                  connect_only_paired - (TRUE or FALSE) whether or not to
    384 **                      only allow paired devices to connect.
    385 **
    386 ** Returns          void
    387 **
    388 *******************************************************************************/
    389 void BTM_SetPairableMode (BOOLEAN allow_pairing, BOOLEAN connect_only_paired)
    390 {
    391     BTM_TRACE_API2 ("BTM_SetPairableMode()  allow_pairing: %u   connect_only_paired: %u", allow_pairing, connect_only_paired);
    392 
    393     btm_cb.pairing_disabled    = !allow_pairing;
    394     btm_cb.connect_only_paired = connect_only_paired;
    395 }
    396 
    397 
    398 #define BTM_NO_AVAIL_SEC_SERVICES   ((UINT16) 0xffff)
    399 
    400 /*******************************************************************************
    401 **
    402 ** Function         BTM_SetUCDSecurityLevel
    403 **
    404 ** Description      Register UCD service security level with Security Manager
    405 **
    406 ** Parameters:      is_originator - TRUE if originating the connection, FALSE if not
    407 **                  p_name      - Name of the service relevant only if
    408 **                                authorization will show this name to user. ignored
    409 **                                if BTM_SEC_SERVICE_NAME_LEN is 0.
    410 **                  service_id  - service ID for the service passed to authorization callback
    411 **                  sec_level   - bit mask of the security features
    412 **                  psm         - L2CAP PSM
    413 **                  mx_proto_id - protocol ID of multiplexing proto below
    414 **                  mx_chan_id  - channel ID of multiplexing proto below
    415 **
    416 ** Returns          TRUE if registered OK, else FALSE
    417 **
    418 *******************************************************************************/
    419 BOOLEAN BTM_SetUCDSecurityLevel (BOOLEAN is_originator, char *p_name, UINT8 service_id,
    420                                  UINT16 sec_level, UINT16 psm, UINT32 mx_proto_id,
    421                                  UINT32 mx_chan_id)
    422 {
    423 #if (L2CAP_UCD_INCLUDED == TRUE)
    424     CONNECTION_TYPE conn_type;
    425 
    426     if (is_originator)
    427         conn_type = CONNLESS_ORIG;
    428     else
    429         conn_type = CONNLESS_TERM;
    430 
    431     return(btm_sec_set_security_level (conn_type, p_name, service_id,
    432                                        sec_level, psm, mx_proto_id, mx_chan_id));
    433 #else
    434     return FALSE;
    435 #endif
    436 }
    437 
    438 /*******************************************************************************
    439 **
    440 ** Function         BTM_SetSecurityLevel
    441 **
    442 ** Description      Register service security level with Security Manager
    443 **
    444 ** Parameters:      is_originator - TRUE if originating the connection, FALSE if not
    445 **                  p_name      - Name of the service relevant only if
    446 **                                authorization will show this name to user. ignored
    447 **                                if BTM_SEC_SERVICE_NAME_LEN is 0.
    448 **                  service_id  - service ID for the service passed to authorization callback
    449 **                  sec_level   - bit mask of the security features
    450 **                  psm         - L2CAP PSM
    451 **                  mx_proto_id - protocol ID of multiplexing proto below
    452 **                  mx_chan_id  - channel ID of multiplexing proto below
    453 **
    454 ** Returns          TRUE if registered OK, else FALSE
    455 **
    456 *******************************************************************************/
    457 BOOLEAN BTM_SetSecurityLevel (BOOLEAN is_originator, char *p_name, UINT8 service_id,
    458                               UINT16 sec_level, UINT16 psm, UINT32 mx_proto_id,
    459                               UINT32 mx_chan_id)
    460 {
    461 #if (L2CAP_UCD_INCLUDED == TRUE)
    462     CONNECTION_TYPE conn_type;
    463 
    464     if (is_originator)
    465         conn_type = CONN_ORIENT_ORIG;
    466     else
    467         conn_type = CONN_ORIENT_TERM;
    468 
    469     return(btm_sec_set_security_level (conn_type, p_name, service_id,
    470                                        sec_level, psm, mx_proto_id, mx_chan_id));
    471 #else
    472     return(btm_sec_set_security_level (is_originator, p_name, service_id,
    473                                        sec_level, psm, mx_proto_id, mx_chan_id));
    474 #endif
    475 }
    476 
    477 /*******************************************************************************
    478 **
    479 ** Function         btm_sec_set_security_level
    480 **
    481 ** Description      Register service security level with Security Manager
    482 **
    483 ** Parameters:      conn_type   - TRUE if originating the connection, FALSE if not
    484 **                  p_name      - Name of the service relevant only if
    485 **                                authorization will show this name to user. ignored
    486 **                                if BTM_SEC_SERVICE_NAME_LEN is 0.
    487 **                  service_id  - service ID for the service passed to authorization callback
    488 **                  sec_level   - bit mask of the security features
    489 **                  psm         - L2CAP PSM
    490 **                  mx_proto_id - protocol ID of multiplexing proto below
    491 **                  mx_chan_id  - channel ID of multiplexing proto below
    492 **
    493 ** Returns          TRUE if registered OK, else FALSE
    494 **
    495 *******************************************************************************/
    496 static BOOLEAN btm_sec_set_security_level (CONNECTION_TYPE conn_type, char *p_name, UINT8 service_id,
    497                                            UINT16 sec_level, UINT16 psm, UINT32 mx_proto_id,
    498                                            UINT32 mx_chan_id)
    499 {
    500     tBTM_SEC_SERV_REC   *p_srec;
    501     UINT16               index;
    502     UINT16               first_unused_record = BTM_NO_AVAIL_SEC_SERVICES;
    503     BOOLEAN              record_allocated = FALSE;
    504     BOOLEAN              is_originator;
    505 #if (L2CAP_UCD_INCLUDED == TRUE)
    506     BOOLEAN              is_ucd;
    507 
    508     if (conn_type & CONNECTION_TYPE_ORIG_MASK)
    509         is_originator = TRUE;
    510     else
    511         is_originator = FALSE;
    512 
    513     if (conn_type & CONNECTION_TYPE_CONNLESS_MASK )
    514     {
    515         is_ucd = TRUE;
    516     }
    517     else
    518     {
    519         is_ucd = FALSE;
    520     }
    521 #else
    522     is_originator = conn_type;
    523 #endif
    524 
    525     /* See if the record can be reused (same service name, psm, mx_proto_id,
    526        service_id, and mx_chan_id), or obtain the next unused record */
    527 
    528     p_srec = &btm_cb.sec_serv_rec[0];
    529 
    530 
    531     for (index = 0; index < BTM_SEC_MAX_SERVICE_RECORDS; index++, p_srec++)
    532     {
    533         /* Check if there is already a record for this service */
    534         if (p_srec->security_flags & BTM_SEC_IN_USE)
    535         {
    536 #if BTM_SEC_SERVICE_NAME_LEN > 0
    537             if (p_srec->psm == psm                  &&
    538                 p_srec->mx_proto_id == mx_proto_id  &&
    539                 service_id == p_srec->service_id    &&
    540                 (!strncmp (p_name, (char *) p_srec->orig_service_name,
    541                            BTM_SEC_SERVICE_NAME_LEN) ||
    542                  !strncmp (p_name, (char *) p_srec->term_service_name,
    543                            BTM_SEC_SERVICE_NAME_LEN)))
    544 #else
    545             if (p_srec->psm == psm                  &&
    546                 p_srec->mx_proto_id == mx_proto_id  &&
    547                 service_id == p_srec->service_id)
    548 #endif
    549             {
    550                 record_allocated = TRUE;
    551                 break;
    552             }
    553         }
    554         /* Mark the first available service record */
    555         else if (!record_allocated)
    556         {
    557             memset (p_srec, 0, sizeof(tBTM_SEC_SERV_REC));
    558             record_allocated = TRUE;
    559             first_unused_record = index;
    560         }
    561     }
    562 
    563     if (!record_allocated)
    564     {
    565         BTM_TRACE_WARNING1("BTM_SEC_REG: Out of Service Records (%d)",  BTM_SEC_MAX_SERVICE_RECORDS);
    566         return(record_allocated);
    567     }
    568 
    569     /* Process the request if service record is valid */
    570     /* If a duplicate service wasn't found, use the first available */
    571     if (index >= BTM_SEC_MAX_SERVICE_RECORDS)
    572     {
    573         index = first_unused_record;
    574         p_srec = &btm_cb.sec_serv_rec[index];
    575     }
    576 
    577     p_srec->psm         = psm;
    578     p_srec->service_id  = service_id;
    579     p_srec->mx_proto_id = mx_proto_id;
    580 
    581     if (is_originator)
    582     {
    583         p_srec->orig_mx_chan_id = mx_chan_id;
    584 #if BTM_SEC_SERVICE_NAME_LEN > 0
    585         BCM_STRNCPY_S ((char *)p_srec->orig_service_name, sizeof(p_srec->orig_service_name), p_name, BTM_SEC_SERVICE_NAME_LEN);
    586 #endif
    587         /* clear out the old setting, just in case it exists */
    588 #if (L2CAP_UCD_INCLUDED == TRUE)
    589         if ( is_ucd )
    590         {
    591             p_srec->ucd_security_flags &=
    592             ~(BTM_SEC_OUT_AUTHORIZE | BTM_SEC_OUT_ENCRYPT    | BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_OUT_MITM |
    593               BTM_SEC_FORCE_MASTER | BTM_SEC_ATTEMPT_MASTER | BTM_SEC_FORCE_SLAVE | BTM_SEC_ATTEMPT_SLAVE);
    594         }
    595         else
    596 #endif
    597         {
    598             p_srec->security_flags &=
    599             ~(BTM_SEC_OUT_AUTHORIZE | BTM_SEC_OUT_ENCRYPT    | BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_OUT_MITM |
    600               BTM_SEC_FORCE_MASTER | BTM_SEC_ATTEMPT_MASTER | BTM_SEC_FORCE_SLAVE | BTM_SEC_ATTEMPT_SLAVE);
    601         }
    602 
    603         /* Parameter validation.  Originator should not set requirements for incoming connections */
    604         sec_level &= ~(BTM_SEC_IN_AUTHORIZE | BTM_SEC_IN_ENCRYPT | BTM_SEC_IN_AUTHENTICATE | BTM_SEC_IN_MITM);
    605 
    606         if (btm_cb.security_mode == BTM_SEC_MODE_SP)
    607         {
    608             if (sec_level & BTM_SEC_OUT_AUTHENTICATE)
    609                 sec_level |= BTM_SEC_OUT_MITM;
    610         }
    611 
    612         /* Make sure the authenticate bit is set, when encrypt bit is set */
    613         if (sec_level & BTM_SEC_OUT_ENCRYPT)
    614             sec_level |= BTM_SEC_OUT_AUTHENTICATE;
    615 
    616         /* outgoing connections usually set the security level right before
    617          * the connection is initiated.
    618          * set it to be the outgoing service */
    619 #if (L2CAP_UCD_INCLUDED == TRUE)
    620         if ( is_ucd == FALSE )
    621 #endif
    622         {
    623             btm_cb.p_out_serv = p_srec;
    624         }
    625     }
    626     else
    627     {
    628         p_srec->term_mx_chan_id = mx_chan_id;
    629 #if BTM_SEC_SERVICE_NAME_LEN > 0
    630         BCM_STRNCPY_S ((char *)p_srec->term_service_name, sizeof(p_srec->term_service_name), p_name, BTM_SEC_SERVICE_NAME_LEN);
    631 #endif
    632         /* clear out the old setting, just in case it exists */
    633 #if (L2CAP_UCD_INCLUDED == TRUE)
    634         if ( is_ucd )
    635         {
    636             p_srec->ucd_security_flags &=
    637             ~(BTM_SEC_IN_AUTHORIZE | BTM_SEC_IN_ENCRYPT     | BTM_SEC_IN_AUTHENTICATE | BTM_SEC_IN_MITM |
    638               BTM_SEC_FORCE_MASTER | BTM_SEC_ATTEMPT_MASTER | BTM_SEC_FORCE_SLAVE | BTM_SEC_ATTEMPT_SLAVE);
    639         }
    640         else
    641 #endif
    642         {
    643             p_srec->security_flags &=
    644             ~(BTM_SEC_IN_AUTHORIZE | BTM_SEC_IN_ENCRYPT     | BTM_SEC_IN_AUTHENTICATE | BTM_SEC_IN_MITM |
    645               BTM_SEC_FORCE_MASTER | BTM_SEC_ATTEMPT_MASTER | BTM_SEC_FORCE_SLAVE | BTM_SEC_ATTEMPT_SLAVE);
    646         }
    647 
    648         /* Parameter validation.  Acceptor should not set requirements for outgoing connections */
    649         sec_level &= ~(BTM_SEC_OUT_AUTHORIZE | BTM_SEC_OUT_ENCRYPT | BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_OUT_MITM);
    650 
    651         if (btm_cb.security_mode == BTM_SEC_MODE_SP)
    652         {
    653             if (sec_level & BTM_SEC_IN_AUTHENTICATE)
    654                 sec_level |= BTM_SEC_IN_MITM;
    655         }
    656 
    657         /* Make sure the authenticate bit is set, when encrypt bit is set */
    658         if (sec_level & BTM_SEC_IN_ENCRYPT)
    659             sec_level |= BTM_SEC_IN_AUTHENTICATE;
    660     }
    661 
    662 #if (L2CAP_UCD_INCLUDED == TRUE)
    663     if ( is_ucd )
    664     {
    665         p_srec->security_flags     |= (UINT16)(BTM_SEC_IN_USE);
    666         p_srec->ucd_security_flags |= (UINT16)(sec_level | BTM_SEC_IN_USE);
    667     }
    668     else
    669     {
    670         p_srec->security_flags |= (UINT16)(sec_level | BTM_SEC_IN_USE);
    671     }
    672 
    673     BTM_TRACE_API6("BTM_SEC_REG[%d]: id %d, conn_type 0x%x, psm 0x%04x, proto_id %d, chan_id %d",
    674                    index, service_id, conn_type, psm, mx_proto_id, mx_chan_id);
    675 
    676     BTM_TRACE_API2("               : security_flags: 0x%04x, ucd_security_flags: 0x%04x",
    677                    p_srec->security_flags, p_srec->ucd_security_flags);
    678 
    679 #if BTM_SEC_SERVICE_NAME_LEN > 0
    680     BTM_TRACE_API2("               : service name [%s] (up to %d chars saved)",
    681                    p_name, BTM_SEC_SERVICE_NAME_LEN);
    682 #endif
    683 #else
    684     p_srec->security_flags |= (UINT16)(sec_level | BTM_SEC_IN_USE);
    685 
    686     BTM_TRACE_API6("BTM_SEC_REG[%d]: id %d, is_orig %d, psm 0x%04x, proto_id %d, chan_id %d",
    687                    index, service_id, is_originator, psm, mx_proto_id, mx_chan_id);
    688 
    689 #if BTM_SEC_SERVICE_NAME_LEN > 0
    690     BTM_TRACE_API3("               : sec: 0x%x, service name [%s] (up to %d chars saved)",
    691                    p_srec->security_flags, p_name, BTM_SEC_SERVICE_NAME_LEN);
    692 #endif
    693 #endif
    694 
    695 
    696     return(record_allocated);
    697 }
    698 
    699 /*******************************************************************************
    700 **
    701 ** Function         BTM_SecClrService
    702 **
    703 ** Description      Removes specified service record(s) from the security database.
    704 **                  All service records with the specified name are removed.
    705 **                  Typically used only by devices with limited RAM so that it can
    706 **                  reuse an old security service record.
    707 **
    708 **                  Note: Unpredictable results may occur if a service is cleared
    709 **                      that is still in use by an application/profile.
    710 **
    711 ** Parameters       Service ID - Id of the service to remove. ('0' removes all service
    712 **                          records (except SDP).
    713 **
    714 ** Returns          Number of records that were freed.
    715 **
    716 *******************************************************************************/
    717 UINT8 BTM_SecClrService (UINT8 service_id)
    718 {
    719     tBTM_SEC_SERV_REC   *p_srec = &btm_cb.sec_serv_rec[0];
    720     UINT8   num_freed = 0;
    721     int     i;
    722 
    723     for (i = 0; i < BTM_SEC_MAX_SERVICE_RECORDS; i++, p_srec++)
    724     {
    725         /* Delete services with specified name (if in use and not SDP) */
    726         if ((p_srec->security_flags & BTM_SEC_IN_USE) && (p_srec->psm != BT_PSM_SDP) &&
    727             (!service_id || (service_id == p_srec->service_id)))
    728         {
    729             BTM_TRACE_API2("BTM_SEC_CLR[%d]: id %d", i, service_id);
    730             p_srec->security_flags = 0;
    731 #if (L2CAP_UCD_INCLUDED == TRUE)
    732             p_srec->ucd_security_flags = 0;
    733 #endif
    734             num_freed++;
    735         }
    736     }
    737 
    738     return(num_freed);
    739 }
    740 
    741 /*******************************************************************************
    742 **
    743 ** Function         btm_sec_clr_service_by_psm
    744 **
    745 ** Description      Removes specified service record from the security database.
    746 **                  All service records with the specified psm are removed.
    747 **                  Typically used by L2CAP to free up the service record used
    748 **                  by dynamic PSM clients when the channel is closed.
    749 **                  The given psm must be a virtual psm.
    750 **
    751 ** Parameters       Service ID - Id of the service to remove. ('0' removes all service
    752 **                          records (except SDP).
    753 **
    754 ** Returns          Number of records that were freed.
    755 **
    756 *******************************************************************************/
    757 UINT8 btm_sec_clr_service_by_psm (UINT16 psm)
    758 {
    759     tBTM_SEC_SERV_REC   *p_srec = &btm_cb.sec_serv_rec[0];
    760     UINT8   num_freed = 0;
    761     int     i;
    762 
    763     for (i = 0; i < BTM_SEC_MAX_SERVICE_RECORDS; i++, p_srec++)
    764     {
    765         /* Delete services with specified name (if in use and not SDP) */
    766         if ((p_srec->security_flags & BTM_SEC_IN_USE) && (p_srec->psm == psm) )
    767         {
    768             BTM_TRACE_API2("BTM_SEC_CLR[%d]: id %d ", i, p_srec->service_id);
    769             p_srec->security_flags = 0;
    770             num_freed++;
    771         }
    772     }
    773     BTM_TRACE_API2("btm_sec_clr_service_by_psm psm:0x%x num_freed:%d", psm, num_freed);
    774 
    775     return(num_freed);
    776 }
    777 
    778 /*******************************************************************************
    779 **
    780 ** Function         btm_sec_clr_temp_auth_service
    781 **
    782 ** Description      Removes specified device record's temporary authorization
    783 **                  flag from the security database.
    784 **
    785 ** Parameters       Device address to be cleared
    786 **
    787 ** Returns          void.
    788 **
    789 *******************************************************************************/
    790 void btm_sec_clr_temp_auth_service (BD_ADDR bda)
    791 {
    792     tBTM_SEC_DEV_REC   *p_dev_rec;
    793 
    794     if ((p_dev_rec = btm_find_dev (bda)) == NULL)
    795     {
    796         BTM_TRACE_WARNING0 ("btm_sec_clr_temp_auth_service() - no dev CB");
    797         return;
    798     }
    799 
    800     /* Reset the temporary authorized flag so that next time (untrusted) service is accessed autorization will take place */
    801     if (p_dev_rec->last_author_service_id != BTM_SEC_NO_LAST_SERVICE_ID && p_dev_rec->p_cur_service)
    802     {
    803         BTM_TRACE_DEBUG6 ("btm_sec_clr_auth_service_by_psm [clearing device: %02x:%02x:%02x:%02x:%02x:%02x]",
    804                     bda[0], bda[1], bda[2], bda[3], bda[4], bda[5]);
    805 
    806         p_dev_rec->last_author_service_id = BTM_SEC_NO_LAST_SERVICE_ID;
    807     }
    808 }
    809 
    810 /*******************************************************************************
    811 **
    812 **
    813 ** Function         BTM_SecClrUCDService
    814 **
    815 ** Description
    816 **
    817 ** Parameters       Service ID - Id of the service to remove.
    818 **                               ('0' removes all service records )
    819 **
    820 ** Returns          Number of records that were cleared.
    821 **
    822 *******************************************************************************/
    823 UINT8 BTM_SecClrUCDService (UINT8 service_id)
    824 {
    825 #if (L2CAP_UCD_INCLUDED == TRUE)
    826     tBTM_SEC_SERV_REC   *p_srec = &btm_cb.sec_serv_rec[0];
    827     UINT8   num_cleared = 0;
    828     int     i;
    829 
    830     for (i = 0; i < BTM_SEC_MAX_SERVICE_RECORDS; i++, p_srec++)
    831     {
    832         /* Delete services with specified name (if in use and not SDP) */
    833         if ((p_srec->security_flags & BTM_SEC_IN_USE) &&
    834             (!service_id || (service_id == (UINT32)p_srec->service_id)))
    835         {
    836             BTM_TRACE_API2("BTM_UCD_SEC_CLR[%d]: id %d", i, service_id);
    837             p_srec->ucd_security_flags = 0;
    838             num_cleared++;
    839         }
    840     }
    841 
    842     return(num_cleared);
    843 #else
    844     return(0);
    845 #endif
    846 }
    847 
    848 /*******************************************************************************
    849 **
    850 ** Function         BTM_PINCodeReply
    851 **
    852 ** Description      This function is called after Security Manager submitted
    853 **                  PIN code request to the UI.
    854 **
    855 ** Parameters:      bd_addr      - Address of the device for which PIN was requested
    856 **                  res          - result of the operation BTM_SUCCESS if success
    857 **                  pin_len      - length in bytes of the PIN Code
    858 **                  p_pin        - pointer to array with the PIN Code
    859 **                  trusted_mask - bitwise OR of trusted services (array of UINT32)
    860 **
    861 *******************************************************************************/
    862 void BTM_PINCodeReply (BD_ADDR bd_addr, UINT8 res, UINT8 pin_len, UINT8 *p_pin, UINT32 trusted_mask[])
    863 {
    864     tBTM_SEC_DEV_REC *p_dev_rec;
    865 
    866     BTM_TRACE_API4 ("BTM_PINCodeReply(): PairState: %s   PairFlags: 0x%02x  PinLen:%d  Result:%d",
    867                     btm_pair_state_descr(btm_cb.pairing_state), btm_cb.pairing_flags, pin_len, res);
    868 
    869     /* If timeout already expired or has been canceled, ignore the reply */
    870     if (btm_cb.pairing_state != BTM_PAIR_STATE_WAIT_LOCAL_PIN)
    871     {
    872         BTM_TRACE_WARNING1 ("BTM_PINCodeReply() - Wrong State: %d", btm_cb.pairing_state);
    873         return;
    874     }
    875 
    876     if (memcmp (bd_addr, btm_cb.pairing_bda, BD_ADDR_LEN) != 0)
    877     {
    878         BTM_TRACE_ERROR0 ("BTM_PINCodeReply() - Wrong BD Addr");
    879         return;
    880     }
    881 
    882     if ((p_dev_rec = btm_find_dev (bd_addr)) == NULL)
    883     {
    884         BTM_TRACE_ERROR0 ("BTM_PINCodeReply() - no dev CB");
    885         return;
    886     }
    887 
    888     if ( (pin_len > PIN_CODE_LEN) || (pin_len == 0) || (p_pin == NULL) )
    889         res = BTM_ILLEGAL_VALUE;
    890 
    891     if (res != BTM_SUCCESS)
    892     {
    893         /* if peer started dd OR we started dd and pre-fetch pin was not used send negative reply */
    894         if ((btm_cb.pairing_flags & BTM_PAIR_FLAGS_PEER_STARTED_DD) ||
    895             ((btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD) &&
    896             (btm_cb.pairing_flags & BTM_PAIR_FLAGS_DISC_WHEN_DONE)) )
    897         {
    898             /* use BTM_PAIR_STATE_WAIT_AUTH_COMPLETE to report authentication failed event */
    899             btm_sec_change_pairing_state (BTM_PAIR_STATE_WAIT_AUTH_COMPLETE);
    900             btm_cb.acl_disc_reason = HCI_ERR_HOST_REJECT_SECURITY;
    901 
    902             btsnd_hcic_pin_code_neg_reply (bd_addr);
    903         }
    904         else
    905         {
    906             p_dev_rec->security_required = BTM_SEC_NONE;
    907             btm_sec_change_pairing_state (BTM_PAIR_STATE_IDLE);
    908         }
    909         return;
    910     }
    911     if (trusted_mask)
    912         BTM_SEC_COPY_TRUSTED_DEVICE(trusted_mask, p_dev_rec->trusted_mask);
    913     p_dev_rec->sec_flags   |= BTM_SEC_LINK_KEY_AUTHED;
    914 
    915     if ( (btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD)
    916          &&  (p_dev_rec->hci_handle == BTM_SEC_INVALID_HANDLE)
    917          &&  (btm_cb.security_mode_changed == FALSE) )
    918     {
    919         /* This is start of the dedicated bonding if local device is 2.0 */
    920         btm_cb.pin_code_len = pin_len;
    921         memcpy (btm_cb.pin_code, p_pin, pin_len);
    922 
    923         btm_cb.security_mode_changed = TRUE;
    924 #ifdef APPL_AUTH_WRITE_EXCEPTION
    925         if(!(APPL_AUTH_WRITE_EXCEPTION)(p_dev_rec->bd_addr))
    926 #endif
    927         btsnd_hcic_write_auth_enable (TRUE);
    928 
    929         btm_cb.acl_disc_reason = 0xff ;
    930 
    931         /* if we rejected incoming connection request, we have to wait HCI_Connection_Complete event */
    932         /*  before originating  */
    933         if (btm_cb.pairing_flags & BTM_PAIR_FLAGS_REJECTED_CONNECT)
    934         {
    935             BTM_TRACE_WARNING0 ("BTM_PINCodeReply(): waiting HCI_Connection_Complete after rejected incoming connection");
    936             /* we change state little bit early so btm_sec_connected() will originate connection */
    937             /*   when existing ACL link is down completely */
    938             btm_sec_change_pairing_state (BTM_PAIR_STATE_WAIT_PIN_REQ);
    939         }
    940         /* if we already accepted incoming connection from pairing device */
    941         else if (p_dev_rec->sm4 & BTM_SM4_CONN_PEND)
    942         {
    943             BTM_TRACE_WARNING0 ("BTM_PINCodeReply(): link is connecting so wait pin code request from peer");
    944             btm_sec_change_pairing_state (BTM_PAIR_STATE_WAIT_PIN_REQ);
    945         }
    946         else if (btm_sec_dd_create_conn(p_dev_rec) != BTM_CMD_STARTED)
    947         {
    948             btm_sec_change_pairing_state (BTM_PAIR_STATE_IDLE);
    949             p_dev_rec->sec_flags &= ~BTM_SEC_LINK_KEY_AUTHED;
    950 
    951             (*btm_cb.api.p_auth_complete_callback) (p_dev_rec->bd_addr,  p_dev_rec->dev_class,
    952                                                     p_dev_rec->sec_bd_name, HCI_ERR_AUTH_FAILURE);
    953         }
    954         return;
    955     }
    956 
    957     btm_sec_change_pairing_state (BTM_PAIR_STATE_WAIT_AUTH_COMPLETE);
    958     btm_cb.acl_disc_reason = HCI_SUCCESS;
    959 
    960 #ifdef PORCHE_PAIRING_CONFLICT
    961     BTM_TRACE_EVENT2("BTM_PINCodeReply(): Saving pin_len: %d btm_cb.pin_code_len: %d", pin_len, btm_cb.pin_code_len);
    962     /* if this was not pre-fetched, save the PIN */
    963     if (btm_cb.pin_code_len == 0)
    964         memcpy (btm_cb.pin_code, p_pin, pin_len);
    965     btm_cb.pin_code_len_saved = pin_len;
    966 #endif
    967     btsnd_hcic_pin_code_req_reply (bd_addr, pin_len, p_pin);
    968 }
    969 
    970 
    971 /*******************************************************************************
    972 **
    973 ** Function         BTM_DeviceAuthorized
    974 **
    975 ** Description      This function is called after Security Manager submitted
    976 **                  authorization request to the UI.
    977 **
    978 ** Parameters:      bd_addr     - Address of the device for which PIN was requested
    979 **                  res         - result of the operation BTM_SUCCESS if success
    980 **
    981 *******************************************************************************/
    982 void BTM_DeviceAuthorized (BD_ADDR bd_addr, UINT8 res, UINT32 trusted_mask[])
    983 {
    984     tBTM_SEC_DEV_REC *p_dev_rec;
    985 
    986     if ((p_dev_rec = btm_find_dev (bd_addr)) == NULL)
    987     {
    988         BTM_TRACE_WARNING6 ("Security Manager: Attempting Authorization of Unknown Device Address [%02x%02x%02x%02x%02x%02x]",
    989                             bd_addr[0], bd_addr[1], bd_addr[2], bd_addr[3], bd_addr[4], bd_addr[5]);
    990         return;
    991     }
    992 
    993     BTM_TRACE_EVENT4 ("Security Manager: authorized status:%d State:%d Trusted:%08x %08x",
    994                       res, (p_dev_rec) ? p_dev_rec->sec_state : 0, trusted_mask[0], trusted_mask[1]);
    995 
    996     if (res == BTM_SUCCESS)
    997     {
    998         p_dev_rec->sec_flags   |= BTM_SEC_AUTHORIZED;
    999         if (trusted_mask)
   1000         {
   1001             BTM_SEC_COPY_TRUSTED_DEVICE(trusted_mask, p_dev_rec->trusted_mask);
   1002         }
   1003 
   1004         /* Save the currently authorized service in case we are asked again
   1005         by another multiplexer layer */
   1006         if (!p_dev_rec->is_originator)
   1007         {
   1008             BTM_TRACE_DEBUG1("BTM_DeviceAuthorized: Setting last_author_service_id to %d",
   1009                              p_dev_rec->p_cur_service->service_id);
   1010             p_dev_rec->last_author_service_id = p_dev_rec->p_cur_service->service_id;
   1011         }
   1012     }
   1013 
   1014     if (p_dev_rec->sec_state != BTM_SEC_STATE_AUTHORIZING)
   1015         return;
   1016 
   1017     p_dev_rec->sec_state = BTM_SEC_STATE_IDLE;
   1018 
   1019     if (res != BTM_SUCCESS)
   1020     {
   1021         btm_sec_dev_rec_cback_event (p_dev_rec, res);
   1022         return;
   1023     }
   1024 
   1025     if ((res = (UINT8)btm_sec_execute_procedure (p_dev_rec)) != BTM_CMD_STARTED)
   1026     {
   1027         btm_sec_dev_rec_cback_event (p_dev_rec, res);
   1028     }
   1029 }
   1030 
   1031 
   1032 
   1033 /*******************************************************************************
   1034 **
   1035 ** Function         BTM_SecBond
   1036 **
   1037 ** Description      This function is called to perform bonding with peer device.
   1038 **                  If the connection is already up, but not secure, pairing
   1039 **                  is attempted.  If already paired BTM_SUCCESS is returned.
   1040 **
   1041 ** Parameters:      bd_addr      - Address of the device to bond
   1042 **                  pin_len      - length in bytes of the PIN Code
   1043 **                  p_pin        - pointer to array with the PIN Code
   1044 **                  trusted_mask - bitwise OR of trusted services (array of UINT32)
   1045 **
   1046 **  Note: After 2.1 parameters are not used and preserved here not to change API
   1047 *******************************************************************************/
   1048 tBTM_STATUS BTM_SecBond (BD_ADDR bd_addr, UINT8 pin_len, UINT8 *p_pin, UINT32 trusted_mask[])
   1049 {
   1050     tBTM_SEC_DEV_REC *p_dev_rec;
   1051     tBTM_STATUS      status;
   1052     UINT8            *p_features;
   1053     UINT8            ii;
   1054 #if SMP_INCLUDED == TRUE
   1055     tACL_CONN   *p=NULL;
   1056     BOOLEAN     is_le_slave_role=FALSE;
   1057     tBT_DEVICE_TYPE     dev_type;
   1058     tBLE_ADDR_TYPE      addr_type;
   1059 #endif
   1060     BTM_TRACE_API6 ("BTM_SecBond BDA: %02x:%02x:%02x:%02x:%02x:%02x",
   1061                     bd_addr[0], bd_addr[1], bd_addr[2], bd_addr[3], bd_addr[4], bd_addr[5]);
   1062 
   1063     /* Other security process is in progress */
   1064     if (btm_cb.pairing_state != BTM_PAIR_STATE_IDLE)
   1065     {
   1066         BTM_TRACE_ERROR1 ("BTM_SecBond: already busy in state: %s", btm_pair_state_descr(btm_cb.pairing_state));
   1067         return(BTM_WRONG_MODE);
   1068     }
   1069 
   1070 
   1071     p_dev_rec = btm_find_or_alloc_dev (bd_addr);
   1072     BTM_TRACE_DEBUG1 ("before update sec_flags=0x%x", p_dev_rec->sec_flags);
   1073 
   1074 
   1075 #if SMP_INCLUDED == TRUE
   1076     p = btm_bda_to_acl(bd_addr);
   1077     if (p && p->is_le_link )
   1078     {
   1079         if (p_dev_rec->sec_state == BTM_SEC_STATE_AUTHENTICATING)
   1080         {
   1081             BTM_TRACE_ERROR1 ("BTM_SecBond: LE already busy in state: %x", p_dev_rec->sec_state );
   1082             return(BTM_WRONG_MODE);
   1083         }
   1084 
   1085         if (p->link_role == BTM_ROLE_SLAVE)
   1086         {
   1087             is_le_slave_role = TRUE;
   1088             BTM_TRACE_DEBUG0 ("LE Link Slave" );
   1089         }
   1090         else
   1091         {
   1092             BTM_TRACE_DEBUG0 ("LE Link Maste" );
   1093         }
   1094     }
   1095     else
   1096     {
   1097         BTM_TRACE_DEBUG0 ("No LE Link" );
   1098     }
   1099 
   1100     if (!is_le_slave_role)
   1101     {
   1102         /* Finished if connection is active and already paired */
   1103         if ( (p_dev_rec->hci_handle != BTM_SEC_INVALID_HANDLE)
   1104              &&  (p_dev_rec->sec_flags & BTM_SEC_AUTHENTICATED) )
   1105         {
   1106             BTM_TRACE_WARNING0("BTM_SecBond -> Already Paired");
   1107             return(BTM_SUCCESS);
   1108         }
   1109     }
   1110 #else
   1111     /* Finished if connection is active and already paired */
   1112     if ( (p_dev_rec->hci_handle != BTM_SEC_INVALID_HANDLE)
   1113          &&  (p_dev_rec->sec_flags & BTM_SEC_AUTHENTICATED) )
   1114     {
   1115         BTM_TRACE_WARNING0("BTM_SecBond -> Already Paired");
   1116         return(BTM_SUCCESS);
   1117     }
   1118 #endif
   1119 
   1120     /* Tell controller to get rid of the link key if it has one stored */
   1121     if ((BTM_DeleteStoredLinkKey (bd_addr, NULL)) != BTM_SUCCESS)
   1122         return(BTM_NO_RESOURCES);
   1123 
   1124     /* Save the PIN code if we got a valid one */
   1125     if (p_pin && (pin_len <= PIN_CODE_LEN) && (pin_len != 0))
   1126     {
   1127         btm_cb.pin_code_len = pin_len;
   1128         memcpy (btm_cb.pin_code, p_pin, PIN_CODE_LEN);
   1129     }
   1130 
   1131     memcpy (btm_cb.pairing_bda, bd_addr, BD_ADDR_LEN);
   1132 
   1133     btm_cb.pairing_flags = BTM_PAIR_FLAGS_WE_STARTED_DD;
   1134 
   1135     p_dev_rec->security_required = BTM_SEC_OUT_AUTHENTICATE;
   1136     p_dev_rec->is_originator     = TRUE;
   1137     if (trusted_mask)
   1138         BTM_SEC_COPY_TRUSTED_DEVICE(trusted_mask, p_dev_rec->trusted_mask);
   1139 
   1140 
   1141 
   1142 #if SMP_INCLUDED == TRUE
   1143 
   1144     if (!is_le_slave_role)
   1145     {
   1146         p_dev_rec->sec_flags &= ~(BTM_SEC_LINK_KEY_KNOWN | BTM_SEC_AUTHENTICATED | BTM_SEC_ENCRYPTED
   1147                                   | BTM_SEC_ROLE_SWITCHED  | BTM_SEC_LINK_KEY_AUTHED);
   1148 
   1149     }
   1150 
   1151     BTM_ReadDevInfo(bd_addr, &dev_type, &addr_type);
   1152     /* LE device, do SMP pairing */
   1153     if (dev_type == BT_DEVICE_TYPE_BLE)
   1154     {
   1155         if (SMP_Pair(bd_addr) == SMP_STARTED)
   1156         {
   1157             p_dev_rec->sec_state = BTM_SEC_STATE_AUTHENTICATING;
   1158             return BTM_CMD_STARTED;
   1159         }
   1160         else
   1161             return(BTM_NO_RESOURCES);
   1162     }
   1163 #else
   1164     p_dev_rec->sec_flags &= ~(BTM_SEC_LINK_KEY_KNOWN | BTM_SEC_AUTHENTICATED | BTM_SEC_ENCRYPTED
   1165                               | BTM_SEC_ROLE_SWITCHED  | BTM_SEC_LINK_KEY_AUTHED);
   1166 #endif
   1167 
   1168     BTM_TRACE_DEBUG1 ("after update sec_flags=0x%x", p_dev_rec->sec_flags);
   1169     if (!HCI_SIMPLE_PAIRING_SUPPORTED(btm_cb.devcb.local_lmp_features[HCI_EXT_FEATURES_PAGE_0]))
   1170     {
   1171         /* The special case when we authenticate keyboard.  Set pin type to fixed */
   1172         /* It would be probably better to do it from the application, but it is */
   1173         /* complicated */
   1174         if (((p_dev_rec->dev_class[1] & BTM_COD_MAJOR_CLASS_MASK) == BTM_COD_MAJOR_PERIPHERAL)
   1175             && (p_dev_rec->dev_class[2] & BTM_COD_MINOR_KEYBOARD)
   1176             && (btm_cb.cfg.pin_type != HCI_PIN_TYPE_FIXED))
   1177         {
   1178             btm_cb.pin_type_changed = TRUE;
   1179             btsnd_hcic_write_pin_type (HCI_PIN_TYPE_FIXED);
   1180         }
   1181     }
   1182 
   1183     BTM_TRACE_EVENT1("BTM_SecBond: Local device supports SSP=%d",
   1184             HCI_SIMPLE_PAIRING_SUPPORTED(btm_cb.devcb.local_lmp_features[HCI_EXT_FEATURES_PAGE_0]));
   1185 
   1186     for (ii = 0; ii <= HCI_EXT_FEATURES_PAGE_MAX; ii++)
   1187     {
   1188         p_features = p_dev_rec->features[ii];
   1189         BTM_TRACE_EVENT5("  remote_features page[%1d] = %02x-%02x-%02x-%02x",
   1190                          ii, p_features[0], p_features[1], p_features[2], p_features[3]);
   1191         BTM_TRACE_EVENT4("                              %02x-%02x-%02x-%02x",
   1192                              p_features[4], p_features[5], p_features[6], p_features[7]);
   1193     }
   1194 
   1195     BTM_TRACE_EVENT2 ("BTM_SecBond: Remote sm4: 0x%x  HCI Handle: 0x%04x", p_dev_rec->sm4, p_dev_rec->hci_handle);
   1196 
   1197 #if BTM_SEC_FORCE_RNR_FOR_DBOND == TRUE
   1198     p_dev_rec->sec_flags &= ~BTM_SEC_NAME_KNOWN;
   1199 #endif
   1200 
   1201     /* If connection already exists... */
   1202     if (p_dev_rec->hci_handle != BTM_SEC_INVALID_HANDLE)
   1203     {
   1204         if (!btm_sec_start_authentication (p_dev_rec))
   1205             return(BTM_NO_RESOURCES);
   1206 
   1207         btm_sec_change_pairing_state (BTM_PAIR_STATE_WAIT_PIN_REQ);
   1208 
   1209         /* Mark lcb as bonding */
   1210         l2cu_update_lcb_4_bonding (bd_addr, TRUE);
   1211         return(BTM_CMD_STARTED);
   1212     }
   1213 
   1214     BTM_TRACE_DEBUG2 ("sec mode: %d sm4:x%x", btm_cb.security_mode, p_dev_rec->sm4);
   1215     if (!HCI_SIMPLE_PAIRING_SUPPORTED(btm_cb.devcb.local_lmp_features[HCI_EXT_FEATURES_PAGE_0])
   1216         || (p_dev_rec->sm4 == BTM_SM4_KNOWN))
   1217     {
   1218         if ( btm_sec_check_prefetch_pin (p_dev_rec) )
   1219 	        return(BTM_CMD_STARTED);
   1220     }
   1221     if (BTM_SEC_MODE_SP == btm_cb.security_mode && BTM_SEC_IS_SM4_UNKNOWN(p_dev_rec->sm4))
   1222     {
   1223         /* local is 2.1 and peer is unknown */
   1224         if ((p_dev_rec->sm4 & BTM_SM4_CONN_PEND) == 0)
   1225         {
   1226             /* we are not accepting connection request from peer
   1227              * -> RNR (to learn if peer is 2.1)
   1228              * RNR when no ACL causes HCI_RMT_HOST_SUP_FEAT_NOTIFY_EVT */
   1229             btm_sec_change_pairing_state (BTM_PAIR_STATE_GET_REM_NAME);
   1230             BTM_ReadRemoteDeviceName(bd_addr, NULL);
   1231         }
   1232         else
   1233         {
   1234             /* We are accepting connection request from peer */
   1235             btm_sec_change_pairing_state (BTM_PAIR_STATE_WAIT_PIN_REQ);
   1236         }
   1237         BTM_TRACE_DEBUG3 ("State:%s sm4: 0x%x sec_state:%d", btm_pair_state_descr (btm_cb.pairing_state), p_dev_rec->sm4, p_dev_rec->sec_state);
   1238         return BTM_CMD_STARTED;
   1239     }
   1240 
   1241     /* both local and peer are 2.1  */
   1242     status = btm_sec_dd_create_conn(p_dev_rec);
   1243 
   1244     if (status != BTM_CMD_STARTED)
   1245     {
   1246         btm_sec_change_pairing_state (BTM_PAIR_STATE_IDLE);
   1247     }
   1248 
   1249     return status;
   1250 }
   1251 
   1252 
   1253 /*******************************************************************************
   1254 **
   1255 ** Function         BTM_SecBondCancel
   1256 **
   1257 ** Description      This function is called to cancel ongoing bonding process
   1258 **                  with peer device.
   1259 **
   1260 ** Parameters:      bd_addr      - Address of the peer device
   1261 **
   1262 *******************************************************************************/
   1263 tBTM_STATUS BTM_SecBondCancel (BD_ADDR bd_addr)
   1264 {
   1265     tBTM_SEC_DEV_REC *p_dev_rec;
   1266 #if SMP_INCLUDED == TRUE
   1267     tACL_CONN   *p=NULL;
   1268 #endif
   1269 
   1270     BTM_TRACE_API2 ("BTM_SecBondCancel()  State: %s flags:0x%x",
   1271                     btm_pair_state_descr (btm_cb.pairing_state), btm_cb.pairing_flags);
   1272 
   1273     if (((p_dev_rec = btm_find_dev (bd_addr)) == NULL)
   1274         ||  (memcmp (btm_cb.pairing_bda, bd_addr, BD_ADDR_LEN) != 0) )
   1275         return BTM_UNKNOWN_ADDR;
   1276 
   1277 #if SMP_INCLUDED == TRUE
   1278     p = btm_bda_to_acl(bd_addr);
   1279     if (p && p->is_le_link &&
   1280         (p_dev_rec->sec_state == BTM_SEC_STATE_AUTHENTICATING))
   1281     {
   1282         BTM_TRACE_DEBUG0 ("Cancel LE pairing");
   1283         if (SMP_PairCancel(bd_addr))
   1284         {
   1285             return BTM_CMD_STARTED;
   1286         }
   1287         else
   1288         {
   1289             return BTM_WRONG_MODE;
   1290         }
   1291     }
   1292 
   1293 #endif
   1294     BTM_TRACE_DEBUG2 ("hci_handle:0x%x sec_state:%d", p_dev_rec->hci_handle, p_dev_rec->sec_state );
   1295     if (BTM_PAIR_STATE_WAIT_LOCAL_PIN == btm_cb.pairing_state &&
   1296         BTM_PAIR_FLAGS_WE_STARTED_DD & btm_cb.pairing_flags)
   1297     {
   1298         /* pre-fetching pin for dedicated bonding */
   1299         btm_sec_bond_cancel_complete();
   1300         return BTM_SUCCESS;
   1301     }
   1302 
   1303     /* If this BDA is in a bonding procedure */
   1304     if ( (btm_cb.pairing_state != BTM_PAIR_STATE_IDLE)
   1305          &&  (btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD))
   1306     {
   1307         /* If the HCI link is up */
   1308         if (p_dev_rec->hci_handle != BTM_SEC_INVALID_HANDLE)
   1309         {
   1310             /* If some other thread disconnecting, we do not send second command */
   1311             if (p_dev_rec->sec_state == BTM_SEC_STATE_DISCONNECTING)
   1312                 return(BTM_CMD_STARTED);
   1313 
   1314             /* If the HCI link was set up by Bonding process */
   1315             if (btm_cb.pairing_flags & BTM_PAIR_FLAGS_DISC_WHEN_DONE)
   1316                 return btm_sec_send_hci_disconnect(p_dev_rec, HCI_ERR_PEER_USER);
   1317             else
   1318                 l2cu_update_lcb_4_bonding(bd_addr, FALSE);
   1319 
   1320             return BTM_NOT_AUTHORIZED;
   1321         }
   1322         else /*HCI link is not up */
   1323         {
   1324             /* If the HCI link creation was started by Bonding process */
   1325             if (btm_cb.pairing_flags & BTM_PAIR_FLAGS_DISC_WHEN_DONE)
   1326             {
   1327                 if (btsnd_hcic_create_conn_cancel(bd_addr))
   1328                     return BTM_CMD_STARTED;
   1329 
   1330                 return BTM_NO_RESOURCES;
   1331             }
   1332             if (btm_cb.pairing_state == BTM_PAIR_STATE_GET_REM_NAME)
   1333             {
   1334                 BTM_CancelRemoteDeviceName();
   1335                 btm_cb.pairing_flags |= BTM_PAIR_FLAGS_WE_CANCEL_DD;
   1336                 return BTM_CMD_STARTED;
   1337             }
   1338             return BTM_NOT_AUTHORIZED;
   1339         }
   1340     }
   1341 
   1342     return BTM_WRONG_MODE;
   1343 }
   1344 
   1345 /*******************************************************************************
   1346 **
   1347 ** Function         BTM_SecUseMasterLinkKey
   1348 **
   1349 ** Description      This function is called to tell master of the piconet to
   1350 **                  switch to master link key
   1351 **
   1352 ** Parameters:      use_master_key - If true Master Link Key shoul be used
   1353 **
   1354 *******************************************************************************/
   1355 tBTM_STATUS BTM_SecUseMasterLinkKey (BOOLEAN use_master_key)
   1356 {
   1357     return(btsnd_hcic_master_link_key (use_master_key) ?  BTM_SUCCESS :
   1358            BTM_NO_RESOURCES);
   1359 }
   1360 
   1361 /*******************************************************************************
   1362 **
   1363 ** Function         BTM_SetMasterKeyCompCback
   1364 **
   1365 ** Description      This function is called to register for the master key complete
   1366 **                  status event.
   1367 **
   1368 ** Parameters:      mkey_cback - callback registered with the security manager
   1369 **
   1370 *******************************************************************************/
   1371 void BTM_SetMasterKeyCompCback( tBTM_MKEY_CALLBACK *mkey_cback )
   1372 {
   1373     btm_cb.mkey_cback = mkey_cback;
   1374 }
   1375 
   1376 /*******************************************************************************
   1377 **
   1378 ** Function         BTM_SecGetDeviceLinkKey
   1379 **
   1380 ** Description      This function is called to obtain link key for the device
   1381 **                  it returns BTM_SUCCESS if link key is available, or
   1382 **                  BTM_UNKNOWN_ADDR if Security Manager does not know about
   1383 **                  the device or device record does not contain link key info
   1384 **
   1385 ** Parameters:      bd_addr      - Address of the device
   1386 **                  link_key     - Link Key is copied into this array
   1387 **
   1388 *******************************************************************************/
   1389 tBTM_STATUS BTM_SecGetDeviceLinkKey (BD_ADDR bd_addr, LINK_KEY link_key)
   1390 {
   1391     tBTM_SEC_DEV_REC *p_dev_rec;
   1392 
   1393     if (((p_dev_rec = btm_find_dev (bd_addr)) != NULL)
   1394         && (p_dev_rec->sec_flags & BTM_SEC_LINK_KEY_KNOWN))
   1395     {
   1396         memcpy (link_key, p_dev_rec->link_key, LINK_KEY_LEN);
   1397         return(BTM_SUCCESS);
   1398     }
   1399     return(BTM_UNKNOWN_ADDR);
   1400 }
   1401 
   1402 
   1403 /*******************************************************************************
   1404 **
   1405 ** Function         BTM_SetEncryption
   1406 **
   1407 ** Description      This function is called to ensure that connection is
   1408 **                  encrypted.  Should be called only on an open connection.
   1409 **                  Typically only needed for connections that first want to
   1410 **                  bring up unencrypted links, then later encrypt them.
   1411 **
   1412 ** Parameters:      bd_addr       - Address of the peer device
   1413 **                  p_callback    - Pointer to callback function called if
   1414 **                                  this function returns PENDING after required
   1415 **                                  procedures are completed.  Can be set to NULL
   1416 **                                  if status is not desired.
   1417 **                  p_ref_data    - pointer to any data the caller wishes to receive
   1418 **                                  in the callback function upon completion.
   1419 *                                   can be set to NULL if not used.
   1420 **
   1421 ** Returns          BTM_SUCCESS   - already encrypted
   1422 **                  BTM_PENDING   - command will be returned in the callback
   1423 **                  BTM_WRONG_MODE- connection not up.
   1424 **                  BTM_BUSY      - security procedures are currently active
   1425 **                  BTM_MODE_UNSUPPORTED - if security manager not linked in.
   1426 **
   1427 *******************************************************************************/
   1428 tBTM_STATUS BTM_SetEncryption (BD_ADDR bd_addr, tBTM_SEC_CBACK *p_callback,
   1429                                void *p_ref_data)
   1430 {
   1431     tBTM_SEC_DEV_REC  *p_dev_rec;
   1432     tBTM_STATUS       rc;
   1433 
   1434 #if BLE_INCLUDED == TRUE
   1435     tACL_CONN         *p;
   1436     p = btm_bda_to_acl(bd_addr);
   1437 #endif
   1438 
   1439     p_dev_rec = btm_find_dev (bd_addr);
   1440     if (!p_dev_rec || (p_dev_rec->hci_handle == BTM_SEC_INVALID_HANDLE))
   1441     {
   1442         /* Connection should be up and runnning */
   1443         BTM_TRACE_WARNING0 ("Security Manager: BTM_SetEncryption not connected");
   1444 
   1445         if (p_callback)
   1446             (*p_callback) (bd_addr, p_ref_data, BTM_WRONG_MODE);
   1447 
   1448         return(BTM_WRONG_MODE);
   1449     }
   1450 
   1451 
   1452     if (
   1453 #if BLE_INCLUDED == TRUE
   1454        !p->is_le_link &&
   1455 #endif
   1456        (p_dev_rec->sec_flags & (BTM_SEC_AUTHENTICATED | BTM_SEC_ENCRYPTED))
   1457        == (BTM_SEC_AUTHENTICATED | BTM_SEC_ENCRYPTED))
   1458     {
   1459         BTM_TRACE_EVENT0 ("Security Manager: BTM_SetEncryption already encrypted");
   1460 
   1461         if (p_callback)
   1462             (*p_callback) (bd_addr, p_ref_data, BTM_SUCCESS);
   1463 
   1464         return(BTM_SUCCESS);
   1465     }
   1466 
   1467     if (p_dev_rec->p_callback)
   1468     {
   1469         /* Connection should be up and runnning */
   1470         BTM_TRACE_WARNING0 ("Security Manager: BTM_SetEncryption busy");
   1471 
   1472         if (p_callback)
   1473             (*p_callback) (bd_addr, p_ref_data, BTM_BUSY);
   1474 
   1475         return(BTM_BUSY);
   1476     }
   1477 
   1478     p_dev_rec->p_callback        = p_callback;
   1479     p_dev_rec->p_ref_data        = p_ref_data;
   1480     p_dev_rec->security_required |= (BTM_SEC_IN_AUTHENTICATE | BTM_SEC_IN_ENCRYPT);
   1481     p_dev_rec->is_originator     = FALSE;
   1482 
   1483     BTM_TRACE_API4 ("Security Manager: BTM_SetEncryption Handle:%d State:%d Flags:0x%x Required:0x%x",
   1484                     p_dev_rec->hci_handle, p_dev_rec->sec_state, p_dev_rec->sec_flags,
   1485                     p_dev_rec->security_required);
   1486 #if BLE_INCLUDED == TRUE && SMP_INCLUDED == TRUE
   1487     if (p->is_le_link)
   1488     {
   1489         rc = btm_ble_set_encryption(bd_addr, p_ref_data, p->link_role);
   1490     }
   1491     else
   1492 #endif
   1493 
   1494         rc = btm_sec_execute_procedure (p_dev_rec);
   1495 
   1496     if ( rc != BTM_CMD_STARTED)
   1497     {
   1498         if (p_callback)
   1499         {
   1500             p_dev_rec->p_callback = NULL;
   1501             (*p_callback) (bd_addr, p_dev_rec->p_ref_data, rc);
   1502         }
   1503     }
   1504     return(rc);
   1505 }
   1506 
   1507 /*******************************************************************************
   1508  * disconnect the ACL link, if it's not done yet.
   1509 *******************************************************************************/
   1510 static tBTM_STATUS btm_sec_send_hci_disconnect (tBTM_SEC_DEV_REC *p_dev_rec, UINT8 reason)
   1511 {
   1512     UINT8       old_state = p_dev_rec->sec_state;
   1513     tBTM_STATUS status = BTM_CMD_STARTED;
   1514 
   1515     BTM_TRACE_EVENT2 ("btm_sec_send_hci_disconnect:  handle:0x%x, reason=0x%x",
   1516                       p_dev_rec->hci_handle, reason);
   1517 
   1518     /* if some other thread disconnecting, we do not send second command */
   1519     if (BTM_SEC_STATE_DISCONNECTING != old_state)
   1520     {
   1521         p_dev_rec->sec_state = BTM_SEC_STATE_DISCONNECTING;
   1522 
   1523 #if BTM_DISC_DURING_RS == TRUE
   1524         /* If a Role Switch is in progress, delay the HCI Disconnect to avoid controller problem (4329B1) */
   1525         if (p_dev_rec->rs_disc_pending == BTM_SEC_RS_PENDING)
   1526         {
   1527                  BTM_TRACE_ERROR0("RS in progress - Set DISC Pending flag in btm_sec_send_hci_disconnect to delay disconnect");
   1528                  p_dev_rec->rs_disc_pending = BTM_SEC_DISC_PENDING;
   1529                  status = BTM_SUCCESS;
   1530         }
   1531         else
   1532 #endif
   1533         /* Tear down the HCI link */
   1534         if (!btsnd_hcic_disconnect (p_dev_rec->hci_handle, reason))
   1535         {
   1536             /* could not send disconnect. restore old state */
   1537             p_dev_rec->sec_state = old_state;
   1538             status = BTM_NO_RESOURCES;
   1539         }
   1540     }
   1541     return (status);
   1542 }
   1543 
   1544 /*******************************************************************************
   1545 **
   1546 ** Function         BTM_ConfirmReqReply
   1547 **
   1548 ** Description      This function is called to confirm the numeric value for
   1549 **                  Simple Pairing in response to BTM_SP_CFM_REQ_EVT
   1550 **
   1551 ** Parameters:      res           - result of the operation BTM_SUCCESS if success
   1552 **                  bd_addr       - Address of the peer device
   1553 **
   1554 *******************************************************************************/
   1555 void BTM_ConfirmReqReply(tBTM_STATUS res, BD_ADDR bd_addr)
   1556 {
   1557     tBTM_SEC_DEV_REC *p_dev_rec;
   1558 
   1559     BTM_TRACE_EVENT2 ("BTM_ConfirmReqReply() State: %s  Res: %u",
   1560                       btm_pair_state_descr(btm_cb.pairing_state), res);
   1561 
   1562     /* If timeout already expired or has been canceled, ignore the reply */
   1563     if ( (btm_cb.pairing_state != BTM_PAIR_STATE_WAIT_NUMERIC_CONFIRM)
   1564          ||  (memcmp (btm_cb.pairing_bda, bd_addr, BD_ADDR_LEN) != 0) )
   1565         return;
   1566 
   1567     btm_sec_change_pairing_state (BTM_PAIR_STATE_WAIT_AUTH_COMPLETE);
   1568 
   1569     if ( (res == BTM_SUCCESS) || (res == BTM_SUCCESS_NO_SECURITY) )
   1570     {
   1571         btm_cb.acl_disc_reason = HCI_SUCCESS;
   1572 
   1573         if (res == BTM_SUCCESS)
   1574         {
   1575             if ((p_dev_rec = btm_find_dev (bd_addr)) != NULL)
   1576                 p_dev_rec->sec_flags |= BTM_SEC_LINK_KEY_AUTHED;
   1577         }
   1578 
   1579         btsnd_hcic_user_conf_reply (bd_addr, TRUE);
   1580     }
   1581     else
   1582     {
   1583         /* Report authentication failed event from state BTM_PAIR_STATE_WAIT_AUTH_COMPLETE */
   1584         btm_cb.acl_disc_reason = HCI_ERR_HOST_REJECT_SECURITY;
   1585         btsnd_hcic_user_conf_reply (bd_addr, FALSE);
   1586     }
   1587 }
   1588 
   1589 /*******************************************************************************
   1590 **
   1591 ** Function         BTM_PasskeyReqReply
   1592 **
   1593 ** Description      This function is called to provide the passkey for
   1594 **                  Simple Pairing in response to BTM_SP_KEY_REQ_EVT
   1595 **
   1596 ** Parameters:      res     - result of the operation BTM_SUCCESS if success
   1597 **                  bd_addr - Address of the peer device
   1598 **                  passkey - numeric value in the range of
   1599 **                  BTM_MIN_PASSKEY_VAL(0) - BTM_MAX_PASSKEY_VAL(999999(0xF423F)).
   1600 **
   1601 *******************************************************************************/
   1602 #if (BTM_LOCAL_IO_CAPS != BTM_IO_CAP_NONE)
   1603 void BTM_PasskeyReqReply(tBTM_STATUS res, BD_ADDR bd_addr, UINT32 passkey)
   1604 {
   1605     tBTM_SEC_DEV_REC *p_dev_rec;
   1606 
   1607     BTM_TRACE_API2 ("BTM_PasskeyReqReply: State: %s  res:%d",
   1608                     btm_pair_state_descr(btm_cb.pairing_state), res);
   1609 
   1610     if ( (btm_cb.pairing_state == BTM_PAIR_STATE_IDLE)
   1611          ||  (memcmp (btm_cb.pairing_bda, bd_addr, BD_ADDR_LEN) != 0) )
   1612     {
   1613         return;
   1614     }
   1615 
   1616     /* If timeout already expired or has been canceled, ignore the reply */
   1617     if ( (btm_cb.pairing_state == BTM_PAIR_STATE_WAIT_AUTH_COMPLETE) && (res != BTM_SUCCESS) )
   1618     {
   1619         if ((p_dev_rec = btm_find_dev (bd_addr)) != NULL)
   1620         {
   1621             btm_cb.acl_disc_reason = HCI_ERR_HOST_REJECT_SECURITY;
   1622 
   1623             if (p_dev_rec->hci_handle != BTM_SEC_INVALID_HANDLE)
   1624                 btm_sec_send_hci_disconnect (p_dev_rec, HCI_ERR_AUTH_FAILURE);
   1625             else
   1626                 BTM_SecBondCancel(bd_addr);
   1627 
   1628             p_dev_rec->sec_flags &= ~(BTM_SEC_LINK_KEY_AUTHED | BTM_SEC_LINK_KEY_KNOWN);
   1629 
   1630             btm_sec_change_pairing_state (BTM_PAIR_STATE_IDLE);
   1631             return;
   1632         }
   1633     }
   1634     else if (btm_cb.pairing_state != BTM_PAIR_STATE_KEY_ENTRY)
   1635         return;
   1636 
   1637     if (passkey > BTM_MAX_PASSKEY_VAL)
   1638         res = BTM_ILLEGAL_VALUE;
   1639 
   1640     btm_sec_change_pairing_state (BTM_PAIR_STATE_WAIT_AUTH_COMPLETE);
   1641 
   1642     if (res != BTM_SUCCESS)
   1643     {
   1644         /* use BTM_PAIR_STATE_WAIT_AUTH_COMPLETE to report authentication failed event */
   1645         btm_cb.acl_disc_reason = HCI_ERR_HOST_REJECT_SECURITY;
   1646         btsnd_hcic_user_passkey_neg_reply (bd_addr);
   1647     }
   1648     else
   1649     {
   1650         btm_cb.acl_disc_reason = HCI_SUCCESS;
   1651         btsnd_hcic_user_passkey_reply (bd_addr, passkey);
   1652     }
   1653 }
   1654 #endif
   1655 
   1656 /*******************************************************************************
   1657 **
   1658 ** Function         BTM_SendKeypressNotif
   1659 **
   1660 ** Description      This function is used during the passkey entry model
   1661 **                  by a device with KeyboardOnly IO capabilities
   1662 **                  (very likely to be a HID Device).
   1663 **                  It is called by a HID Device to inform the remote device when
   1664 **                  a key has been entered or erased.
   1665 **
   1666 ** Parameters:      bd_addr - Address of the peer device
   1667 **                  type - notification type
   1668 **
   1669 *******************************************************************************/
   1670 #if (BTM_LOCAL_IO_CAPS != BTM_IO_CAP_NONE)
   1671 void BTM_SendKeypressNotif(BD_ADDR bd_addr, tBTM_SP_KEY_TYPE type)
   1672 {
   1673     /* This API only make sense between PASSKEY_REQ and SP complete */
   1674     if (btm_cb.pairing_state == BTM_PAIR_STATE_KEY_ENTRY)
   1675         btsnd_hcic_send_keypress_notif (bd_addr, type);
   1676 }
   1677 #endif
   1678 
   1679 #if BTM_OOB_INCLUDED == TRUE
   1680 /*******************************************************************************
   1681 **
   1682 ** Function         BTM_IoCapRsp
   1683 **
   1684 ** Description      This function is called in response to BTM_SP_IO_REQ_EVT
   1685 **                  When the event data io_req.oob_data is set to BTM_OOB_UNKNOWN
   1686 **                  by the tBTM_SP_CALLBACK implementation, this function is
   1687 **                  called to provide the actual response
   1688 **
   1689 ** Parameters:      bd_addr - Address of the peer device
   1690 **                  io_cap  - The IO capability of local device.
   1691 **                  oob     - BTM_OOB_NONE or BTM_OOB_PRESENT.
   1692 **                  auth_req- MITM protection required or not.
   1693 **
   1694 *******************************************************************************/
   1695 void BTM_IoCapRsp(BD_ADDR bd_addr, tBTM_IO_CAP io_cap, tBTM_OOB_DATA oob, tBTM_AUTH_REQ auth_req)
   1696 {
   1697     BTM_TRACE_EVENT3 ("BTM_IoCapRsp: state: %s  oob: %d io_cap: %d",
   1698                       btm_pair_state_descr(btm_cb.pairing_state), oob, io_cap);
   1699 
   1700     if ( (btm_cb.pairing_state != BTM_PAIR_STATE_WAIT_LOCAL_IOCAPS)
   1701          ||  (memcmp (btm_cb.pairing_bda, bd_addr, BD_ADDR_LEN) != 0) )
   1702         return;
   1703 
   1704     if (oob < BTM_OOB_UNKNOWN && io_cap < BTM_IO_CAP_MAX)
   1705     {
   1706         btm_cb.devcb.loc_auth_req   = auth_req;
   1707         btm_cb.devcb.loc_io_caps    = io_cap;
   1708 
   1709         if (btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD)
   1710             auth_req = (BTM_AUTH_DD_BOND | (auth_req&BTM_AUTH_YN_BIT));
   1711 
   1712         btsnd_hcic_io_cap_req_reply (bd_addr, io_cap, oob, auth_req);
   1713     }
   1714 }
   1715 
   1716 /*******************************************************************************
   1717 **
   1718 ** Function         BTM_ReadLocalOobData
   1719 **
   1720 ** Description      This function is called to read the local OOB data from
   1721 **                  LM
   1722 **
   1723 *******************************************************************************/
   1724 tBTM_STATUS BTM_ReadLocalOobData(void)
   1725 {
   1726     tBTM_STATUS status = BTM_SUCCESS;
   1727 
   1728     if (btsnd_hcic_read_local_oob_data() == FALSE)
   1729         status = BTM_NO_RESOURCES;
   1730 
   1731     return status;
   1732 }
   1733 
   1734 /*******************************************************************************
   1735 **
   1736 ** Function         BTM_RemoteOobDataReply
   1737 **
   1738 ** Description      This function is called to provide the remote OOB data for
   1739 **                  Simple Pairing in response to BTM_SP_RMT_OOB_EVT
   1740 **
   1741 ** Parameters:      bd_addr     - Address of the peer device
   1742 **                  c           - simple pairing Hash C.
   1743 **                  r           - simple pairing Randomizer  C.
   1744 **
   1745 *******************************************************************************/
   1746 void BTM_RemoteOobDataReply(tBTM_STATUS res, BD_ADDR bd_addr, BT_OCTET16 c, BT_OCTET16 r)
   1747 {
   1748     BTM_TRACE_EVENT2 ("BTM_RemoteOobDataReply():  State: %s  res:%d",
   1749                       btm_pair_state_descr(btm_cb.pairing_state), res);
   1750 
   1751     /* If timeout already expired or has been canceled, ignore the reply */
   1752     if (btm_cb.pairing_state != BTM_PAIR_STATE_WAIT_LOCAL_OOB_RSP)
   1753         return;
   1754 
   1755     btm_sec_change_pairing_state (BTM_PAIR_STATE_WAIT_AUTH_COMPLETE);
   1756 
   1757     if (res != BTM_SUCCESS)
   1758     {
   1759         /* use BTM_PAIR_STATE_WAIT_AUTH_COMPLETE to report authentication failed event */
   1760         btm_cb.acl_disc_reason = HCI_ERR_HOST_REJECT_SECURITY;
   1761         btsnd_hcic_rem_oob_neg_reply (bd_addr);
   1762     }
   1763     else
   1764     {
   1765         btm_cb.acl_disc_reason = HCI_SUCCESS;
   1766         btsnd_hcic_rem_oob_reply (bd_addr, c, r);
   1767     }
   1768 }
   1769 
   1770 /*******************************************************************************
   1771 **
   1772 ** Function         BTM_BuildOobData
   1773 **
   1774 ** Description      This function is called to build the OOB data payload to
   1775 **                  be sent over OOB (non-Bluetooth) link
   1776 **
   1777 ** Parameters:      p_data  - the location for OOB data
   1778 **                  max_len - p_data size.
   1779 **                  c       - simple pairing Hash C.
   1780 **                  r       - simple pairing Randomizer  C.
   1781 **                  name_len- 0, local device name would not be included.
   1782 **                            otherwise, the local device name is included for
   1783 **                            up to this specified length
   1784 **
   1785 ** Returns          Number of bytes in p_data.
   1786 **
   1787 *******************************************************************************/
   1788 UINT16 BTM_BuildOobData(UINT8 *p_data, UINT16 max_len, BT_OCTET16 c,
   1789                         BT_OCTET16 r, UINT8 name_len)
   1790 {
   1791     UINT8   *p = p_data;
   1792     UINT16  len = 0;
   1793     UINT16  delta;
   1794 #if BTM_MAX_LOC_BD_NAME_LEN > 0
   1795     UINT16  name_size;
   1796     UINT8   name_type = BTM_EIR_SHORTENED_LOCAL_NAME_TYPE;
   1797 #endif
   1798 
   1799     if (p_data && max_len >= BTM_OOB_MANDATORY_SIZE)
   1800     {
   1801         /* add mandatory part */
   1802         UINT16_TO_STREAM(p, len);
   1803         BDADDR_TO_STREAM(p, btm_cb.devcb.local_addr);
   1804 
   1805         len = BTM_OOB_MANDATORY_SIZE;
   1806         max_len -= len;
   1807 
   1808         /* now optional part */
   1809 
   1810         /* add Hash C */
   1811         delta = BTM_OOB_HASH_C_SIZE + 2;
   1812         if (max_len >= delta)
   1813         {
   1814             *p++ = BTM_OOB_HASH_C_SIZE + 1;
   1815             *p++ = BTM_EIR_OOB_SSP_HASH_C_TYPE;
   1816             ARRAY_TO_STREAM(p, c, BTM_OOB_HASH_C_SIZE);
   1817             len     += delta;
   1818             max_len -= delta;
   1819         }
   1820 
   1821         /* add Rand R */
   1822         delta = BTM_OOB_RAND_R_SIZE + 2;
   1823         if (max_len >= delta)
   1824         {
   1825             *p++ = BTM_OOB_RAND_R_SIZE + 1;
   1826             *p++ = BTM_EIR_OOB_SSP_RAND_R_TYPE;
   1827             ARRAY_TO_STREAM(p, r, BTM_OOB_RAND_R_SIZE);
   1828             len     += delta;
   1829             max_len -= delta;
   1830         }
   1831 
   1832         /* add class of device */
   1833         delta = BTM_OOB_COD_SIZE + 2;
   1834         if (max_len >= delta)
   1835         {
   1836             *p++ = BTM_OOB_COD_SIZE + 1;
   1837             *p++ = BTM_EIR_OOB_COD_TYPE;
   1838             DEVCLASS_TO_STREAM(p, btm_cb.devcb.dev_class);
   1839             len     += delta;
   1840             max_len -= delta;
   1841         }
   1842 #if BTM_MAX_LOC_BD_NAME_LEN > 0
   1843         name_size = name_len;
   1844         if (name_size > strlen(btm_cb.cfg.bd_name))
   1845         {
   1846             name_type = BTM_EIR_COMPLETE_LOCAL_NAME_TYPE;
   1847             name_size = (UINT16)strlen(btm_cb.cfg.bd_name);
   1848         }
   1849         delta = name_size + 2;
   1850         if (max_len >= delta)
   1851         {
   1852             *p++ = name_size + 1;
   1853             *p++ = name_type;
   1854             ARRAY_TO_STREAM (p, btm_cb.cfg.bd_name, name_size);
   1855             len     += delta;
   1856             max_len -= delta;
   1857         }
   1858 #endif
   1859         /* update len */
   1860         p = p_data;
   1861         UINT16_TO_STREAM(p, len);
   1862     }
   1863     return len;
   1864 }
   1865 
   1866 /*******************************************************************************
   1867 **
   1868 ** Function         BTM_ReadOobData
   1869 **
   1870 ** Description      This function is called to parse the OOB data payload
   1871 **                  received over OOB (non-Bluetooth) link
   1872 **
   1873 ** Parameters:      p_data  - the location for OOB data
   1874 **                  eir_tag - The associated EIR tag to read the data.
   1875 **                  *p_len(output) - the length of the data with the given tag.
   1876 **
   1877 ** Returns          the beginning of the data with the given tag.
   1878 **                  NULL, if the tag is not found.
   1879 **
   1880 *******************************************************************************/
   1881 UINT8 * BTM_ReadOobData(UINT8 *p_data, UINT8 eir_tag, UINT8 *p_len)
   1882 {
   1883     UINT8   *p = p_data;
   1884     UINT16  max_len;
   1885     UINT8   len, type;
   1886     UINT8   *p_ret = NULL;
   1887     UINT8   ret_len = 0;
   1888 
   1889     if (p_data)
   1890     {
   1891         STREAM_TO_UINT16(max_len, p);
   1892         if (max_len >= BTM_OOB_MANDATORY_SIZE)
   1893         {
   1894             if (BTM_EIR_OOB_BD_ADDR_TYPE == eir_tag)
   1895             {
   1896                 p_ret = p; /* the location for bd_addr */
   1897                 ret_len = BTM_OOB_BD_ADDR_SIZE;
   1898             }
   1899             else
   1900             {
   1901                 p += BD_ADDR_LEN;
   1902                 max_len -= BTM_OOB_MANDATORY_SIZE;
   1903                 /* now the optional data in EIR format */
   1904                 while (max_len > 0)
   1905                 {
   1906                     len     = *p++; /* tag data len + 1 */
   1907                     type    = *p++;
   1908                     if (eir_tag == type)
   1909                     {
   1910                         p_ret = p;
   1911                         ret_len = len - 1;
   1912                         break;
   1913                     }
   1914                     /* the data size of this tag is len + 1 (tag data len + 2) */
   1915                     if (max_len > len)
   1916                     {
   1917                         max_len -= len;
   1918                         max_len--;
   1919                         len--;
   1920                         p += len;
   1921                     }
   1922                     else
   1923                         max_len = 0;
   1924                 }
   1925             }
   1926         }
   1927     }
   1928 
   1929     if (p_len)
   1930         *p_len = ret_len;
   1931 
   1932     return p_ret;
   1933 }
   1934 #endif
   1935 
   1936 /*******************************************************************************
   1937 **
   1938 ** Function         BTM_SetOutService
   1939 **
   1940 ** Description      This function is called to set the service for
   1941 **                  outgoing connections.
   1942 **
   1943 **                  If the profile/application calls BTM_SetSecurityLevel
   1944 **                  before initiating a connection, this function does not
   1945 **                  need to be called.
   1946 **
   1947 ** Returns          void
   1948 **
   1949 *******************************************************************************/
   1950 void BTM_SetOutService(BD_ADDR bd_addr, UINT8 service_id, UINT32 mx_chan_id)
   1951 {
   1952     tBTM_SEC_DEV_REC *p_dev_rec;
   1953     tBTM_SEC_SERV_REC *p_serv_rec = &btm_cb.sec_serv_rec[0];
   1954     int i;
   1955 
   1956     btm_cb.p_out_serv = p_serv_rec;
   1957     p_dev_rec = btm_find_dev (bd_addr);
   1958 
   1959     for (i = 0; i < BTM_SEC_MAX_SERVICE_RECORDS; i++, p_serv_rec++)
   1960     {
   1961         if ((p_serv_rec->security_flags & BTM_SEC_IN_USE)
   1962             && (p_serv_rec->service_id == service_id)
   1963             && (p_serv_rec->orig_mx_chan_id == mx_chan_id))
   1964         {
   1965             BTM_TRACE_API4("BTM_SetOutService p_out_serv id %d, psm 0x%04x, proto_id %d, chan_id %d",
   1966                            p_serv_rec->service_id, p_serv_rec->psm, p_serv_rec->mx_proto_id, p_serv_rec->orig_mx_chan_id);
   1967             btm_cb.p_out_serv = p_serv_rec;
   1968             if (p_dev_rec)
   1969                 p_dev_rec->p_cur_service = p_serv_rec;
   1970             break;
   1971         }
   1972     }
   1973 }
   1974 
   1975 /************************************************************************
   1976 **              I N T E R N A L     F U N C T I O N S
   1977 *************************************************************************/
   1978 /*******************************************************************************
   1979 **
   1980 ** Function         btm_sec_is_upgrade_possible
   1981 **
   1982 ** Description      This function returns TRUE if the existing link key
   1983 **                  can be upgraded or if the link key does not exist.
   1984 **
   1985 ** Returns          BOOLEAN
   1986 **
   1987 *******************************************************************************/
   1988 static BOOLEAN btm_sec_is_upgrade_possible(tBTM_SEC_DEV_REC  *p_dev_rec, BOOLEAN is_originator)
   1989 {
   1990     UINT16              mtm_check = is_originator ? BTM_SEC_OUT_MITM : BTM_SEC_IN_MITM;
   1991     BOOLEAN             is_possible = TRUE;
   1992 
   1993     if (p_dev_rec->sec_flags & BTM_SEC_LINK_KEY_KNOWN)
   1994     {
   1995         is_possible = FALSE;
   1996         BTM_TRACE_DEBUG5 ("btm_sec_is_upgrade_possible id:%d, link_key_typet:%d, rmt_io_caps:%d, chk flags:x%x, flags:x%x",
   1997                           p_dev_rec->p_cur_service->service_id, p_dev_rec->link_key_type, p_dev_rec->rmt_io_caps,
   1998                           mtm_check, p_dev_rec->p_cur_service->security_flags);
   1999         /* Already have a link key to the connected peer. Is the link key secure enough?
   2000         ** Is a link key upgrade even possible?
   2001         */
   2002         if ((p_dev_rec->security_required & mtm_check)                          /* needs MITM */
   2003             && (p_dev_rec->link_key_type == BTM_LKEY_TYPE_UNAUTH_COMB) /* has unauthenticated link key */
   2004             && (p_dev_rec->rmt_io_caps < BTM_IO_CAP_MAX)                           /* a valid peer IO cap */
   2005             && (btm_sec_io_map[p_dev_rec->rmt_io_caps][btm_cb.devcb.loc_io_caps])) /* authenticated link key is possible */
   2006         {
   2007             /* upgrade is possible: check if the application wants the upgrade.
   2008              * If the application is configured to use a global MITM flag,
   2009              * it probably would not want to upgrade the link key based on the security level database */
   2010             is_possible = TRUE;
   2011         }
   2012     }
   2013     BTM_TRACE_DEBUG2 ("btm_sec_is_upgrade_possible is_possible:%d sec_flags:0x%x", is_possible, p_dev_rec->sec_flags);
   2014     return is_possible;
   2015 }
   2016 
   2017 /*******************************************************************************
   2018 **
   2019 ** Function         btm_sec_check_upgrade
   2020 **
   2021 ** Description      This function is called to check if the existing link key
   2022 **                  needs to be upgraded.
   2023 **
   2024 ** Returns          void
   2025 **
   2026 *******************************************************************************/
   2027 static void btm_sec_check_upgrade(tBTM_SEC_DEV_REC  *p_dev_rec, BOOLEAN is_originator)
   2028 {
   2029     tBTM_SP_UPGRADE     evt_data;
   2030 
   2031     BTM_TRACE_DEBUG0 ("btm_sec_check_upgrade...");
   2032 
   2033     /* Only check if link key already exists */
   2034     if (!(p_dev_rec->sec_flags & BTM_SEC_LINK_KEY_KNOWN))
   2035         return;
   2036     if (btm_sec_is_upgrade_possible (p_dev_rec, is_originator) == TRUE)
   2037     {
   2038         BTM_TRACE_DEBUG1 ("need upgrade!! sec_flags:0x%x", p_dev_rec->sec_flags);
   2039         /* upgrade is possible: check if the application wants the upgrade.
   2040          * If the application is configured to use a global MITM flag,
   2041          * it probably would not want to upgrade the link key based on the security level database */
   2042         memcpy (evt_data.bd_addr, p_dev_rec->bd_addr, BD_ADDR_LEN);
   2043         evt_data.upgrade = TRUE;
   2044         if (btm_cb.api.p_sp_callback)
   2045             (*btm_cb.api.p_sp_callback) (BTM_SP_UPGRADE_EVT, (tBTM_SP_EVT_DATA *)&evt_data);
   2046 
   2047         BTM_TRACE_DEBUG1 ("evt_data.upgrade:0x%x", evt_data.upgrade);
   2048         if (evt_data.upgrade)
   2049         {
   2050             /* if the application confirms the upgrade, set the upgrade bit */
   2051             p_dev_rec->sm4 |= BTM_SM4_UPGRADE;
   2052 
   2053             /* Clear the link key known to go through authentication/pairing again */
   2054             p_dev_rec->sec_flags &= ~(BTM_SEC_LINK_KEY_KNOWN | BTM_SEC_LINK_KEY_AUTHED);
   2055             p_dev_rec->sec_flags &= ~BTM_SEC_AUTHENTICATED;
   2056             BTM_TRACE_DEBUG1 ("sec_flags:0x%x", p_dev_rec->sec_flags);
   2057         }
   2058     }
   2059 }
   2060 
   2061 /*******************************************************************************
   2062 **
   2063 ** Function         btm_sec_l2cap_access_req
   2064 **
   2065 ** Description      This function is called by the L2CAP to grant permission to
   2066 **                  establish L2CAP connection to or from the peer device.
   2067 **
   2068 ** Parameters:      bd_addr       - Address of the peer device
   2069 **                  psm           - L2CAP PSM
   2070 **                  is_originator - TRUE if protocol above L2CAP originates
   2071 **                                  connection
   2072 **                  p_callback    - Pointer to callback function called if
   2073 **                                  this function returns PENDING after required
   2074 **                                  procedures are complete. MUST NOT BE NULL.
   2075 **
   2076 ** Returns          tBTM_STATUS
   2077 **
   2078 *******************************************************************************/
   2079 #define BTM_SEC_OUT_FLAGS   (BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_OUT_ENCRYPT | BTM_SEC_OUT_AUTHORIZE)
   2080 #define BTM_SEC_IN_FLAGS    (BTM_SEC_IN_AUTHENTICATE | BTM_SEC_IN_ENCRYPT | BTM_SEC_IN_AUTHORIZE)
   2081 
   2082 tBTM_STATUS btm_sec_l2cap_access_req (BD_ADDR bd_addr, UINT16 psm, UINT16 handle,
   2083                                       CONNECTION_TYPE conn_type,
   2084                                       tBTM_SEC_CALLBACK *p_callback,
   2085                                       void *p_ref_data)
   2086 {
   2087     tBTM_SEC_DEV_REC  *p_dev_rec;
   2088     tBTM_SEC_SERV_REC *p_serv_rec;
   2089     UINT16         security_required;
   2090     UINT16         old_security_required;
   2091     BOOLEAN       old_is_originator;
   2092     tBTM_STATUS   rc = BTM_SUCCESS;
   2093     BOOLEAN       chk_acp_auth_done = FALSE;
   2094     BOOLEAN is_originator;
   2095 
   2096 #if (L2CAP_UCD_INCLUDED == TRUE)
   2097     if (conn_type & CONNECTION_TYPE_ORIG_MASK)
   2098         is_originator = TRUE;
   2099     else
   2100         is_originator = FALSE;
   2101 
   2102     BTM_TRACE_DEBUG2 ("btm_sec_l2cap_access_req conn_type:0x%x, 0x%x", conn_type, p_ref_data);
   2103 #else
   2104     is_originator = conn_type;
   2105 
   2106     BTM_TRACE_DEBUG2 ("btm_sec_l2cap_access_req is_originator:%d, 0x%x", is_originator, p_ref_data);
   2107 #endif
   2108 
   2109     /* Find or get oldest record */
   2110     p_dev_rec = btm_find_or_alloc_dev (bd_addr);
   2111 
   2112     p_dev_rec->hci_handle = handle;
   2113 
   2114     /* Find the service record for the PSM */
   2115     p_serv_rec = btm_sec_find_first_serv (conn_type, psm);
   2116 
   2117     /* If there is no application registered with this PSM do not allow connection */
   2118     if (!p_serv_rec)
   2119     {
   2120         BTM_TRACE_WARNING1 ("btm_sec_l2cap_access_req()  PSM:%d no application registerd", psm);
   2121 
   2122         (*p_callback) (bd_addr, p_ref_data, BTM_MODE_UNSUPPORTED);
   2123 
   2124         return(BTM_MODE_UNSUPPORTED);
   2125     }
   2126 
   2127     /* SDP connection we will always let through */
   2128     if (BT_PSM_SDP == psm)
   2129     {
   2130         (*p_callback) (bd_addr, p_ref_data, BTM_SUCCESS_NO_SECURITY);
   2131 
   2132         return(BTM_SUCCESS);
   2133     }
   2134 #if (L2CAP_UCD_INCLUDED == TRUE)
   2135     if ( conn_type & CONNECTION_TYPE_CONNLESS_MASK )
   2136     {
   2137         security_required = p_serv_rec->ucd_security_flags;
   2138 
   2139         rc = BTM_CMD_STARTED;
   2140         if (is_originator)
   2141         {
   2142             if (((security_required & BTM_SEC_OUT_FLAGS) == 0) ||
   2143                 ((((security_required & BTM_SEC_OUT_FLAGS) == BTM_SEC_OUT_AUTHENTICATE) && (p_dev_rec->sec_flags & BTM_SEC_AUTHENTICATED))) ||
   2144                 ((((security_required & BTM_SEC_OUT_FLAGS) == (BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_OUT_ENCRYPT)) && (p_dev_rec->sec_flags & BTM_SEC_ENCRYPTED))) ||
   2145                 ((((security_required & BTM_SEC_OUT_FLAGS) == BTM_SEC_OUT_FLAGS) && (p_dev_rec->sec_flags & BTM_SEC_AUTHORIZED))) )
   2146             {
   2147                 rc = BTM_SUCCESS;
   2148             }
   2149         }
   2150         else
   2151         {
   2152             if (((security_required & BTM_SEC_IN_FLAGS) == 0) ||
   2153                 ((((security_required & BTM_SEC_IN_FLAGS) == BTM_SEC_IN_AUTHENTICATE) && (p_dev_rec->sec_flags & BTM_SEC_AUTHENTICATED))) ||
   2154                 ((((security_required & BTM_SEC_IN_FLAGS) == (BTM_SEC_IN_AUTHENTICATE | BTM_SEC_IN_ENCRYPT)) && (p_dev_rec->sec_flags & BTM_SEC_ENCRYPTED))) ||
   2155                 ((((security_required & BTM_SEC_IN_FLAGS) == BTM_SEC_IN_FLAGS) && (p_dev_rec->sec_flags & BTM_SEC_AUTHORIZED))) )
   2156             {
   2157                 rc = BTM_SUCCESS;
   2158             }
   2159         }
   2160 
   2161         if (rc == BTM_SUCCESS)
   2162         {
   2163             if (p_callback)
   2164                 (*p_callback) (bd_addr, (void *)p_ref_data, BTM_SUCCESS);
   2165 
   2166             return(BTM_SUCCESS);
   2167         }
   2168     }
   2169     else
   2170 #endif
   2171     {
   2172         security_required = p_serv_rec->security_flags;
   2173     }
   2174 
   2175     /* there are some devices (moto KRZR) which connects to several services at the same time */
   2176     /* we will process one after another */
   2177     if ( (p_dev_rec->p_callback) || (btm_cb.pairing_state != BTM_PAIR_STATE_IDLE) )
   2178     {
   2179         BTM_TRACE_EVENT4 ("btm_sec_l2cap_access_req() - busy - PSM:%d delayed  state: %s mode:%d, sm4:0x%x",
   2180                           psm, btm_pair_state_descr(btm_cb.pairing_state), btm_cb.security_mode, p_dev_rec->sm4);
   2181         BTM_TRACE_EVENT2 ("security_flags:x%x, sec_flags:x%x", security_required, p_dev_rec->sec_flags);
   2182         rc = BTM_CMD_STARTED;
   2183         if ((BTM_SEC_MODE_SP != btm_cb.security_mode)
   2184             || ((BTM_SEC_MODE_SP == btm_cb.security_mode) && (BTM_SM4_KNOWN == p_dev_rec->sm4))
   2185             || (BTM_SEC_IS_SM4(p_dev_rec->sm4) && (btm_sec_is_upgrade_possible(p_dev_rec, is_originator) == FALSE))
   2186            )
   2187         {
   2188             /* legacy mode - local is legacy or local is lisbon/peer is legacy
   2189              * or SM4 with no possibility of link key upgrade */
   2190             if (is_originator)
   2191             {
   2192                 if (((security_required & BTM_SEC_OUT_FLAGS) == 0) ||
   2193                     ((((security_required & BTM_SEC_OUT_FLAGS) == BTM_SEC_OUT_AUTHENTICATE) && (p_dev_rec->sec_flags & BTM_SEC_AUTHENTICATED))) ||
   2194                     ((((security_required & BTM_SEC_OUT_FLAGS) == (BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_OUT_ENCRYPT)) && (p_dev_rec->sec_flags & BTM_SEC_ENCRYPTED))) ||
   2195                     ((((security_required & BTM_SEC_OUT_FLAGS) == BTM_SEC_OUT_FLAGS) && (p_dev_rec->sec_flags & BTM_SEC_AUTHORIZED))) )
   2196                 {
   2197                     rc = BTM_SUCCESS;
   2198                 }
   2199             }
   2200             else
   2201             {
   2202                 if (((security_required & BTM_SEC_IN_FLAGS) == 0) ||
   2203                     ((((security_required & BTM_SEC_IN_FLAGS) == BTM_SEC_IN_AUTHENTICATE) && (p_dev_rec->sec_flags & BTM_SEC_AUTHENTICATED))) ||
   2204                     ((((security_required & BTM_SEC_IN_FLAGS) == (BTM_SEC_IN_AUTHENTICATE | BTM_SEC_IN_ENCRYPT)) && (p_dev_rec->sec_flags & BTM_SEC_ENCRYPTED))) ||
   2205                     ((((security_required & BTM_SEC_IN_FLAGS) == BTM_SEC_IN_FLAGS) && (p_dev_rec->sec_flags & BTM_SEC_AUTHORIZED))) )
   2206                 {
   2207                     rc = BTM_SUCCESS;
   2208                 }
   2209             }
   2210 
   2211             if (rc == BTM_SUCCESS)
   2212             {
   2213                 if (p_callback)
   2214                     (*p_callback) (bd_addr, (void *)p_ref_data, BTM_SUCCESS);
   2215 
   2216                 return(BTM_SUCCESS);
   2217             }
   2218         }
   2219 
   2220         btm_cb.sec_req_pending = TRUE;
   2221         return(BTM_CMD_STARTED);
   2222     }
   2223 
   2224     /* Save pointer to service record */
   2225     p_dev_rec->p_cur_service = p_serv_rec;
   2226 
   2227 
   2228     /* mess /w security_required in btm_sec_l2cap_access_req for Lisbon */
   2229     if (btm_cb.security_mode == BTM_SEC_MODE_SP)
   2230     {
   2231         if (is_originator)
   2232         {
   2233             if (BTM_SEC_IS_SM4(p_dev_rec->sm4))
   2234             {
   2235                 /* SM4 to SM4 -> always authenticate & encrypt */
   2236                 security_required |= (BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_OUT_ENCRYPT);
   2237             }
   2238             else
   2239             {
   2240                 if ( !(BTM_SM4_KNOWN & p_dev_rec->sm4))
   2241                 {
   2242                     BTM_TRACE_DEBUG1 ("remote features unknown!!sec_flags:0x%x", p_dev_rec->sec_flags);
   2243                     /* the remote features are not known yet */
   2244                     p_dev_rec->sm4          |= BTM_SM4_REQ_PEND;
   2245 
   2246                     return(BTM_CMD_STARTED);
   2247                 }
   2248             }
   2249         }
   2250         else
   2251         {
   2252             /* responder */
   2253             if (BTM_SEC_IS_SM4(p_dev_rec->sm4))
   2254             {
   2255                 /* SM4 to SM4: the acceptor needs to make sure the authentication is already done */
   2256                 chk_acp_auth_done = TRUE;
   2257                 /* SM4 to SM4 -> always authenticate & encrypt */
   2258                 security_required |= (BTM_SEC_IN_AUTHENTICATE | BTM_SEC_IN_ENCRYPT);
   2259             }
   2260             else
   2261             {
   2262                 if ( !(BTM_SM4_KNOWN & p_dev_rec->sm4))
   2263                 {
   2264                     BTM_TRACE_DEBUG1 ("(rsp) remote features unknown!!sec_flags:0x%x", p_dev_rec->sec_flags);
   2265                     /* the remote features are not known yet */
   2266                     p_dev_rec->sm4          |= BTM_SM4_REQ_PEND;
   2267 
   2268                     return(BTM_CMD_STARTED);
   2269                 }
   2270             }
   2271         }
   2272     }
   2273 
   2274     BTM_TRACE_DEBUG4 ("btm_sec_l2cap_access_req()  sm4:0x%x, sec_flags:0x%x, security_required:0x%x chk:%d",
   2275                       p_dev_rec->sm4, p_dev_rec->sec_flags, security_required, chk_acp_auth_done);
   2276 
   2277     old_security_required        = p_dev_rec->security_required;
   2278     old_is_originator            = p_dev_rec->is_originator;
   2279     p_dev_rec->security_required = security_required;
   2280     p_dev_rec->p_ref_data        = p_ref_data;
   2281     p_dev_rec->is_originator     = is_originator;
   2282 
   2283 #if (L2CAP_UCD_INCLUDED == TRUE)
   2284     if ( conn_type & CONNECTION_TYPE_CONNLESS_MASK )
   2285         p_dev_rec->is_ucd = TRUE;
   2286     else
   2287         p_dev_rec->is_ucd = FALSE;
   2288 #endif
   2289 
   2290     /* If there are multiple service records used through the same PSM */
   2291     /* leave security decision for the multiplexor on the top */
   2292 #if (L2CAP_UCD_INCLUDED == TRUE)
   2293     if (((btm_sec_find_next_serv (p_serv_rec)) != NULL)
   2294         &&(!( conn_type & CONNECTION_TYPE_CONNLESS_MASK ))) /* if not UCD */
   2295 #else
   2296     if ((btm_sec_find_next_serv (p_serv_rec)) != NULL)
   2297 #endif
   2298     {
   2299         BTM_TRACE_DEBUG2 ("no next_serv sm4:0x%x, chk:%d", p_dev_rec->sm4, chk_acp_auth_done);
   2300         if (!BTM_SEC_IS_SM4(p_dev_rec->sm4))
   2301         {
   2302             BTM_TRACE_EVENT1 ("Security Manager: l2cap_access_req PSM:%d postponed for multiplexer", psm);
   2303             /* pre-Lisbon: restore the old settings */
   2304             p_dev_rec->security_required = old_security_required;
   2305             p_dev_rec->is_originator     = old_is_originator;
   2306 
   2307             (*p_callback) (bd_addr, p_ref_data, BTM_SUCCESS);
   2308 
   2309             return(BTM_SUCCESS);
   2310         }
   2311     }
   2312 
   2313     /* if the originator is using dynamic PSM in legacy mode, do not start any security process now.
   2314      * The layer above L2CAP needs to carry out the security requirement after L2CAP connect response is received*/
   2315     if (is_originator && (btm_cb.security_mode != BTM_SEC_MODE_SP || !BTM_SEC_IS_SM4(p_dev_rec->sm4)) && (psm >= 0x1001))
   2316     {
   2317         BTM_TRACE_EVENT1 ("dynamic PSM:0x%x in legacy mode - postponed for upper layer", psm);
   2318         /* restore the old settings */
   2319         p_dev_rec->security_required = old_security_required;
   2320         p_dev_rec->is_originator     = old_is_originator;
   2321 
   2322         (*p_callback) (bd_addr, p_ref_data, BTM_SUCCESS);
   2323 
   2324         return(BTM_SUCCESS);
   2325     }
   2326 
   2327     if (chk_acp_auth_done)
   2328     {
   2329         BTM_TRACE_DEBUG2 ("(SM4 to SM4) btm_sec_l2cap_access_req rspd. authenticated: x%x, enc: x%x",
   2330                           (p_dev_rec->sec_flags & BTM_SEC_AUTHENTICATED), (p_dev_rec->sec_flags & BTM_SEC_ENCRYPTED));
   2331         /* SM4, but we do not know for sure which level of security we need.
   2332          * as long as we have a link key, it's OK */
   2333         if ((0 == (p_dev_rec->sec_flags & BTM_SEC_AUTHENTICATED))
   2334             ||(0 == (p_dev_rec->sec_flags & BTM_SEC_ENCRYPTED)))
   2335         {
   2336             rc = BTM_DELAY_CHECK;
   2337             /*
   2338             2046 may report HCI_Encryption_Change and L2C Connection Request out of sequence
   2339             because of data path issues. Delay this disconnect a little bit
   2340             */
   2341             BTM_TRACE_ERROR0 ("peer should have initiated security process by now (SM4 to SM4)");
   2342             p_dev_rec->p_callback        = p_callback;
   2343             p_dev_rec->sec_state         = BTM_SEC_STATE_DELAY_FOR_ENC;
   2344             (*p_callback) (bd_addr, p_ref_data, rc);
   2345 
   2346             return(BTM_SUCCESS);
   2347         }
   2348     }
   2349 
   2350     p_dev_rec->p_callback        = p_callback;
   2351 
   2352     if (p_dev_rec->last_author_service_id == BTM_SEC_NO_LAST_SERVICE_ID
   2353         || p_dev_rec->last_author_service_id != p_dev_rec->p_cur_service->service_id)
   2354     {
   2355         /* Although authentication and encryption are per connection
   2356         ** authorization is per access request.  For example when serial connection
   2357         ** is up and authorized and client requests to read file (access to other
   2358         ** scn), we need to request user's permission again.
   2359         */
   2360         p_dev_rec->sec_flags &= ~BTM_SEC_AUTHORIZED;
   2361     }
   2362 
   2363     if (BTM_SEC_IS_SM4(p_dev_rec->sm4))
   2364     {
   2365         /* If we already have a link key to the connected peer, is the link key secure enough ? */
   2366         btm_sec_check_upgrade(p_dev_rec, is_originator);
   2367     }
   2368 
   2369     BTM_TRACE_EVENT6 ("Security Manager: l2cap_access_req PSM:%d Handle:%d State:%d Flags:0x%x Required:0x%x Service ID:%d",
   2370                       psm, handle, p_dev_rec->sec_state, p_dev_rec->sec_flags, p_dev_rec->security_required, p_dev_rec->p_cur_service->service_id);
   2371 
   2372     if ((rc = btm_sec_execute_procedure (p_dev_rec)) != BTM_CMD_STARTED)
   2373     {
   2374         p_dev_rec->p_callback = NULL;
   2375         (*p_callback) (bd_addr, p_dev_rec->p_ref_data, (UINT8)rc);
   2376     }
   2377 
   2378     return(rc);
   2379 }
   2380 
   2381 /*******************************************************************************
   2382 **
   2383 ** Function         btm_sec_mx_access_request
   2384 **
   2385 ** Description      This function is called by all Multiplexing Protocols during
   2386 **                  establishing connection to or from peer device to grant
   2387 **                  permission to establish application connection.
   2388 **
   2389 ** Parameters:      bd_addr       - Address of the peer device
   2390 **                  psm           - L2CAP PSM
   2391 **                  is_originator - TRUE if protocol above L2CAP originates
   2392 **                                  connection
   2393 **                  mx_proto_id   - protocol ID of the multiplexer
   2394 **                  mx_chan_id    - multiplexer channel to reach application
   2395 **                  p_callback    - Pointer to callback function called if
   2396 **                                  this function returns PENDING after required
   2397 **                                  procedures are completed
   2398 **                  p_ref_data    - Pointer to any reference data needed by the
   2399 **                                  the callback function.
   2400 **
   2401 ** Returns          BTM_CMD_STARTED
   2402 **
   2403 *******************************************************************************/
   2404 tBTM_STATUS btm_sec_mx_access_request (BD_ADDR bd_addr, UINT16 psm, BOOLEAN is_originator,
   2405                                        UINT32 mx_proto_id, UINT32 mx_chan_id,
   2406                                        tBTM_SEC_CALLBACK *p_callback, void *p_ref_data)
   2407 
   2408 {
   2409     tBTM_SEC_DEV_REC  *p_dev_rec;
   2410     tBTM_SEC_SERV_REC *p_serv_rec;
   2411     tBTM_STATUS        rc;
   2412     UINT16             security_required;
   2413 
   2414     BTM_TRACE_DEBUG1 ("btm_sec_mx_access_request is_originator:%d", is_originator);
   2415     /* Find or get oldest record */
   2416     p_dev_rec = btm_find_or_alloc_dev (bd_addr);
   2417 
   2418     /* Find the service record for the PSM */
   2419     p_serv_rec = btm_sec_find_mx_serv (is_originator, psm, mx_proto_id, mx_chan_id);
   2420 
   2421     /* If there is no application registered with this PSM do not allow connection */
   2422     if (!p_serv_rec)
   2423     {
   2424         if (p_callback)
   2425             (*p_callback) (bd_addr, p_ref_data, BTM_MODE_UNSUPPORTED);
   2426 
   2427         BTM_TRACE_ERROR3 ("Security Manager: MX service not found PSM:%d Proto:%d SCN:%d",
   2428                           psm, mx_proto_id, mx_chan_id);
   2429         return BTM_NO_RESOURCES;
   2430     }
   2431 
   2432     /* there are some devices (moto phone) which connects to several services at the same time */
   2433     /* we will process one after another */
   2434     if ( (p_dev_rec->p_callback) || (btm_cb.pairing_state != BTM_PAIR_STATE_IDLE) )
   2435     {
   2436         BTM_TRACE_EVENT4 ("btm_sec_mx_access_request service PSM:%d Proto:%d SCN:%d delayed  state: %s",
   2437                           psm, mx_proto_id, mx_chan_id, btm_pair_state_descr(btm_cb.pairing_state));
   2438 
   2439         rc = BTM_CMD_STARTED;
   2440         security_required = p_serv_rec->security_flags;
   2441         if ((BTM_SEC_MODE_SP != btm_cb.security_mode)
   2442             || ((BTM_SEC_MODE_SP == btm_cb.security_mode) && (BTM_SM4_KNOWN == p_dev_rec->sm4))
   2443             || (BTM_SEC_IS_SM4(p_dev_rec->sm4) && (btm_sec_is_upgrade_possible(p_dev_rec, is_originator) == FALSE))
   2444            )
   2445         {
   2446             /* legacy mode - local is legacy or local is lisbon/peer is legacy
   2447              * or SM4 with no possibility of link key upgrade */
   2448             if (is_originator)
   2449             {
   2450                 if (((security_required & BTM_SEC_OUT_FLAGS) == 0) ||
   2451                     ((((security_required & BTM_SEC_OUT_FLAGS) == BTM_SEC_OUT_AUTHENTICATE) && (p_dev_rec->sec_flags & BTM_SEC_AUTHENTICATED))) ||
   2452                     ((((security_required & BTM_SEC_OUT_FLAGS) == (BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_OUT_ENCRYPT)) && (p_dev_rec->sec_flags & BTM_SEC_ENCRYPTED)))
   2453                     )
   2454                 {
   2455                     rc = BTM_SUCCESS;
   2456                 }
   2457             }
   2458             else
   2459             {
   2460                 if (((security_required & BTM_SEC_IN_FLAGS) == 0) ||
   2461                     ((((security_required & BTM_SEC_IN_FLAGS) == BTM_SEC_IN_AUTHENTICATE) && (p_dev_rec->sec_flags & BTM_SEC_AUTHENTICATED))) ||
   2462                     ((((security_required & BTM_SEC_IN_FLAGS) == (BTM_SEC_IN_AUTHENTICATE | BTM_SEC_IN_ENCRYPT)) && (p_dev_rec->sec_flags & BTM_SEC_ENCRYPTED)))
   2463                     )
   2464                 {
   2465                     rc = BTM_SUCCESS;
   2466                 }
   2467             }
   2468         }
   2469         if (rc == BTM_CMD_STARTED)
   2470         {
   2471             btm_sec_queue_mx_request (bd_addr, psm,  is_originator, mx_proto_id, mx_chan_id, p_callback, p_ref_data);
   2472             return rc;
   2473         }
   2474     }
   2475 
   2476     p_dev_rec->p_cur_service     = p_serv_rec;
   2477     p_dev_rec->security_required = p_serv_rec->security_flags;
   2478 
   2479     if (BTM_SEC_MODE_SP == btm_cb.security_mode)
   2480     {
   2481         if (BTM_SEC_IS_SM4(p_dev_rec->sm4))
   2482         {
   2483             /* If we already have a link key, check if that link key is good enough */
   2484             btm_sec_check_upgrade(p_dev_rec, is_originator);
   2485         }
   2486     }
   2487 
   2488     p_dev_rec->is_originator     = is_originator;
   2489     p_dev_rec->p_callback        = p_callback;
   2490     p_dev_rec->p_ref_data        = p_ref_data;
   2491 
   2492     /* Although authentication and encryption are per connection */
   2493     /* authorization is per access request.  For example when serial connection */
   2494     /* is up and authorized and client requests to read file (access to other */
   2495     /* scn, we need to request user's permission again. */
   2496     p_dev_rec->sec_flags &= ~(BTM_SEC_AUTHORIZED);
   2497 
   2498     BTM_TRACE_EVENT6 ("Security Manager: mx_access_req proto_id:%d chan_id:%d State:%d Flags:0x%x Required:0x%x Service ID:%d",
   2499                       mx_proto_id, mx_chan_id, p_dev_rec->sec_state, p_dev_rec->sec_flags, p_dev_rec->security_required, p_dev_rec->p_cur_service->service_id);
   2500 
   2501     if ((rc = btm_sec_execute_procedure (p_dev_rec)) != BTM_CMD_STARTED)
   2502     {
   2503         if (p_callback)
   2504         {
   2505             p_dev_rec->p_callback = NULL;
   2506 
   2507             (*p_callback) (bd_addr, p_ref_data, (UINT8)rc);
   2508         }
   2509     }
   2510 
   2511     return rc;
   2512 }
   2513 
   2514 /*******************************************************************************
   2515 **
   2516 ** Function         btm_sec_conn_req
   2517 **
   2518 ** Description      This function is when the peer device is requesting
   2519 **                  connection
   2520 **
   2521 ** Returns          void
   2522 **
   2523 *******************************************************************************/
   2524 void btm_sec_conn_req (UINT8 *bda, UINT8 *dc)
   2525 {
   2526     tBTM_SEC_DEV_REC  *p_dev_rec = btm_find_dev (bda);
   2527 
   2528     /* Some device may request a connection before we are done with the HCI_Reset sequence */
   2529     if (btm_cb.devcb.state != BTM_DEV_STATE_READY)
   2530     {
   2531         BTM_TRACE_EVENT0 ("Security Manager: connect request when device not ready");
   2532         btsnd_hcic_reject_conn (bda, HCI_ERR_HOST_REJECT_DEVICE);
   2533         return;
   2534     }
   2535 
   2536     /* Security guys wants us not to allow connection from not paired devices */
   2537 
   2538     /* Check if connection is allowed for only paired devices */
   2539     if (btm_cb.connect_only_paired)
   2540     {
   2541         if (!p_dev_rec || !(p_dev_rec->sec_flags & BTM_SEC_LINK_KEY_AUTHED))
   2542         {
   2543             BTM_TRACE_EVENT0 ("Security Manager: connect request from non-paired device");
   2544             btsnd_hcic_reject_conn (bda, HCI_ERR_HOST_REJECT_DEVICE);
   2545             return;
   2546         }
   2547     }
   2548 
   2549 #if BTM_ALLOW_CONN_IF_NONDISCOVER == FALSE
   2550     /* If non-discoverable, only allow known devices to connect */
   2551     if (btm_cb.btm_inq_vars.discoverable_mode == BTM_NON_DISCOVERABLE)
   2552     {
   2553         if (!p_dev_rec)
   2554         {
   2555             BTM_TRACE_EVENT0 ("Security Manager: connect request from not paired device");
   2556             btsnd_hcic_reject_conn (bda, HCI_ERR_HOST_REJECT_DEVICE);
   2557             return;
   2558         }
   2559     }
   2560 #endif
   2561 
   2562     /* Host can be registered to verify comming BDA or DC */
   2563     if (btm_cb.p_conn_filter_cb)
   2564     {
   2565         if (!(* btm_cb.p_conn_filter_cb) (bda, dc))
   2566         {
   2567             BTM_TRACE_EVENT0 ("Security Manager: connect request did not pass filter");
   2568 
   2569             /* incomming call did not pass connection filters.  Reject */
   2570             btsnd_hcic_reject_conn (bda, HCI_ERR_HOST_REJECT_DEVICE);
   2571             return;
   2572         }
   2573     }
   2574 
   2575     if ((btm_cb.pairing_state != BTM_PAIR_STATE_IDLE)
   2576         &&(btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD)
   2577         &&(!memcmp (btm_cb.pairing_bda, bda, BD_ADDR_LEN)))
   2578     {
   2579         BTM_TRACE_EVENT0 ("Security Manager: reject connect request from bonding device");
   2580 
   2581         /* incoming connection from bonding device is rejected */
   2582         btm_cb.pairing_flags |= BTM_PAIR_FLAGS_REJECTED_CONNECT;
   2583         btsnd_hcic_reject_conn (bda, HCI_ERR_HOST_REJECT_DEVICE);
   2584         return;
   2585     }
   2586 
   2587     /* Host is not interested or approved connection.  Save BDA and DC and */
   2588     /* pass request to L2CAP */
   2589     memcpy (btm_cb.connecting_bda, bda, BD_ADDR_LEN);
   2590     memcpy (btm_cb.connecting_dc,  dc,  DEV_CLASS_LEN);
   2591 
   2592     if (l2c_link_hci_conn_req (bda))
   2593     {
   2594         if (!p_dev_rec)
   2595         {
   2596             /* accept the connection -> allocate a device record */
   2597             p_dev_rec = btm_sec_alloc_dev (bda);
   2598         }
   2599         if (p_dev_rec)
   2600         {
   2601             p_dev_rec->sm4 |= BTM_SM4_CONN_PEND;
   2602         }
   2603     }
   2604 }
   2605 
   2606 /*******************************************************************************
   2607 **
   2608 ** Function         btm_sec_bond_cancel_complete
   2609 **
   2610 ** Description      This function is called to report bond cancel complete
   2611 **                  event.
   2612 **
   2613 ** Returns          void
   2614 **
   2615 *******************************************************************************/
   2616 static void btm_sec_bond_cancel_complete (void)
   2617 {
   2618     tBTM_SEC_DEV_REC *p_dev_rec;
   2619 
   2620     if ((btm_cb.pairing_flags & BTM_PAIR_FLAGS_DISC_WHEN_DONE) ||
   2621         (BTM_PAIR_STATE_WAIT_LOCAL_PIN == btm_cb.pairing_state &&
   2622          BTM_PAIR_FLAGS_WE_STARTED_DD & btm_cb.pairing_flags) ||
   2623          (btm_cb.pairing_state == BTM_PAIR_STATE_GET_REM_NAME &&
   2624           BTM_PAIR_FLAGS_WE_CANCEL_DD & btm_cb.pairing_flags))
   2625     {
   2626         /* for dedicated bonding in legacy mode, authentication happens at "link level"
   2627          * btm_sec_connected is called with failed status.
   2628          * In theory, the code that handles is_pairing_device/TRUE should clean out security related code.
   2629          * However, this function may clean out the security related flags and btm_sec_connected would not know
   2630          * this function also needs to do proper clean up.
   2631          */
   2632         if ((p_dev_rec = btm_find_dev (btm_cb.pairing_bda)) != NULL)
   2633             p_dev_rec->security_required = BTM_SEC_NONE;
   2634         btm_sec_change_pairing_state (BTM_PAIR_STATE_IDLE);
   2635 
   2636         /* Notify application that the cancel succeeded */
   2637         if (btm_cb.api.p_bond_cancel_cmpl_callback)
   2638             btm_cb.api.p_bond_cancel_cmpl_callback(BTM_SUCCESS);
   2639     }
   2640 }
   2641 
   2642 /*******************************************************************************
   2643 **
   2644 ** Function         btm_create_conn_cancel_complete
   2645 **
   2646 ** Description      This function is called when the command complete message
   2647 **                  is received from the HCI for the create connection cancel
   2648 **                  command.
   2649 **
   2650 ** Returns          void
   2651 **
   2652 *******************************************************************************/
   2653 void btm_create_conn_cancel_complete (UINT8 *p)
   2654 {
   2655     UINT8       status;
   2656 
   2657     STREAM_TO_UINT8 (status, p);
   2658     BTM_TRACE_EVENT2 ("btm_create_conn_cancel_complete(): in State: %s  status:%d",
   2659                       btm_pair_state_descr(btm_cb.pairing_state), status);
   2660 
   2661     /* if the create conn cancel cmd was issued by the bond cancel,
   2662     ** the application needs to be notified that bond cancel succeeded
   2663     */
   2664     switch (status)
   2665     {
   2666         case HCI_SUCCESS:
   2667             btm_sec_bond_cancel_complete();
   2668             break;
   2669         case HCI_ERR_CONNECTION_EXISTS:
   2670         case HCI_ERR_NO_CONNECTION:
   2671         default:
   2672             /* Notify application of the error */
   2673             if (btm_cb.api.p_bond_cancel_cmpl_callback)
   2674                 btm_cb.api.p_bond_cancel_cmpl_callback(BTM_ERR_PROCESSING);
   2675             break;
   2676     }
   2677 }
   2678 
   2679 /*******************************************************************************
   2680 **
   2681 ** Function         btm_sec_check_pending_reqs
   2682 **
   2683 ** Description      This function is called at the end of the security procedure
   2684 **                  to let L2CAP and RFCOMM know to re-submit any pending requests
   2685 **
   2686 ** Returns          void
   2687 **
   2688 *******************************************************************************/
   2689 void btm_sec_check_pending_reqs (void)
   2690 {
   2691     tBTM_SEC_QUEUE_ENTRY    *p_e;
   2692     BUFFER_Q                bq;
   2693 
   2694     if (btm_cb.pairing_state == BTM_PAIR_STATE_IDLE)
   2695     {
   2696         /* First, resubmit L2CAP requests */
   2697         if (btm_cb.sec_req_pending)
   2698         {
   2699             btm_cb.sec_req_pending = FALSE;
   2700             l2cu_resubmit_pending_sec_req (NULL);
   2701         }
   2702 
   2703         /* Now, re-submit anything in the mux queue */
   2704         bq = btm_cb.sec_pending_q;
   2705 
   2706         GKI_init_q (&btm_cb.sec_pending_q);
   2707 
   2708         while ((p_e = (tBTM_SEC_QUEUE_ENTRY *)GKI_dequeue (&bq)) != NULL)
   2709         {
   2710             /* Check that the ACL is still up before starting security procedures */
   2711             if (btm_bda_to_acl(p_e->bd_addr) != NULL)
   2712             {
   2713                 BTM_TRACE_EVENT4 ("btm_sec_check_pending_reqs() submitting  PSM: 0x%04x  Is_Orig: %u  mx_proto_id: %u  mx_chan_id: %u",
   2714                                   p_e->psm, p_e->is_orig, p_e->mx_proto_id, p_e->mx_chan_id);
   2715 
   2716                 btm_sec_mx_access_request (p_e->bd_addr, p_e->psm, p_e->is_orig,
   2717                                            p_e->mx_proto_id, p_e->mx_chan_id,
   2718                                            p_e->p_callback, p_e->p_ref_data);
   2719             }
   2720 
   2721             GKI_freebuf (p_e);
   2722         }
   2723     }
   2724 }
   2725 
   2726 /*******************************************************************************
   2727 **
   2728 ** Function         btm_sec_init
   2729 **
   2730 ** Description      This function is on the SEC startup
   2731 **
   2732 ** Returns          void
   2733 **
   2734 *******************************************************************************/
   2735 void btm_sec_init (UINT8 sec_mode)
   2736 {
   2737 #if 0  /* cleared in btm_init; put back in if calling from anywhere else! */
   2738     int i;
   2739 
   2740     memset (btm_cb.sec_serv_rec, 0, sizeof (btm_cb.sec_serv_rec));
   2741     memset (btm_cb.sec_dev_rec, 0, sizeof (btm_cb.sec_dev_rec));
   2742     memset (&btm_cb.pairing_tle, 0, sizeof(TIMER_LIST_ENT));
   2743 
   2744 #endif
   2745     btm_cb.security_mode = sec_mode;
   2746     memset (btm_cb.pairing_bda, 0xff, BD_ADDR_LEN);
   2747     btm_cb.max_collision_delay = BTM_SEC_MAX_COLLISION_DELAY;
   2748 }
   2749 
   2750 /*******************************************************************************
   2751 **
   2752 ** Function         btm_sec_device_down
   2753 **
   2754 ** Description      This function should be called when device is disabled or
   2755 **                  turned off
   2756 **
   2757 ** Returns          void
   2758 **
   2759 *******************************************************************************/
   2760 void btm_sec_device_down (void)
   2761 {
   2762     BTM_TRACE_EVENT1 ("btm_sec_device_down()  State: %s", btm_pair_state_descr(btm_cb.pairing_state));
   2763 
   2764     btm_sec_change_pairing_state (BTM_PAIR_STATE_IDLE);
   2765 }
   2766 
   2767 /*******************************************************************************
   2768 **
   2769 ** Function         btm_sec_dev_reset
   2770 **
   2771 ** Description      This function should be called after device reset
   2772 **
   2773 ** Returns          void
   2774 **
   2775 *******************************************************************************/
   2776 void btm_sec_dev_reset (void)
   2777 {
   2778 #if (BTM_PRE_LISBON_INCLUDED == TRUE)
   2779     if (btm_cb.security_mode == BTM_SEC_MODE_LINK)
   2780     {
   2781         btsnd_hcic_write_auth_enable (TRUE);
   2782         btsnd_hcic_write_encr_mode (HCI_ENCRYPT_MODE_POINT_TO_POINT);
   2783     }
   2784 #endif
   2785 #if (BTM_PRE_LISBON_INCLUDED == TRUE)
   2786     else
   2787 #endif
   2788         /* btm_sec_dev_reset() is only called from btm_decode_ext_features_page(...)
   2789          * right now. */
   2790         if (HCI_SIMPLE_PAIRING_SUPPORTED(btm_cb.devcb.local_lmp_features[HCI_EXT_FEATURES_PAGE_0]))
   2791     {
   2792 #if BLE_INCLUDED == TRUE
   2793         btsnd_hcic_set_event_mask(LOCAL_BR_EDR_CONTROLLER_ID,
   2794                                   (UINT8 *)HCI_DUMO_EVENT_MASK_EXT);
   2795 #else
   2796         btsnd_hcic_set_event_mask(LOCAL_BR_EDR_CONTROLLER_ID,
   2797                                   (UINT8 *)HCI_LISBON_EVENT_MASK_EXT);
   2798 #endif
   2799         /* set the default IO capabilities */
   2800         btm_cb.devcb.loc_io_caps = BTM_LOCAL_IO_CAPS;
   2801         /* add mx service to use no security */
   2802 #if (RFCOMM_INCLUDED == TRUE)
   2803         BTM_SetSecurityLevel(FALSE, "RFC_MUX", BTM_SEC_SERVICE_RFC_MUX,
   2804                              BTM_SEC_NONE, BT_PSM_RFCOMM, BTM_SEC_PROTO_RFCOMM, 0);
   2805 #endif
   2806     }
   2807     else
   2808     {
   2809         btm_cb.security_mode = BTM_SEC_MODE_SERVICE;
   2810     }
   2811 
   2812     BTM_TRACE_DEBUG1 ("btm_sec_dev_reset sec mode: %d", btm_cb.security_mode);
   2813 }
   2814 
   2815 /*******************************************************************************
   2816 **
   2817 ** Function         btm_sec_abort_access_req
   2818 **
   2819 ** Description      This function is called by the L2CAP or RFCOMM to abort
   2820 **                  the pending operation.
   2821 **
   2822 ** Parameters:      bd_addr       - Address of the peer device
   2823 **
   2824 ** Returns          void
   2825 **
   2826 *******************************************************************************/
   2827 void btm_sec_abort_access_req (BD_ADDR bd_addr)
   2828 {
   2829     tBTM_SEC_DEV_REC  *p_dev_rec = btm_find_dev (bd_addr);
   2830 
   2831     if (!p_dev_rec)
   2832         return;
   2833 
   2834     if (btm_cb.api.p_abort_callback)
   2835         (*btm_cb.api.p_abort_callback)(bd_addr, p_dev_rec->dev_class, p_dev_rec->sec_bd_name);
   2836 
   2837     if ((p_dev_rec->sec_state != BTM_SEC_STATE_AUTHORIZING)
   2838         && (p_dev_rec->sec_state != BTM_SEC_STATE_AUTHENTICATING))
   2839         return;
   2840 
   2841     p_dev_rec->sec_state  = BTM_SEC_STATE_IDLE;
   2842     p_dev_rec->p_callback = NULL;
   2843 }
   2844 
   2845 /*******************************************************************************
   2846 **
   2847 ** Function         btm_sec_dd_create_conn
   2848 **
   2849 ** Description      This function is called to create the ACL connection for
   2850 **                  the dedicated boding process
   2851 **
   2852 ** Returns          void
   2853 **
   2854 *******************************************************************************/
   2855 static tBTM_STATUS btm_sec_dd_create_conn (tBTM_SEC_DEV_REC *p_dev_rec)
   2856 {
   2857     tL2C_LCB         *p_lcb;
   2858 
   2859     /* Make sure an L2cap link control block is available */
   2860     if ((p_lcb = l2cu_allocate_lcb (p_dev_rec->bd_addr, TRUE)) == NULL)
   2861     {
   2862         BTM_TRACE_WARNING6 ("Security Manager: failed allocate LCB [%02x%02x%02x%02x%02x%02x]",
   2863                             p_dev_rec->bd_addr[0], p_dev_rec->bd_addr[1], p_dev_rec->bd_addr[2],
   2864                             p_dev_rec->bd_addr[3], p_dev_rec->bd_addr[4], p_dev_rec->bd_addr[5]);
   2865 
   2866         return(BTM_NO_RESOURCES);
   2867     }
   2868 
   2869     /* set up the control block to indicated dedicated bonding */
   2870     btm_cb.pairing_flags |= BTM_PAIR_FLAGS_DISC_WHEN_DONE;
   2871 
   2872     if (l2cu_create_conn(p_lcb) == FALSE)
   2873     {
   2874         BTM_TRACE_WARNING6 ("Security Manager: failed create  [%02x%02x%02x%02x%02x%02x]",
   2875                             p_dev_rec->bd_addr[0], p_dev_rec->bd_addr[1], p_dev_rec->bd_addr[2],
   2876                             p_dev_rec->bd_addr[3], p_dev_rec->bd_addr[4], p_dev_rec->bd_addr[5]);
   2877 
   2878         l2cu_release_lcb(p_lcb);
   2879         return(BTM_NO_RESOURCES);
   2880     }
   2881 
   2882 #if (defined(BTM_BUSY_LEVEL_CHANGE_INCLUDED) && BTM_BUSY_LEVEL_CHANGE_INCLUDED == TRUE)
   2883     btm_acl_update_busy_level (BTM_BLI_PAGE_EVT);
   2884 #endif
   2885 
   2886     BTM_TRACE_DEBUG6 ("Security Manager: btm_sec_dd_create_conn [%02x%02x%02x%02x%02x%02x]",
   2887                       p_dev_rec->bd_addr[0], p_dev_rec->bd_addr[1], p_dev_rec->bd_addr[2],
   2888                       p_dev_rec->bd_addr[3], p_dev_rec->bd_addr[4], p_dev_rec->bd_addr[5]);
   2889 
   2890     btm_sec_change_pairing_state (BTM_PAIR_STATE_WAIT_PIN_REQ);
   2891 
   2892     return(BTM_CMD_STARTED);
   2893 }
   2894 
   2895 /*******************************************************************************
   2896 **
   2897 ** Function         btm_sec_rmt_name_request_complete
   2898 **
   2899 ** Description      This function is called when remote name was obtained from
   2900 **                  the peer device
   2901 **
   2902 ** Returns          void
   2903 **
   2904 *******************************************************************************/
   2905 void btm_sec_rmt_name_request_complete (UINT8 *p_bd_addr, UINT8 *p_bd_name, UINT8 status)
   2906 {
   2907     tBTM_SEC_DEV_REC *p_dev_rec;
   2908     int              i;
   2909     DEV_CLASS        dev_class;
   2910     UINT8            old_sec_state;
   2911 
   2912     BTM_TRACE_EVENT0 ("btm_sec_rmt_name_request_complete");
   2913     if (((p_bd_addr == NULL) && !BTM_ACL_IS_CONNECTED(btm_cb.connecting_bda))
   2914         || ((p_bd_addr != NULL) && !BTM_ACL_IS_CONNECTED(p_bd_addr)))
   2915     {
   2916         btm_acl_resubmit_page();
   2917     }
   2918 
   2919     /* If remote name request failed, p_bd_addr is null and we need to search */
   2920     /* based on state assuming that we are doing 1 at a time */
   2921     if (p_bd_addr)
   2922         p_dev_rec = btm_find_dev (p_bd_addr);
   2923     else
   2924     {
   2925         p_dev_rec = &btm_cb.sec_dev_rec[0];
   2926 
   2927         for (i = 0; i < BTM_SEC_MAX_DEVICE_RECORDS; i++, p_dev_rec++)
   2928         {
   2929             if ((p_dev_rec->sec_flags & BTM_SEC_IN_USE)
   2930                 && (p_dev_rec->sec_state == BTM_SEC_STATE_GETTING_NAME))
   2931             {
   2932                 p_bd_addr = p_dev_rec->bd_addr;
   2933                 break;
   2934             }
   2935         }
   2936 
   2937         if (i == BTM_SEC_MAX_DEVICE_RECORDS)
   2938             p_dev_rec = NULL;
   2939     }
   2940 
   2941 
   2942     /* Commenting out trace due to obf/compilation problems.
   2943     */
   2944 #if (BT_USE_TRACES == TRUE)
   2945     if (!p_bd_name)
   2946         p_bd_name = (UINT8 *)"";
   2947 
   2948     if (p_dev_rec)
   2949     {
   2950         BTM_TRACE_EVENT5 ("Security Manager: rmt_name_complete PairState: %s  RemName: %s  status: %d State:%d  p_dev_rec: 0x%08x ",
   2951                           btm_pair_state_descr (btm_cb.pairing_state), p_bd_name,
   2952                           status, p_dev_rec->sec_state, p_dev_rec);
   2953     }
   2954     else
   2955     {
   2956         BTM_TRACE_EVENT3 ("Security Manager: rmt_name_complete PairState: %s  RemName: %s  status: %d",
   2957                           btm_pair_state_descr (btm_cb.pairing_state), p_bd_name,
   2958                           status);
   2959     }
   2960 #endif
   2961 
   2962     if (p_dev_rec)
   2963     {
   2964         old_sec_state = p_dev_rec->sec_state;
   2965         if (status == HCI_SUCCESS)
   2966         {
   2967             BCM_STRNCPY_S ((char *)p_dev_rec->sec_bd_name, sizeof (p_dev_rec->sec_bd_name), (char *)p_bd_name, BTM_MAX_REM_BD_NAME_LEN);
   2968             p_dev_rec->sec_flags |= BTM_SEC_NAME_KNOWN;
   2969             BTM_TRACE_EVENT1 ("setting BTM_SEC_NAME_KNOWN sec_flags:0x%x", p_dev_rec->sec_flags);
   2970         }
   2971         else
   2972         {
   2973             /* Notify all clients waiting for name to be resolved even if it failed so clients can continue */
   2974             p_dev_rec->sec_bd_name[0] = 0;
   2975         }
   2976 
   2977         if (p_dev_rec->sec_state == BTM_SEC_STATE_GETTING_NAME)
   2978             p_dev_rec->sec_state = BTM_SEC_STATE_IDLE;
   2979 
   2980         /* Notify all clients waiting for name to be resolved */
   2981         for (i = 0;i < BTM_SEC_MAX_RMT_NAME_CALLBACKS; i++)
   2982         {
   2983             if (btm_cb.p_rmt_name_callback[i])
   2984                 (*btm_cb.p_rmt_name_callback[i])(p_bd_addr, p_dev_rec->dev_class,
   2985                                                  p_dev_rec->sec_bd_name);
   2986         }
   2987     }
   2988     else
   2989     {
   2990         dev_class[0] = 0;
   2991         dev_class[1] = 0;
   2992         dev_class[2] = 0;
   2993 
   2994         /* Notify all clients waiting for name to be resolved even if not found so clients can continue */
   2995         for (i = 0;i < BTM_SEC_MAX_RMT_NAME_CALLBACKS; i++)
   2996         {
   2997             if (btm_cb.p_rmt_name_callback[i])
   2998                 (*btm_cb.p_rmt_name_callback[i])(p_bd_addr, dev_class, (UINT8 *)"");
   2999         }
   3000 
   3001         return;
   3002     }
   3003 
   3004     /* If we were delaying asking UI for a PIN because name was not resolved, ask now */
   3005     if ( (btm_cb.pairing_state == BTM_PAIR_STATE_WAIT_LOCAL_PIN) && p_bd_addr
   3006          &&  (memcmp (btm_cb.pairing_bda, p_bd_addr, BD_ADDR_LEN) == 0) )
   3007     {
   3008         BTM_TRACE_EVENT2 ("btm_sec_rmt_name_request_complete() delayed pin now being requested flags:0x%x, (p_pin_callback=0x%p)", btm_cb.pairing_flags, btm_cb.api.p_pin_callback);
   3009 
   3010         if (((btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD) == 0) &&
   3011             ((btm_cb.pairing_flags & BTM_PAIR_FLAGS_PIN_REQD) == 0) &&
   3012             btm_cb.api.p_pin_callback)
   3013         {
   3014             BTM_TRACE_EVENT0 ("btm_sec_rmt_name_request_complete() calling pin_callback");
   3015             btm_cb.pairing_flags |= BTM_PAIR_FLAGS_PIN_REQD;
   3016             (*btm_cb.api.p_pin_callback) (p_dev_rec->bd_addr, p_dev_rec->dev_class, p_bd_name);
   3017         }
   3018 
   3019         /* Set the same state again to force the timer to be restarted */
   3020         btm_sec_change_pairing_state (BTM_PAIR_STATE_WAIT_LOCAL_PIN);
   3021         return;
   3022     }
   3023 
   3024     /* Check if we were delaying bonding because name was not resolved */
   3025     if ( btm_cb.pairing_state == BTM_PAIR_STATE_GET_REM_NAME)
   3026     {
   3027         if (p_bd_addr && memcmp (btm_cb.pairing_bda, p_bd_addr, BD_ADDR_LEN) == 0)
   3028         {
   3029             BTM_TRACE_EVENT2 ("btm_sec_rmt_name_request_complete() continue bonding sm4: 0x%04x, status:0x%x", p_dev_rec->sm4, status);
   3030             if(btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_CANCEL_DD)
   3031             {
   3032                 btm_sec_bond_cancel_complete();
   3033                 return;
   3034             }
   3035 
   3036             if (status != HCI_SUCCESS)
   3037             {
   3038                 btm_sec_change_pairing_state (BTM_PAIR_STATE_IDLE);
   3039 
   3040                 (*btm_cb.api.p_auth_complete_callback) (p_dev_rec->bd_addr,  p_dev_rec->dev_class,
   3041                                                         p_dev_rec->sec_bd_name, status);
   3042                 return;
   3043             }
   3044 
   3045             /* if peer is very old legacy devices, HCI_RMT_HOST_SUP_FEAT_NOTIFY_EVT is not reported */
   3046             if (BTM_SEC_IS_SM4_UNKNOWN(p_dev_rec->sm4))
   3047             {
   3048                 /* set the KNOWN flag only if BTM_PAIR_FLAGS_REJECTED_CONNECT is not set.
   3049                  * If it is set, there may be a race condition */
   3050 				BTM_TRACE_EVENT1 ("btm_sec_rmt_name_request_complete  IS_SM4_UNKNOWN Flags:0x%04x", btm_cb.pairing_flags);
   3051                 if ((btm_cb.pairing_flags & BTM_PAIR_FLAGS_REJECTED_CONNECT) == 0)
   3052                 {
   3053                     p_dev_rec->sm4 |= BTM_SM4_KNOWN;
   3054                 }
   3055             }
   3056 
   3057             /* BT 2.1 or carkit, bring up the connection to force the peer to request PIN.
   3058             ** Else prefetch (btm_sec_check_prefetch_pin will do the prefetching if needed)
   3059             */
   3060             if ((p_dev_rec->sm4 != BTM_SM4_KNOWN) || !btm_sec_check_prefetch_pin(p_dev_rec))
   3061             {
   3062                 /* if we rejected incoming connection request, we have to wait HCI_Connection_Complete event */
   3063                 /*  before originating  */
   3064                 if (btm_cb.pairing_flags & BTM_PAIR_FLAGS_REJECTED_CONNECT)
   3065                 {
   3066                     BTM_TRACE_WARNING0 ("btm_sec_rmt_name_request_complete: waiting HCI_Connection_Complete after rejecting connection");
   3067                 }
   3068                 /* Both we and the peer are 2.1 - continue to create connection */
   3069                 else if (btm_sec_dd_create_conn(p_dev_rec) != BTM_CMD_STARTED)
   3070                 {
   3071                     BTM_TRACE_WARNING0 ("btm_sec_rmt_name_request_complete: failed to start connection");
   3072 
   3073                     btm_sec_change_pairing_state (BTM_PAIR_STATE_IDLE);
   3074 
   3075                     (*btm_cb.api.p_auth_complete_callback) (p_dev_rec->bd_addr,  p_dev_rec->dev_class,
   3076                                                             p_dev_rec->sec_bd_name, HCI_ERR_MEMORY_FULL);
   3077                 }
   3078             }
   3079             return;
   3080         }
   3081         else
   3082         {
   3083             BTM_TRACE_WARNING0 ("btm_sec_rmt_name_request_complete: wrong BDA, retry with pairing BDA");
   3084 
   3085             BTM_ReadRemoteDeviceName (btm_cb.pairing_bda, NULL);
   3086             return;
   3087         }
   3088     }
   3089 
   3090     /* check if we were delaying link_key_callback because name was not resolved */
   3091     if (p_dev_rec->link_key_not_sent)
   3092     {
   3093         /* If HCI connection complete has not arrived, wait for it */
   3094         if (p_dev_rec->hci_handle == BTM_SEC_INVALID_HANDLE)
   3095             return;
   3096 
   3097         p_dev_rec->link_key_not_sent = FALSE;
   3098         btm_send_link_key_notif(p_dev_rec);
   3099 
   3100         /* If its not us who perform authentication, we should tell stackserver */
   3101         /* that some authentication has been completed                          */
   3102         /* This is required when different entities receive link notification and auth complete */
   3103         if (!(p_dev_rec->security_required & BTM_SEC_OUT_AUTHENTICATE))
   3104         {
   3105             if (btm_cb.api.p_auth_complete_callback)
   3106                 (*btm_cb.api.p_auth_complete_callback) (p_dev_rec->bd_addr,
   3107                                                         p_dev_rec->dev_class,
   3108                                                         p_dev_rec->sec_bd_name, HCI_SUCCESS);
   3109 
   3110         }
   3111     }
   3112 
   3113     /* If this is a bonding procedure can disconnect the link now */
   3114     if ((btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD)
   3115         && (p_dev_rec->sec_flags & BTM_SEC_AUTHENTICATED))
   3116     {
   3117         BTM_TRACE_WARNING0 ("btm_sec_rmt_name_request_complete (none/ce)");
   3118         p_dev_rec->security_required &= ~(BTM_SEC_OUT_AUTHENTICATE);
   3119         l2cu_start_post_bond_timer(p_dev_rec->hci_handle);
   3120         return;
   3121     }
   3122 
   3123     if (old_sec_state != BTM_SEC_STATE_GETTING_NAME)
   3124         return;
   3125 
   3126     /* If get name failed, notify the waiting layer */
   3127     if (status != HCI_SUCCESS)
   3128     {
   3129         btm_sec_dev_rec_cback_event  (p_dev_rec, BTM_ERR_PROCESSING);
   3130         return;
   3131     }
   3132 
   3133     if (p_dev_rec->sm4 & BTM_SM4_REQ_PEND)
   3134     {
   3135         BTM_TRACE_EVENT0 ("waiting for remote features!!");
   3136         return;
   3137     }
   3138 
   3139     /* Remote Name succeeded, execute the next security procedure, if any */
   3140     status = (UINT8)btm_sec_execute_procedure (p_dev_rec);
   3141 
   3142     /* If result is pending reply from the user or from the device is pending */
   3143     if (status == BTM_CMD_STARTED)
   3144         return;
   3145 
   3146     /* There is no next procedure or start of procedure failed, notify the waiting layer */
   3147     btm_sec_dev_rec_cback_event  (p_dev_rec, status);
   3148 }
   3149 
   3150 /*******************************************************************************
   3151 **
   3152 ** Function         btm_sec_rmt_host_support_feat_evt
   3153 **
   3154 ** Description      This function is called when the
   3155 **                  HCI_RMT_HOST_SUP_FEAT_NOTIFY_EVT is received
   3156 **
   3157 ** Returns          void
   3158 **
   3159 *******************************************************************************/
   3160 void btm_sec_rmt_host_support_feat_evt (UINT8 *p)
   3161 {
   3162     tBTM_SEC_DEV_REC *p_dev_rec;
   3163     BD_ADDR         bd_addr;        /* peer address */
   3164     BD_FEATURES     features;
   3165 
   3166     STREAM_TO_BDADDR (bd_addr, p);
   3167     p_dev_rec = btm_find_or_alloc_dev (bd_addr);
   3168 
   3169     BTM_TRACE_EVENT2 ("btm_sec_rmt_host_support_feat_evt  sm4: 0x%x  p[0]: 0x%x", p_dev_rec->sm4, p[0]);
   3170 
   3171     if (BTM_SEC_IS_SM4_UNKNOWN(p_dev_rec->sm4))
   3172     {
   3173         p_dev_rec->sm4 = BTM_SM4_KNOWN;
   3174         STREAM_TO_ARRAY(features, p, HCI_FEATURE_BYTES_PER_PAGE);
   3175         if (HCI_SSP_HOST_SUPPORTED(features))
   3176         {
   3177             p_dev_rec->sm4 = BTM_SM4_TRUE;
   3178         }
   3179         BTM_TRACE_EVENT2 ("btm_sec_rmt_host_support_feat_evt sm4: 0x%x features[0]: 0x%x", p_dev_rec->sm4, features[0]);
   3180     }
   3181 }
   3182 
   3183 /*******************************************************************************
   3184 **
   3185 ** Function         btm_io_capabilities_req
   3186 **
   3187 ** Description      This function is called when LM request for the IO
   3188 **                  capability of the local device and
   3189 **                  if the OOB data is present for the device in the event
   3190 **
   3191 ** Returns          void
   3192 **
   3193 *******************************************************************************/
   3194 void btm_io_capabilities_req (UINT8 *p)
   3195 {
   3196     tBTM_SP_IO_REQ  evt_data;
   3197     UINT8           err_code = 0;
   3198     tBTM_SEC_DEV_REC *p_dev_rec;
   3199     BOOLEAN         is_orig = TRUE;
   3200     UINT8           callback_rc = BTM_SUCCESS;
   3201 
   3202     STREAM_TO_BDADDR (evt_data.bd_addr, p);
   3203 
   3204     /* setup the default response according to compile options */
   3205     /* assume that the local IO capability does not change
   3206      * loc_io_caps is initialized with the default value */
   3207     evt_data.io_cap = btm_cb.devcb.loc_io_caps;
   3208     evt_data.oob_data = BTM_OOB_NONE;
   3209     evt_data.auth_req = BTM_DEFAULT_AUTH_REQ;
   3210 
   3211     BTM_TRACE_EVENT1 ("btm_io_capabilities_req() State: %s", btm_pair_state_descr(btm_cb.pairing_state));
   3212 
   3213     p_dev_rec = btm_find_or_alloc_dev (evt_data.bd_addr);
   3214     p_dev_rec->sm4 |= BTM_SM4_TRUE;
   3215 
   3216     BTM_TRACE_EVENT3 ("btm_io_capabilities_req() State: %s  Flags: 0x%04x  p_cur_service: 0x%08x",
   3217                       btm_pair_state_descr(btm_cb.pairing_state), btm_cb.pairing_flags, p_dev_rec->p_cur_service);
   3218 
   3219     if (btm_cb.pairing_state != BTM_PAIR_STATE_IDLE)
   3220     {
   3221         if (btm_cb.pairing_state == BTM_PAIR_STATE_INCOMING_SSP)
   3222         {
   3223             /* received IO capability response already-> not the originator of SSP */
   3224             is_orig = FALSE;
   3225 
   3226             if (btm_cb.pairing_flags & BTM_PAIR_FLAGS_PEER_STARTED_DD)
   3227                 evt_data.auth_req = BTM_DEFAULT_DD_AUTH_REQ;
   3228         }
   3229         /* security is already in progress */
   3230         else if (btm_cb.pairing_state == BTM_PAIR_STATE_WAIT_PIN_REQ)
   3231         {
   3232 /* coverity[uninit_use_in_call]
   3233 Event uninit_use_in_call: Using uninitialized element of array "evt_data.bd_addr" in call to function "memcmp"
   3234 False-positive: evt_data.bd_addr is set at the beginning with:     STREAM_TO_BDADDR (evt_data.bd_addr, p);
   3235 */
   3236             if (memcmp (evt_data.bd_addr, btm_cb.pairing_bda, BD_ADDR_LEN))
   3237             {
   3238                 /* and it's not the device in bonding -> reject it */
   3239                 err_code = HCI_ERR_HOST_BUSY_PAIRING;
   3240             }
   3241             else
   3242             {
   3243                 /* local device initiated dedicated bonding */
   3244                 evt_data.auth_req = BTM_DEFAULT_DD_AUTH_REQ;
   3245             }
   3246         }
   3247         else
   3248         {
   3249             err_code = HCI_ERR_HOST_BUSY_PAIRING;
   3250         }
   3251     }
   3252 
   3253     /* paring is not allowed */
   3254     if (btm_cb.pairing_disabled)
   3255         err_code = HCI_ERR_PAIRING_NOT_ALLOWED;
   3256 
   3257     if (err_code != 0)
   3258     {
   3259 /* coverity[uninit_use_in_call]
   3260 Event uninit_use_in_call: Using uninitialized element of array "evt_data.bd_addr" in call to function "memcmp"
   3261 False-positive: evt_data.bd_addr is set at the beginning with:     STREAM_TO_BDADDR (evt_data.bd_addr, p);
   3262 */
   3263         btsnd_hcic_io_cap_req_neg_reply(evt_data.bd_addr, err_code);
   3264         return;
   3265     }
   3266 
   3267     evt_data.is_orig = is_orig;
   3268 
   3269     if (is_orig)
   3270     {
   3271         /* local device initiated the pairing non-bonding -> use p_cur_service */
   3272         if (!(btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD) &&
   3273             p_dev_rec->p_cur_service &&
   3274             (p_dev_rec->p_cur_service->security_flags & BTM_SEC_OUT_AUTHENTICATE))
   3275         {
   3276             evt_data.auth_req = (p_dev_rec->p_cur_service->security_flags & BTM_SEC_OUT_MITM) ? BTM_AUTH_SP_YES : BTM_AUTH_SP_NO;
   3277         }
   3278     }
   3279 
   3280     /* Notify L2CAP to increase timeout */
   3281     l2c_pin_code_request (evt_data.bd_addr);
   3282 
   3283     memcpy (btm_cb.pairing_bda, evt_data.bd_addr, BD_ADDR_LEN);
   3284 
   3285 /* coverity[uninit_use_in_call]
   3286 Event uninit_use_in_call: Using uninitialized element of array "evt_data.bd_addr" in call to function "memcmp"
   3287 False-positive: False-positive: evt_data.bd_addr is set at the beginning with:     STREAM_TO_BDADDR (evt_data.bd_addr, p);
   3288 */
   3289     if (!memcmp (evt_data.bd_addr, btm_cb.connecting_bda, BD_ADDR_LEN))
   3290         memcpy (p_dev_rec->dev_class, btm_cb.connecting_dc, DEV_CLASS_LEN);
   3291 
   3292     btm_sec_change_pairing_state (BTM_PAIR_STATE_WAIT_LOCAL_IOCAPS);
   3293 
   3294     callback_rc = BTM_SUCCESS;
   3295     if (p_dev_rec->sm4 & BTM_SM4_UPGRADE)
   3296     {
   3297         p_dev_rec->sm4 &= ~BTM_SM4_UPGRADE;
   3298 
   3299         /* link key upgrade: always use SPGB_YES - assuming we want to save the link key */
   3300         evt_data.auth_req = BTM_AUTH_SPGB_YES;
   3301     }
   3302     else if (btm_cb.api.p_sp_callback)
   3303     {
   3304         /* the callback function implementation may change the IO capability... */
   3305         callback_rc = (*btm_cb.api.p_sp_callback) (BTM_SP_IO_REQ_EVT, (tBTM_SP_EVT_DATA *)&evt_data);
   3306     }
   3307 
   3308 #if BTM_OOB_INCLUDED == TRUE
   3309     if ((callback_rc == BTM_SUCCESS) || (BTM_OOB_UNKNOWN != evt_data.oob_data))
   3310 #else
   3311     if (callback_rc == BTM_SUCCESS)
   3312 #endif
   3313     {
   3314         if ((btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD))
   3315         {
   3316             evt_data.auth_req = (BTM_AUTH_DD_BOND | (evt_data.auth_req & BTM_AUTH_YN_BIT));
   3317         }
   3318 
   3319         /* if the user does not indicate "reply later" by setting the oob_data to unknown
   3320          * send the response right now. Save the current IO capability in the control block */
   3321         btm_cb.devcb.loc_auth_req   = evt_data.auth_req;
   3322         btm_cb.devcb.loc_io_caps    = evt_data.io_cap;
   3323 
   3324         BTM_TRACE_EVENT4 ("btm_io_capabilities_req: State: %s  IO_CAP:%d oob_data:%d auth_req:%d",
   3325                           btm_pair_state_descr(btm_cb.pairing_state), evt_data.io_cap,
   3326                           evt_data.oob_data, evt_data.auth_req);
   3327 
   3328         btsnd_hcic_io_cap_req_reply(evt_data.bd_addr, evt_data.io_cap,
   3329                                     evt_data.oob_data, evt_data.auth_req);
   3330     }
   3331 }
   3332 
   3333 /*******************************************************************************
   3334 **
   3335 ** Function         btm_io_capabilities_rsp
   3336 **
   3337 ** Description      This function is called when the IO capability of the
   3338 **                  specified device is received
   3339 **
   3340 ** Returns          void
   3341 **
   3342 *******************************************************************************/
   3343 void btm_io_capabilities_rsp (UINT8 *p)
   3344 {
   3345     tBTM_SEC_DEV_REC *p_dev_rec;
   3346     tBTM_SP_IO_RSP evt_data;
   3347 
   3348     STREAM_TO_BDADDR (evt_data.bd_addr, p);
   3349     STREAM_TO_UINT8 (evt_data.io_cap, p);
   3350     STREAM_TO_UINT8 (evt_data.oob_data, p);
   3351     STREAM_TO_UINT8 (evt_data.auth_req, p);
   3352 
   3353     /* Allocate a new device record or reuse the oldest one */
   3354     p_dev_rec = btm_find_or_alloc_dev (evt_data.bd_addr);
   3355 
   3356     /* If no security is in progress, this indicates incoming security */
   3357     if (btm_cb.pairing_state == BTM_PAIR_STATE_IDLE)
   3358     {
   3359         memcpy (btm_cb.pairing_bda, evt_data.bd_addr, BD_ADDR_LEN);
   3360 
   3361         btm_sec_change_pairing_state (BTM_PAIR_STATE_INCOMING_SSP);
   3362 
   3363         /* Make sure we reset the trusted mask to help against attacks */
   3364         BTM_SEC_CLR_TRUSTED_DEVICE(p_dev_rec->trusted_mask);
   3365 
   3366         /* work around for FW bug */
   3367         btm_inq_stop_on_ssp();
   3368     }
   3369 
   3370     /* Notify L2CAP to increase timeout */
   3371     l2c_pin_code_request (evt_data.bd_addr);
   3372 
   3373     /* We must have a device record here.
   3374      * Use the connecting device's CoD for the connection */
   3375 /* coverity[uninit_use_in_call]
   3376 Event uninit_use_in_call: Using uninitialized element of array "evt_data.bd_addr" in call to function "memcmp"
   3377 FALSE-POSITIVE error from Coverity test-tool. evt_data.bd_addr is set at the beginning with:     STREAM_TO_BDADDR (evt_data.bd_addr, p);
   3378 */
   3379     if (!memcmp (evt_data.bd_addr, btm_cb.connecting_bda, BD_ADDR_LEN))
   3380         memcpy (p_dev_rec->dev_class, btm_cb.connecting_dc, DEV_CLASS_LEN);
   3381 
   3382     /* peer sets dedicated bonding bit and we did not initiate dedicated bonding */
   3383     if (btm_cb.pairing_state == BTM_PAIR_STATE_INCOMING_SSP /* peer initiated bonding */
   3384         && (evt_data.auth_req & BTM_AUTH_DD_BOND) )            /* and dedicated bonding bit is set */
   3385     {
   3386         btm_cb.pairing_flags |= BTM_PAIR_FLAGS_PEER_STARTED_DD;
   3387     }
   3388 
   3389     /* save the IO capability in the device record */
   3390     p_dev_rec->rmt_io_caps  = evt_data.io_cap;
   3391     p_dev_rec->rmt_auth_req = evt_data.auth_req;
   3392 
   3393     if (btm_cb.api.p_sp_callback)
   3394         (*btm_cb.api.p_sp_callback) (BTM_SP_IO_RSP_EVT, (tBTM_SP_EVT_DATA *)&evt_data);
   3395 }
   3396 
   3397 /*******************************************************************************
   3398 **
   3399 ** Function         btm_proc_sp_req_evt
   3400 **
   3401 ** Description      This function is called to process/report
   3402 **                  HCI_USER_CONFIRMATION_REQUEST_EVT
   3403 **                  or HCI_USER_PASSKEY_REQUEST_EVT
   3404 **                  or HCI_USER_PASSKEY_NOTIFY_EVT
   3405 **
   3406 ** Returns          void
   3407 **
   3408 *******************************************************************************/
   3409 void btm_proc_sp_req_evt (tBTM_SP_EVT event, UINT8 *p)
   3410 {
   3411     tBTM_STATUS status = BTM_ERR_PROCESSING;
   3412     tBTM_SP_EVT_DATA evt_data;
   3413     UINT8               *p_bda = evt_data.cfm_req.bd_addr;
   3414     tBTM_SEC_DEV_REC *p_dev_rec;
   3415 
   3416     /* All events start with bd_addr */
   3417     STREAM_TO_BDADDR (p_bda, p);
   3418 
   3419     BTM_TRACE_EVENT4 ("btm_proc_sp_req_evt() BDA: %08x%04x event: 0x%x, State: %s",
   3420                       (p_bda[0]<<24) + (p_bda[1]<<16) + (p_bda[2]<<8) + p_bda[3], (p_bda[4] << 8) + p_bda[5],
   3421                       event, btm_pair_state_descr(btm_cb.pairing_state));
   3422 
   3423     if ( ((p_dev_rec = btm_find_dev (p_bda)) != NULL)
   3424          &&  (btm_cb.pairing_state != BTM_PAIR_STATE_IDLE)
   3425          &&  (memcmp (btm_cb.pairing_bda, p_bda, BD_ADDR_LEN) == 0) )
   3426     {
   3427         memcpy (evt_data.cfm_req.bd_addr, p_dev_rec->bd_addr, BD_ADDR_LEN);
   3428         memcpy (evt_data.cfm_req.dev_class, p_dev_rec->dev_class, DEV_CLASS_LEN);
   3429 
   3430         BCM_STRNCPY_S ((char *)evt_data.cfm_req.bd_name, sizeof(evt_data.cfm_req.bd_name), (char *)p_dev_rec->sec_bd_name, BTM_MAX_REM_BD_NAME_LEN);
   3431 
   3432         switch (event)
   3433         {
   3434             case BTM_SP_CFM_REQ_EVT:
   3435                 /* Numeric confirmation. Need user to conf the passkey */
   3436                 btm_sec_change_pairing_state (BTM_PAIR_STATE_WAIT_NUMERIC_CONFIRM);
   3437 
   3438                 /* The device record must be allocated in the "IO cap exchange" step */
   3439                 STREAM_TO_UINT32 (evt_data.cfm_req.num_val, p);
   3440 
   3441                 evt_data.cfm_req.just_works = TRUE;
   3442 
   3443                 /* process user confirm req in association with the auth_req param */
   3444 #if (BTM_LOCAL_IO_CAPS == BTM_IO_CAP_IO)
   3445                 if ( (p_dev_rec->rmt_io_caps == BTM_IO_CAP_IO)
   3446                      &&  (btm_cb.devcb.loc_io_caps == BTM_IO_CAP_IO)
   3447                      &&  ((p_dev_rec->rmt_auth_req & BTM_AUTH_SP_YES) || (btm_cb.devcb.loc_auth_req & BTM_AUTH_SP_YES)) )
   3448                 {
   3449                     /* Both devices are DisplayYesNo and one or both devices want to authenticate
   3450                        -> use authenticated link key */
   3451                     evt_data.cfm_req.just_works = FALSE;
   3452                 }
   3453 #endif
   3454                 BTM_TRACE_DEBUG5 ("btm_proc_sp_req_evt()  just_works:%d, io loc:%d, rmt:%d, auth loc:%d, rmt:%d",
   3455                                   evt_data.cfm_req.just_works, btm_cb.devcb.loc_io_caps, p_dev_rec->rmt_io_caps,
   3456                                   btm_cb.devcb.loc_auth_req, p_dev_rec->rmt_auth_req);
   3457 
   3458                 evt_data.cfm_req.loc_auth_req   = btm_cb.devcb.loc_auth_req;
   3459                 evt_data.cfm_req.rmt_auth_req   = p_dev_rec->rmt_auth_req;
   3460                 evt_data.cfm_req.loc_io_caps    = btm_cb.devcb.loc_io_caps;
   3461                 evt_data.cfm_req.rmt_io_caps    = p_dev_rec->rmt_io_caps;
   3462                 break;
   3463 
   3464             case BTM_SP_KEY_NOTIF_EVT:
   3465                 /* Passkey notification (other side is a keyboard) */
   3466                 STREAM_TO_UINT32 (evt_data.key_notif.passkey, p);
   3467 
   3468                 BTM_TRACE_DEBUG1 ("BTM_SP_KEY_NOTIF_EVT:  passkey: %u", evt_data.key_notif.passkey);
   3469 
   3470                 btm_sec_change_pairing_state (BTM_PAIR_STATE_WAIT_AUTH_COMPLETE);
   3471                 break;
   3472 
   3473 #if (BTM_LOCAL_IO_CAPS != BTM_IO_CAP_NONE)
   3474             case BTM_SP_KEY_REQ_EVT:
   3475                 /* HCI_USER_PASSKEY_REQUEST_EVT */
   3476                 btm_sec_change_pairing_state (BTM_PAIR_STATE_KEY_ENTRY);
   3477                 break;
   3478 #endif
   3479         }
   3480 
   3481         if (btm_cb.api.p_sp_callback)
   3482         {
   3483             status = (*btm_cb.api.p_sp_callback) (event, (tBTM_SP_EVT_DATA *)&evt_data);
   3484             if (status != BTM_NOT_AUTHORIZED)
   3485             {
   3486                 return;
   3487             }
   3488             /* else BTM_NOT_AUTHORIZED means when the app wants to reject the req right now */
   3489         }
   3490         else if ( (event == BTM_SP_CFM_REQ_EVT) && (evt_data.cfm_req.just_works == TRUE) )
   3491         {
   3492             /* automatically reply with just works if no sp_cback */
   3493             status = BTM_SUCCESS;
   3494         }
   3495 
   3496         if (event == BTM_SP_CFM_REQ_EVT)
   3497         {
   3498             BTM_TRACE_DEBUG1 ("calling BTM_ConfirmReqReply with status: %d", status);
   3499             BTM_ConfirmReqReply (status, p_bda);
   3500         }
   3501 #if (BTM_LOCAL_IO_CAPS != BTM_IO_CAP_NONE)
   3502         else if (event == BTM_SP_KEY_REQ_EVT)
   3503         {
   3504             BTM_PasskeyReqReply(status, p_bda, 0);
   3505         }
   3506 #endif
   3507         return;
   3508     }
   3509 
   3510     /* Something bad. we can only fail this connection */
   3511     btm_cb.acl_disc_reason = HCI_ERR_HOST_REJECT_SECURITY;
   3512 
   3513     if (BTM_SP_CFM_REQ_EVT == event)
   3514     {
   3515         btsnd_hcic_user_conf_reply (p_bda, FALSE);
   3516     }
   3517     else if (BTM_SP_KEY_NOTIF_EVT == event)
   3518     {
   3519         /* do nothing -> it very unlikely to happen.
   3520         This event is most likely to be received by a HID host when it first connects to a HID device.
   3521         Usually the Host initiated the connection in this case.
   3522         On Mobile platforms, if there's a security process happening,
   3523         the host probably can not initiate another connection.
   3524         BTW (PC) is another story.  */
   3525         if (NULL != (p_dev_rec = btm_find_dev (p_bda)) )
   3526         {
   3527             btm_sec_disconnect (p_dev_rec->hci_handle, HCI_ERR_AUTH_FAILURE);
   3528         }
   3529     }
   3530 #if (BTM_LOCAL_IO_CAPS != BTM_IO_CAP_NONE)
   3531     else
   3532     {
   3533         btsnd_hcic_user_passkey_neg_reply(p_bda);
   3534     }
   3535 #endif
   3536 }
   3537 
   3538 /*******************************************************************************
   3539 **
   3540 ** Function         btm_keypress_notif_evt
   3541 **
   3542 ** Description      This function is called when a key press notification is
   3543 **                  received
   3544 **
   3545 ** Returns          void
   3546 **
   3547 *******************************************************************************/
   3548 void  btm_keypress_notif_evt (UINT8 *p)
   3549 {
   3550     tBTM_SP_KEYPRESS    evt_data;
   3551     UINT8 *p_bda;
   3552 
   3553     /* parse & report BTM_SP_KEYPRESS_EVT */
   3554     if (btm_cb.api.p_sp_callback)
   3555     {
   3556         p_bda = evt_data.bd_addr;
   3557 
   3558         STREAM_TO_BDADDR (p_bda, p);
   3559         evt_data.notif_type = *p;
   3560 
   3561         (*btm_cb.api.p_sp_callback) (BTM_SP_KEYPRESS_EVT, (tBTM_SP_EVT_DATA *)&evt_data);
   3562     }
   3563 }
   3564 
   3565 /*******************************************************************************
   3566 **
   3567 ** Function         btm_simple_pair_complete
   3568 **
   3569 ** Description      This function is called when simple pairing process is
   3570 **                  complete
   3571 **
   3572 ** Returns          void
   3573 **
   3574 *******************************************************************************/
   3575 void btm_simple_pair_complete (UINT8 *p)
   3576 {
   3577     tBTM_SP_COMPLT  evt_data;
   3578     tBTM_SEC_DEV_REC *p_dev_rec;
   3579     UINT8           status;
   3580     BOOLEAN         disc = FALSE;
   3581 
   3582     status = *p++;
   3583     STREAM_TO_BDADDR (evt_data.bd_addr, p);
   3584 
   3585     if ((p_dev_rec = btm_find_dev (evt_data.bd_addr)) == NULL)
   3586     {
   3587         BTM_TRACE_ERROR2 ("btm_simple_pair_complete() with unknown BDA: %08x%04x",
   3588                           (evt_data.bd_addr[0]<<24) + (evt_data.bd_addr[1]<<16) + (evt_data.bd_addr[2]<<8) + evt_data.bd_addr[3],
   3589                           (evt_data.bd_addr[4] << 8) + evt_data.bd_addr[5]);
   3590         return;
   3591     }
   3592 
   3593     BTM_TRACE_EVENT3 ("btm_simple_pair_complete()  Pair State: %s  Status:%d  sec_state: %u",
   3594                       btm_pair_state_descr(btm_cb.pairing_state),  status, p_dev_rec->sec_state);
   3595 
   3596     evt_data.status = BTM_ERR_PROCESSING;
   3597     if (status == HCI_SUCCESS)
   3598     {
   3599         evt_data.status = BTM_SUCCESS;
   3600         p_dev_rec->sec_flags |= BTM_SEC_AUTHENTICATED;
   3601     }
   3602     else
   3603     {
   3604         if (status == HCI_ERR_PAIRING_NOT_ALLOWED)
   3605         {
   3606             /* The test spec wants the peer device to get this failure code. */
   3607             btm_sec_change_pairing_state (BTM_PAIR_STATE_WAIT_DISCONNECT);
   3608 
   3609             /* Change the timer to 1 second */
   3610             btu_start_timer (&btm_cb.pairing_tle, BTU_TTYPE_USER_FUNC, BT_1SEC_TIMEOUT);
   3611         }
   3612         else if (memcmp (btm_cb.pairing_bda, evt_data.bd_addr, BD_ADDR_LEN) == 0)
   3613         {
   3614             /* stop the timer */
   3615             btu_stop_timer (&btm_cb.pairing_tle);
   3616 
   3617             if (p_dev_rec->sec_state != BTM_SEC_STATE_AUTHENTICATING)
   3618             {
   3619                 /* the initiating side: will receive auth complete event. disconnect ACL at that time */
   3620                 disc = TRUE;
   3621             }
   3622         }
   3623         else
   3624             disc = TRUE;
   3625     }
   3626 
   3627     /* Let the pairing state stay active, p_auth_complete_callback will report the failure */
   3628     memcpy (evt_data.bd_addr, p_dev_rec->bd_addr, BD_ADDR_LEN);
   3629     memcpy (evt_data.dev_class, p_dev_rec->dev_class, DEV_CLASS_LEN);
   3630 
   3631     if (btm_cb.api.p_sp_callback)
   3632         (*btm_cb.api.p_sp_callback) (BTM_SP_COMPLT_EVT, (tBTM_SP_EVT_DATA *)&evt_data);
   3633 
   3634     if (disc)
   3635     {
   3636         /* simple pairing failed */
   3637         btm_sec_send_hci_disconnect (p_dev_rec, HCI_ERR_AUTH_FAILURE);
   3638     }
   3639 }
   3640 
   3641 #if BTM_OOB_INCLUDED == TRUE
   3642 /*******************************************************************************
   3643 **
   3644 ** Function         btm_rem_oob_req
   3645 **
   3646 ** Description      This function is called to process/report
   3647 **                  HCI_REMOTE_OOB_DATA_REQUEST_EVT
   3648 **
   3649 ** Returns          void
   3650 **
   3651 *******************************************************************************/
   3652 void btm_rem_oob_req (UINT8 *p)
   3653 {
   3654     UINT8 *p_bda;
   3655     tBTM_SP_RMT_OOB  evt_data;
   3656     tBTM_SEC_DEV_REC *p_dev_rec;
   3657     BT_OCTET16      c;
   3658     BT_OCTET16      r;
   3659 
   3660     p_bda = evt_data.bd_addr;
   3661 
   3662     STREAM_TO_BDADDR (p_bda, p);
   3663 
   3664     BTM_TRACE_EVENT6 ("btm_rem_oob_req() BDA: %02x:%02x:%02x:%02x:%02x:%02x",
   3665                       p_bda[0], p_bda[1], p_bda[2], p_bda[3], p_bda[4], p_bda[5]);
   3666 
   3667     if ( (NULL != (p_dev_rec = btm_find_dev (p_bda))) &&
   3668          btm_cb.api.p_sp_callback)
   3669     {
   3670         memcpy (evt_data.bd_addr, p_dev_rec->bd_addr, BD_ADDR_LEN);
   3671         memcpy (evt_data.dev_class, p_dev_rec->dev_class, DEV_CLASS_LEN);
   3672         BCM_STRNCPY_S((char *)evt_data.bd_name, sizeof(evt_data.bd_name), (char *)p_dev_rec->sec_bd_name, BTM_MAX_REM_BD_NAME_LEN+1);
   3673         evt_data.bd_name[BTM_MAX_REM_BD_NAME_LEN] = 0;
   3674 
   3675         btm_sec_change_pairing_state(BTM_PAIR_STATE_WAIT_LOCAL_OOB_RSP);
   3676         if ((*btm_cb.api.p_sp_callback) (BTM_SP_RMT_OOB_EVT, (tBTM_SP_EVT_DATA *)&evt_data) == BTM_NOT_AUTHORIZED)
   3677         {
   3678             BTM_RemoteOobDataReply(TRUE, p_bda, c, r);
   3679         }
   3680         return;
   3681     }
   3682 
   3683     /* something bad. we can only fail this connection */
   3684     btm_cb.acl_disc_reason = HCI_ERR_HOST_REJECT_SECURITY;
   3685     btsnd_hcic_rem_oob_neg_reply (p_bda);
   3686 }
   3687 
   3688 /*******************************************************************************
   3689 **
   3690 ** Function         btm_read_local_oob_complete
   3691 **
   3692 ** Description      This function is called when read local oob data is
   3693 **                  completed by the LM
   3694 **
   3695 ** Returns          void
   3696 **
   3697 *******************************************************************************/
   3698 void btm_read_local_oob_complete (UINT8 *p)
   3699 {
   3700     tBTM_SP_LOC_OOB evt_data;
   3701     UINT8           status = *p++;
   3702 
   3703     BTM_TRACE_EVENT1 ("btm_read_local_oob_complete:%d", status);
   3704     if (status == HCI_SUCCESS)
   3705     {
   3706         evt_data.status = BTM_SUCCESS;
   3707         STREAM_TO_ARRAY16(evt_data.c, p);
   3708         STREAM_TO_ARRAY16(evt_data.r, p);
   3709     }
   3710     else
   3711         evt_data.status = BTM_ERR_PROCESSING;
   3712 
   3713     if (btm_cb.api.p_sp_callback)
   3714         (*btm_cb.api.p_sp_callback) (BTM_SP_LOC_OOB_EVT, (tBTM_SP_EVT_DATA *)&evt_data);
   3715 }
   3716 #endif /* BTM_OOB_INCLUDED */
   3717 
   3718 /*******************************************************************************
   3719 **
   3720 ** Function         btm_sec_auth_collision
   3721 **
   3722 ** Description      This function is called when authentication or encryption
   3723 **                  needs to be retried at a later time.
   3724 **
   3725 ** Returns          void
   3726 **
   3727 *******************************************************************************/
   3728 static void btm_sec_auth_collision (UINT16 handle)
   3729 {
   3730     tBTM_SEC_DEV_REC *p_dev_rec;
   3731 
   3732     if (!btm_cb.collision_start_time)
   3733         btm_cb.collision_start_time = GKI_get_tick_count ();
   3734 
   3735     if ((GKI_get_tick_count () - btm_cb.collision_start_time) < btm_cb.max_collision_delay)
   3736     {
   3737         if (handle == BTM_SEC_INVALID_HANDLE)
   3738         {
   3739             if ((p_dev_rec = btm_sec_find_dev_by_sec_state (BTM_SEC_STATE_AUTHENTICATING)) == NULL)
   3740                 p_dev_rec = btm_sec_find_dev_by_sec_state (BTM_SEC_STATE_ENCRYPTING);
   3741         }
   3742         else
   3743             p_dev_rec = btm_find_dev_by_handle (handle);
   3744 
   3745         if (p_dev_rec != NULL)
   3746         {
   3747             BTM_TRACE_DEBUG1 ("btm_sec_auth_collision: state %d (retrying in a moment...)", p_dev_rec->sec_state);
   3748             /* We will restart authentication after timeout */
   3749             if (p_dev_rec->sec_state == BTM_SEC_STATE_AUTHENTICATING || p_dev_rec->sec_state == BTM_SEC_STATE_ENCRYPTING)
   3750                 p_dev_rec->sec_state = 0;
   3751 
   3752             btm_cb.p_collided_dev_rec = p_dev_rec;
   3753             btm_cb.sec_collision_tle.param = (UINT32) btm_sec_collision_timeout;
   3754             btu_start_timer (&btm_cb.sec_collision_tle, BTU_TTYPE_USER_FUNC, BT_1SEC_TIMEOUT);
   3755         }
   3756     }
   3757 }
   3758 
   3759 /*******************************************************************************
   3760 **
   3761 ** Function         btm_sec_auth_complete
   3762 **
   3763 ** Description      This function is when authentication of the connection is
   3764 **                  completed by the LM
   3765 **
   3766 ** Returns          void
   3767 **
   3768 *******************************************************************************/
   3769 void btm_sec_auth_complete (UINT16 handle, UINT8 status)
   3770 {
   3771     UINT8            old_sm4;
   3772     tBTM_PAIRING_STATE  old_state   = btm_cb.pairing_state;
   3773     tBTM_SEC_DEV_REC *p_dev_rec = btm_find_dev_by_handle (handle);
   3774     BOOLEAN             are_bonding = FALSE;
   3775 
   3776     /* Commenting out trace due to obf/compilation problems.
   3777     */
   3778 #if (BT_USE_TRACES == TRUE)
   3779     if (p_dev_rec)
   3780     {
   3781         BTM_TRACE_EVENT6 ("Security Manager: auth_complete PairState: %s  handle:%u  status:%d  dev->sec_state: %u  Bda:%08x, RName:%s",
   3782                           btm_pair_state_descr (btm_cb.pairing_state),
   3783                           handle, status,
   3784                           p_dev_rec->sec_state,
   3785                           (p_dev_rec->bd_addr[2]<<24)+(p_dev_rec->bd_addr[3]<<16)+(p_dev_rec->bd_addr[4]<<8)+p_dev_rec->bd_addr[5],
   3786                           p_dev_rec->sec_bd_name);
   3787     }
   3788     else
   3789     {
   3790         BTM_TRACE_EVENT3 ("Security Manager: auth_complete PairState: %s  handle:%u  status:%d",
   3791                           btm_pair_state_descr (btm_cb.pairing_state),
   3792                           handle, status);
   3793     }
   3794 #endif
   3795 
   3796     /* For transaction collision we need to wait and repeat.  There is no need */
   3797     /* for random timeout because only slave should receive the result */
   3798     if ((status == HCI_ERR_LMP_ERR_TRANS_COLLISION) || (status == HCI_ERR_DIFF_TRANSACTION_COLLISION))
   3799     {
   3800         btm_sec_auth_collision(handle);
   3801         return;
   3802     }
   3803     btm_cb.collision_start_time = 0;
   3804 
   3805     btm_restore_mode();
   3806 
   3807     /* Check if connection was made just to do bonding.  If we authenticate
   3808        the connection that is up, this is the last event received.
   3809     */
   3810     if (p_dev_rec
   3811         && (btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD)
   3812         && !(btm_cb.pairing_flags & BTM_PAIR_FLAGS_DISC_WHEN_DONE))
   3813     {
   3814         p_dev_rec->security_required &= ~BTM_SEC_OUT_AUTHENTICATE;
   3815 
   3816         l2cu_start_post_bond_timer (p_dev_rec->hci_handle);
   3817     }
   3818 
   3819     if (!p_dev_rec)
   3820         return;
   3821 
   3822     /* keep the old sm4 flag and clear the retry bit in control block */
   3823     old_sm4 = p_dev_rec->sm4;
   3824     p_dev_rec->sm4 &= ~BTM_SM4_RETRY;
   3825 
   3826     if ( (btm_cb.pairing_state != BTM_PAIR_STATE_IDLE)
   3827          &&  (btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD)
   3828          &&  (memcmp (p_dev_rec->bd_addr, btm_cb.pairing_bda, BD_ADDR_LEN) == 0) )
   3829         are_bonding = TRUE;
   3830 
   3831     btm_sec_change_pairing_state (BTM_PAIR_STATE_IDLE);
   3832 
   3833     if (p_dev_rec->sec_state != BTM_SEC_STATE_AUTHENTICATING)
   3834     {
   3835         if ( (btm_cb.api.p_auth_complete_callback && status != HCI_SUCCESS)
   3836              &&  (old_state != BTM_PAIR_STATE_IDLE) )
   3837         {
   3838             (*btm_cb.api.p_auth_complete_callback) (p_dev_rec->bd_addr,
   3839                                                     p_dev_rec->dev_class,
   3840                                                     p_dev_rec->sec_bd_name, status);
   3841         }
   3842         return;
   3843     }
   3844 
   3845     /* There can be a race condition, when we are starting authentication and
   3846     ** the peer device is doing encryption.
   3847     ** If first we receive encryption change up, then initiated authentication
   3848     ** can not be performed.  According to the spec we can not do authentication
   3849     ** on the encrypted link, so device is correct.
   3850     */
   3851     if ((status == HCI_ERR_COMMAND_DISALLOWED)
   3852         && ((p_dev_rec->sec_flags & (BTM_SEC_AUTHENTICATED | BTM_SEC_ENCRYPTED)) ==
   3853             (BTM_SEC_AUTHENTICATED | BTM_SEC_ENCRYPTED)))
   3854     {
   3855         status = HCI_SUCCESS;
   3856     }
   3857     /* Currently we do not notify user if it is a keyboard which connects */
   3858     /* User probably Disabled the keyboard while it was asleap.  Let her try */
   3859     if (btm_cb.api.p_auth_complete_callback)
   3860     {
   3861         /* report the suthentication status */
   3862         if (old_state != BTM_PAIR_STATE_IDLE)
   3863             (*btm_cb.api.p_auth_complete_callback) (p_dev_rec->bd_addr,
   3864                                                     p_dev_rec->dev_class,
   3865                                                     p_dev_rec->sec_bd_name, status);
   3866     }
   3867 
   3868     p_dev_rec->sec_state = BTM_SEC_STATE_IDLE;
   3869 
   3870     /* If this is a bonding procedure can disconnect the link now */
   3871     if (are_bonding)
   3872     {
   3873         p_dev_rec->security_required &= ~BTM_SEC_OUT_AUTHENTICATE;
   3874 
   3875         if (status != HCI_SUCCESS)
   3876             btm_sec_send_hci_disconnect (p_dev_rec, HCI_ERR_PEER_USER);
   3877         else
   3878             l2cu_start_post_bond_timer (p_dev_rec->hci_handle);
   3879 
   3880         return;
   3881     }
   3882 
   3883     /* If authentication failed, notify the waiting layer */
   3884     if (status != HCI_SUCCESS)
   3885     {
   3886         if ((old_sm4 & BTM_SM4_RETRY) == 0)
   3887         {
   3888             /* allow retry only once */
   3889             if (status == HCI_ERR_LMP_ERR_TRANS_COLLISION)
   3890             {
   3891                 /* not retried yet. set the retry bit */
   3892                 p_dev_rec->sm4 |= BTM_SM4_RETRY;
   3893                 BTM_TRACE_DEBUG2 ("Collision retry sm4:x%x sec_flags:0x%x", p_dev_rec->sm4, p_dev_rec->sec_flags);
   3894             }
   3895             /* this retry for missing key is for Lisbon or later only.
   3896              * Legacy device do not need this. the controller will drive the retry automatically */
   3897             else if (HCI_ERR_KEY_MISSING == status && BTM_SEC_IS_SM4(p_dev_rec->sm4))
   3898             {
   3899                 /* not retried yet. set the retry bit */
   3900                 p_dev_rec->sm4 |= BTM_SM4_RETRY;
   3901                 p_dev_rec->sec_flags &= ~BTM_SEC_LINK_KEY_KNOWN;
   3902                 BTM_TRACE_DEBUG2 ("Retry for missing key sm4:x%x sec_flags:0x%x", p_dev_rec->sm4, p_dev_rec->sec_flags);
   3903 
   3904                 /* With BRCM controller, we do not need to delete the stored link key in controller.
   3905                 If the stack may sit on top of other controller, we may need this
   3906                 BTM_DeleteStoredLinkKey (bd_addr, NULL); */
   3907             }
   3908 
   3909             if (p_dev_rec->sm4 & BTM_SM4_RETRY)
   3910             {
   3911                 btm_sec_execute_procedure (p_dev_rec);
   3912                 return;
   3913             }
   3914         }
   3915 
   3916         btm_sec_dev_rec_cback_event (p_dev_rec, BTM_ERR_PROCESSING);
   3917 
   3918         if (btm_cb.pairing_flags & BTM_PAIR_FLAGS_DISC_WHEN_DONE)
   3919         {
   3920             btm_sec_send_hci_disconnect (p_dev_rec, HCI_ERR_AUTH_FAILURE);
   3921         }
   3922         return;
   3923     }
   3924 
   3925     p_dev_rec->sec_flags |= BTM_SEC_AUTHENTICATED;
   3926 
   3927     /* Authentication succeeded, execute the next security procedure, if any */
   3928     status = btm_sec_execute_procedure (p_dev_rec);
   3929 
   3930     /* If there is no next procedure, or procedure failed to start, notify the caller */
   3931     if (status != BTM_CMD_STARTED)
   3932         btm_sec_dev_rec_cback_event (p_dev_rec, status);
   3933 }
   3934 
   3935 /*******************************************************************************
   3936 **
   3937 ** Function         btm_sec_mkey_comp_event
   3938 **
   3939 ** Description      This function is when encryption of the connection is
   3940 **                  completed by the LM
   3941 **
   3942 ** Returns          void
   3943 **
   3944 *******************************************************************************/
   3945 void btm_sec_mkey_comp_event (UINT16 handle, UINT8 status, UINT8 key_flg)
   3946 {
   3947     tBTM_SEC_DEV_REC  *p_dev_rec = btm_find_dev_by_handle (handle);
   3948     UINT8 bd_addr[BD_ADDR_LEN] = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff} ;
   3949 
   3950     BTM_TRACE_EVENT2 ("Security Manager: mkey comp status:%d State:%d",
   3951                       status, (p_dev_rec) ? p_dev_rec->sec_state : 0);
   3952 
   3953     /* If encryption setup failed, notify the waiting layer */
   3954     /* There is no next procedure or start of procedure failed, notify the waiting layer */
   3955     if (btm_cb.mkey_cback)
   3956     {
   3957         if (!p_dev_rec)
   3958             (btm_cb.mkey_cback)(bd_addr, status, key_flg );
   3959         else
   3960             (btm_cb.mkey_cback)(p_dev_rec->bd_addr, status, key_flg );
   3961     }
   3962 }
   3963 
   3964 /*******************************************************************************
   3965 **
   3966 ** Function         btm_sec_encrypt_change
   3967 **
   3968 ** Description      This function is when encryption of the connection is
   3969 **                  completed by the LM
   3970 **
   3971 ** Returns          void
   3972 **
   3973 *******************************************************************************/
   3974 void btm_sec_encrypt_change (UINT16 handle, UINT8 status, UINT8 encr_enable)
   3975 {
   3976     tBTM_SEC_DEV_REC  *p_dev_rec = btm_find_dev_by_handle (handle);
   3977 #if BLE_INCLUDED == TRUE && SMP_INCLUDED == TRUE
   3978     tACL_CONN         *p_acl;
   3979 #endif
   3980     BTM_TRACE_EVENT3 ("Security Manager: encrypt_change status:%d State:%d, encr_enable = %d",
   3981                       status, (p_dev_rec) ? p_dev_rec->sec_state : 0, encr_enable);
   3982     BTM_TRACE_DEBUG1 ("before update p_dev_rec->sec_flags=0x%x", (p_dev_rec) ? p_dev_rec->sec_flags : 0 );
   3983 
   3984     /* For transaction collision we need to wait and repeat.  There is no need */
   3985     /* for random timeout because only slave should receive the result */
   3986     if ((status == HCI_ERR_LMP_ERR_TRANS_COLLISION) || (status == HCI_ERR_DIFF_TRANSACTION_COLLISION))
   3987     {
   3988         btm_sec_auth_collision(handle);
   3989         return;
   3990     }
   3991     btm_cb.collision_start_time = 0;
   3992 
   3993     if (!p_dev_rec)
   3994         return;
   3995 
   3996     if ((status == HCI_SUCCESS) && encr_enable)
   3997         p_dev_rec->sec_flags |= (BTM_SEC_AUTHENTICATED | BTM_SEC_ENCRYPTED);
   3998 
   3999     /* It is possible that we decrypted the link to perform role switch */
   4000     /* mark link not to be encrypted, so that when we execute security next time it will kick in again */
   4001     if ((status == HCI_SUCCESS) && !encr_enable)
   4002         p_dev_rec->sec_flags &= ~BTM_SEC_ENCRYPTED;
   4003 
   4004     BTM_TRACE_DEBUG1 ("after update p_dev_rec->sec_flags=0x%x", p_dev_rec->sec_flags );
   4005 
   4006 #if BLE_INCLUDED == TRUE && SMP_INCLUDED == TRUE
   4007     p_acl = btm_bda_to_acl(p_dev_rec->bd_addr);
   4008 
   4009     if (p_acl && p_acl->is_le_link)
   4010     {
   4011         btm_ble_link_encrypted(p_dev_rec->bd_addr, encr_enable);
   4012         return;
   4013     }
   4014     else
   4015         /* BR/EDR connection, update the encryption key size to be 16 as always */
   4016         p_dev_rec->enc_key_size = 16;
   4017 #endif
   4018 
   4019     /* If this encryption was started by peer do not need to do anything */
   4020     if (p_dev_rec->sec_state != BTM_SEC_STATE_ENCRYPTING)
   4021     {
   4022         if (BTM_SEC_STATE_DELAY_FOR_ENC == p_dev_rec->sec_state)
   4023         {
   4024             p_dev_rec->sec_state = BTM_SEC_STATE_IDLE;
   4025             p_dev_rec->p_callback = NULL;
   4026             l2cu_resubmit_pending_sec_req (p_dev_rec->bd_addr);
   4027         }
   4028         return;
   4029     }
   4030 
   4031     p_dev_rec->sec_state = BTM_SEC_STATE_IDLE;
   4032 
   4033     /* If encryption setup failed, notify the waiting layer */
   4034     if (status != HCI_SUCCESS)
   4035     {
   4036         btm_sec_dev_rec_cback_event (p_dev_rec, BTM_ERR_PROCESSING);
   4037         return;
   4038     }
   4039 
   4040     /* Encryption setup succeeded, execute the next security procedure, if any */
   4041     status = (UINT8)btm_sec_execute_procedure (p_dev_rec);
   4042 
   4043     /* If there is no next procedure, or procedure failed to start, notify the caller */
   4044     if (status != BTM_CMD_STARTED)
   4045         btm_sec_dev_rec_cback_event (p_dev_rec, status);
   4046 }
   4047 
   4048 /*******************************************************************************
   4049 **
   4050 ** Function         btm_sec_create_conn
   4051 **
   4052 ** Description      This function records current role and forwards request to
   4053 **                  HCI
   4054 **
   4055 ** Returns          void
   4056 **
   4057 *******************************************************************************/
   4058 BOOLEAN btm_sec_create_conn (BD_ADDR bda, UINT16 packet_types,
   4059                              UINT8 page_scan_rep_mode, UINT8 page_scan_mode,
   4060                              UINT16 clock_offset, UINT8 allow_switch)
   4061 {
   4062     tBTM_SEC_DEV_REC *p_dev_rec = btm_find_or_alloc_dev (bda);
   4063 
   4064     memcpy (btm_cb.connecting_bda, p_dev_rec->bd_addr,   BD_ADDR_LEN);
   4065     memcpy (btm_cb.connecting_dc,  p_dev_rec->dev_class, DEV_CLASS_LEN);
   4066 
   4067     btm_cb.acl_disc_reason = 0xff ;
   4068 
   4069     p_dev_rec->sec_state   = BTM_SEC_STATE_IDLE;
   4070     p_dev_rec->role_master = TRUE;
   4071 
   4072     /* If any SCO link up, do not allow a switch */
   4073     if (BTM_GetNumScoLinks() != 0)
   4074         allow_switch = HCI_CR_CONN_NOT_ALLOW_SWITCH;
   4075 
   4076     return(btsnd_hcic_create_conn (bda, packet_types, page_scan_rep_mode,
   4077                                    page_scan_mode, clock_offset, allow_switch));
   4078 }
   4079 
   4080 /*******************************************************************************
   4081 **
   4082 ** Function         btm_sec_connect_after_reject_timeout
   4083 **
   4084 ** Description      Connection for bonding could not start because of the collision
   4085 **                  Initiate outgoing connection
   4086 **
   4087 ** Returns          Pointer to the TLE struct
   4088 **
   4089 *******************************************************************************/
   4090 static void btm_sec_connect_after_reject_timeout (TIMER_LIST_ENT *p_tle)
   4091 {
   4092     tBTM_SEC_DEV_REC *p_dev_rec = btm_cb.p_collided_dev_rec;
   4093 
   4094     BTM_TRACE_EVENT0 ("btm_sec_connect_after_reject_timeout()");
   4095     btm_cb.sec_collision_tle.param = 0;
   4096     btm_cb.p_collided_dev_rec = 0;
   4097 
   4098     if (btm_sec_dd_create_conn(p_dev_rec) != BTM_CMD_STARTED)
   4099     {
   4100         BTM_TRACE_WARNING0 ("Security Manager: btm_sec_connect_after_reject_timeout: failed to start connection");
   4101 
   4102         btm_sec_change_pairing_state (BTM_PAIR_STATE_IDLE);
   4103 
   4104         (*btm_cb.api.p_auth_complete_callback) (p_dev_rec->bd_addr,  p_dev_rec->dev_class,
   4105                                                 p_dev_rec->sec_bd_name, HCI_ERR_MEMORY_FULL);
   4106     }
   4107 }
   4108 
   4109 /*******************************************************************************
   4110 **
   4111 ** Function         btm_sec_connected
   4112 **
   4113 ** Description      This function is when a connection to the peer device is
   4114 **                  establsihed
   4115 **
   4116 ** Returns          void
   4117 **
   4118 *******************************************************************************/
   4119 void btm_sec_connected (UINT8 *bda, UINT16 handle, UINT8 status, UINT8 enc_mode)
   4120 {
   4121     tBTM_SEC_DEV_REC *p_dev_rec = btm_find_dev (bda);
   4122     UINT8            res;
   4123     BOOLEAN          is_pairing_device = FALSE;
   4124     tACL_CONN        *p_acl_cb;
   4125 
   4126     btm_acl_resubmit_page();
   4127 
   4128     /* Commenting out trace due to obf/compilation problems.
   4129     */
   4130 #if (BT_USE_TRACES == TRUE)
   4131     if (p_dev_rec)
   4132     {
   4133         BTM_TRACE_EVENT6 ("Security Manager: btm_sec_connected in state: %s  handle:%d status:%d enc_mode:%d  bda:%x RName:%s",
   4134                           btm_pair_state_descr(btm_cb.pairing_state), handle, status, enc_mode,
   4135                           (bda[2]<<24)+(bda[3]<<16)+(bda[4]<<8)+bda[5],
   4136                           p_dev_rec->sec_bd_name);
   4137     }
   4138     else
   4139     {
   4140         BTM_TRACE_EVENT5 ("Security Manager: btm_sec_connected in state: %s  handle:%d status:%d enc_mode:%d  bda:%x ",
   4141                           btm_pair_state_descr(btm_cb.pairing_state), handle, status, enc_mode,
   4142                           (bda[2]<<24)+(bda[3]<<16)+(bda[4]<<8)+bda[5]);
   4143     }
   4144 #endif
   4145 
   4146     if (!p_dev_rec)
   4147     {
   4148         /* There is no device record for new connection.  Allocate one */
   4149         if (status == HCI_SUCCESS)
   4150         {
   4151             p_dev_rec = btm_sec_alloc_dev (bda);
   4152 #if BLE_INCLUDED == TRUE
   4153             p_dev_rec->device_type |= BT_DEVICE_TYPE_BREDR;
   4154 #endif
   4155         }
   4156         else
   4157         {
   4158             /* can not find the device record and the status is error,
   4159              * just ignore it */
   4160             return;
   4161         }
   4162     }
   4163     else    /* Update the timestamp for this device */
   4164     {
   4165         p_dev_rec->timestamp = btm_cb.dev_rec_count++;
   4166         if (p_dev_rec->sm4 & BTM_SM4_CONN_PEND)
   4167         {
   4168             /* tell L2CAP it's a bonding connection. */
   4169             if ( (btm_cb.pairing_state != BTM_PAIR_STATE_IDLE)
   4170                  &&  (memcmp (btm_cb.pairing_bda, p_dev_rec->bd_addr, BD_ADDR_LEN) == 0)
   4171                  &&  (btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD) )
   4172             {
   4173                 /* if incoming connection failed while pairing, then try to connect and continue */
   4174                 /* Motorola S9 disconnects without asking pin code */
   4175                 if ((status != HCI_SUCCESS)&&(btm_cb.pairing_state == BTM_PAIR_STATE_WAIT_PIN_REQ))
   4176                 {
   4177                     BTM_TRACE_WARNING0 ("Security Manager: btm_sec_connected: incoming connection failed without asking PIN");
   4178 
   4179                     p_dev_rec->sm4 &= ~BTM_SM4_CONN_PEND;
   4180                     if (p_dev_rec->sec_flags & BTM_SEC_NAME_KNOWN)
   4181                     {
   4182                         /* Start timer with 0 to initiate connection with new LCB */
   4183                         /* because L2CAP will delete current LCB with this event  */
   4184                         btm_cb.p_collided_dev_rec = p_dev_rec;
   4185                         btm_cb.sec_collision_tle.param = (UINT32) btm_sec_connect_after_reject_timeout;
   4186                         btu_start_timer (&btm_cb.sec_collision_tle, BTU_TTYPE_USER_FUNC, 0);
   4187                     }
   4188                     else
   4189                     {
   4190                         btm_sec_change_pairing_state (BTM_PAIR_STATE_GET_REM_NAME);
   4191                         BTM_ReadRemoteDeviceName(p_dev_rec->bd_addr, NULL);
   4192                     }
   4193 #if BTM_DISC_DURING_RS == TRUE
   4194                     p_dev_rec->rs_disc_pending   = BTM_SEC_RS_NOT_PENDING;     /* reset flag */
   4195 #endif
   4196                     return;
   4197                 }
   4198                 else
   4199                 {
   4200                     l2cu_update_lcb_4_bonding(p_dev_rec->bd_addr, TRUE);
   4201                 }
   4202             }
   4203             /* always clear the pending flag */
   4204             p_dev_rec->sm4 &= ~BTM_SM4_CONN_PEND;
   4205         }
   4206     }
   4207 
   4208 #if BTM_DISC_DURING_RS == TRUE
   4209     p_dev_rec->rs_disc_pending   = BTM_SEC_RS_NOT_PENDING;     /* reset flag */
   4210 #endif
   4211 
   4212     p_dev_rec->rs_disc_pending   = BTM_SEC_RS_NOT_PENDING;     /* reset flag */
   4213 
   4214     if ( (btm_cb.pairing_state != BTM_PAIR_STATE_IDLE)
   4215          && (memcmp (btm_cb.pairing_bda, bda, BD_ADDR_LEN) == 0) )
   4216     {
   4217         /* if we rejected incoming connection from bonding device */
   4218         if ((status == HCI_ERR_HOST_REJECT_DEVICE)
   4219             &&(btm_cb.pairing_flags & BTM_PAIR_FLAGS_REJECTED_CONNECT))
   4220         {
   4221             BTM_TRACE_WARNING2 ("Security Manager: btm_sec_connected: HCI_Conn_Comp Flags:0x%04x, sm4: 0x%x",
   4222                 btm_cb.pairing_flags, p_dev_rec->sm4);
   4223 
   4224             btm_cb.pairing_flags &= ~BTM_PAIR_FLAGS_REJECTED_CONNECT;
   4225             if (BTM_SEC_IS_SM4_UNKNOWN(p_dev_rec->sm4))
   4226             {
   4227                 /* Try again: RNR when no ACL causes HCI_RMT_HOST_SUP_FEAT_NOTIFY_EVT */
   4228                 btm_sec_change_pairing_state (BTM_PAIR_STATE_GET_REM_NAME);
   4229                 BTM_ReadRemoteDeviceName(bda, NULL);
   4230                 return;
   4231             }
   4232 
   4233             /* if we already have pin code */
   4234             if (btm_cb.pairing_state != BTM_PAIR_STATE_WAIT_LOCAL_PIN)
   4235             {
   4236                 /* Start timer with 0 to initiate connection with new LCB */
   4237                 /* because L2CAP will delete current LCB with this event  */
   4238                 btm_cb.p_collided_dev_rec = p_dev_rec;
   4239                 btm_cb.sec_collision_tle.param = (UINT32) btm_sec_connect_after_reject_timeout;
   4240                 btu_start_timer (&btm_cb.sec_collision_tle, BTU_TTYPE_USER_FUNC, 0);
   4241             }
   4242 
   4243             return;
   4244         }
   4245         /* wait for incoming connection without resetting pairing state */
   4246         else if (status == HCI_ERR_CONNECTION_EXISTS)
   4247         {
   4248             BTM_TRACE_WARNING0 ("Security Manager: btm_sec_connected: Wait for incoming connection");
   4249             return;
   4250         }
   4251 
   4252         is_pairing_device = TRUE;
   4253     }
   4254 
   4255     /* If connection was made to do bonding restore link security if changed */
   4256     btm_restore_mode();
   4257 
   4258     /* if connection fails during pin request, notify application */
   4259     if (status != HCI_SUCCESS)
   4260     {
   4261         /* If connection failed because of during pairing, need to tell user */
   4262         if (is_pairing_device)
   4263         {
   4264             p_dev_rec->security_required &= ~BTM_SEC_OUT_AUTHENTICATE;
   4265             p_dev_rec->sec_flags &= ~(BTM_SEC_LINK_KEY_KNOWN | BTM_SEC_LINK_KEY_AUTHED);
   4266             BTM_TRACE_DEBUG1 ("security_required:%x ", p_dev_rec->security_required );
   4267 
   4268             btm_sec_change_pairing_state (BTM_PAIR_STATE_IDLE);
   4269 
   4270             /* We need to notify host that the key is not known any more */
   4271             if (btm_cb.api.p_auth_complete_callback)
   4272             {
   4273                 (*btm_cb.api.p_auth_complete_callback) (p_dev_rec->bd_addr,
   4274                                                         p_dev_rec->dev_class,
   4275                                                         p_dev_rec->sec_bd_name, status);
   4276             }
   4277         }
   4278         else if ((status == HCI_ERR_AUTH_FAILURE)                   ||
   4279                  (status == HCI_ERR_KEY_MISSING)                         ||
   4280                  (status == HCI_ERR_HOST_REJECT_SECURITY)                ||
   4281                  (status == HCI_ERR_PAIRING_NOT_ALLOWED)                 ||
   4282                  (status == HCI_ERR_UNIT_KEY_USED)                       ||
   4283                  (status == HCI_ERR_PAIRING_WITH_UNIT_KEY_NOT_SUPPORTED) ||
   4284                  (status == HCI_ERR_ENCRY_MODE_NOT_ACCEPTABLE)           ||
   4285                  (status == HCI_ERR_REPEATED_ATTEMPTS))
   4286         {
   4287             p_dev_rec->security_required &= ~BTM_SEC_OUT_AUTHENTICATE;
   4288             p_dev_rec->sec_flags &= ~BTM_SEC_LINK_KEY_KNOWN;
   4289 
   4290             /* We need to notify host that the key is not known any more */
   4291             if (btm_cb.api.p_auth_complete_callback)
   4292             {
   4293                 (*btm_cb.api.p_auth_complete_callback) (p_dev_rec->bd_addr,
   4294                                                         p_dev_rec->dev_class,
   4295                                                         p_dev_rec->sec_bd_name, status);
   4296             }
   4297         }
   4298 
   4299         if (status == HCI_ERR_CONNECTION_TOUT || status == HCI_ERR_LMP_RESPONSE_TIMEOUT  ||
   4300             status == HCI_ERR_UNSPECIFIED     || status == HCI_ERR_PAGE_TIMEOUT)
   4301             btm_sec_dev_rec_cback_event (p_dev_rec, BTM_DEVICE_TIMEOUT);
   4302         else
   4303             btm_sec_dev_rec_cback_event (p_dev_rec, BTM_ERR_PROCESSING);
   4304 
   4305         return;
   4306     }
   4307 
   4308     /* If initiated dedicated bonding, return the link key now, and initiate disconnect */
   4309     /* If dedicated bonding, and we now have a link key, we are all done */
   4310     if ( is_pairing_device
   4311          && (p_dev_rec->sec_flags & BTM_SEC_LINK_KEY_KNOWN) )
   4312     {
   4313         if (p_dev_rec->link_key_not_sent)
   4314         {
   4315             p_dev_rec->link_key_not_sent = FALSE;
   4316             btm_send_link_key_notif(p_dev_rec);
   4317         }
   4318 
   4319         p_dev_rec->security_required &= ~BTM_SEC_OUT_AUTHENTICATE;
   4320 
   4321         /* remember flag before it is initialized */
   4322         if (btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD)
   4323             res = TRUE;
   4324         else
   4325             res = FALSE;
   4326 
   4327         if (btm_cb.api.p_auth_complete_callback)
   4328             (*btm_cb.api.p_auth_complete_callback) (p_dev_rec->bd_addr,
   4329                                                     p_dev_rec->dev_class,
   4330                                                     p_dev_rec->sec_bd_name, HCI_SUCCESS);
   4331 
   4332         btm_sec_change_pairing_state (BTM_PAIR_STATE_IDLE);
   4333 
   4334         if ( res )
   4335         {
   4336             /* Let l2cap start bond timer */
   4337             l2cu_update_lcb_4_bonding (p_dev_rec->bd_addr, TRUE);
   4338         }
   4339 
   4340         return;
   4341     }
   4342 
   4343     p_dev_rec->hci_handle = handle;
   4344 
   4345     /* role may not be correct here, it will be updated by l2cap, but we need to */
   4346     /* notify btm_acl that link is up, so starting of rmt name request will not */
   4347     /* set paging flag up */
   4348     p_acl_cb = btm_bda_to_acl(bda);
   4349     if (p_acl_cb)
   4350     {
   4351         /* whatever is in btm_establish_continue() without reporting the BTM_BL_CONN_EVT event */
   4352 #if (!defined(BTM_BYPASS_EXTRA_ACL_SETUP) || BTM_BYPASS_EXTRA_ACL_SETUP == FALSE)
   4353         /* For now there are a some devices that do not like sending */
   4354         /* commands events and data at the same time. */
   4355         /* Set the packet types to the default allowed by the device */
   4356         btm_set_packet_types (p_acl_cb, btm_cb.btm_acl_pkt_types_supported);
   4357 
   4358         if (btm_cb.btm_def_link_policy)
   4359             BTM_SetLinkPolicy (p_acl_cb->remote_addr, &btm_cb.btm_def_link_policy);
   4360 #endif
   4361     }
   4362     btm_acl_created (bda, p_dev_rec->dev_class, p_dev_rec->sec_bd_name, handle, HCI_ROLE_SLAVE, FALSE);
   4363 
   4364     /* Initialize security flags.  We need to do that because some            */
   4365     /* authorization complete could have come after the connection is dropped */
   4366     /* and that would set wrong flag that link has been authorized already    */
   4367     p_dev_rec->sec_flags &= ~(BTM_SEC_AUTHORIZED | BTM_SEC_AUTHENTICATED |
   4368                               BTM_SEC_ENCRYPTED | BTM_SEC_ROLE_SWITCHED);
   4369 
   4370     if (enc_mode != HCI_ENCRYPT_MODE_DISABLED)
   4371         p_dev_rec->sec_flags |= (BTM_SEC_AUTHENTICATED | BTM_SEC_ENCRYPTED);
   4372 
   4373     if (btm_cb.security_mode == BTM_SEC_MODE_LINK)
   4374         p_dev_rec->sec_flags |= BTM_SEC_AUTHENTICATED;
   4375 
   4376     p_dev_rec->link_key_changed = FALSE;
   4377 
   4378     /* After connection is established we perform security if we do not know */
   4379     /* the name, or if we are originator because some procedure can have */
   4380     /* been scheduled while connection was down */
   4381     BTM_TRACE_DEBUG1 ("is_originator:%d ", p_dev_rec->is_originator);
   4382     if (!(p_dev_rec->sec_flags & BTM_SEC_NAME_KNOWN) || p_dev_rec->is_originator)
   4383     {
   4384         if ((res = btm_sec_execute_procedure (p_dev_rec)) != BTM_CMD_STARTED)
   4385             btm_sec_dev_rec_cback_event (p_dev_rec, res);
   4386     }
   4387     return;
   4388 }
   4389 
   4390 /*******************************************************************************
   4391 **
   4392 ** Function         btm_sec_role_changed
   4393 **
   4394 ** Description      This function is colled when controller reports role
   4395 **                  changed, or failed command status for Role Change request
   4396 **
   4397 ** Returns          void
   4398 **
   4399 *******************************************************************************/
   4400 void btm_sec_role_changed (void *p_ref_data)
   4401 {
   4402     tBTM_SEC_DEV_REC *p_dev_rec = (tBTM_SEC_DEV_REC *)p_ref_data;
   4403     UINT8 res;
   4404 
   4405     BTM_TRACE_EVENT0 ("Security Manager: role changed");
   4406 
   4407     /* If this role switch was started by peer do not need to do anything */
   4408     if (p_dev_rec->sec_state != BTM_SEC_STATE_SWITCHING_ROLE)
   4409         return;
   4410 
   4411     /* If serurity required was to FORCE switch and it failed, notify the waiting layer */
   4412     if (((p_dev_rec->security_required & BTM_SEC_FORCE_MASTER) && !p_dev_rec->role_master)
   4413         || ((p_dev_rec->security_required & BTM_SEC_FORCE_SLAVE)  &&  p_dev_rec->role_master))
   4414     {
   4415         btm_sec_dev_rec_cback_event (p_dev_rec, BTM_ERR_PROCESSING);
   4416         return;
   4417     }
   4418 
   4419     p_dev_rec->sec_flags |= BTM_SEC_ROLE_SWITCHED;
   4420 
   4421     p_dev_rec->security_required &= ~(BTM_SEC_FORCE_MASTER | BTM_SEC_ATTEMPT_MASTER |
   4422                                       BTM_SEC_FORCE_SLAVE  | BTM_SEC_ATTEMPT_SLAVE);
   4423 
   4424     p_dev_rec->sec_state = BTM_SEC_STATE_IDLE;
   4425 
   4426     if ((res = (UINT8)btm_sec_execute_procedure (p_dev_rec)) != BTM_CMD_STARTED)
   4427     {
   4428         btm_sec_dev_rec_cback_event (p_dev_rec, res);
   4429     }
   4430 }
   4431 
   4432 /*******************************************************************************
   4433 **
   4434 ** Function         btm_sec_disconnect
   4435 **
   4436 ** Description      This function is called to disconnect HCI link
   4437 **
   4438 ** Returns          btm status
   4439 **
   4440 *******************************************************************************/
   4441 tBTM_STATUS btm_sec_disconnect (UINT16 handle, UINT8 reason)
   4442 {
   4443     tBTM_SEC_DEV_REC  *p_dev_rec = btm_find_dev_by_handle (handle);
   4444 
   4445     /* In some weird race condition we may not have a record */
   4446     if (!p_dev_rec)
   4447     {
   4448         btsnd_hcic_disconnect (handle, reason);
   4449         return(BTM_SUCCESS);
   4450     }
   4451 
   4452     /* If we are in the process of bonding we need to tell client that auth failed */
   4453     if ( (btm_cb.pairing_state != BTM_PAIR_STATE_IDLE)
   4454          &&  (memcmp (btm_cb.pairing_bda, p_dev_rec->bd_addr, BD_ADDR_LEN) == 0)
   4455          &&  (btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD) )
   4456     {
   4457         /* we are currently doing bonding.  Link will be disconnected when done */
   4458         btm_cb.pairing_flags |= BTM_PAIR_FLAGS_DISC_WHEN_DONE;
   4459         return(BTM_BUSY);
   4460     }
   4461 
   4462     return(btm_sec_send_hci_disconnect(p_dev_rec, reason));
   4463 }
   4464 
   4465 /*******************************************************************************
   4466 **
   4467 ** Function         btm_sec_disconnected
   4468 **
   4469 ** Description      This function is when a connection to the peer device is
   4470 **                  dropped
   4471 **
   4472 ** Returns          void
   4473 **
   4474 *******************************************************************************/
   4475 void btm_sec_disconnected (UINT16 handle, UINT8 reason)
   4476 {
   4477     tBTM_SEC_DEV_REC  *p_dev_rec = btm_find_dev_by_handle (handle);
   4478     UINT8             old_pairing_flags = btm_cb.pairing_flags;
   4479     int               result = HCI_ERR_AUTH_FAILURE;
   4480     tBTM_SEC_CALLBACK   *p_callback = NULL;
   4481 
   4482     /* If page was delayed for disc complete, can do it now */
   4483     btm_cb.discing = FALSE;
   4484 
   4485     btm_acl_resubmit_page();
   4486 
   4487     if (!p_dev_rec)
   4488         return;
   4489 
   4490     p_dev_rec->rs_disc_pending = BTM_SEC_RS_NOT_PENDING;     /* reset flag */
   4491 
   4492 #if BTM_DISC_DURING_RS == TRUE
   4493     BTM_TRACE_ERROR0("btm_sec_disconnected - Clearing Pending flag");
   4494     p_dev_rec->rs_disc_pending = BTM_SEC_RS_NOT_PENDING;     /* reset flag */
   4495 #endif
   4496 
   4497     /* clear unused flags */
   4498     p_dev_rec->sm4 &= BTM_SM4_TRUE;
   4499 
   4500     BTM_TRACE_EVENT6("btm_sec_disconnected() sec_req:x%x  State: %s   reason:%d bda:%04x%08x RName:%s",
   4501                      p_dev_rec->security_required, btm_pair_state_descr(btm_cb.pairing_state), reason,  (p_dev_rec->bd_addr[0]<<8)+p_dev_rec->bd_addr[1],
   4502                      (p_dev_rec->bd_addr[2]<<24)+(p_dev_rec->bd_addr[3]<<16)+(p_dev_rec->bd_addr[4]<<8)+p_dev_rec->bd_addr[5], p_dev_rec->sec_bd_name);
   4503 
   4504     BTM_TRACE_EVENT1("before Update sec_flags=0x%x", p_dev_rec->sec_flags);
   4505 
   4506     /* If we are in the process of bonding we need to tell client that auth failed */
   4507     if ( (btm_cb.pairing_state != BTM_PAIR_STATE_IDLE)
   4508          && (memcmp (btm_cb.pairing_bda, p_dev_rec->bd_addr, BD_ADDR_LEN) == 0))
   4509     {
   4510         btm_sec_change_pairing_state (BTM_PAIR_STATE_IDLE);
   4511         p_dev_rec->sec_flags &= ~BTM_SEC_LINK_KEY_KNOWN;
   4512         if (btm_cb.api.p_auth_complete_callback)
   4513         {
   4514             /* If the disconnection reason is REPEATED_ATTEMPTS,
   4515                send this error message to complete callback function
   4516                to display the error message of Repeated attempts.
   4517                All others, send HCI_ERR_AUTH_FAILURE. */
   4518             if (reason == HCI_ERR_REPEATED_ATTEMPTS)
   4519             {
   4520                 result = HCI_ERR_REPEATED_ATTEMPTS;
   4521             }
   4522             else if (old_pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD)
   4523             {
   4524                 result = HCI_ERR_HOST_REJECT_SECURITY;
   4525             }
   4526             (*btm_cb.api.p_auth_complete_callback) (p_dev_rec->bd_addr,     p_dev_rec->dev_class,
   4527                                                     p_dev_rec->sec_bd_name, result);
   4528         }
   4529     }
   4530 
   4531     p_dev_rec->hci_handle = BTM_SEC_INVALID_HANDLE;
   4532     p_dev_rec->sec_state  = BTM_SEC_STATE_IDLE;
   4533 
   4534 #if BLE_INCLUDED == TRUE && SMP_INCLUDED == TRUE
   4535     p_dev_rec->enc_key_size = 0;
   4536     btm_ble_update_mode_operation(HCI_ROLE_UNKNOWN, p_dev_rec->bd_addr, FALSE);
   4537     /* see sec_flags processing in btm_acl_removed */
   4538 #endif
   4539     p_dev_rec->sec_flags &= ~(BTM_SEC_AUTHORIZED | BTM_SEC_AUTHENTICATED | BTM_SEC_ENCRYPTED | BTM_SEC_ROLE_SWITCHED);
   4540 
   4541     p_dev_rec->security_required = BTM_SEC_NONE;
   4542 
   4543     p_callback = p_dev_rec->p_callback;
   4544 
   4545     /* if security is pending, send callback to clean up the security state */
   4546     if(p_callback)
   4547     {
   4548         p_dev_rec->p_callback = NULL; /* when the peer device time out the authentication before
   4549                                          we do, this call back must be reset here */
   4550         (*p_callback) (p_dev_rec->bd_addr, p_dev_rec->p_ref_data, BTM_ERR_PROCESSING);
   4551     }
   4552 
   4553     BTM_TRACE_EVENT1("after Update sec_flags=0x%x", p_dev_rec->sec_flags);
   4554 }
   4555 
   4556 /*******************************************************************************
   4557 **
   4558 ** Function         btm_sec_link_key_notification
   4559 **
   4560 ** Description      This function is called when a new connection link key is
   4561 **                  generated
   4562 **
   4563 ** Returns          Pointer to the record or NULL
   4564 **
   4565 *******************************************************************************/
   4566 void btm_sec_link_key_notification (UINT8 *p_bda, UINT8 *p_link_key, UINT8 key_type)
   4567 {
   4568     tBTM_SEC_DEV_REC *p_dev_rec = btm_find_or_alloc_dev (p_bda);
   4569     BOOLEAN          we_are_bonding = FALSE;
   4570 
   4571     BTM_TRACE_EVENT3 ("btm_sec_link_key_notification()  BDA:%04x%08x, TYPE: %d",
   4572                       (p_bda[0]<<8)+p_bda[1], (p_bda[2]<<24)+(p_bda[3]<<16)+(p_bda[4]<<8)+p_bda[5],
   4573                       key_type);
   4574 
   4575     /* If connection was made to do bonding restore link security if changed */
   4576     btm_restore_mode();
   4577 
   4578     /* Override the key type if version is pre-1.1 */
   4579     if (btm_cb.devcb.local_version.hci_version < HCI_VERSION_1_1)
   4580         p_dev_rec->link_key_type = BTM_LKEY_TYPE_IGNORE;
   4581     if (key_type != BTM_LKEY_TYPE_CHANGED_COMB)
   4582         p_dev_rec->link_key_type = key_type;
   4583 
   4584     p_dev_rec->sec_flags |= BTM_SEC_LINK_KEY_KNOWN;
   4585 #if (BLE_INCLUDED == TRUE)
   4586     /* BR/EDR connection, update the encryption key size to be 16 as always */
   4587     p_dev_rec->enc_key_size = 16;
   4588 #endif
   4589     memcpy (p_dev_rec->link_key, p_link_key, LINK_KEY_LEN);
   4590 
   4591     if ( (btm_cb.pairing_state != BTM_PAIR_STATE_IDLE)
   4592          && (memcmp (btm_cb.pairing_bda, p_bda, BD_ADDR_LEN) == 0) )
   4593     {
   4594         if (btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD)
   4595             we_are_bonding = TRUE;
   4596         else
   4597             btm_sec_change_pairing_state (BTM_PAIR_STATE_IDLE);
   4598     }
   4599 
   4600     /* If name is not known at this point delay calling callback until the name is   */
   4601     /* resolved. Unless it is a HID Device and we really need to send all link keys. */
   4602     if ((!(p_dev_rec->sec_flags & BTM_SEC_NAME_KNOWN)
   4603         &&  ((p_dev_rec->dev_class[1] & BTM_COD_MAJOR_CLASS_MASK) != BTM_COD_MAJOR_PERIPHERAL)) )
   4604     {
   4605         BTM_TRACE_EVENT3 ("btm_sec_link_key_notification()  Delayed BDA: %08x%04x Type:%d",
   4606                           (p_bda[0]<<24) + (p_bda[1]<<16) + (p_bda[2]<<8) + p_bda[3], (p_bda[4] << 8) + p_bda[5], key_type);
   4607 
   4608         p_dev_rec->link_key_not_sent = TRUE;
   4609 
   4610         /* If it is for bonding nothing else will follow, so we need to start name resolution */
   4611         if (we_are_bonding)
   4612         {
   4613             if (!(btsnd_hcic_rmt_name_req (p_bda, HCI_PAGE_SCAN_REP_MODE_R1, HCI_MANDATARY_PAGE_SCAN_MODE, 0)))
   4614                 btm_inq_rmt_name_failed();
   4615         }
   4616 
   4617         BTM_TRACE_EVENT3 ("rmt_io_caps:%d, sec_flags:x%x, dev_class[1]:x%02x", p_dev_rec->rmt_io_caps, p_dev_rec->sec_flags, p_dev_rec->dev_class[1])
   4618         return;
   4619     }
   4620 
   4621     /* If its not us who perform authentication, we should tell stackserver */
   4622     /* that some authentication has been completed                          */
   4623     /* This is required when different entities receive link notification and auth complete */
   4624     if (!(p_dev_rec->security_required & BTM_SEC_OUT_AUTHENTICATE))
   4625     {
   4626         if (btm_cb.api.p_auth_complete_callback)
   4627             (*btm_cb.api.p_auth_complete_callback) (p_dev_rec->bd_addr, p_dev_rec->dev_class,
   4628                                                     p_dev_rec->sec_bd_name, HCI_SUCCESS);
   4629     }
   4630 
   4631     /* We will save link key only if the user authorized it - BTE report link key in all cases */
   4632 #ifdef BRCM_NONE_BTE
   4633     if (p_dev_rec->sec_flags & BTM_SEC_LINK_KEY_AUTHED)
   4634 #endif
   4635     {
   4636         if (btm_cb.api.p_link_key_callback)
   4637         {
   4638             (*btm_cb.api.p_link_key_callback) (p_bda, p_dev_rec->dev_class,  p_dev_rec->sec_bd_name,
   4639                                                p_link_key, p_dev_rec->link_key_type);
   4640         }
   4641     }
   4642 }
   4643 
   4644 /*******************************************************************************
   4645 **
   4646 ** Function         btm_sec_link_key_request
   4647 **
   4648 ** Description      This function is called when controller requests link key
   4649 **
   4650 ** Returns          Pointer to the record or NULL
   4651 **
   4652 *******************************************************************************/
   4653 void btm_sec_link_key_request (UINT8 *p_bda)
   4654 {
   4655     tBTM_SEC_DEV_REC *p_dev_rec = btm_find_or_alloc_dev (p_bda);
   4656 
   4657     BTM_TRACE_EVENT6 ("btm_sec_link_key_request()  BDA: %02x:%02x:%02x:%02x:%02x:%02x",
   4658                       p_bda[0], p_bda[1], p_bda[2], p_bda[3], p_bda[4], p_bda[5]);
   4659 
   4660     if (p_dev_rec->sec_flags & BTM_SEC_LINK_KEY_KNOWN)
   4661     {
   4662         btsnd_hcic_link_key_req_reply (p_bda, p_dev_rec->link_key);
   4663         return;
   4664     }
   4665 
   4666     /* Notify L2CAP to increase timeout */
   4667     l2c_pin_code_request (p_bda);
   4668 
   4669     /* Only ask the host for a key if this guy is not already bonding */
   4670     if ( (btm_cb.pairing_state == BTM_PAIR_STATE_IDLE)
   4671          || (memcmp (p_bda, btm_cb.pairing_bda, BD_ADDR_LEN) != 0) )
   4672     {
   4673         if (btm_cb.api.p_link_key_req_callback)
   4674         {
   4675             if ((*btm_cb.api.p_link_key_req_callback)(p_bda, p_dev_rec->link_key) == BTM_SUCCESS)
   4676             {
   4677                 btsnd_hcic_link_key_req_reply (p_bda, p_dev_rec->link_key);
   4678                 return;
   4679             }
   4680         }
   4681     }
   4682 
   4683     /* The link key is not in the database and it is not known to the manager */
   4684     btsnd_hcic_link_key_neg_reply (p_bda);
   4685 }
   4686 
   4687 /*******************************************************************************
   4688 **
   4689 ** Function         btm_sec_pairing_timeout
   4690 **
   4691 ** Description      This function is called when host does not provide PIN
   4692 **                  within requested time
   4693 **
   4694 ** Returns          Pointer to the TLE struct
   4695 **
   4696 *******************************************************************************/
   4697 static void btm_sec_pairing_timeout (TIMER_LIST_ENT *p_tle)
   4698 {
   4699     tBTM_CB *p_cb = &btm_cb;
   4700     tBTM_SEC_DEV_REC *p_dev_rec;
   4701 #if BTM_OOB_INCLUDED == TRUE
   4702 #if (BTM_LOCAL_IO_CAPS == BTM_IO_CAP_NONE)
   4703     tBTM_AUTH_REQ   auth_req = BTM_AUTH_AP_NO;
   4704 #else
   4705     tBTM_AUTH_REQ   auth_req = BTM_AUTH_AP_YES;
   4706 #endif
   4707 #endif
   4708     UINT8   name[2];
   4709 
   4710     p_cb->pairing_tle.param = 0;
   4711 /* Coverity: FALSE-POSITIVE error from Coverity tool. Please do NOT remove following comment. */
   4712 /* coverity[UNUSED_VALUE] pointer p_dev_rec is actually used several times... This is a Coverity false-positive, i.e. a fake issue.
   4713 */
   4714     p_dev_rec = btm_find_dev (p_cb->pairing_bda);
   4715 
   4716     BTM_TRACE_EVENT2 ("btm_sec_pairing_timeout()  State: %s   Flags: %u",
   4717                       btm_pair_state_descr(p_cb->pairing_state), p_cb->pairing_flags);
   4718 
   4719     switch (p_cb->pairing_state)
   4720     {
   4721         case BTM_PAIR_STATE_WAIT_PIN_REQ:
   4722             btm_sec_bond_cancel_complete();
   4723             break;
   4724 
   4725         case BTM_PAIR_STATE_WAIT_LOCAL_PIN:
   4726             if ( (btm_cb.pairing_flags & BTM_PAIR_FLAGS_PRE_FETCH_PIN) == 0)
   4727                 btsnd_hcic_pin_code_neg_reply (p_cb->pairing_bda);
   4728             btm_sec_change_pairing_state (BTM_PAIR_STATE_IDLE);
   4729             /* We need to notify the UI that no longer need the PIN */
   4730             if (btm_cb.api.p_auth_complete_callback)
   4731             {
   4732                 if (p_dev_rec == NULL)
   4733                 {
   4734                     name[0] = 0;
   4735                     (*btm_cb.api.p_auth_complete_callback) (p_cb->pairing_bda,
   4736                                                             NULL,
   4737                                                             name, HCI_ERR_CONNECTION_TOUT);
   4738                 }
   4739                 else
   4740                     (*btm_cb.api.p_auth_complete_callback) (p_dev_rec->bd_addr,
   4741                                                             p_dev_rec->dev_class,
   4742                                                             p_dev_rec->sec_bd_name, HCI_ERR_CONNECTION_TOUT);
   4743             }
   4744             break;
   4745 
   4746         case BTM_PAIR_STATE_WAIT_NUMERIC_CONFIRM:
   4747             btsnd_hcic_user_conf_reply (p_cb->pairing_bda, FALSE);
   4748             /* btm_sec_change_pairing_state (BTM_PAIR_STATE_IDLE); */
   4749             break;
   4750 
   4751 #if (BTM_LOCAL_IO_CAPS != BTM_IO_CAP_NONE)
   4752         case BTM_PAIR_STATE_KEY_ENTRY:
   4753             btsnd_hcic_user_passkey_neg_reply(p_cb->pairing_bda);
   4754             /* btm_sec_change_pairing_state (BTM_PAIR_STATE_IDLE); */
   4755             break;
   4756 #endif /* !BTM_IO_CAP_NONE */
   4757 
   4758 #if BTM_OOB_INCLUDED == TRUE
   4759         case BTM_PAIR_STATE_WAIT_LOCAL_IOCAPS:
   4760             if (btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD)
   4761                 auth_req |= BTM_AUTH_DD_BOND;
   4762 
   4763             btsnd_hcic_io_cap_req_reply (p_cb->pairing_bda, btm_cb.devcb.loc_io_caps,
   4764                                          BTM_OOB_NONE, auth_req);
   4765             btm_sec_change_pairing_state (BTM_PAIR_STATE_IDLE);
   4766             break;
   4767 
   4768         case BTM_PAIR_STATE_WAIT_LOCAL_OOB_RSP:
   4769             btsnd_hcic_rem_oob_neg_reply (p_cb->pairing_bda);
   4770             btm_sec_change_pairing_state (BTM_PAIR_STATE_IDLE);
   4771             break;
   4772 #endif /* BTM_OOB_INCLUDED */
   4773 
   4774         case BTM_PAIR_STATE_WAIT_DISCONNECT:
   4775             /* simple pairing failed. Started a 1-sec timer at simple pairing complete.
   4776              * now it's time to tear down the ACL link*/
   4777             if (p_dev_rec == NULL)
   4778             {
   4779                 BTM_TRACE_ERROR2 ("btm_sec_pairing_timeout() BTM_PAIR_STATE_WAIT_DISCONNECT unknown BDA: %08x%04x",
   4780                                   (p_cb->pairing_bda[0]<<24) + (p_cb->pairing_bda[1]<<16) + (p_cb->pairing_bda[2]<<8) + p_cb->pairing_bda[3],
   4781                                   (p_cb->pairing_bda[4] << 8) + p_cb->pairing_bda[5]);
   4782                 break;
   4783             }
   4784             btm_sec_send_hci_disconnect (p_dev_rec, HCI_ERR_AUTH_FAILURE);
   4785             btm_sec_change_pairing_state (BTM_PAIR_STATE_IDLE);
   4786             break;
   4787 
   4788         case BTM_PAIR_STATE_WAIT_AUTH_COMPLETE:
   4789             /* We need to notify the UI that timeout has happened while waiting for authentication*/
   4790             btm_sec_change_pairing_state (BTM_PAIR_STATE_IDLE);
   4791             if (btm_cb.api.p_auth_complete_callback)
   4792             {
   4793                 if (p_dev_rec == NULL)
   4794                 {
   4795                     name[0] = 0;
   4796                     (*btm_cb.api.p_auth_complete_callback) (p_cb->pairing_bda,
   4797                                                             NULL,
   4798                                                             name, HCI_ERR_CONNECTION_TOUT);
   4799                 }
   4800                 else
   4801                     (*btm_cb.api.p_auth_complete_callback) (p_dev_rec->bd_addr,
   4802                                                             p_dev_rec->dev_class,
   4803                                                             p_dev_rec->sec_bd_name, HCI_ERR_CONNECTION_TOUT);
   4804             }
   4805             break;
   4806 
   4807         default:
   4808             BTM_TRACE_WARNING1 ("btm_sec_pairing_timeout() not processed state: %s", btm_pair_state_descr(btm_cb.pairing_state));
   4809             btm_sec_change_pairing_state (BTM_PAIR_STATE_IDLE);
   4810             break;
   4811     }
   4812 }
   4813 
   4814 /*******************************************************************************
   4815 **
   4816 ** Function         btm_sec_pin_code_request
   4817 **
   4818 ** Description      This function is called when controller requests PIN code
   4819 **
   4820 ** Returns          Pointer to the record or NULL
   4821 **
   4822 *******************************************************************************/
   4823 void btm_sec_pin_code_request (UINT8 *p_bda)
   4824 {
   4825     tBTM_SEC_DEV_REC *p_dev_rec;
   4826     tBTM_CB          *p_cb = &btm_cb;
   4827 
   4828     BTM_TRACE_EVENT3 ("btm_sec_pin_code_request()  State: %s, BDA:%04x%08x",
   4829                       btm_pair_state_descr(btm_cb.pairing_state),
   4830                       (p_bda[0]<<8)+p_bda[1], (p_bda[2]<<24)+(p_bda[3]<<16)+(p_bda[4]<<8)+p_bda[5] );
   4831 
   4832     if (btm_cb.pairing_state != BTM_PAIR_STATE_IDLE)
   4833     {
   4834         if ( (memcmp (p_bda, btm_cb.pairing_bda, BD_ADDR_LEN) == 0)  &&
   4835              (btm_cb.pairing_state == BTM_PAIR_STATE_WAIT_AUTH_COMPLETE) )
   4836         {
   4837              /* fake this out - porshe carkit issue - */
   4838 //            btm_cb.pairing_state = BTM_PAIR_STATE_IDLE;
   4839              if(! btm_cb.pin_code_len_saved)
   4840              {
   4841                  btsnd_hcic_pin_code_neg_reply (p_bda);
   4842                  return;
   4843              }
   4844              else
   4845              {
   4846                  btsnd_hcic_pin_code_req_reply (p_bda, btm_cb.pin_code_len_saved, p_cb->pin_code);
   4847       	         return;
   4848              }
   4849         }
   4850         else if ((btm_cb.pairing_state != BTM_PAIR_STATE_WAIT_PIN_REQ)
   4851                  || memcmp (p_bda, btm_cb.pairing_bda, BD_ADDR_LEN) != 0)
   4852         {
   4853             BTM_TRACE_WARNING1 ("btm_sec_pin_code_request() rejected - state: %s",
   4854                                 btm_pair_state_descr(btm_cb.pairing_state));
   4855 
   4856 #ifdef PORCHE_PAIRING_CONFLICT
   4857             /* reply pin code again due to counter in_rand when local initiates pairing */
   4858             BTM_TRACE_EVENT0 ("btm_sec_pin_code_request from remote dev. for local initiated pairing");
   4859             if(! btm_cb.pin_code_len_saved)
   4860             {
   4861                 btsnd_hcic_pin_code_neg_reply (p_bda);
   4862             }
   4863             else
   4864             {
   4865                 btm_sec_change_pairing_state (BTM_PAIR_STATE_WAIT_AUTH_COMPLETE);
   4866                 btsnd_hcic_pin_code_req_reply (p_bda, btm_cb.pin_code_len_saved, p_cb->pin_code);
   4867             }
   4868 #else
   4869             btsnd_hcic_pin_code_neg_reply (p_bda);
   4870 #endif
   4871             return;
   4872         }
   4873     }
   4874 
   4875     p_dev_rec = btm_find_or_alloc_dev (p_bda);
   4876     /* received PIN code request. must be non-sm4 */
   4877     p_dev_rec->sm4 = BTM_SM4_KNOWN;
   4878 
   4879     if (btm_cb.pairing_state == BTM_PAIR_STATE_IDLE)
   4880     {
   4881         memcpy (btm_cb.pairing_bda, p_bda, BD_ADDR_LEN);
   4882 
   4883         btm_cb.pairing_flags = BTM_PAIR_FLAGS_PEER_STARTED_DD;
   4884         /* Make sure we reset the trusted mask to help against attacks */
   4885         BTM_SEC_CLR_TRUSTED_DEVICE(p_dev_rec->trusted_mask);
   4886     }
   4887 
   4888     if (!p_cb->pairing_disabled && (p_cb->cfg.pin_type == HCI_PIN_TYPE_FIXED))
   4889     {
   4890         BTM_TRACE_EVENT0 ("btm_sec_pin_code_request fixed pin replying");
   4891         btm_sec_change_pairing_state (BTM_PAIR_STATE_WAIT_AUTH_COMPLETE);
   4892         btsnd_hcic_pin_code_req_reply (p_bda, p_cb->cfg.pin_code_len, p_cb->cfg.pin_code);
   4893         return;
   4894     }
   4895 
   4896     /* Use the connecting device's CoD for the connection */
   4897     if ( (!memcmp (p_bda, p_cb->connecting_bda, BD_ADDR_LEN))
   4898          &&  (p_cb->connecting_dc[0] || p_cb->connecting_dc[1] || p_cb->connecting_dc[2]) )
   4899         memcpy (p_dev_rec->dev_class, p_cb->connecting_dc, DEV_CLASS_LEN);
   4900 
   4901     /* We could have started connection after asking user for the PIN code */
   4902     if (btm_cb.pin_code_len != 0)
   4903     {
   4904         BTM_TRACE_EVENT0 ("btm_sec_pin_code_request bonding sending reply");
   4905         btsnd_hcic_pin_code_req_reply (p_bda, btm_cb.pin_code_len, p_cb->pin_code);
   4906 
   4907 #ifdef PORCHE_PAIRING_CONFLICT
   4908         btm_cb.pin_code_len_saved = btm_cb.pin_code_len;
   4909 #endif
   4910 
   4911         /* Mark that we forwarded received from the user PIN code */
   4912         btm_cb.pin_code_len = 0;
   4913 
   4914         /* We can change mode back right away, that other connection being established */
   4915         /* is not forced to be secure - found a FW issue, so we can not do this
   4916         btm_restore_mode(); */
   4917 
   4918         btm_sec_change_pairing_state (BTM_PAIR_STATE_WAIT_AUTH_COMPLETE);
   4919     }
   4920 
   4921     /* If pairing disabled OR (no PIN callback and not bonding) */
   4922     /* OR we could not allocate entry in the database reject pairing request */
   4923     else if (p_cb->pairing_disabled
   4924              || (p_cb->api.p_pin_callback == NULL)
   4925 
   4926              /* OR Microsoft keyboard can for some reason try to establish connection */
   4927              /*  the only thing we can do here is to shut it up.  Normally we will be originator */
   4928              /*  for keyboard bonding */
   4929              || (!p_dev_rec->is_originator
   4930                  && ((p_dev_rec->dev_class[1] & BTM_COD_MAJOR_CLASS_MASK) == BTM_COD_MAJOR_PERIPHERAL)
   4931                  &&  (p_dev_rec->dev_class[2] & BTM_COD_MINOR_KEYBOARD)) )
   4932     {
   4933         BTM_TRACE_WARNING3("btm_sec_pin_code_request(): Pairing disabled:%d; PIN callback:%x, Dev Rec:%x!",
   4934                            p_cb->pairing_disabled, p_cb->api.p_pin_callback, p_dev_rec);
   4935 
   4936         btsnd_hcic_pin_code_neg_reply (p_bda);
   4937     }
   4938     /* Notify upper layer of PIN request and start expiration timer */
   4939     else
   4940     {
   4941         btm_cb.pin_code_len_saved = 0;
   4942         btm_sec_change_pairing_state (BTM_PAIR_STATE_WAIT_LOCAL_PIN);
   4943         /* Pin code request can not come at the same time as connection request */
   4944         memcpy (p_cb->connecting_bda, p_bda, BD_ADDR_LEN);
   4945         memcpy (p_cb->connecting_dc,  p_dev_rec->dev_class, DEV_CLASS_LEN);
   4946 
   4947         /* Check if the name is known */
   4948         /* Even if name is not known we might not be able to get one */
   4949         /* this is the case when we are already getting something from the */
   4950         /* device, so HCI level is flow controlled */
   4951         /* Also cannot send remote name request while paging, i.e. connection is not completed */
   4952         if (p_dev_rec->sec_flags & BTM_SEC_NAME_KNOWN)
   4953         {
   4954             BTM_TRACE_EVENT0 ("btm_sec_pin_code_request going for callback");
   4955 
   4956             btm_cb.pairing_flags |= BTM_PAIR_FLAGS_PIN_REQD;
   4957             if (p_cb->api.p_pin_callback)
   4958                 (*p_cb->api.p_pin_callback) (p_bda, p_dev_rec->dev_class, p_dev_rec->sec_bd_name);
   4959         }
   4960         else
   4961         {
   4962             BTM_TRACE_EVENT0 ("btm_sec_pin_code_request going for remote name");
   4963 
   4964             /* We received PIN code request for the device with unknown name */
   4965             /* it is not user friendly just to ask for the PIN without name */
   4966             /* try to get name at first */
   4967             if (!btsnd_hcic_rmt_name_req (p_dev_rec->bd_addr,
   4968                                           HCI_PAGE_SCAN_REP_MODE_R1,
   4969                                           HCI_MANDATARY_PAGE_SCAN_MODE, 0))
   4970             {
   4971                 p_dev_rec->sec_flags |= BTM_SEC_NAME_KNOWN;
   4972                 p_dev_rec->sec_bd_name[0] = 'f';
   4973                 p_dev_rec->sec_bd_name[1] = '0';
   4974                 BTM_TRACE_ERROR0 ("can not send rmt_name_req?? fake a name and call callback");
   4975 
   4976                 btm_cb.pairing_flags |= BTM_PAIR_FLAGS_PIN_REQD;
   4977                 if (p_cb->api.p_pin_callback)
   4978                     (*p_cb->api.p_pin_callback) (p_bda, p_dev_rec->dev_class, p_dev_rec->sec_bd_name);
   4979             }
   4980         }
   4981     }
   4982 
   4983     return;
   4984 }
   4985 
   4986 /*******************************************************************************
   4987 **
   4988 ** Function         btm_sec_update_clock_offset
   4989 **
   4990 ** Description      This function is called to update clock offset
   4991 **
   4992 ** Returns          void
   4993 **
   4994 *******************************************************************************/
   4995 void btm_sec_update_clock_offset (UINT16 handle, UINT16 clock_offset)
   4996 {
   4997     tBTM_SEC_DEV_REC  *p_dev_rec;
   4998     tBTM_INQ_INFO     *p_inq_info;
   4999 
   5000     if ((p_dev_rec = btm_find_dev_by_handle (handle)) == NULL)
   5001         return;
   5002 
   5003     p_dev_rec->clock_offset = clock_offset | BTM_CLOCK_OFFSET_VALID;
   5004 
   5005     if ((p_inq_info = BTM_InqDbRead(p_dev_rec->bd_addr)) == NULL)
   5006         return;
   5007 
   5008     p_inq_info->results.clock_offset = clock_offset | BTM_CLOCK_OFFSET_VALID;
   5009 }
   5010 
   5011 
   5012 /******************************************************************
   5013 ** S T A T I C     F U N C T I O N S
   5014 *******************************************************************/
   5015 
   5016 /*******************************************************************************
   5017 **
   5018 ** Function         btm_sec_execute_procedure
   5019 **
   5020 ** Description      This function is called to start required security
   5021 **                  procedure.  There is a case when multiplexing protocol
   5022 **                  calls this function on the originating side, connection to
   5023 **                  the peer will not be established.  This function in this
   5024 **                  case performs only authorization.
   5025 **
   5026 ** Returns          BTM_SUCCESS     - permission is granted
   5027 **                  BTM_CMD_STARTED - in process
   5028 **                  BTM_NO_RESOURCES  - permission declined
   5029 **
   5030 *******************************************************************************/
   5031 static tBTM_STATUS btm_sec_execute_procedure (tBTM_SEC_DEV_REC *p_dev_rec)
   5032 {
   5033     BTM_TRACE_EVENT3 ("btm_sec_execute_procedure: Required:0x%x Flags:0x%x State:%d",
   5034                       p_dev_rec->security_required, p_dev_rec->sec_flags, p_dev_rec->sec_state);
   5035 
   5036     /* There is a chance that we are getting name.  Wait until done. */
   5037     if (p_dev_rec->sec_state != 0)
   5038         return(BTM_CMD_STARTED);
   5039 
   5040     /* If any security is required, get the name first */
   5041     if (!(p_dev_rec->sec_flags & BTM_SEC_NAME_KNOWN)
   5042         && (p_dev_rec->hci_handle != BTM_SEC_INVALID_HANDLE))
   5043     {
   5044         BTM_TRACE_EVENT0 ("Security Manager: Start get name");
   5045         if (!btm_sec_start_get_name (p_dev_rec))
   5046         {
   5047             return(BTM_NO_RESOURCES);
   5048         }
   5049         return(BTM_CMD_STARTED);
   5050     }
   5051 
   5052     /* If connection is not authenticated and authentication is required */
   5053     /* start authentication and return PENDING to the caller */
   5054     if ((!(p_dev_rec->sec_flags & BTM_SEC_AUTHENTICATED))
   5055         && (( p_dev_rec->is_originator && (p_dev_rec->security_required & BTM_SEC_OUT_AUTHENTICATE))
   5056             || (!p_dev_rec->is_originator && (p_dev_rec->security_required & BTM_SEC_IN_AUTHENTICATE)))
   5057         && (p_dev_rec->hci_handle != BTM_SEC_INVALID_HANDLE))
   5058     {
   5059 #if (L2CAP_UCD_INCLUDED == TRUE)
   5060         /* if incoming UCD packet, discard it */
   5061         if ( !p_dev_rec->is_originator && (p_dev_rec->is_ucd == TRUE ))
   5062             return(BTM_FAILED_ON_SECURITY);
   5063 #endif
   5064 
   5065         BTM_TRACE_EVENT0 ("Security Manager: Start authentication");
   5066 
   5067         if (!btm_sec_start_authentication (p_dev_rec))
   5068         {
   5069             return(BTM_NO_RESOURCES);
   5070         }
   5071         return(BTM_CMD_STARTED);
   5072     }
   5073 
   5074     /* If connection is not encrypted and encryption is required */
   5075     /* start encryption and return PENDING to the caller */
   5076     if (!(p_dev_rec->sec_flags & BTM_SEC_ENCRYPTED)
   5077         && (( p_dev_rec->is_originator && (p_dev_rec->security_required & BTM_SEC_OUT_ENCRYPT))
   5078             || (!p_dev_rec->is_originator && (p_dev_rec->security_required & BTM_SEC_IN_ENCRYPT)))
   5079         && (p_dev_rec->hci_handle != BTM_SEC_INVALID_HANDLE))
   5080     {
   5081 #if (L2CAP_UCD_INCLUDED == TRUE)
   5082         /* if incoming UCD packet, discard it */
   5083         if ( !p_dev_rec->is_originator && (p_dev_rec->is_ucd == TRUE ))
   5084             return(BTM_FAILED_ON_SECURITY);
   5085 #endif
   5086 
   5087         BTM_TRACE_EVENT0 ("Security Manager: Start encryption");
   5088 
   5089         if (!btm_sec_start_encryption (p_dev_rec))
   5090         {
   5091             return(BTM_NO_RESOURCES);
   5092         }
   5093         return(BTM_CMD_STARTED);
   5094     }
   5095 
   5096     /* If connection is not authorized and authorization is required */
   5097     /* start authorization and return PENDING to the caller */
   5098     if (!(p_dev_rec->sec_flags & BTM_SEC_AUTHORIZED)
   5099         && (( p_dev_rec->is_originator && (p_dev_rec->security_required & BTM_SEC_OUT_AUTHORIZE))
   5100             || (!p_dev_rec->is_originator && (p_dev_rec->security_required & BTM_SEC_IN_AUTHORIZE))))
   5101     {
   5102         BTM_TRACE_EVENT2 ("service id:%d, is trusted:%d",
   5103                           p_dev_rec->p_cur_service->service_id,
   5104                           (BTM_SEC_IS_SERVICE_TRUSTED(p_dev_rec->trusted_mask,
   5105                                                       p_dev_rec->p_cur_service->service_id)));
   5106         if ((btm_sec_are_all_trusted(p_dev_rec->trusted_mask) == FALSE) &&
   5107             (p_dev_rec->p_cur_service->service_id < BTM_SEC_MAX_SERVICES) &&
   5108             (BTM_SEC_IS_SERVICE_TRUSTED(p_dev_rec->trusted_mask,
   5109                                         p_dev_rec->p_cur_service->service_id) == FALSE))
   5110         {
   5111             BTM_TRACE_EVENT0 ("Security Manager: Start authorization");
   5112             return(btm_sec_start_authorization (p_dev_rec));
   5113         }
   5114     }
   5115 
   5116     /* All required  security procedures already established */
   5117     p_dev_rec->security_required &= ~(BTM_SEC_OUT_AUTHORIZE | BTM_SEC_IN_AUTHORIZE |
   5118                                       BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_IN_AUTHENTICATE |
   5119                                       BTM_SEC_OUT_ENCRYPT | BTM_SEC_IN_ENCRYPT |
   5120                                       BTM_SEC_FORCE_MASTER | BTM_SEC_ATTEMPT_MASTER |
   5121                                       BTM_SEC_FORCE_SLAVE | BTM_SEC_ATTEMPT_SLAVE);
   5122 
   5123     BTM_TRACE_EVENT2 ("Security Manager: trusted:0x%04x%04x", p_dev_rec->trusted_mask[1], p_dev_rec->trusted_mask[0]);
   5124     BTM_TRACE_EVENT0 ("Security Manager: access granted");
   5125 
   5126     return(BTM_SUCCESS);
   5127 }
   5128 
   5129 
   5130 /*******************************************************************************
   5131 **
   5132 ** Function         btm_sec_start_get_name
   5133 **
   5134 ** Description      This function is called to start get name procedure
   5135 **
   5136 ** Returns          TRUE if started
   5137 **
   5138 *******************************************************************************/
   5139 static BOOLEAN btm_sec_start_get_name (tBTM_SEC_DEV_REC *p_dev_rec)
   5140 {
   5141     UINT8 tempstate = p_dev_rec->sec_state;
   5142 
   5143     p_dev_rec->sec_state = BTM_SEC_STATE_GETTING_NAME;
   5144 
   5145     /* Device should be connected, no need to provide correct page params */
   5146     /* 0 and NULL are as timeout and callback params because they are not used in security get name case */
   5147     if ((btm_initiate_rem_name (p_dev_rec->bd_addr, NULL, BTM_RMT_NAME_SEC,
   5148                                 0, NULL)) != BTM_CMD_STARTED)
   5149     {
   5150         p_dev_rec->sec_state = tempstate;
   5151         return(FALSE);
   5152     }
   5153 
   5154     return(TRUE);
   5155 }
   5156 
   5157 /*******************************************************************************
   5158 **
   5159 ** Function         btm_sec_start_authentication
   5160 **
   5161 ** Description      This function is called to start authentication
   5162 **
   5163 ** Returns          TRUE if started
   5164 **
   5165 *******************************************************************************/
   5166 static BOOLEAN btm_sec_start_authentication (tBTM_SEC_DEV_REC *p_dev_rec)
   5167 {
   5168     p_dev_rec->sec_state = BTM_SEC_STATE_AUTHENTICATING;
   5169 
   5170     return(btsnd_hcic_auth_request (p_dev_rec->hci_handle));
   5171 }
   5172 
   5173 /*******************************************************************************
   5174 **
   5175 ** Function         btm_sec_start_encryption
   5176 **
   5177 ** Description      This function is called to start encryption
   5178 **
   5179 ** Returns          TRUE if started
   5180 **
   5181 *******************************************************************************/
   5182 static BOOLEAN btm_sec_start_encryption (tBTM_SEC_DEV_REC *p_dev_rec)
   5183 {
   5184     if (!btsnd_hcic_set_conn_encrypt (p_dev_rec->hci_handle, TRUE))
   5185         return(FALSE);
   5186 
   5187     p_dev_rec->sec_state = BTM_SEC_STATE_ENCRYPTING;
   5188     return(TRUE);
   5189 }
   5190 
   5191 
   5192 /*******************************************************************************
   5193 **
   5194 ** Function         btm_sec_start_authorization
   5195 **
   5196 ** Description      This function is called to start authorization
   5197 **
   5198 ** Returns          TRUE if started
   5199 **
   5200 *******************************************************************************/
   5201 static UINT8 btm_sec_start_authorization (tBTM_SEC_DEV_REC *p_dev_rec)
   5202 {
   5203     UINT8    result;
   5204     UINT8   *p_service_name = NULL;
   5205     UINT8    service_id;
   5206 
   5207     if ((p_dev_rec->sec_flags & BTM_SEC_NAME_KNOWN)
   5208         || (p_dev_rec->hci_handle == BTM_SEC_INVALID_HANDLE))
   5209     {
   5210         if (!btm_cb.api.p_authorize_callback)
   5211             return(BTM_MODE_UNSUPPORTED);
   5212 
   5213         if (p_dev_rec->p_cur_service)
   5214         {
   5215 #if BTM_SEC_SERVICE_NAME_LEN > 0
   5216             if (p_dev_rec->is_originator)
   5217                 p_service_name = p_dev_rec->p_cur_service->orig_service_name;
   5218             else
   5219                 p_service_name = p_dev_rec->p_cur_service->term_service_name;
   5220 #endif
   5221             service_id = p_dev_rec->p_cur_service->service_id;
   5222         }
   5223         else
   5224             service_id = 0;
   5225 
   5226         /* Send authorization request if not already sent during this service connection */
   5227         if (p_dev_rec->last_author_service_id == BTM_SEC_NO_LAST_SERVICE_ID
   5228             || p_dev_rec->last_author_service_id != service_id)
   5229         {
   5230             p_dev_rec->sec_state = BTM_SEC_STATE_AUTHORIZING;
   5231             result = (*btm_cb.api.p_authorize_callback) (p_dev_rec->bd_addr,
   5232                                                      p_dev_rec->dev_class,
   5233                                                      p_dev_rec->sec_bd_name,
   5234                                                      p_service_name,
   5235                                                      service_id,
   5236                                                      p_dev_rec->is_originator);
   5237         }
   5238 
   5239         else    /* Already authorized once for this L2CAP bringup */
   5240         {
   5241             BTM_TRACE_DEBUG1 ("btm_sec_start_authorization: (Ignoring extra Authorization prompt for service %d)", service_id);
   5242             return (BTM_SUCCESS);
   5243         }
   5244 
   5245         if (result == BTM_SUCCESS)
   5246         {
   5247             p_dev_rec->sec_flags |= BTM_SEC_AUTHORIZED;
   5248 
   5249             /* Save the currently authorized service in case we are asked again by another multiplexer layer */
   5250             if (!p_dev_rec->is_originator)
   5251                 p_dev_rec->last_author_service_id = service_id;
   5252 
   5253             p_dev_rec->sec_state = BTM_SEC_STATE_IDLE;
   5254         }
   5255         return(result);
   5256     }
   5257     btm_sec_start_get_name (p_dev_rec);
   5258     return(BTM_CMD_STARTED);
   5259 }
   5260 
   5261 /*******************************************************************************
   5262 **
   5263 ** Function         btm_sec_are_all_trusted
   5264 **
   5265 ** Description      This function is called check if all services are trusted
   5266 **
   5267 ** Returns          TRUE if all are trusted, otherwise FALSE
   5268 **
   5269 *******************************************************************************/
   5270 BOOLEAN btm_sec_are_all_trusted(UINT32 p_mask[])
   5271 {
   5272     UINT32 trusted_inx;
   5273     for (trusted_inx = 0; trusted_inx < BTM_SEC_SERVICE_ARRAY_SIZE; trusted_inx++)
   5274     {
   5275         if (p_mask[trusted_inx] != BTM_SEC_TRUST_ALL)
   5276             return(FALSE);
   5277     }
   5278 
   5279     return(TRUE);
   5280 }
   5281 
   5282 /*******************************************************************************
   5283 **
   5284 ** Function         btm_sec_find_first_serv
   5285 **
   5286 ** Description      Look for the first record in the service database
   5287 **                  with specified PSM
   5288 **
   5289 ** Returns          Pointer to the record or NULL
   5290 **
   5291 *******************************************************************************/
   5292 static tBTM_SEC_SERV_REC *btm_sec_find_first_serv (CONNECTION_TYPE conn_type, UINT16 psm)
   5293 {
   5294     tBTM_SEC_SERV_REC *p_serv_rec = &btm_cb.sec_serv_rec[0];
   5295     int i;
   5296     BOOLEAN is_originator;
   5297 
   5298 #if (L2CAP_UCD_INCLUDED == TRUE)
   5299 
   5300     if ( conn_type & CONNECTION_TYPE_ORIG_MASK )
   5301         is_originator = TRUE;
   5302     else
   5303         is_originator = FALSE;
   5304 #else
   5305     is_originator = conn_type;
   5306 #endif
   5307 
   5308     if (is_originator && btm_cb.p_out_serv && btm_cb.p_out_serv->psm == psm)
   5309     {
   5310         /* If this is outgoing connection and the PSM matches p_out_serv,
   5311          * use it as the current service */
   5312         return btm_cb.p_out_serv;
   5313     }
   5314 
   5315     /* otherwise, just find the first record with the specified PSM */
   5316     for (i = 0; i < BTM_SEC_MAX_SERVICE_RECORDS; i++, p_serv_rec++)
   5317     {
   5318         if ( (p_serv_rec->security_flags & BTM_SEC_IN_USE) && (p_serv_rec->psm == psm) )
   5319             return(p_serv_rec);
   5320     }
   5321     return(NULL);
   5322 }
   5323 
   5324 
   5325 /*******************************************************************************
   5326 **
   5327 ** Function         btm_sec_find_next_serv
   5328 **
   5329 ** Description      Look for the next record in the service database
   5330 **                  with specified PSM
   5331 **
   5332 ** Returns          Pointer to the record or NULL
   5333 **
   5334 *******************************************************************************/
   5335 static tBTM_SEC_SERV_REC *btm_sec_find_next_serv (tBTM_SEC_SERV_REC *p_cur)
   5336 {
   5337     tBTM_SEC_SERV_REC *p_serv_rec   = &btm_cb.sec_serv_rec[0];
   5338     int               i;
   5339 
   5340     for (i = 0; i < BTM_SEC_MAX_SERVICE_RECORDS; i++, p_serv_rec++)
   5341     {
   5342         if ((p_serv_rec->security_flags & BTM_SEC_IN_USE)
   5343             && (p_serv_rec->psm == p_cur->psm) )
   5344         {
   5345             if (p_cur != p_serv_rec)
   5346             {
   5347                 return(p_serv_rec);
   5348             }
   5349         }
   5350     }
   5351     return(NULL);
   5352 }
   5353 
   5354 
   5355 /*******************************************************************************
   5356 **
   5357 ** Function         btm_sec_find_mx_serv
   5358 **
   5359 ** Description      Look for the record in the service database with specified
   5360 **                  PSM and multiplexor channel information
   5361 **
   5362 ** Returns          Pointer to the record or NULL
   5363 **
   5364 *******************************************************************************/
   5365 static tBTM_SEC_SERV_REC *btm_sec_find_mx_serv (UINT8 is_originator, UINT16 psm,
   5366                                                 UINT32 mx_proto_id, UINT32 mx_chan_id)
   5367 {
   5368     tBTM_SEC_SERV_REC *p_out_serv = btm_cb.p_out_serv;
   5369     tBTM_SEC_SERV_REC *p_serv_rec = &btm_cb.sec_serv_rec[0];
   5370     int i;
   5371 
   5372     BTM_TRACE_DEBUG0 ("btm_sec_find_mx_serv");
   5373     if (is_originator && p_out_serv && p_out_serv->psm == psm
   5374         && p_out_serv->mx_proto_id == mx_proto_id
   5375         && p_out_serv->orig_mx_chan_id == mx_chan_id)
   5376     {
   5377         /* If this is outgoing connection and the parameters match p_out_serv,
   5378          * use it as the current service */
   5379         return btm_cb.p_out_serv;
   5380     }
   5381 
   5382     /* otherwise, the old way */
   5383     for (i = 0; i < BTM_SEC_MAX_SERVICE_RECORDS; i++, p_serv_rec++)
   5384     {
   5385         if ((p_serv_rec->security_flags & BTM_SEC_IN_USE)
   5386             && (p_serv_rec->psm == psm)
   5387             && (p_serv_rec->mx_proto_id == mx_proto_id)
   5388             && (( is_originator && (p_serv_rec->orig_mx_chan_id  == mx_chan_id))
   5389                 || (!is_originator && (p_serv_rec->term_mx_chan_id  == mx_chan_id))))
   5390         {
   5391             return(p_serv_rec);
   5392         }
   5393     }
   5394     return(NULL);
   5395 }
   5396 
   5397 
   5398 /*******************************************************************************
   5399 **
   5400 ** Function         btm_sec_collision_timeout
   5401 **
   5402 ** Description      Encryption could not start because of the collision
   5403 **                  try to do it again
   5404 **
   5405 ** Returns          Pointer to the TLE struct
   5406 **
   5407 *******************************************************************************/
   5408 static void btm_sec_collision_timeout (TIMER_LIST_ENT *p_tle)
   5409 {
   5410     tBTM_STATUS status;
   5411 
   5412     BTM_TRACE_EVENT0 ("btm_sec_collision_timeout()");
   5413     btm_cb.sec_collision_tle.param = 0;
   5414 
   5415     status = btm_sec_execute_procedure (btm_cb.p_collided_dev_rec);
   5416 
   5417     /* If result is pending reply from the user or from the device is pending */
   5418     if (status != BTM_CMD_STARTED)
   5419     {
   5420         /* There is no next procedure or start of procedure failed, notify the waiting layer */
   5421         btm_sec_dev_rec_cback_event (btm_cb.p_collided_dev_rec, status);
   5422     }
   5423 }
   5424 
   5425 /*******************************************************************************
   5426 **
   5427 ** Function         btm_sec_link_key_request
   5428 **
   5429 ** Description      This function is called when controller requests link key
   5430 **
   5431 ** Returns          Pointer to the record or NULL
   5432 **
   5433 *******************************************************************************/
   5434 static void btm_send_link_key_notif (tBTM_SEC_DEV_REC *p_dev_rec)
   5435 {
   5436     if (btm_cb.api.p_link_key_callback)
   5437         (*btm_cb.api.p_link_key_callback) (p_dev_rec->bd_addr, p_dev_rec->dev_class,
   5438                                            p_dev_rec->sec_bd_name, p_dev_rec->link_key,
   5439                                            p_dev_rec->link_key_type);
   5440 }
   5441 
   5442 /*******************************************************************************
   5443 **
   5444 ** Function         BTM_ReadTrustedMask
   5445 **
   5446 ** Description      Get trusted mask for the peer device
   5447 **
   5448 ** Parameters:      bd_addr   - Address of the device
   5449 **
   5450 ** Returns          NULL, if the device record is not found.
   5451 **                  otherwise, the trusted mask
   5452 **
   5453 *******************************************************************************/
   5454 UINT32 * BTM_ReadTrustedMask (BD_ADDR bd_addr)
   5455 {
   5456     tBTM_SEC_DEV_REC *p_dev_rec;
   5457 
   5458     if ((p_dev_rec = btm_find_dev (bd_addr)) != NULL)
   5459     {
   5460         return(p_dev_rec->trusted_mask);
   5461     }
   5462     else
   5463     {
   5464         return NULL;
   5465     }
   5466 }
   5467 
   5468 /*******************************************************************************
   5469 **
   5470 ** Function         btm_restore_mode
   5471 **
   5472 ** Description      This function returns the security mode to previous setting
   5473 **                  if it was changed during bonding.
   5474 **
   5475 **
   5476 ** Parameters:      void
   5477 **
   5478 *******************************************************************************/
   5479 static void btm_restore_mode(void)
   5480 {
   5481     if (btm_cb.security_mode_changed)
   5482     {
   5483         btm_cb.security_mode_changed = FALSE;
   5484         BTM_TRACE_DEBUG1("btm_restore_mode: Authen Enable -> %d", (btm_cb.security_mode == BTM_SEC_MODE_LINK));
   5485         btsnd_hcic_write_auth_enable ((UINT8)(btm_cb.security_mode == BTM_SEC_MODE_LINK));
   5486     }
   5487 
   5488     if (btm_cb.pin_type_changed)
   5489     {
   5490         btm_cb.pin_type_changed = FALSE;
   5491         btsnd_hcic_write_pin_type (btm_cb.cfg.pin_type);
   5492     }
   5493 }
   5494 
   5495 
   5496 /*******************************************************************************
   5497 **
   5498 ** Function         btm_sec_find_dev_by_sec_state
   5499 **
   5500 ** Description      Look for the record in the device database for the device
   5501 **                  which is being authenticated or encrypted
   5502 **
   5503 ** Returns          Pointer to the record or NULL
   5504 **
   5505 *******************************************************************************/
   5506 tBTM_SEC_DEV_REC *btm_sec_find_dev_by_sec_state (UINT8 state)
   5507 {
   5508     tBTM_SEC_DEV_REC *p_dev_rec = &btm_cb.sec_dev_rec[0];
   5509     int i;
   5510 
   5511     for (i = 0; i < BTM_SEC_MAX_DEVICE_RECORDS; i++, p_dev_rec++)
   5512     {
   5513         if ((p_dev_rec->sec_flags & BTM_SEC_IN_USE)
   5514             && (p_dev_rec->sec_state == state))
   5515             return(p_dev_rec);
   5516     }
   5517     return(NULL);
   5518 }
   5519 
   5520 /*******************************************************************************
   5521 **
   5522 ** Function         BTM_snd_conn_encrypt
   5523 **
   5524 ** Description      This function is called to start/stop encryption
   5525 **                  Used by JSR-82
   5526 **
   5527 ** Returns          TRUE if request started
   5528 **
   5529 *******************************************************************************/
   5530 BOOLEAN BTM_snd_conn_encrypt (UINT16  handle, BOOLEAN enable)
   5531 {
   5532     tBTM_SEC_DEV_REC  *p_dev_rec = btm_find_dev_by_handle (handle);
   5533 
   5534     BTM_TRACE_EVENT2 ("BTM_snd_conn_encrypt Security Manager: encrypt_change p_dev_rec : 0x%x, enable = %s", p_dev_rec, (enable == TRUE) ? "TRUE" : "FALSE");
   5535 
   5536     if (!p_dev_rec)
   5537     {
   5538         BTM_TRACE_EVENT1 ("BTM_snd_conn_encrypt Error no  p_dev_rec : 0x%x\n", p_dev_rec);
   5539         return(FALSE);
   5540     }
   5541 
   5542     if ( p_dev_rec->sec_state == BTM_SEC_STATE_IDLE)
   5543     {
   5544         if (!btsnd_hcic_set_conn_encrypt (handle, enable))
   5545             return(FALSE);
   5546 
   5547         p_dev_rec->sec_state = BTM_SEC_STATE_ENCRYPTING;
   5548 
   5549         return(TRUE);
   5550     }
   5551     else
   5552         return(FALSE);
   5553 }
   5554 
   5555 /*******************************************************************************
   5556 **
   5557 ** Function         btm_sec_change_pairing_state
   5558 **
   5559 ** Description      This function is called to change pairing state
   5560 **
   5561 *******************************************************************************/
   5562 static void btm_sec_change_pairing_state (tBTM_PAIRING_STATE new_state)
   5563 {
   5564     tBTM_PAIRING_STATE  old_state = btm_cb.pairing_state;
   5565 
   5566     BTM_TRACE_EVENT1 ("btm_sec_change_pairing_state  Old: %s",  btm_pair_state_descr(btm_cb.pairing_state));
   5567     BTM_TRACE_EVENT2 ("btm_sec_change_pairing_state  New: %s pairing_flags:0x%x",btm_pair_state_descr(new_state), btm_cb.pairing_flags);
   5568 
   5569     btm_cb.pairing_state = new_state;
   5570 
   5571     if (new_state == BTM_PAIR_STATE_IDLE)
   5572     {
   5573         btu_stop_timer (&btm_cb.pairing_tle);
   5574 
   5575         btm_cb.pairing_flags = 0;
   5576         btm_cb.pin_code_len  = 0;
   5577 
   5578         /* Make sure the the lcb shows we are not bonding */
   5579         l2cu_update_lcb_4_bonding (btm_cb.pairing_bda, FALSE);
   5580 
   5581         btm_restore_mode();
   5582         btm_sec_check_pending_reqs();
   5583         btm_inq_clear_ssp();
   5584 
   5585         memset (btm_cb.pairing_bda, 0xFF, BD_ADDR_LEN);
   5586     }
   5587     else
   5588     {
   5589         /* If transitionng out of idle, mark the lcb as bonding */
   5590         if (old_state == BTM_PAIR_STATE_IDLE)
   5591             l2cu_update_lcb_4_bonding (btm_cb.pairing_bda, TRUE);
   5592 
   5593         btm_cb.pairing_tle.param = (TIMER_PARAM_TYPE)btm_sec_pairing_timeout;
   5594 
   5595         btu_start_timer (&btm_cb.pairing_tle, BTU_TTYPE_USER_FUNC, BTM_SEC_TIMEOUT_VALUE);
   5596     }
   5597 }
   5598 
   5599 
   5600 /*******************************************************************************
   5601 **
   5602 ** Function         btm_pair_state_descr
   5603 **
   5604 ** Description      Return state description for tracing
   5605 **
   5606 *******************************************************************************/
   5607 #if (BT_USE_TRACES == TRUE)
   5608 static char *btm_pair_state_descr (tBTM_PAIRING_STATE state)
   5609 {
   5610 #if (BT_TRACE_VERBOSE == TRUE)
   5611     switch (state)
   5612     {
   5613         case BTM_PAIR_STATE_IDLE:                   return("IDLE");
   5614         case BTM_PAIR_STATE_GET_REM_NAME:           return("GET_REM_NAME");
   5615         case BTM_PAIR_STATE_WAIT_PIN_REQ:           return("WAIT_PIN_REQ");
   5616         case BTM_PAIR_STATE_WAIT_LOCAL_PIN:         return("WAIT_LOCAL_PIN");
   5617         case BTM_PAIR_STATE_WAIT_NUMERIC_CONFIRM:   return("WAIT_NUM_CONFIRM");
   5618         case BTM_PAIR_STATE_KEY_ENTRY:              return("KEY_ENTRY");
   5619         case BTM_PAIR_STATE_WAIT_LOCAL_OOB_RSP:     return("WAIT_LOCAL_OOB_RSP");
   5620         case BTM_PAIR_STATE_WAIT_LOCAL_IOCAPS:      return("WAIT_LOCAL_IOCAPS");
   5621         case BTM_PAIR_STATE_INCOMING_SSP:           return("INCOMING_SSP");
   5622         case BTM_PAIR_STATE_WAIT_AUTH_COMPLETE:     return("WAIT_AUTH_COMPLETE");
   5623         case BTM_PAIR_STATE_WAIT_DISCONNECT:        return("WAIT_DISCONNECT");
   5624     }
   5625 
   5626     return("???");
   5627 #else
   5628     sprintf(btm_cb.state_temp_buffer,"%hu",state);
   5629 
   5630     return(btm_cb.state_temp_buffer);
   5631 #endif
   5632 }
   5633 #endif
   5634 
   5635 
   5636 /*******************************************************************************
   5637 **
   5638 ** Function         btm_sec_dev_rec_cback_event
   5639 **
   5640 ** Description      This function calls the callback function with the given
   5641 **                  result and clear the callback function.
   5642 **
   5643 ** Parameters:      void
   5644 **
   5645 *******************************************************************************/
   5646 void btm_sec_dev_rec_cback_event (tBTM_SEC_DEV_REC *p_dev_rec, UINT8 res)
   5647 {
   5648     tBTM_SEC_CALLBACK   *p_callback = p_dev_rec->p_callback;
   5649 
   5650     if (p_dev_rec->p_callback)
   5651     {
   5652         p_dev_rec->p_callback = NULL;
   5653 
   5654         (*p_callback) (p_dev_rec->bd_addr, p_dev_rec->p_ref_data, res);
   5655 
   5656     }
   5657     btm_sec_check_pending_reqs();
   5658 }
   5659 
   5660 /*******************************************************************************
   5661 **
   5662 ** Function         btm_sec_queue_mx_request
   5663 **
   5664 ** Description      Return state description for tracing
   5665 **
   5666 *******************************************************************************/
   5667 static BOOLEAN btm_sec_queue_mx_request (BD_ADDR bd_addr,  UINT16 psm,  BOOLEAN is_orig,
   5668                                          UINT32 mx_proto_id, UINT32 mx_chan_id,
   5669                                          tBTM_SEC_CALLBACK *p_callback, void *p_ref_data)
   5670 {
   5671     tBTM_SEC_QUEUE_ENTRY    *p_e;
   5672 
   5673     p_e = (tBTM_SEC_QUEUE_ENTRY *)GKI_getbuf (sizeof(tBTM_SEC_QUEUE_ENTRY));
   5674 
   5675     if (p_e)
   5676     {
   5677         p_e->psm            = psm;
   5678         p_e->is_orig        = is_orig;
   5679         p_e->p_callback     = p_callback;
   5680         p_e->p_ref_data     = p_ref_data;
   5681         p_e->mx_proto_id    = mx_proto_id;
   5682         p_e->mx_chan_id     = mx_chan_id;
   5683 
   5684         memcpy (p_e->bd_addr, bd_addr, BD_ADDR_LEN);
   5685 
   5686         BTM_TRACE_EVENT4 ("btm_sec_queue_mx_request() PSM: 0x%04x  Is_Orig: %u  mx_proto_id: %u  mx_chan_id: %u",
   5687                           psm, is_orig, mx_proto_id, mx_chan_id);
   5688 
   5689         GKI_enqueue (&btm_cb.sec_pending_q, p_e);
   5690 
   5691         return(TRUE);
   5692     }
   5693 
   5694     return(FALSE);
   5695 }
   5696 
   5697 static BOOLEAN btm_sec_check_prefetch_pin (tBTM_SEC_DEV_REC  *p_dev_rec)
   5698 {
   5699     UINT8 major = (UINT8)(p_dev_rec->dev_class[1] & BTM_COD_MAJOR_CLASS_MASK);
   5700     UINT8 minor = (UINT8)(p_dev_rec->dev_class[2] & BTM_COD_MINOR_CLASS_MASK);
   5701     BOOLEAN rv = FALSE;
   5702 
   5703     if ((major == BTM_COD_MAJOR_AUDIO)
   5704         &&  ((minor == BTM_COD_MINOR_CONFM_HANDSFREE) || (minor == BTM_COD_MINOR_CAR_AUDIO)) )
   5705     {
   5706         BTM_TRACE_EVENT2 ("btm_sec_check_prefetch_pin: Skipping pre-fetch PIN for carkit COD Major: 0x%02x Minor: 0x%02x", major, minor);
   5707 
   5708         if (btm_cb.security_mode_changed == FALSE)
   5709         {
   5710             btm_cb.security_mode_changed = TRUE;
   5711 #ifdef APPL_AUTH_WRITE_EXCEPTION
   5712             if(!(APPL_AUTH_WRITE_EXCEPTION)(p_dev_rec->bd_addr))
   5713 #endif
   5714                 btsnd_hcic_write_auth_enable (TRUE);
   5715         }
   5716     }
   5717     else
   5718     {
   5719         btm_sec_change_pairing_state (BTM_PAIR_STATE_WAIT_LOCAL_PIN);
   5720 
   5721         /* If we got a PIN, use that, else try to get one */
   5722         if (btm_cb.pin_code_len)
   5723         {
   5724             BTM_PINCodeReply (p_dev_rec->bd_addr, BTM_SUCCESS, btm_cb.pin_code_len, btm_cb.pin_code, p_dev_rec->trusted_mask);
   5725         }
   5726         else
   5727         {
   5728             /* pin was not supplied - pre-fetch pin code now */
   5729             if (btm_cb.api.p_pin_callback && ((btm_cb.pairing_flags & BTM_PAIR_FLAGS_PIN_REQD) == 0))
   5730             {
   5731                 BTM_TRACE_DEBUG0("btm_sec_check_prefetch_pin: PIN code callback called");
   5732                 if (btm_bda_to_acl(p_dev_rec->bd_addr) == NULL)
   5733                 btm_cb.pairing_flags |= BTM_PAIR_FLAGS_PIN_REQD;
   5734                 (btm_cb.api.p_pin_callback) (p_dev_rec->bd_addr, p_dev_rec->dev_class, p_dev_rec->sec_bd_name);
   5735             }
   5736         }
   5737 
   5738         rv = TRUE;
   5739     }
   5740 
   5741     return rv;
   5742 }
   5743 
   5744 #if (BLE_INCLUDED == TRUE)
   5745 /*******************************************************************************
   5746 **
   5747 ** Function         btm_sec_clear_ble_keys
   5748 **
   5749 ** Description      This function is called to clear out the BLE keys.
   5750 **                  Typically when devices are removed in BTM_SecDeleteDevice,
   5751 **                  or when a new BT Link key is generated.
   5752 **
   5753 ** Returns          void
   5754 **
   5755 *******************************************************************************/
   5756 void btm_sec_clear_ble_keys (tBTM_SEC_DEV_REC  *p_dev_rec)
   5757 {
   5758 
   5759     BTM_TRACE_DEBUG0 ("btm_sec_clear_ble_keys: Clearing BLE Keys");
   5760 #if (SMP_INCLUDED== TRUE)
   5761     p_dev_rec->ble.key_type = 0;
   5762     memset (&p_dev_rec->ble.keys, 0, sizeof(tBTM_SEC_BLE_KEYS));
   5763 #endif
   5764     gatt_delete_dev_from_srv_chg_clt_list(p_dev_rec->bd_addr);
   5765 }
   5766 
   5767 
   5768 /*******************************************************************************
   5769 **
   5770 ** Function         btm_sec_is_a_bonded_dev
   5771 **
   5772 ** Description       Is the specified device is a bonded device
   5773 **
   5774 ** Returns          TRUE - dev is bonded
   5775 **
   5776 *******************************************************************************/
   5777 BOOLEAN btm_sec_is_a_bonded_dev (BD_ADDR bda)
   5778 {
   5779 
   5780     tBTM_SEC_DEV_REC *p_dev_rec= btm_find_dev (bda);
   5781     BOOLEAN is_bonded= FALSE;
   5782 
   5783 #if (SMP_INCLUDED== TRUE)
   5784     if (p_dev_rec && (p_dev_rec->ble.key_type || (p_dev_rec->sec_flags & BTM_SEC_LINK_KEY_KNOWN)))
   5785     {
   5786         is_bonded = TRUE;
   5787     }
   5788 #endif
   5789     BTM_TRACE_DEBUG1 ("btm_sec_is_a_bonded_dev is_bonded=%d", is_bonded);
   5790     return(is_bonded);
   5791 }
   5792 
   5793 /*******************************************************************************
   5794 **
   5795 ** Function         btm_sec_is_le_capable_dev
   5796 **
   5797 ** Description       Is the specified device is dual mode or LE only device
   5798 **
   5799 ** Returns          TRUE - dev is a dual mode
   5800 **
   5801 *******************************************************************************/
   5802 BOOLEAN btm_sec_is_le_capable_dev (BD_ADDR bda)
   5803 {
   5804     tBTM_SEC_DEV_REC *p_dev_rec= btm_find_dev (bda);
   5805     BOOLEAN le_capable = FALSE;
   5806 
   5807 #if (BLE_INCLUDED== TRUE)
   5808     if (p_dev_rec && ((p_dev_rec->device_type == BT_DEVICE_TYPE_DUMO) ||
   5809          (p_dev_rec->device_type == BT_DEVICE_TYPE_BLE) ) )
   5810     {
   5811         le_capable  = TRUE;
   5812     }
   5813 #endif
   5814     return le_capable;
   5815 }
   5816 
   5817 /*******************************************************************************
   5818 **
   5819 ** Function         btm_sec_find_bonded_dev
   5820 **
   5821 ** Description      Find a bonded device starting from the specified index
   5822 **
   5823 ** Returns          TRUE - found a bonded device
   5824 **
   5825 *******************************************************************************/
   5826 BOOLEAN btm_sec_find_bonded_dev (UINT8 start_idx, UINT8 *p_found_idx, tBTM_SEC_DEV_REC *p_rec)
   5827 {
   5828     BOOLEAN found= FALSE;
   5829 
   5830 #if (SMP_INCLUDED== TRUE)
   5831     tBTM_SEC_DEV_REC *p_dev_rec;
   5832     int i;
   5833     if (start_idx >= BTM_SEC_MAX_DEVICE_RECORDS)
   5834     {
   5835         BTM_TRACE_DEBUG0 ("LE bonded device not found");
   5836         return found;
   5837     }
   5838 
   5839     p_dev_rec = &btm_cb.sec_dev_rec[start_idx];
   5840     for (i = start_idx; i < BTM_SEC_MAX_DEVICE_RECORDS; i++, p_dev_rec++)
   5841     {
   5842         if (p_dev_rec->ble.key_type || (p_dev_rec->sec_flags & BTM_SEC_LINK_KEY_KNOWN))
   5843         {
   5844             *p_found_idx = i;
   5845             p_rec = p_dev_rec;
   5846             break;
   5847         }
   5848     }
   5849     BTM_TRACE_DEBUG1 ("btm_sec_find_bonded_dev=%d", found);
   5850 #endif
   5851     return(found);
   5852 }
   5853 #endif /* BLE_INCLUDED */
   5854 
   5855