diff options
author | Johan Hedberg <johan.hedberg@intel.com> | 2015-01-07 12:16:11 +0200 |
---|---|---|
committer | Johan Hedberg <johan.hedberg@intel.com> | 2015-01-07 13:13:27 +0200 |
commit | 4003a333dc4484dd68671ffecda894f57149ff07 (patch) | |
tree | 30ee605defc356fdfff066a8aacf1d7071987289 /emulator/smp.c | |
parent | f5653c83e84d36b0745355d35a9741e0cb0c7901 (diff) | |
download | bluez-4003a333dc4484dd68671ffecda894f57149ff07.tar.gz |
emulator/bthost: Add support for triggering SMP over BR/EDR
Diffstat (limited to 'emulator/smp.c')
-rw-r--r-- | emulator/smp.c | 37 |
1 files changed, 37 insertions, 0 deletions
diff --git a/emulator/smp.c b/emulator/smp.c index 5d338b7e0..4f527e990 100644 --- a/emulator/smp.c +++ b/emulator/smp.c @@ -47,6 +47,8 @@ #define SMP_CID 0x0006 #define SMP_BREDR_CID 0x0007 +#define L2CAP_FC_SMP_BREDR 0x80 + #define SMP_PASSKEY_ENTRY_FAILED 0x01 #define SMP_OOB_NOT_AVAIL 0x02 #define SMP_AUTH_REQUIREMENTS 0x03 @@ -462,6 +464,13 @@ static void pairing_rsp(struct smp_conn *conn, const void *data, uint16_t len) conn->local_key_dist = conn->prsp[5]; conn->remote_key_dist = conn->prsp[6]; + if (conn->addr_type == BDADDR_BREDR) { + conn->local_key_dist &= ~SC_NO_DIST; + conn->remote_key_dist &= ~SC_NO_DIST; + distribute_keys(conn); + return; + } + if (((conn->prsp[3] & 0x08) && (conn->preq[3] & 0x08)) || conn->addr_type == BDADDR_BREDR) { conn->sc = true; @@ -788,6 +797,29 @@ int smp_get_ltk(void *smp_data, uint64_t rand, uint16_t ediv, uint8_t *ltk) return 0; } +static void smp_conn_bredr(struct smp_conn *conn, uint8_t encrypt) +{ + struct smp *smp = conn->smp; + struct bt_l2cap_smp_pairing_request req; + uint64_t fixed_chan; + + if (encrypt != 0x02) + return; + + conn->sc = true; + + fixed_chan = bthost_conn_get_fixed_chan(smp->bthost, conn->handle); + if (!(fixed_chan & L2CAP_FC_SMP_BREDR)) + return; + + memset(&req, 0, sizeof(req)); + req.max_key_size = 0x10; + req.init_key_dist = KEY_DIST; + req.resp_key_dist = KEY_DIST; + + smp_send(conn, BT_L2CAP_SMP_PAIRING_REQUEST, &req, sizeof(req)); +} + void smp_conn_encrypted(void *conn_data, uint8_t encrypt) { struct smp_conn *conn = conn_data; @@ -795,6 +827,11 @@ void smp_conn_encrypted(void *conn_data, uint8_t encrypt) if (!encrypt) return; + if (conn->addr_type == BDADDR_BREDR) { + smp_conn_bredr(conn, encrypt); + return; + } + if (conn->out && conn->remote_key_dist) return; |