Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 5ab506a4 authored by Jacky Cheung's avatar Jacky Cheung
Browse files

SMP: Delay authorization complete.

Delay authorization complete during Bond Pending state in SMP.
Instead of automatically advancing the Bond Pending state, create
a 500ms window to allow the slave to stop pairing by sending over
the Pairing Failed command during the Bond Pending state.

BUG: 28475887
Change-Id: Id6c30247d15258cd18eb34827694b6cd79ca753a
parent 1888b767
Loading
Loading
Loading
Loading
+20 −3
Original line number Diff line number Diff line
@@ -24,6 +24,8 @@
#include "stack/smp/smp_int.h"
#include "utils/include/bt_utils.h"

extern fixed_queue_t *btu_general_alarm_queue;

#if SMP_INCLUDED == TRUE
const UINT8 smp_association_table[2][SMP_IO_CAP_MAX][SMP_IO_CAP_MAX] =
{
@@ -553,6 +555,9 @@ void smp_proc_pair_fail(tSMP_CB *p_cb, tSMP_INT_DATA *p_data)
{
    SMP_TRACE_DEBUG("%s", __func__);
    p_cb->status = *(UINT8 *)p_data;

    /* Cancel pending auth complete timer if set */
    alarm_cancel(p_cb->delayed_auth_timer_ent);
}

/*******************************************************************************
@@ -1287,7 +1292,6 @@ void smp_key_pick_key(tSMP_CB *p_cb, tSMP_INT_DATA *p_data)
*******************************************************************************/
void smp_key_distribution(tSMP_CB *p_cb, tSMP_INT_DATA *p_data)
{
    UINT8   reason = SMP_SUCCESS;
    SMP_TRACE_DEBUG("%s role=%d (0-master) r_keys=0x%x i_keys=0x%x",
                      __func__, p_cb->role, p_cb->local_r_key, p_cb->local_i_key);

@@ -1309,12 +1313,25 @@ void smp_key_distribution(tSMP_CB *p_cb, tSMP_INT_DATA *p_data)
            }

            if (p_cb->total_tx_unacked == 0)
                smp_sm_event(p_cb, SMP_AUTH_CMPL_EVT, &reason);
            else
            {
                /*
                 * Instead of declaring authorization complete immediately,
                 * delay the event from being sent by SMP_DELAYED_AUTH_TIMEOUT_MS.
                 * This allows the slave to send over Pairing Failed if the
                 * last key is rejected.  During this waiting window, the
                 * state should remain in SMP_STATE_BOND_PENDING.
                 */
                if (!alarm_is_scheduled(p_cb->delayed_auth_timer_ent)) {
                    SMP_TRACE_DEBUG("%s delaying auth complete.", __func__);
                    alarm_set_on_queue(p_cb->delayed_auth_timer_ent, SMP_DELAYED_AUTH_TIMEOUT_MS,
                                       smp_delayed_auth_complete_timeout, NULL, btu_general_alarm_queue);
                }
            } else {
                p_cb->wait_for_authorization_complete = TRUE;
            }
        }
    }
}

/*******************************************************************************
** Function         smp_decide_association_model
+1 −0
Original line number Diff line number Diff line
@@ -52,6 +52,7 @@ void SMP_Init(void)
{
    memset(&smp_cb, 0, sizeof(tSMP_CB));
    smp_cb.smp_rsp_timer_ent = alarm_new("smp.smp_rsp_timer_ent");
    smp_cb.delayed_auth_timer_ent = alarm_new("smp.delayed_auth_timer_ent");

#if defined(SMP_INITIAL_TRACE_LEVEL)
    smp_cb.trace_level = SMP_INITIAL_TRACE_LEVEL;
+4 −1
Original line number Diff line number Diff line
@@ -51,6 +51,7 @@ typedef UINT8 tSMP_ASSO_MODEL;
#endif

#define SMP_WAIT_FOR_RSP_TIMEOUT_MS      (30 * 1000)
#define SMP_DELAYED_AUTH_TIMEOUT_MS      500

#define SMP_OPCODE_INIT                   0x04

@@ -340,6 +341,7 @@ typedef struct
    UINT16          total_tx_unacked;
    BOOLEAN         wait_for_authorization_complete;
    UINT8           cert_failure; /*failure case for certification */
    alarm_t         *delayed_auth_timer_ent;
}tSMP_CB;

/* Server Action functions are of this type */
@@ -481,6 +483,7 @@ extern void smp_proc_pairing_cmpl(tSMP_CB *p_cb);
extern void smp_convert_string_to_tk(BT_OCTET16 tk, UINT32 passkey);
extern void smp_mask_enc_key(UINT8 loc_enc_size, UINT8 * p_data);
extern void smp_rsp_timeout(void *data);
extern void smp_delayed_auth_complete_timeout(void *data);
extern void smp_xor_128(BT_OCTET16 a, BT_OCTET16 b);
extern BOOLEAN smp_encrypt_data (UINT8 *key, UINT8 key_len,
                                 UINT8 *plain_text, UINT8 pt_len,
+1 −1
Original line number Diff line number Diff line
@@ -240,7 +240,7 @@ static const UINT8 smp_master_entry_map[][SMP_STATE_MAX] =
/* PAIR_RSP             */{ 0,    0,     0,      1,     0,   0,    0,   0,      0,      0,    0,    0,      0,     0,     0,    0,     0   },
/* CONFIRM              */{ 0,    0,     0,      0,     0,   1,    0,   0,      0,      0,    0,    0,      0,     0,     0,    0,     0   },
/* RAND                 */{ 0,    0,     0,      0,     0,   0,    1,   0,      0,      0,    1,    0,      0,     0,     0,    0,     0   },
/* PAIR_FAIL            */{ 0,    0x81,  0,      0x81,  0x81,0x81, 0x81,0x81,   0x81,   0x81, 0x81, 0x81,   0x81,  0x81,  0,    0,     0   },
/* PAIR_FAIL            */{ 0,    0x81,  0,      0x81,  0x81,0x81, 0x81,0x81,   0x81,   0x81, 0x81, 0x81,   0x81,  0x81,  0,    0x81,  0   },
/* ENC_INFO             */{ 0,    0,     0,      0,     0,   0,    0,   0,      0,      0,    0,    0,      0,     0,     0,    1,     0   },
/* MASTER_ID            */{ 0,    0,     0,      0,     0,   0,    0,   0,      0,      0,    0,    0,      0,     0,     0,    4,     0   },
/* ID_INFO              */{ 0,    0,     0,      0,     0,   0,    0,   0,      0,      0,    0,    0,      0,     0,     0,    2,     0   },
+26 −0
Original line number Diff line number Diff line
@@ -373,6 +373,30 @@ void smp_rsp_timeout(UNUSED_ATTR void *data)
    }
}

/*******************************************************************************
**
** Function         smp_delayed_auth_complete_timeout
**
** Description      Called when no pairing failed command received within timeout
**                  period.
**
** Returns          void
**
*******************************************************************************/
void smp_delayed_auth_complete_timeout(UNUSED_ATTR void *data)
{
    /*
     * Waited for potential pair failure. Send SMP_AUTH_CMPL_EVT if
     * the state is still in bond pending.
     */
    if (smp_get_state() == SMP_STATE_BOND_PENDING)
    {
        UINT8 reason = SMP_SUCCESS;
        SMP_TRACE_EVENT("%s sending delayed auth complete.", __func__);
        smp_sm_event(&smp_cb, SMP_AUTH_CMPL_EVT, &reason);
    }
}

/*******************************************************************************
**
** Function         smp_build_pairing_req_cmd
@@ -842,10 +866,12 @@ void smp_cb_cleanup(tSMP_CB *p_cb)
    SMP_TRACE_EVENT("smp_cb_cleanup");

    alarm_free(p_cb->smp_rsp_timer_ent);
    alarm_free(p_cb->delayed_auth_timer_ent);
    memset(p_cb, 0, sizeof(tSMP_CB));
    p_cb->p_callback = p_callback;
    p_cb->trace_level = trace_level;
    p_cb->smp_rsp_timer_ent = alarm_new("smp.smp_rsp_timer_ent");
    p_cb->delayed_auth_timer_ent = alarm_new("smp.delayed_auth_timer_ent");
}

/*******************************************************************************