Bluetooth: SMP: Fix using identity address while re-pairing
When remote device initiate pairing but its IRK is already known identity address was used to calculate confirmation value. This resulted in 'Confirm Value Failed' error and pairing failure. To avoid any confusion simply track initiator and responder addresses used for connection. This fix re-enabling security with iPhone if device was unpaired only on iPhone side. Change-Id: I07d9589bee5fea7f6b028472b1709090a5755e31 Signed-off-by: Szymon Janc <ext.szymon.janc@tieto.com>
This commit is contained in:
parent
c0ee86d1bf
commit
4bf5573055
3 changed files with 15 additions and 21 deletions
|
@ -61,6 +61,9 @@ struct bt_conn {
|
|||
bt_addr_le_t src;
|
||||
bt_addr_le_t dst;
|
||||
|
||||
bt_addr_le_t init_addr;
|
||||
bt_addr_le_t resp_addr;
|
||||
|
||||
uint8_t encrypt;
|
||||
bt_security_t sec_level;
|
||||
bt_security_t required_sec_level;
|
||||
|
|
|
@ -804,6 +804,14 @@ static void le_conn_complete(struct bt_buf *buf)
|
|||
copy_id_addr(conn, &evt->peer_addr);
|
||||
conn->le_conn_interval = sys_le16_to_cpu(evt->interval);
|
||||
|
||||
if (conn->role == BT_HCI_ROLE_MASTER) {
|
||||
bt_addr_le_copy(&conn->init_addr, &conn->src);
|
||||
bt_addr_le_copy(&conn->resp_addr, &evt->peer_addr);
|
||||
} else {
|
||||
bt_addr_le_copy(&conn->init_addr, &evt->peer_addr);
|
||||
bt_addr_le_copy(&conn->resp_addr, &conn->src);
|
||||
}
|
||||
|
||||
bt_conn_set_state(conn, BT_CONN_CONNECTED);
|
||||
|
||||
if ((evt->role == BT_HCI_ROLE_MASTER) ||
|
||||
|
|
|
@ -598,7 +598,6 @@ static uint8_t smp_send_pairing_confirm(struct bt_conn *conn)
|
|||
{
|
||||
struct bt_smp_pairing_confirm *req;
|
||||
struct bt_smp *smp = conn->smp;
|
||||
const bt_addr_le_t *ra, *ia;
|
||||
struct bt_buf *rsp_buf;
|
||||
int err;
|
||||
|
||||
|
@ -610,16 +609,8 @@ static uint8_t smp_send_pairing_confirm(struct bt_conn *conn)
|
|||
|
||||
req = bt_buf_add(rsp_buf, sizeof(*req));
|
||||
|
||||
if (conn->role == BT_HCI_ROLE_MASTER) {
|
||||
ra = &conn->dst;
|
||||
ia = &conn->src;
|
||||
} else {
|
||||
ra = &conn->src;
|
||||
ia = &conn->dst;
|
||||
}
|
||||
|
||||
err = smp_c1(smp->tk, smp->prnd, smp->preq, smp->prsp, ia, ra,
|
||||
req->val);
|
||||
err = smp_c1(smp->tk, smp->prnd, smp->preq, smp->prsp, &conn->init_addr,
|
||||
&conn->resp_addr, req->val);
|
||||
if (err) {
|
||||
bt_buf_put(rsp_buf);
|
||||
return BT_SMP_ERR_UNSPECIFIED;
|
||||
|
@ -726,7 +717,6 @@ static uint8_t get_keys_type(uint8_t method)
|
|||
static uint8_t smp_pairing_random(struct bt_conn *conn, struct bt_buf *buf)
|
||||
{
|
||||
struct bt_smp_pairing_random *req = (void *)buf->data;
|
||||
const bt_addr_le_t *ra, *ia;
|
||||
struct bt_smp *smp = conn->smp;
|
||||
struct bt_keys *keys;
|
||||
uint8_t cfm[16];
|
||||
|
@ -736,15 +726,8 @@ static uint8_t smp_pairing_random(struct bt_conn *conn, struct bt_buf *buf)
|
|||
|
||||
memcpy(smp->rrnd, req->val, sizeof(smp->rrnd));
|
||||
|
||||
if (conn->role == BT_HCI_ROLE_MASTER) {
|
||||
ra = &conn->dst;
|
||||
ia = &conn->src;
|
||||
} else {
|
||||
ra = &conn->src;
|
||||
ia = &conn->dst;
|
||||
}
|
||||
|
||||
err = smp_c1(smp->tk, smp->rrnd, smp->preq, smp->prsp, ia, ra, cfm);
|
||||
err = smp_c1(smp->tk, smp->rrnd, smp->preq, smp->prsp, &conn->init_addr,
|
||||
&conn->resp_addr, cfm);
|
||||
if (err) {
|
||||
return BT_SMP_ERR_UNSPECIFIED;
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue