Merge pull request #279 from ccollins476ad/key-wont-fit

BLE Host - Policy for SM key overflow

X-Original-Commit: d877c32d698bbca943bdbc8cccd50e9c18de0977
This commit is contained in:
ccollins476ad
2017-06-26 09:14:09 -07:00
committed by GitHub
10 changed files with 589 additions and 117 deletions
+11
View File
@@ -71,6 +71,7 @@ struct os_event;
#define BLE_HS_EAUTHOR 24
#define BLE_HS_EENCRYPT 25
#define BLE_HS_EENCRYPT_KEY_SZ 26
#define BLE_HS_ESTORE_CAP 27
#define BLE_HS_ERR_ATT_BASE 0x100 /* 256 */
#define BLE_HS_ATT_ERR(x) ((x) ? BLE_HS_ERR_ATT_BASE + (x) : 0)
@@ -151,6 +152,16 @@ struct ble_hs_cfg {
ble_store_read_fn *store_read_cb;
ble_store_write_fn *store_write_cb;
ble_store_delete_fn *store_delete_cb;
/**
* This callback gets executed when a persistence operation cannot be
* performed or a persistence failure is imminent. For example, if is
* insufficient storage capacity for a record to be persisted, this
* function gets called to give the application the opportunity to make
* room.
*/
ble_store_status_fn *store_status_cb;
void *store_status_arg;
};
extern struct ble_hs_cfg ble_hs_cfg;
+68
View File
@@ -31,6 +31,12 @@ extern "C" {
#define BLE_STORE_OBJ_TYPE_PEER_SEC 2
#define BLE_STORE_OBJ_TYPE_CCCD 3
/** Failed to persist record; insufficient storage capacity. */
#define BLE_STORE_EVENT_OVERFLOW 1
/** About to execute a procedure that may fail due to overflow. */
#define BLE_STORE_EVENT_FULL 2
/**
* Used as a key for lookups of security material. This struct corresponds to
* the following store object types:
@@ -132,6 +138,46 @@ union ble_store_value {
struct ble_store_value_cccd cccd;
};
struct ble_store_status_event {
/**
* The type of event being reported; one of the BLE_STORE_EVENT_TYPE_[...]
* codes.
*/
int event_code;
/**
* Additional data related to the event; the valid field is inferred from
* the obj_type,event_code pair.
*/
union {
/**
* Represents a write that failed due to storage exhaustion. Valid for
* the following event types:
* o BLE_STORE_EVENT_OVERFLOW
*/
struct {
/** The type of object that failed to be written. */
int obj_type;
/** The object that failed to be written. */
const union ble_store_value *value;
} overflow;
/**
* Represents the possiblity that a scheduled write will fail due to
* storage exhaustion. Valid for the following event types:
* o BLE_STORE_EVENT_FULL
*/
struct {
/** The type of object that may fail to be written. */
int obj_type;
/** The handle of the connection which prompted the write. */
uint16_t conn_handle;
} full;
};
};
/**
* Searches the store for an object matching the specified criteria. If a
* match is found, it is read from the store and the dst parameter is populated
@@ -182,10 +228,29 @@ typedef int ble_store_write_fn(int obj_type, const union ble_store_value *val);
*/
typedef int ble_store_delete_fn(int obj_type, const union ble_store_key *key);
/**
* Indicates an inability to perform a store operation. This callback should
* do one of two things:
* o Address the problem and return 0, indicating that the store operation
* should proceed.
* o Return nonzero to indicate that the store operation should be aborted.
*
* @param event Describes the store event being reported.
* @param arg Optional user argument.
*
* @return 0 if the store operation should proceed;
* nonzero if the store operation should be
* aborted.
*/
typedef int ble_store_status_fn(struct ble_store_status_event *event,
void *arg);
int ble_store_read(int obj_type, const union ble_store_key *key,
union ble_store_value *val);
int ble_store_write(int obj_type, const union ble_store_value *val);
int ble_store_delete(int obj_type, const union ble_store_key *key);
int ble_store_overflow_event(int obj_type, const union ble_store_value *value);
int ble_store_full_event(int obj_type, uint16_t conn_handle);
int ble_store_read_our_sec(const struct ble_store_key_sec *key_sec,
struct ble_store_value_sec *value_sec);
@@ -225,6 +290,9 @@ int ble_store_util_bonded_peers(ble_addr_t *out_peer_id_addrs,
int max_peers);
int ble_store_util_delete_all(int type, const union ble_store_key *key);
int ble_store_util_delete_peer(const ble_addr_t *peer_id_addr);
int ble_store_util_delete_oldest_peer(void);
int ble_store_util_count(int type, int *out_count);
int ble_store_util_status_rr(struct ble_store_status_event *event, void *arg);
#ifdef __cplusplus
}
+116 -34
View File
@@ -195,28 +195,13 @@ ble_sm_dbg_set_next_csrk(uint8_t *next_csrk)
ble_sm_dbg_next_csrk_set = 1;
}
int
ble_sm_dbg_num_procs(void)
{
struct ble_sm_proc *proc;
int cnt;
cnt = 0;
STAILQ_FOREACH(proc, &ble_sm_procs, next) {
BLE_HS_DBG_ASSERT(cnt < MYNEWT_VAL(BLE_SM_MAX_PROCS));
cnt++;
}
return cnt;
}
#endif
static void
ble_sm_dbg_assert_no_cycles(void)
{
#if MYNEWT_VAL(BLE_HS_DEBUG)
ble_sm_dbg_num_procs();
ble_sm_num_procs();
#endif
}
@@ -236,6 +221,24 @@ ble_sm_dbg_assert_not_inserted(struct ble_sm_proc *proc)
* $misc *
*****************************************************************************/
/**
* Calculates the number of active SM procedures.
*/
int
ble_sm_num_procs(void)
{
struct ble_sm_proc *proc;
int cnt;
cnt = 0;
STAILQ_FOREACH(proc, &ble_sm_procs, next) {
BLE_HS_DBG_ASSERT(cnt < MYNEWT_VAL(BLE_SM_MAX_PROCS));
cnt++;
}
return cnt;
}
int
ble_sm_gen_pair_rand(uint8_t *pair_rand)
{
@@ -971,6 +974,62 @@ ble_sm_key_dist(struct ble_sm_proc *proc,
}
}
static int
ble_sm_chk_store_overflow_by_type(int obj_type, uint16_t conn_handle)
{
#if !MYNEWT_VAL(BLE_SM_BONDING)
return 0;
#endif
int count;
int rc;
rc = ble_store_util_count(obj_type, &count);
if (rc != 0) {
return rc;
}
/* Pessimistically assume all active procs will persist bonds. */
ble_hs_lock();
count += ble_sm_num_procs();
ble_hs_unlock();
if (count < MYNEWT_VAL(BLE_STORE_MAX_BONDS)) {
/* There is sufficient capacity for another bond. */
return 0;
}
/* No capacity for an additional bond. Tell the application to make
* room.
*/
rc = ble_store_full_event(obj_type, conn_handle);
if (rc != 0) {
return rc;
}
return 0;
}
static int
ble_sm_chk_store_overflow(uint16_t conn_handle)
{
int rc;
rc = ble_sm_chk_store_overflow_by_type(BLE_STORE_OBJ_TYPE_PEER_SEC,
conn_handle);
if (rc != 0) {
return rc;
}
rc = ble_sm_chk_store_overflow_by_type(BLE_STORE_OBJ_TYPE_OUR_SEC,
conn_handle);
if (rc != 0) {
return rc;
}
return 0;
}
/*****************************************************************************
* $enc *
*****************************************************************************/
@@ -1689,6 +1748,20 @@ ble_sm_pair_req_rx(uint16_t conn_handle, struct os_mbuf **om,
ble_sm_proc_free(proc);
}
ble_hs_unlock();
/* Check if there is storage capacity for a new bond. If there isn't, ask
* the application to make room.
*/
rc = ble_sm_chk_store_overflow(conn_handle);
if (rc != 0) {
res->sm_err = BLE_SM_ERR_UNSPECIFIED;
res->app_status = rc;
return;
}
ble_hs_lock();
proc = ble_sm_proc_alloc();
if (proc != NULL) {
proc->conn_handle = conn_handle;
@@ -1746,6 +1819,7 @@ ble_sm_pair_rsp_rx(uint16_t conn_handle, struct os_mbuf **om,
struct ble_sm_pair_cmd *rsp;
struct ble_sm_proc *proc;
uint8_t ioact;
int rc;
res->app_status = ble_hs_mbuf_pullup_base(om, sizeof(*rsp));
if (res->app_status != 0) {
@@ -1770,8 +1844,6 @@ ble_sm_pair_rsp_rx(uint16_t conn_handle, struct os_mbuf **om,
res->sm_err = BLE_SM_ERR_INVAL;
res->app_status = BLE_HS_SM_US_ERR(BLE_SM_ERR_INVAL);
} else {
int rc;
ble_sm_pair_cfg(proc);
rc = ble_sm_io_action(proc, &ioact);
@@ -2325,30 +2397,40 @@ ble_sm_pair_initiate(uint16_t conn_handle)
{
struct ble_sm_result res;
struct ble_sm_proc *proc;
int rc;
/* Make sure a procedure isn't already in progress for this connection. */
ble_hs_lock();
proc = ble_sm_proc_find(conn_handle, BLE_SM_PROC_STATE_NONE, -1, NULL);
ble_hs_unlock();
if (proc != NULL) {
res.app_status = BLE_HS_EALREADY;
/* Set pointer to null so that existing entry doesn't get freed. */
proc = NULL;
} else {
proc = ble_sm_proc_alloc();
if (proc == NULL) {
res.app_status = BLE_HS_ENOMEM;
} else {
proc->conn_handle = conn_handle;
proc->state = BLE_SM_PROC_STATE_PAIR;
proc->flags |= BLE_SM_PROC_F_INITIATOR;
ble_sm_insert(proc);
res.execute = 1;
}
return BLE_HS_EALREADY;
}
ble_hs_unlock();
/* Check if there is storage capacity for a new bond. If there isn't, ask
* the application to make room.
*/
rc = ble_sm_chk_store_overflow(conn_handle);
if (rc != 0) {
return rc;
}
proc = ble_sm_proc_alloc();
if (proc == NULL) {
res.app_status = BLE_HS_ENOMEM;
} else {
proc->conn_handle = conn_handle;
proc->state = BLE_SM_PROC_STATE_PAIR;
proc->flags |= BLE_SM_PROC_F_INITIATOR;
ble_hs_lock();
ble_sm_insert(proc);
ble_hs_unlock();
res.execute = 1;
}
if (proc != NULL) {
ble_sm_process_result(conn_handle, &res);
+2 -2
View File
@@ -290,9 +290,10 @@ void ble_sm_dbg_set_next_master_id_rand(uint64_t next_master_id_rand);
void ble_sm_dbg_set_next_ltk(uint8_t *next_ltk);
void ble_sm_dbg_set_next_csrk(uint8_t *next_csrk);
void ble_sm_dbg_set_sc_keys(uint8_t *pubkey, uint8_t *privkey);
int ble_sm_dbg_num_procs(void);
#endif
int ble_sm_num_procs(void);
void ble_sm_pair_cmd_log(struct ble_sm_pair_cmd *cmd);
void ble_sm_pair_confirm_log(struct ble_sm_pair_confirm *cmd);
void ble_sm_pair_random_log(struct ble_sm_pair_random *cmd);
@@ -403,7 +404,6 @@ int ble_sm_init(void);
#else
#define ble_sm_dbg_num_procs() 0
#define ble_sm_enc_change_rx(evt) ((void)(evt))
#define ble_sm_ltk_req_rx(evt) ((void)(evt))
#define ble_sm_enc_key_refresh_rx(evt) ((void)(evt))
+74 -5
View File
@@ -28,12 +28,16 @@ ble_store_read(int obj_type, const union ble_store_key *key,
{
int rc;
ble_hs_lock();
if (ble_hs_cfg.store_read_cb == NULL) {
rc = BLE_HS_ENOTSUP;
} else {
rc = ble_hs_cfg.store_read_cb(obj_type, key, val);
}
ble_hs_unlock();
return rc;
}
@@ -43,12 +47,33 @@ ble_store_write(int obj_type, const union ble_store_value *val)
int rc;
if (ble_hs_cfg.store_write_cb == NULL) {
rc = BLE_HS_ENOTSUP;
} else {
rc = ble_hs_cfg.store_write_cb(obj_type, val);
return BLE_HS_ENOTSUP;
}
return rc;
while (1) {
ble_hs_lock();
rc = ble_hs_cfg.store_write_cb(obj_type, val);
ble_hs_unlock();
switch (rc) {
case 0:
return 0;
case BLE_HS_ESTORE_CAP:
/* Record didn't fit. Give the application the opportunity to free
* up some space.
*/
rc = ble_store_overflow_event(obj_type, val);
if (rc != 0) {
return rc;
}
/* Application made room for the record; try again. */
break;
default:
return rc;
}
}
}
int
@@ -56,21 +81,65 @@ ble_store_delete(int obj_type, const union ble_store_key *key)
{
int rc;
ble_hs_lock();
if (ble_hs_cfg.store_delete_cb == NULL) {
rc = BLE_HS_ENOTSUP;
} else {
rc = ble_hs_cfg.store_delete_cb(obj_type, key);
}
ble_hs_unlock();
return rc;
}
static int
ble_store_status(struct ble_store_status_event *event)
{
int rc;
BLE_HS_DBG_ASSERT(!ble_hs_locked_by_cur_task());
if (ble_hs_cfg.store_status_cb == NULL) {
rc = BLE_HS_ENOTSUP;
} else {
rc = ble_hs_cfg.store_status_cb(event, ble_hs_cfg.store_status_arg);
}
return rc;
}
int
ble_store_overflow_event(int obj_type, const union ble_store_value *value)
{
struct ble_store_status_event event;
event.event_code = BLE_STORE_EVENT_OVERFLOW;
event.overflow.obj_type = obj_type;
event.overflow.value = value;
return ble_store_status(&event);
}
int
ble_store_full_event(int obj_type, uint16_t conn_handle)
{
struct ble_store_status_event event;
event.event_code = BLE_STORE_EVENT_FULL;
event.full.obj_type = obj_type;
event.full.conn_handle = conn_handle;
return ble_store_status(&event);
}
int
ble_store_read_our_sec(const struct ble_store_key_sec *key_sec,
struct ble_store_value_sec *value_sec)
{
const union ble_store_key *store_key;
union ble_store_value *store_value;
union ble_store_key *store_key;
int rc;
BLE_HS_DBG_ASSERT(key_sec->peer_addr.type == BLE_ADDR_PUBLIC ||
+90
View File
@@ -162,3 +162,93 @@ ble_store_util_delete_all(int type, const union ble_store_key *key)
return 0;
}
static int
ble_store_util_iter_count(int obj_type,
union ble_store_value *val,
void *arg)
{
int *count;
count = arg;
(*count)++;
return 0;
}
int
ble_store_util_count(int type, int *out_count)
{
int rc;
*out_count = 0;
rc = ble_store_iterate(type,
ble_store_util_iter_count,
out_count);
if (rc != 0) {
return rc;
}
return 0;
}
int
ble_store_util_delete_oldest_peer(void)
{
ble_addr_t peer_id_addrs[MYNEWT_VAL(BLE_STORE_MAX_BONDS)];
int num_peers;
int rc;
rc = ble_store_util_bonded_peers(
peer_id_addrs, &num_peers,
sizeof peer_id_addrs / sizeof peer_id_addrs[0]);
if (rc != 0) {
return rc;
}
if (num_peers == 0) {
return 0;
}
rc = ble_store_util_delete_peer(&peer_id_addrs[0]);
if (rc != 0) {
return rc;
}
return 0;
}
/**
* Round-robin status callback. If a there is insufficient storage capacity
* for a new record, delete the oldest bond and proceed with the persist
* operation.
*
* Note: This is not the best behavior for an actual product because
* uninteresting peers could cause important bonds to be deleted. This is
* useful for demonstrations and sample apps.
*/
int
ble_store_util_status_rr(struct ble_store_status_event *event, void *arg)
{
switch (event->event_code) {
case BLE_STORE_EVENT_OVERFLOW:
switch (event->overflow.obj_type) {
case BLE_STORE_OBJ_TYPE_OUR_SEC:
case BLE_STORE_OBJ_TYPE_PEER_SEC:
case BLE_STORE_OBJ_TYPE_CCCD:
return ble_store_util_delete_oldest_peer();
default:
return BLE_HS_EUNKNOWN;
}
case BLE_STORE_EVENT_FULL:
/* Just proceed with the operation. If it results in an overflow,
* we'll delete a record when the overflow occurs.
*/
return 0;
default:
return BLE_HS_EUNKNOWN;
}
}
+5 -5
View File
@@ -158,7 +158,7 @@ ble_store_ram_write_our_sec(const struct ble_store_value_sec *value_sec)
if (ble_store_ram_num_our_secs >= MYNEWT_VAL(BLE_STORE_MAX_BONDS)) {
BLE_HS_LOG(DEBUG, "error persisting our sec; too many entries "
"(%d)\n", ble_store_ram_num_our_secs);
return BLE_HS_ENOMEM;
return BLE_HS_ESTORE_CAP;
}
idx = ble_store_ram_num_our_secs;
@@ -272,7 +272,7 @@ ble_store_ram_write_peer_sec(const struct ble_store_value_sec *value_sec)
if (ble_store_ram_num_peer_secs >= MYNEWT_VAL(BLE_STORE_MAX_BONDS)) {
BLE_HS_LOG(DEBUG, "error persisting peer sec; too many entries "
"(%d)\n", ble_store_ram_num_peer_secs);
return BLE_HS_ENOMEM;
return BLE_HS_ESTORE_CAP;
}
idx = ble_store_ram_num_peer_secs;
@@ -370,7 +370,7 @@ ble_store_ram_write_cccd(const struct ble_store_value_cccd *value_cccd)
if (ble_store_ram_num_cccds >= MYNEWT_VAL(BLE_STORE_MAX_CCCDS)) {
BLE_HS_LOG(DEBUG, "error persisting cccd; too many entries (%d)\n",
ble_store_ram_num_cccds);
return BLE_HS_ENOMEM;
return BLE_HS_ESTORE_CAP;
}
idx = ble_store_ram_num_cccds;
@@ -431,8 +431,8 @@ ble_store_ram_read(int obj_type, const union ble_store_key *key,
/**
* Adds the specified object to the database.
*
* @return 0 on success; BLE_HS_ENOMEM if the database is
* full.
* @return 0 on success; BLE_HS_ESTORE_CAP if the database
* is full.
*/
int
ble_store_ram_write(int obj_type, const union ble_store_value *val)
+1 -1
View File
@@ -149,7 +149,7 @@ TEST_CASE(ble_sm_test_case_conn_broken)
/* Initiate the pairing procedure. */
rc = ble_hs_test_util_security_initiate(2, 0);
TEST_ASSERT_FATAL(rc == 0);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, BLE_SM_IOACT_NONE);
/* Terminate the connection. */
+69 -69
View File
@@ -1627,7 +1627,7 @@ ble_sm_test_util_peer_bonding_good(int send_enc_req,
ble_hs_unlock();
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 0);
TEST_ASSERT(ble_sm_num_procs() == 0);
if (send_enc_req) {
rc = ble_sm_slave_initiate(2);
@@ -1648,20 +1648,20 @@ ble_sm_test_util_peer_bonding_good(int send_enc_req,
TEST_ASSERT(ble_sm_test_store_key.sec.rand_num == rand_num);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, BLE_SM_IOACT_NONE);
/* Ensure we sent the expected long term key request reply command. */
ble_sm_test_util_verify_tx_lt_key_req_reply(2, ltk);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, BLE_SM_IOACT_NONE);
/* Receive an encryption changed event. */
ble_sm_test_util_rx_enc_change(2, 0, 1);
/* Pairing should now be complete. */
TEST_ASSERT(ble_sm_dbg_num_procs() == 0);
TEST_ASSERT(ble_sm_num_procs() == 0);
/* Verify that security callback was executed. */
TEST_ASSERT(ble_sm_test_gap_event_type == BLE_GAP_EVENT_ENC_CHANGE);
@@ -1700,7 +1700,7 @@ ble_sm_test_util_peer_bonding_bad(uint16_t ediv, uint64_t rand_num)
ble_hs_unlock();
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 0);
TEST_ASSERT(ble_sm_num_procs() == 0);
/* Receive a long term key request from the controller. */
ble_sm_test_util_set_lt_key_req_neg_reply_ack(0, 2);
@@ -1722,7 +1722,7 @@ ble_sm_test_util_peer_bonding_bad(uint16_t ediv, uint64_t rand_num)
/* Ensure the security procedure was aborted. */
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(!conn->bhc_sec_state.authenticated);
TEST_ASSERT(ble_sm_dbg_num_procs() == 0);
TEST_ASSERT(ble_sm_num_procs() == 0);
}
/**
@@ -1756,7 +1756,7 @@ ble_sm_test_util_us_bonding_good(int send_enc_req, uint8_t our_addr_type,
ble_hs_unlock();
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 0);
TEST_ASSERT(ble_sm_num_procs() == 0);
ble_hs_test_util_set_ack(
ble_hs_hci_util_opcode_join(BLE_HCI_OGF_LE,
@@ -1778,14 +1778,14 @@ ble_sm_test_util_us_bonding_good(int send_enc_req, uint8_t our_addr_type,
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_start_enc(2, rand_num, ediv, ltk);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, BLE_SM_IOACT_NONE);
/* Receive an encryption changed event. */
ble_sm_test_util_rx_enc_change(2, 0, 1);
/* Pairing should now be complete. */
TEST_ASSERT(ble_sm_dbg_num_procs() == 0);
TEST_ASSERT(ble_sm_num_procs() == 0);
/* Verify that security callback was executed. */
TEST_ASSERT(ble_sm_test_gap_event_type == BLE_GAP_EVENT_ENC_CHANGE);
@@ -1832,19 +1832,19 @@ ble_sm_test_util_peer_fail_inval(
}
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 0);
TEST_ASSERT(ble_sm_num_procs() == 0);
/* Receive a pair request from the peer. */
ble_sm_test_util_rx_pair_req(2, pair_req,
BLE_HS_SM_US_ERR(pair_fail->reason));
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 0);
TEST_ASSERT(ble_sm_num_procs() == 0);
/* Ensure we sent the expected pair fail. */
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_pair_fail(pair_fail);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 0);
TEST_ASSERT(ble_sm_num_procs() == 0);
/* Verify that security callback was not executed. */
TEST_ASSERT(ble_sm_test_gap_event_type == -1);
@@ -1894,28 +1894,28 @@ ble_sm_test_util_peer_lgcy_fail_confirm(
/* Peer is the initiator so we must be the slave. */
conn->bhc_flags &= ~BLE_HS_CONN_F_MASTER;
TEST_ASSERT(ble_sm_dbg_num_procs() == 0);
TEST_ASSERT(ble_sm_num_procs() == 0);
/* Receive a pair request from the peer. */
ble_sm_test_util_rx_pair_req(2, pair_req, 0);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, BLE_SM_IOACT_NONE);
/* Ensure we sent the expected pair response. */
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_pair_rsp(pair_rsp);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, BLE_SM_IOACT_NONE);
/* Receive a pair confirm from the peer. */
ble_sm_test_util_rx_confirm(2, confirm_req);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, BLE_SM_IOACT_NONE);
/* Ensure we sent the expected pair confirm. */
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_pair_confirm(confirm_rsp);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, BLE_SM_IOACT_NONE);
/* Receive a pair random from the peer. */
@@ -1927,7 +1927,7 @@ ble_sm_test_util_peer_lgcy_fail_confirm(
ble_sm_test_util_verify_tx_pair_fail(fail_rsp);
/* The proc should now be freed. */
TEST_ASSERT(ble_sm_dbg_num_procs() == 0);
TEST_ASSERT(ble_sm_num_procs() == 0);
/* Verify that security callback was executed. */
TEST_ASSERT(ble_sm_test_gap_event_type == BLE_GAP_EVENT_ENC_CHANGE);
@@ -2115,7 +2115,7 @@ ble_sm_test_util_us_lgcy_good_once_no_init(
int rc;
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 0);
TEST_ASSERT(ble_sm_num_procs() == 0);
ble_hs_test_util_set_ack(
ble_hs_hci_util_opcode_join(BLE_HCI_OGF_LE,
@@ -2132,13 +2132,13 @@ ble_sm_test_util_us_lgcy_good_once_no_init(
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_pair_req(our_entity->pair_cmd);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Receive a pair response from the peer. */
ble_sm_test_util_rx_pair_rsp(2, peer_entity->pair_cmd, 0);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
ble_sm_test_util_io_inject(&params->passkey_info,
@@ -2148,33 +2148,33 @@ ble_sm_test_util_us_lgcy_good_once_no_init(
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_pair_confirm(our_entity->confirms);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Receive a pair confirm from the peer. */
ble_sm_test_util_rx_confirm(2, peer_entity->confirms);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Ensure we sent the expected pair random. */
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_pair_random(our_entity->randoms);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Receive a pair random from the peer. */
ble_sm_test_util_rx_random(2, peer_entity->randoms, 0);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Ensure we sent the expected start encryption command. */
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_start_enc(2, 0, 0, params->stk);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Receive an encryption changed event. */
@@ -2187,7 +2187,7 @@ ble_sm_test_util_us_lgcy_good_once_no_init(
ble_sm_test_util_verify_tx_keys(params, 1);
/* Pairing should now be complete. */
TEST_ASSERT(ble_sm_dbg_num_procs() == 0);
TEST_ASSERT(ble_sm_num_procs() == 0);
/* Verify that security callback was executed. */
TEST_ASSERT(ble_sm_test_gap_event_type == BLE_GAP_EVENT_ENC_CHANGE);
@@ -2258,7 +2258,7 @@ ble_sm_test_util_peer_lgcy_good_once_no_init(
int rc;
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 0);
TEST_ASSERT(ble_sm_num_procs() == 0);
if (params->sec_req.authreq != 0) {
rc = ble_sm_slave_initiate(2);
@@ -2271,14 +2271,14 @@ ble_sm_test_util_peer_lgcy_good_once_no_init(
/* Receive a pair request from the peer. */
ble_sm_test_util_rx_pair_req(2, peer_entity->pair_cmd, 0);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Ensure we sent the expected pair response. */
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_pair_rsp(our_entity->pair_cmd);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
ble_sm_test_util_io_check_pre(&params->passkey_info,
@@ -2287,7 +2287,7 @@ ble_sm_test_util_peer_lgcy_good_once_no_init(
/* Receive a pair confirm from the peer. */
ble_sm_test_util_rx_confirm(2, peer_entity->confirms);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
ble_sm_test_util_io_check_post(&params->passkey_info,
@@ -2297,33 +2297,33 @@ ble_sm_test_util_peer_lgcy_good_once_no_init(
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_pair_confirm(our_entity->confirms);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Receive a pair random from the peer. */
ble_sm_test_util_rx_random(2, peer_entity->randoms, 0);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Ensure we sent the expected pair random. */
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_pair_random(our_entity->randoms);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Receive a long term key request from the controller. */
ble_sm_test_util_set_lt_key_req_reply_ack(0, 2);
ble_sm_test_util_rx_lt_key_req(2, 0, 0);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Ensure we sent the expected long term key request reply command. */
ble_sm_test_util_verify_tx_lt_key_req_reply(2, params->stk);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Receive an encryption changed event. */
@@ -2336,7 +2336,7 @@ ble_sm_test_util_peer_lgcy_good_once_no_init(
ble_sm_test_util_rx_keys(params, 0);
/* Pairing should now be complete. */
TEST_ASSERT(ble_sm_dbg_num_procs() == 0);
TEST_ASSERT(ble_sm_num_procs() == 0);
/* Verify that security callback was executed. */
TEST_ASSERT(ble_sm_test_gap_event_type == BLE_GAP_EVENT_ENC_CHANGE);
@@ -2427,7 +2427,7 @@ ble_sm_test_util_us_sc_good_once_no_init(
int i;
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 0);
TEST_ASSERT(ble_sm_num_procs() == 0);
ble_hs_test_util_set_ack(
ble_hs_hci_util_opcode_join(BLE_HCI_OGF_LE,
@@ -2444,26 +2444,26 @@ ble_sm_test_util_us_sc_good_once_no_init(
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_pair_req(our_entity->pair_cmd);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Receive a pair response from the peer. */
ble_sm_test_util_rx_pair_rsp(2, peer_entity->pair_cmd, 0);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Ensure we sent the expected public key. */
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_public_key(our_entity->public_key);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Receive a public key from the peer. */
ble_sm_test_util_rx_public_key(2, peer_entity->public_key);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
switch (params->pair_alg) {
@@ -2492,7 +2492,7 @@ ble_sm_test_util_us_sc_good_once_no_init(
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_pair_confirm(our_entity->confirms + i);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(
2, params->passkey_info.passkey.action);
}
@@ -2500,20 +2500,20 @@ ble_sm_test_util_us_sc_good_once_no_init(
/* Receive a pair confirm from the peer. */
ble_sm_test_util_rx_confirm(2, peer_entity->confirms + i);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Ensure we sent the expected pair random. */
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_pair_random(our_entity->randoms + i);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Receive a pair random from the peer. */
ble_sm_test_util_rx_random(2, peer_entity->randoms + i, 0);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
}
@@ -2524,20 +2524,20 @@ ble_sm_test_util_us_sc_good_once_no_init(
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_dhkey_check(our_entity->dhkey_check);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Receive a dhkey check from the peer. */
ble_sm_test_util_rx_dhkey_check(2, peer_entity->dhkey_check, 0);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Ensure we sent the expected start encryption command. */
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_start_enc(2, 0, 0, params->ltk);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Receive an encryption changed event. */
@@ -2550,7 +2550,7 @@ ble_sm_test_util_us_sc_good_once_no_init(
ble_sm_test_util_verify_tx_keys(params, 1);
/* Pairing should now be complete. */
TEST_ASSERT(ble_sm_dbg_num_procs() == 0);
TEST_ASSERT(ble_sm_num_procs() == 0);
/* Verify that security callback was executed. */
TEST_ASSERT(ble_sm_test_gap_event_type == BLE_GAP_EVENT_ENC_CHANGE);
@@ -2626,7 +2626,7 @@ ble_sm_test_util_peer_sc_good_once_no_init(
int i;
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 0);
TEST_ASSERT(ble_sm_num_procs() == 0);
if (params->sec_req.authreq != 0) {
rc = ble_sm_slave_initiate(2);
@@ -2639,27 +2639,27 @@ ble_sm_test_util_peer_sc_good_once_no_init(
/* Receive a pair request from the peer. */
ble_sm_test_util_rx_pair_req(2, peer_entity->pair_cmd, 0);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Ensure we sent the expected pair response. */
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_pair_rsp(our_entity->pair_cmd);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Receive a public key from the peer. */
ble_sm_test_util_rx_public_key(2, peer_entity->public_key);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Ensure we sent the expected public key. */
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_public_key(our_entity->public_key);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
switch (params->pair_alg) {
@@ -2682,7 +2682,7 @@ ble_sm_test_util_peer_sc_good_once_no_init(
/* Receive a pair confirm from the peer. */
ble_sm_test_util_rx_confirm(2, peer_entity->confirms + i);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(
2, params->passkey_info.passkey.action);
@@ -2701,20 +2701,20 @@ ble_sm_test_util_peer_sc_good_once_no_init(
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_pair_confirm(our_entity->confirms + i);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Receive a pair random from the peer. */
ble_sm_test_util_rx_random(2, peer_entity->randoms + i, 0);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Ensure we sent the expected pair random. */
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_pair_random(our_entity->randoms + i);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
}
@@ -2725,7 +2725,7 @@ ble_sm_test_util_peer_sc_good_once_no_init(
/* Receive a dhkey check from the peer. */
ble_sm_test_util_rx_dhkey_check(2, peer_entity->dhkey_check, 0);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
ble_sm_test_util_io_check_post(&params->passkey_info,
@@ -2735,20 +2735,20 @@ ble_sm_test_util_peer_sc_good_once_no_init(
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_dhkey_check(our_entity->dhkey_check);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Receive a long term key request from the controller. */
ble_sm_test_util_set_lt_key_req_reply_ack(0, 2);
ble_sm_test_util_rx_lt_key_req(2, 0, 0);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Ensure we sent the expected long term key request reply command. */
ble_sm_test_util_verify_tx_lt_key_req_reply(2, params->ltk);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Receive an encryption changed event. */
@@ -2761,7 +2761,7 @@ ble_sm_test_util_peer_sc_good_once_no_init(
ble_sm_test_util_rx_keys(params, 0);
/* Pairing should now be complete. */
TEST_ASSERT(ble_sm_dbg_num_procs() == 0);
TEST_ASSERT(ble_sm_num_procs() == 0);
/* Verify that security callback was executed. */
TEST_ASSERT(ble_sm_test_gap_event_type == BLE_GAP_EVENT_ENC_CHANGE);
@@ -2865,7 +2865,7 @@ ble_sm_test_util_us_fail_inval(struct ble_sm_test_params *params)
ble_hs_unlock();
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 0);
TEST_ASSERT(ble_sm_num_procs() == 0);
/* Initiate the pairing procedure. */
rc = ble_hs_test_util_security_initiate(2, 0);
@@ -2875,20 +2875,20 @@ ble_sm_test_util_us_fail_inval(struct ble_sm_test_params *params)
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_pair_req(&params->pair_req);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 1);
TEST_ASSERT(ble_sm_num_procs() == 1);
ble_sm_test_util_io_inject_bad(2, params->passkey_info.passkey.action);
/* Receive a pair response from the peer. */
ble_sm_test_util_rx_pair_rsp(
2, &params->pair_rsp, BLE_HS_SM_US_ERR(params->pair_fail.reason));
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 0);
TEST_ASSERT(ble_sm_num_procs() == 0);
/* Ensure we sent the expected pair fail. */
ble_hs_test_util_tx_all();
ble_sm_test_util_verify_tx_pair_fail(&params->pair_fail);
TEST_ASSERT(!conn->bhc_sec_state.encrypted);
TEST_ASSERT(ble_sm_dbg_num_procs() == 0);
TEST_ASSERT(ble_sm_num_procs() == 0);
/* Verify that security callback was not executed. */
TEST_ASSERT(ble_sm_test_gap_event_type == -1);
@@ -2944,7 +2944,7 @@ ble_sm_test_util_repeat_pairing(struct ble_sm_test_params *params, int sc)
TEST_ASSERT(ble_sm_test_repeat_pairing.num_calls == 2);
/* Verify no pairing procedures in progress. */
TEST_ASSERT(ble_sm_dbg_num_procs() == 0);
TEST_ASSERT(ble_sm_num_procs() == 0);
/* Verify no SM messages were sent. */
ble_hs_test_util_tx_all();
+153 -1
View File
@@ -21,6 +21,8 @@
#include "host/ble_hs_test.h"
#include "ble_hs_test_util.h"
static struct ble_store_status_event ble_store_test_status_event;
static void
ble_store_test_util_verify_peer_deleted(const ble_addr_t *addr)
{
@@ -51,6 +53,66 @@ ble_store_test_util_verify_peer_deleted(const ble_addr_t *addr)
}
}
static int
ble_store_test_util_status_overflow(struct ble_store_status_event *event,
void *arg)
{
int *status;
status = arg;
ble_store_test_status_event = *event;
return *status;
}
static void
ble_store_test_util_overflow_sec(int is_our_sec)
{
union ble_store_value val;
int obj_type;
int status;
int rc;
int i;
ble_hs_test_util_init();
ble_hs_cfg.store_status_cb = ble_store_test_util_status_overflow;
ble_hs_cfg.store_status_arg = &status;
if (is_our_sec) {
obj_type = BLE_STORE_OBJ_TYPE_OUR_SEC;
} else {
obj_type = BLE_STORE_OBJ_TYPE_PEER_SEC;
}
memset(&ble_store_test_status_event, 0,
sizeof ble_store_test_status_event);
memset(&val, 0, sizeof val);
val.sec.peer_addr =
(ble_addr_t){ BLE_ADDR_PUBLIC, { 1, 2, 3, 4, 5, 6 } };
val.sec.ltk_present = 1,
status = BLE_HS_ESTORE_CAP;
for (i = 0; ; i++) {
rc = ble_store_write(obj_type, &val);
if (i < MYNEWT_VAL(BLE_STORE_MAX_BONDS)) {
TEST_ASSERT_FATAL(rc == 0);
} else {
/* This record should have caused an overflow. */
TEST_ASSERT(rc == BLE_HS_ESTORE_CAP);
TEST_ASSERT(ble_store_test_status_event.event_code ==
BLE_STORE_EVENT_OVERFLOW);
TEST_ASSERT(ble_store_test_status_event.overflow.obj_type ==
obj_type);
TEST_ASSERT(ble_store_test_status_event.overflow.value == &val);
break;
}
val.sec.peer_addr.val[0]++;
}
}
TEST_CASE(ble_store_test_peers)
{
struct ble_store_value_sec secs[4] = {
@@ -77,6 +139,8 @@ TEST_CASE(ble_store_test_peers)
int rc;
int i;
ble_hs_test_util_init();
for (i = 0; i < sizeof secs / sizeof secs[0]; i++) {
rc = ble_store_write_our_sec(secs + i);
TEST_ASSERT_FATAL(rc == 0);
@@ -124,10 +188,11 @@ TEST_CASE(ble_store_test_delete_peer)
.chr_val_handle = 5,
},
};
int rc;
int i;
ble_hs_test_util_init();
for (i = 0; i < sizeof secs / sizeof secs[0]; i++) {
rc = ble_store_write_our_sec(secs + i);
TEST_ASSERT_FATAL(rc == 0);
@@ -155,12 +220,99 @@ TEST_CASE(ble_store_test_delete_peer)
ble_store_test_util_verify_peer_deleted(&secs[1].peer_addr);
}
TEST_CASE(ble_store_test_count)
{
struct ble_store_value_sec secs[4] = {
{
.peer_addr = { BLE_ADDR_PUBLIC, { 1, 2, 3, 4, 5, 6 } },
.ltk_present = 1,
},
{
.peer_addr = { BLE_ADDR_RANDOM, { 1, 2, 3, 4, 5, 6 } },
.ltk_present = 1,
},
{
.peer_addr = { BLE_ADDR_PUBLIC, { 2, 3, 4, 5, 6, 7 } },
.ltk_present = 1,
},
{
.peer_addr = { BLE_ADDR_RANDOM, { 3, 4, 5, 6, 7, 8 } },
.ltk_present = 1,
},
};
struct ble_store_value_cccd cccds[2] = {
{
.peer_addr = secs[0].peer_addr,
.chr_val_handle = 5,
},
{
.peer_addr = secs[0].peer_addr,
.chr_val_handle = 8,
},
};
int count;
int rc;
int i;
ble_hs_test_util_init();
/*** Verify initial counts are 0. */
rc = ble_store_util_count(BLE_STORE_OBJ_TYPE_OUR_SEC, &count);
TEST_ASSERT_FATAL(rc == 0);
TEST_ASSERT(count == 0);
rc = ble_store_util_count(BLE_STORE_OBJ_TYPE_PEER_SEC, &count);
TEST_ASSERT_FATAL(rc == 0);
TEST_ASSERT(count == 0);
rc = ble_store_util_count(BLE_STORE_OBJ_TYPE_CCCD, &count);
TEST_ASSERT_FATAL(rc == 0);
TEST_ASSERT(count == 0);
/* Write some test data. */
for (i = 0; i < 4; i++) {
rc = ble_store_write_our_sec(secs + i);
TEST_ASSERT_FATAL(rc == 0);
}
for (i = 0; i < 3; i++) {
rc = ble_store_write_peer_sec(secs + i);
TEST_ASSERT_FATAL(rc == 0);
}
for (i = 0; i < 2; i++) {
rc = ble_store_write_cccd(cccds + i);
TEST_ASSERT_FATAL(rc == 0);
}
/*** Verify counts after populating store. */
rc = ble_store_util_count(BLE_STORE_OBJ_TYPE_OUR_SEC, &count);
TEST_ASSERT_FATAL(rc == 0);
TEST_ASSERT(count == 4);
rc = ble_store_util_count(BLE_STORE_OBJ_TYPE_PEER_SEC, &count);
TEST_ASSERT_FATAL(rc == 0);
TEST_ASSERT(count == 3);
rc = ble_store_util_count(BLE_STORE_OBJ_TYPE_CCCD, &count);
TEST_ASSERT_FATAL(rc == 0);
TEST_ASSERT(count == 2);
}
TEST_CASE(ble_store_test_overflow)
{
ble_store_test_util_overflow_sec(0);
ble_store_test_util_overflow_sec(1);
}
TEST_SUITE(ble_store_suite)
{
tu_suite_set_post_test_cb(ble_hs_test_util_post_test, NULL);
ble_store_test_peers();
ble_store_test_delete_peer();
ble_store_test_count();
ble_store_test_overflow();
}
int