1eb492e01SAnderson Briglia /* 2eb492e01SAnderson Briglia BlueZ - Bluetooth protocol stack for Linux 3eb492e01SAnderson Briglia Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies). 4eb492e01SAnderson Briglia 5eb492e01SAnderson Briglia This program is free software; you can redistribute it and/or modify 6eb492e01SAnderson Briglia it under the terms of the GNU General Public License version 2 as 7eb492e01SAnderson Briglia published by the Free Software Foundation; 8eb492e01SAnderson Briglia 9eb492e01SAnderson Briglia THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 10eb492e01SAnderson Briglia OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 11eb492e01SAnderson Briglia FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT OF THIRD PARTY RIGHTS. 12eb492e01SAnderson Briglia IN NO EVENT SHALL THE COPYRIGHT HOLDER(S) AND AUTHOR(S) BE LIABLE FOR ANY 13eb492e01SAnderson Briglia CLAIM, OR ANY SPECIAL INDIRECT OR CONSEQUENTIAL DAMAGES, OR ANY DAMAGES 14eb492e01SAnderson Briglia WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 15eb492e01SAnderson Briglia ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 16eb492e01SAnderson Briglia OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 17eb492e01SAnderson Briglia 18eb492e01SAnderson Briglia ALL LIABILITY, INCLUDING LIABILITY FOR INFRINGEMENT OF ANY PATENTS, 19eb492e01SAnderson Briglia COPYRIGHTS, TRADEMARKS OR OTHER RIGHTS, RELATING TO USE OF THIS 20eb492e01SAnderson Briglia SOFTWARE IS DISCLAIMED. 21eb492e01SAnderson Briglia */ 22eb492e01SAnderson Briglia 238c520a59SGustavo Padovan #include <linux/crypto.h> 248c520a59SGustavo Padovan #include <linux/scatterlist.h> 258c520a59SGustavo Padovan #include <crypto/b128ops.h> 268c520a59SGustavo Padovan 27eb492e01SAnderson Briglia #include <net/bluetooth/bluetooth.h> 28eb492e01SAnderson Briglia #include <net/bluetooth/hci_core.h> 29eb492e01SAnderson Briglia #include <net/bluetooth/l2cap.h> 302b64d153SBrian Gix #include <net/bluetooth/mgmt.h> 31ac4b7236SMarcel Holtmann 323b19146dSJohan Hedberg #include "ecc.h" 33ac4b7236SMarcel Holtmann #include "smp.h" 34d22ef0bcSAnderson Briglia 35b28b4943SJohan Hedberg #define SMP_ALLOW_CMD(smp, code) set_bit(code, &smp->allow_cmd) 36b28b4943SJohan Hedberg 373b19146dSJohan Hedberg /* Keys which are not distributed with Secure Connections */ 383b19146dSJohan Hedberg #define SMP_SC_NO_DIST (SMP_DIST_ENC_KEY | SMP_DIST_LINK_KEY); 393b19146dSJohan Hedberg 4017b02e62SMarcel Holtmann #define SMP_TIMEOUT msecs_to_jiffies(30000) 415d3de7dfSVinicius Costa Gomes 420edb14deSJohan Hedberg #define AUTH_REQ_MASK(dev) (test_bit(HCI_SC_ENABLED, &(dev)->dev_flags) ? \ 430edb14deSJohan Hedberg 0x1f : 0x07) 4488d3a8acSJohan Hedberg #define KEY_DIST_MASK 0x07 45065a13e2SJohan Hedberg 46533e35d4SJohan Hedberg enum { 47533e35d4SJohan Hedberg SMP_FLAG_TK_VALID, 48533e35d4SJohan Hedberg SMP_FLAG_CFM_PENDING, 49533e35d4SJohan Hedberg SMP_FLAG_MITM_AUTH, 50533e35d4SJohan Hedberg SMP_FLAG_COMPLETE, 51533e35d4SJohan Hedberg SMP_FLAG_INITIATOR, 5265668776SJohan Hedberg SMP_FLAG_SC, 53d8f8edbeSJohan Hedberg SMP_FLAG_REMOTE_PK, 54533e35d4SJohan Hedberg }; 554bc58f51SJohan Hedberg 564bc58f51SJohan Hedberg struct smp_chan { 574bc58f51SJohan Hedberg struct l2cap_conn *conn; 58b68fda68SJohan Hedberg struct delayed_work security_timer; 59b28b4943SJohan Hedberg unsigned long allow_cmd; /* Bitmask of allowed commands */ 60b68fda68SJohan Hedberg 614bc58f51SJohan Hedberg u8 preq[7]; /* SMP Pairing Request */ 624bc58f51SJohan Hedberg u8 prsp[7]; /* SMP Pairing Response */ 634bc58f51SJohan Hedberg u8 prnd[16]; /* SMP Pairing Random (local) */ 644bc58f51SJohan Hedberg u8 rrnd[16]; /* SMP Pairing Random (remote) */ 654bc58f51SJohan Hedberg u8 pcnf[16]; /* SMP Pairing Confirm */ 664bc58f51SJohan Hedberg u8 tk[16]; /* SMP Temporary Key */ 674bc58f51SJohan Hedberg u8 enc_key_size; 684bc58f51SJohan Hedberg u8 remote_key_dist; 694bc58f51SJohan Hedberg bdaddr_t id_addr; 704bc58f51SJohan Hedberg u8 id_addr_type; 714bc58f51SJohan Hedberg u8 irk[16]; 724bc58f51SJohan Hedberg struct smp_csrk *csrk; 734bc58f51SJohan Hedberg struct smp_csrk *slave_csrk; 744bc58f51SJohan Hedberg struct smp_ltk *ltk; 754bc58f51SJohan Hedberg struct smp_ltk *slave_ltk; 764bc58f51SJohan Hedberg struct smp_irk *remote_irk; 774a74d658SJohan Hedberg unsigned long flags; 786a7bd103SJohan Hedberg 793b19146dSJohan Hedberg /* Secure Connections variables */ 803b19146dSJohan Hedberg u8 local_pk[64]; 813b19146dSJohan Hedberg u8 local_sk[32]; 82d8f8edbeSJohan Hedberg u8 remote_pk[64]; 83d8f8edbeSJohan Hedberg u8 dhkey[32]; 843b19146dSJohan Hedberg 856a7bd103SJohan Hedberg struct crypto_blkcipher *tfm_aes; 86407cecf6SJohan Hedberg struct crypto_hash *tfm_cmac; 874bc58f51SJohan Hedberg }; 884bc58f51SJohan Hedberg 898a2936f4SJohan Hedberg static inline void swap_buf(const u8 *src, u8 *dst, size_t len) 90d22ef0bcSAnderson Briglia { 918a2936f4SJohan Hedberg size_t i; 92d22ef0bcSAnderson Briglia 938a2936f4SJohan Hedberg for (i = 0; i < len; i++) 948a2936f4SJohan Hedberg dst[len - 1 - i] = src[i]; 95d22ef0bcSAnderson Briglia } 96d22ef0bcSAnderson Briglia 97d22ef0bcSAnderson Briglia static int smp_e(struct crypto_blkcipher *tfm, const u8 *k, u8 *r) 98d22ef0bcSAnderson Briglia { 99d22ef0bcSAnderson Briglia struct blkcipher_desc desc; 100d22ef0bcSAnderson Briglia struct scatterlist sg; 101943a732aSJohan Hedberg uint8_t tmp[16], data[16]; 102201a5929SJohan Hedberg int err; 103d22ef0bcSAnderson Briglia 104d22ef0bcSAnderson Briglia if (tfm == NULL) { 105d22ef0bcSAnderson Briglia BT_ERR("tfm %p", tfm); 106d22ef0bcSAnderson Briglia return -EINVAL; 107d22ef0bcSAnderson Briglia } 108d22ef0bcSAnderson Briglia 109d22ef0bcSAnderson Briglia desc.tfm = tfm; 110d22ef0bcSAnderson Briglia desc.flags = 0; 111d22ef0bcSAnderson Briglia 112943a732aSJohan Hedberg /* The most significant octet of key corresponds to k[0] */ 1138a2936f4SJohan Hedberg swap_buf(k, tmp, 16); 114943a732aSJohan Hedberg 115943a732aSJohan Hedberg err = crypto_blkcipher_setkey(tfm, tmp, 16); 116d22ef0bcSAnderson Briglia if (err) { 117d22ef0bcSAnderson Briglia BT_ERR("cipher setkey failed: %d", err); 118d22ef0bcSAnderson Briglia return err; 119d22ef0bcSAnderson Briglia } 120d22ef0bcSAnderson Briglia 121943a732aSJohan Hedberg /* Most significant octet of plaintextData corresponds to data[0] */ 1228a2936f4SJohan Hedberg swap_buf(r, data, 16); 123943a732aSJohan Hedberg 124943a732aSJohan Hedberg sg_init_one(&sg, data, 16); 125d22ef0bcSAnderson Briglia 126d22ef0bcSAnderson Briglia err = crypto_blkcipher_encrypt(&desc, &sg, &sg, 16); 127d22ef0bcSAnderson Briglia if (err) 128d22ef0bcSAnderson Briglia BT_ERR("Encrypt data error %d", err); 129d22ef0bcSAnderson Briglia 130943a732aSJohan Hedberg /* Most significant octet of encryptedData corresponds to data[0] */ 1318a2936f4SJohan Hedberg swap_buf(data, r, 16); 132943a732aSJohan Hedberg 133d22ef0bcSAnderson Briglia return err; 134d22ef0bcSAnderson Briglia } 135d22ef0bcSAnderson Briglia 13660478054SJohan Hedberg static int smp_ah(struct crypto_blkcipher *tfm, u8 irk[16], u8 r[3], u8 res[3]) 13760478054SJohan Hedberg { 138943a732aSJohan Hedberg u8 _res[16]; 13960478054SJohan Hedberg int err; 14060478054SJohan Hedberg 14160478054SJohan Hedberg /* r' = padding || r */ 142943a732aSJohan Hedberg memcpy(_res, r, 3); 143943a732aSJohan Hedberg memset(_res + 3, 0, 13); 14460478054SJohan Hedberg 145943a732aSJohan Hedberg err = smp_e(tfm, irk, _res); 14660478054SJohan Hedberg if (err) { 14760478054SJohan Hedberg BT_ERR("Encrypt error"); 14860478054SJohan Hedberg return err; 14960478054SJohan Hedberg } 15060478054SJohan Hedberg 15160478054SJohan Hedberg /* The output of the random address function ah is: 15260478054SJohan Hedberg * ah(h, r) = e(k, r') mod 2^24 15360478054SJohan Hedberg * The output of the security function e is then truncated to 24 bits 15460478054SJohan Hedberg * by taking the least significant 24 bits of the output of e as the 15560478054SJohan Hedberg * result of ah. 15660478054SJohan Hedberg */ 157943a732aSJohan Hedberg memcpy(res, _res, 3); 15860478054SJohan Hedberg 15960478054SJohan Hedberg return 0; 16060478054SJohan Hedberg } 16160478054SJohan Hedberg 162defce9e8SJohan Hedberg bool smp_irk_matches(struct hci_dev *hdev, u8 irk[16], bdaddr_t *bdaddr) 16360478054SJohan Hedberg { 164defce9e8SJohan Hedberg struct l2cap_chan *chan = hdev->smp_data; 165defce9e8SJohan Hedberg struct crypto_blkcipher *tfm; 16660478054SJohan Hedberg u8 hash[3]; 16760478054SJohan Hedberg int err; 16860478054SJohan Hedberg 169defce9e8SJohan Hedberg if (!chan || !chan->data) 170defce9e8SJohan Hedberg return false; 171defce9e8SJohan Hedberg 172defce9e8SJohan Hedberg tfm = chan->data; 173defce9e8SJohan Hedberg 17460478054SJohan Hedberg BT_DBG("RPA %pMR IRK %*phN", bdaddr, 16, irk); 17560478054SJohan Hedberg 17660478054SJohan Hedberg err = smp_ah(tfm, irk, &bdaddr->b[3], hash); 17760478054SJohan Hedberg if (err) 17860478054SJohan Hedberg return false; 17960478054SJohan Hedberg 18060478054SJohan Hedberg return !memcmp(bdaddr->b, hash, 3); 18160478054SJohan Hedberg } 18260478054SJohan Hedberg 183defce9e8SJohan Hedberg int smp_generate_rpa(struct hci_dev *hdev, u8 irk[16], bdaddr_t *rpa) 184b1e2b3aeSJohan Hedberg { 185defce9e8SJohan Hedberg struct l2cap_chan *chan = hdev->smp_data; 186defce9e8SJohan Hedberg struct crypto_blkcipher *tfm; 187b1e2b3aeSJohan Hedberg int err; 188b1e2b3aeSJohan Hedberg 189defce9e8SJohan Hedberg if (!chan || !chan->data) 190defce9e8SJohan Hedberg return -EOPNOTSUPP; 191defce9e8SJohan Hedberg 192defce9e8SJohan Hedberg tfm = chan->data; 193defce9e8SJohan Hedberg 194b1e2b3aeSJohan Hedberg get_random_bytes(&rpa->b[3], 3); 195b1e2b3aeSJohan Hedberg 196b1e2b3aeSJohan Hedberg rpa->b[5] &= 0x3f; /* Clear two most significant bits */ 197b1e2b3aeSJohan Hedberg rpa->b[5] |= 0x40; /* Set second most significant bit */ 198b1e2b3aeSJohan Hedberg 199b1e2b3aeSJohan Hedberg err = smp_ah(tfm, irk, &rpa->b[3], rpa->b); 200b1e2b3aeSJohan Hedberg if (err < 0) 201b1e2b3aeSJohan Hedberg return err; 202b1e2b3aeSJohan Hedberg 203b1e2b3aeSJohan Hedberg BT_DBG("RPA %pMR", rpa); 204b1e2b3aeSJohan Hedberg 205b1e2b3aeSJohan Hedberg return 0; 206b1e2b3aeSJohan Hedberg } 207b1e2b3aeSJohan Hedberg 208e491eaf3SJohan Hedberg static int smp_c1(struct crypto_blkcipher *tfm_aes, u8 k[16], u8 r[16], 209e491eaf3SJohan Hedberg u8 preq[7], u8 pres[7], u8 _iat, bdaddr_t *ia, u8 _rat, 210e491eaf3SJohan Hedberg bdaddr_t *ra, u8 res[16]) 211d22ef0bcSAnderson Briglia { 212d22ef0bcSAnderson Briglia u8 p1[16], p2[16]; 213d22ef0bcSAnderson Briglia int err; 214d22ef0bcSAnderson Briglia 215d22ef0bcSAnderson Briglia memset(p1, 0, 16); 216d22ef0bcSAnderson Briglia 217d22ef0bcSAnderson Briglia /* p1 = pres || preq || _rat || _iat */ 218943a732aSJohan Hedberg p1[0] = _iat; 219943a732aSJohan Hedberg p1[1] = _rat; 220943a732aSJohan Hedberg memcpy(p1 + 2, preq, 7); 221943a732aSJohan Hedberg memcpy(p1 + 9, pres, 7); 222d22ef0bcSAnderson Briglia 223d22ef0bcSAnderson Briglia /* p2 = padding || ia || ra */ 224943a732aSJohan Hedberg memcpy(p2, ra, 6); 225943a732aSJohan Hedberg memcpy(p2 + 6, ia, 6); 226943a732aSJohan Hedberg memset(p2 + 12, 0, 4); 227d22ef0bcSAnderson Briglia 228d22ef0bcSAnderson Briglia /* res = r XOR p1 */ 229d22ef0bcSAnderson Briglia u128_xor((u128 *) res, (u128 *) r, (u128 *) p1); 230d22ef0bcSAnderson Briglia 231d22ef0bcSAnderson Briglia /* res = e(k, res) */ 232e491eaf3SJohan Hedberg err = smp_e(tfm_aes, k, res); 233d22ef0bcSAnderson Briglia if (err) { 234d22ef0bcSAnderson Briglia BT_ERR("Encrypt data error"); 235d22ef0bcSAnderson Briglia return err; 236d22ef0bcSAnderson Briglia } 237d22ef0bcSAnderson Briglia 238d22ef0bcSAnderson Briglia /* res = res XOR p2 */ 239d22ef0bcSAnderson Briglia u128_xor((u128 *) res, (u128 *) res, (u128 *) p2); 240d22ef0bcSAnderson Briglia 241d22ef0bcSAnderson Briglia /* res = e(k, res) */ 242e491eaf3SJohan Hedberg err = smp_e(tfm_aes, k, res); 243d22ef0bcSAnderson Briglia if (err) 244d22ef0bcSAnderson Briglia BT_ERR("Encrypt data error"); 245d22ef0bcSAnderson Briglia 246d22ef0bcSAnderson Briglia return err; 247d22ef0bcSAnderson Briglia } 248d22ef0bcSAnderson Briglia 249e491eaf3SJohan Hedberg static int smp_s1(struct crypto_blkcipher *tfm_aes, u8 k[16], u8 r1[16], 250e491eaf3SJohan Hedberg u8 r2[16], u8 _r[16]) 251d22ef0bcSAnderson Briglia { 252d22ef0bcSAnderson Briglia int err; 253d22ef0bcSAnderson Briglia 254d22ef0bcSAnderson Briglia /* Just least significant octets from r1 and r2 are considered */ 255943a732aSJohan Hedberg memcpy(_r, r2, 8); 256943a732aSJohan Hedberg memcpy(_r + 8, r1, 8); 257d22ef0bcSAnderson Briglia 258e491eaf3SJohan Hedberg err = smp_e(tfm_aes, k, _r); 259d22ef0bcSAnderson Briglia if (err) 260d22ef0bcSAnderson Briglia BT_ERR("Encrypt data error"); 261d22ef0bcSAnderson Briglia 262d22ef0bcSAnderson Briglia return err; 263d22ef0bcSAnderson Briglia } 264d22ef0bcSAnderson Briglia 265eb492e01SAnderson Briglia static void smp_send_cmd(struct l2cap_conn *conn, u8 code, u16 len, void *data) 266eb492e01SAnderson Briglia { 2675d88cc73SJohan Hedberg struct l2cap_chan *chan = conn->smp; 268b68fda68SJohan Hedberg struct smp_chan *smp; 2695d88cc73SJohan Hedberg struct kvec iv[2]; 2705d88cc73SJohan Hedberg struct msghdr msg; 2715d88cc73SJohan Hedberg 2725d88cc73SJohan Hedberg if (!chan) 2735d88cc73SJohan Hedberg return; 274eb492e01SAnderson Briglia 275eb492e01SAnderson Briglia BT_DBG("code 0x%2.2x", code); 276eb492e01SAnderson Briglia 2775d88cc73SJohan Hedberg iv[0].iov_base = &code; 2785d88cc73SJohan Hedberg iv[0].iov_len = 1; 279eb492e01SAnderson Briglia 2805d88cc73SJohan Hedberg iv[1].iov_base = data; 2815d88cc73SJohan Hedberg iv[1].iov_len = len; 2825d88cc73SJohan Hedberg 2835d88cc73SJohan Hedberg memset(&msg, 0, sizeof(msg)); 2845d88cc73SJohan Hedberg 2855d88cc73SJohan Hedberg msg.msg_iov = (struct iovec *) &iv; 2865d88cc73SJohan Hedberg msg.msg_iovlen = 2; 2875d88cc73SJohan Hedberg 2885d88cc73SJohan Hedberg l2cap_chan_send(chan, &msg, 1 + len); 289e2dcd113SVinicius Costa Gomes 290b68fda68SJohan Hedberg if (!chan->data) 291b68fda68SJohan Hedberg return; 292b68fda68SJohan Hedberg 293b68fda68SJohan Hedberg smp = chan->data; 294b68fda68SJohan Hedberg 295b68fda68SJohan Hedberg cancel_delayed_work_sync(&smp->security_timer); 296b68fda68SJohan Hedberg schedule_delayed_work(&smp->security_timer, SMP_TIMEOUT); 297eb492e01SAnderson Briglia } 298eb492e01SAnderson Briglia 299d2eb9e10SJohan Hedberg static u8 authreq_to_seclevel(u8 authreq) 3002b64d153SBrian Gix { 301d2eb9e10SJohan Hedberg if (authreq & SMP_AUTH_MITM) { 302d2eb9e10SJohan Hedberg if (authreq & SMP_AUTH_SC) 303d2eb9e10SJohan Hedberg return BT_SECURITY_FIPS; 3042b64d153SBrian Gix else 305d2eb9e10SJohan Hedberg return BT_SECURITY_HIGH; 306d2eb9e10SJohan Hedberg } else { 3072b64d153SBrian Gix return BT_SECURITY_MEDIUM; 3082b64d153SBrian Gix } 309d2eb9e10SJohan Hedberg } 3102b64d153SBrian Gix 3112b64d153SBrian Gix static __u8 seclevel_to_authreq(__u8 sec_level) 3122b64d153SBrian Gix { 3132b64d153SBrian Gix switch (sec_level) { 314d2eb9e10SJohan Hedberg case BT_SECURITY_FIPS: 3152b64d153SBrian Gix case BT_SECURITY_HIGH: 3162b64d153SBrian Gix return SMP_AUTH_MITM | SMP_AUTH_BONDING; 3172b64d153SBrian Gix case BT_SECURITY_MEDIUM: 3182b64d153SBrian Gix return SMP_AUTH_BONDING; 3192b64d153SBrian Gix default: 3202b64d153SBrian Gix return SMP_AUTH_NONE; 3212b64d153SBrian Gix } 3222b64d153SBrian Gix } 3232b64d153SBrian Gix 324b8e66eacSVinicius Costa Gomes static void build_pairing_cmd(struct l2cap_conn *conn, 32554790f73SVinicius Costa Gomes struct smp_cmd_pairing *req, 326f1560463SMarcel Holtmann struct smp_cmd_pairing *rsp, __u8 authreq) 327b8e66eacSVinicius Costa Gomes { 3285d88cc73SJohan Hedberg struct l2cap_chan *chan = conn->smp; 3295d88cc73SJohan Hedberg struct smp_chan *smp = chan->data; 330fd349c02SJohan Hedberg struct hci_conn *hcon = conn->hcon; 331fd349c02SJohan Hedberg struct hci_dev *hdev = hcon->hdev; 332fd349c02SJohan Hedberg u8 local_dist = 0, remote_dist = 0; 33354790f73SVinicius Costa Gomes 334b6ae8457SJohan Hedberg if (test_bit(HCI_BONDABLE, &conn->hcon->hdev->dev_flags)) { 3357ee4ea36SMarcel Holtmann local_dist = SMP_DIST_ENC_KEY | SMP_DIST_SIGN; 3367ee4ea36SMarcel Holtmann remote_dist = SMP_DIST_ENC_KEY | SMP_DIST_SIGN; 33754790f73SVinicius Costa Gomes authreq |= SMP_AUTH_BONDING; 3382b64d153SBrian Gix } else { 3392b64d153SBrian Gix authreq &= ~SMP_AUTH_BONDING; 34054790f73SVinicius Costa Gomes } 34154790f73SVinicius Costa Gomes 342fd349c02SJohan Hedberg if (test_bit(HCI_RPA_RESOLVING, &hdev->dev_flags)) 343fd349c02SJohan Hedberg remote_dist |= SMP_DIST_ID_KEY; 344fd349c02SJohan Hedberg 345863efaf2SJohan Hedberg if (test_bit(HCI_PRIVACY, &hdev->dev_flags)) 346863efaf2SJohan Hedberg local_dist |= SMP_DIST_ID_KEY; 347863efaf2SJohan Hedberg 348df8e1a4cSJohan Hedberg if (test_bit(HCI_SC_ENABLED, &hdev->dev_flags)) { 349df8e1a4cSJohan Hedberg if ((authreq & SMP_AUTH_SC) && 350df8e1a4cSJohan Hedberg test_bit(HCI_SSP_ENABLED, &hdev->dev_flags)) { 351df8e1a4cSJohan Hedberg local_dist |= SMP_DIST_LINK_KEY; 352df8e1a4cSJohan Hedberg remote_dist |= SMP_DIST_LINK_KEY; 353df8e1a4cSJohan Hedberg } 354df8e1a4cSJohan Hedberg } else { 355df8e1a4cSJohan Hedberg authreq &= ~SMP_AUTH_SC; 356df8e1a4cSJohan Hedberg } 357df8e1a4cSJohan Hedberg 35854790f73SVinicius Costa Gomes if (rsp == NULL) { 35954790f73SVinicius Costa Gomes req->io_capability = conn->hcon->io_capability; 36054790f73SVinicius Costa Gomes req->oob_flag = SMP_OOB_NOT_PRESENT; 36154790f73SVinicius Costa Gomes req->max_key_size = SMP_MAX_ENC_KEY_SIZE; 362fd349c02SJohan Hedberg req->init_key_dist = local_dist; 363fd349c02SJohan Hedberg req->resp_key_dist = remote_dist; 3640edb14deSJohan Hedberg req->auth_req = (authreq & AUTH_REQ_MASK(hdev)); 365fd349c02SJohan Hedberg 366fd349c02SJohan Hedberg smp->remote_key_dist = remote_dist; 36754790f73SVinicius Costa Gomes return; 36854790f73SVinicius Costa Gomes } 36954790f73SVinicius Costa Gomes 37054790f73SVinicius Costa Gomes rsp->io_capability = conn->hcon->io_capability; 37154790f73SVinicius Costa Gomes rsp->oob_flag = SMP_OOB_NOT_PRESENT; 37254790f73SVinicius Costa Gomes rsp->max_key_size = SMP_MAX_ENC_KEY_SIZE; 373fd349c02SJohan Hedberg rsp->init_key_dist = req->init_key_dist & remote_dist; 374fd349c02SJohan Hedberg rsp->resp_key_dist = req->resp_key_dist & local_dist; 3750edb14deSJohan Hedberg rsp->auth_req = (authreq & AUTH_REQ_MASK(hdev)); 376fd349c02SJohan Hedberg 377fd349c02SJohan Hedberg smp->remote_key_dist = rsp->init_key_dist; 378b8e66eacSVinicius Costa Gomes } 379b8e66eacSVinicius Costa Gomes 3803158c50cSVinicius Costa Gomes static u8 check_enc_key_size(struct l2cap_conn *conn, __u8 max_key_size) 3813158c50cSVinicius Costa Gomes { 3825d88cc73SJohan Hedberg struct l2cap_chan *chan = conn->smp; 3835d88cc73SJohan Hedberg struct smp_chan *smp = chan->data; 3841c1def09SVinicius Costa Gomes 3853158c50cSVinicius Costa Gomes if ((max_key_size > SMP_MAX_ENC_KEY_SIZE) || 3863158c50cSVinicius Costa Gomes (max_key_size < SMP_MIN_ENC_KEY_SIZE)) 3873158c50cSVinicius Costa Gomes return SMP_ENC_KEY_SIZE; 3883158c50cSVinicius Costa Gomes 389f7aa611aSVinicius Costa Gomes smp->enc_key_size = max_key_size; 3903158c50cSVinicius Costa Gomes 3913158c50cSVinicius Costa Gomes return 0; 3923158c50cSVinicius Costa Gomes } 3933158c50cSVinicius Costa Gomes 3946f48e260SJohan Hedberg static void smp_chan_destroy(struct l2cap_conn *conn) 3956f48e260SJohan Hedberg { 3966f48e260SJohan Hedberg struct l2cap_chan *chan = conn->smp; 3976f48e260SJohan Hedberg struct smp_chan *smp = chan->data; 3986f48e260SJohan Hedberg bool complete; 3996f48e260SJohan Hedberg 4006f48e260SJohan Hedberg BUG_ON(!smp); 4016f48e260SJohan Hedberg 4026f48e260SJohan Hedberg cancel_delayed_work_sync(&smp->security_timer); 4036f48e260SJohan Hedberg 4046f48e260SJohan Hedberg complete = test_bit(SMP_FLAG_COMPLETE, &smp->flags); 4056f48e260SJohan Hedberg mgmt_smp_complete(conn->hcon, complete); 4066f48e260SJohan Hedberg 4076f48e260SJohan Hedberg kfree(smp->csrk); 4086f48e260SJohan Hedberg kfree(smp->slave_csrk); 4096f48e260SJohan Hedberg 4106f48e260SJohan Hedberg crypto_free_blkcipher(smp->tfm_aes); 411407cecf6SJohan Hedberg crypto_free_hash(smp->tfm_cmac); 4126f48e260SJohan Hedberg 4136f48e260SJohan Hedberg /* If pairing failed clean up any keys we might have */ 4146f48e260SJohan Hedberg if (!complete) { 4156f48e260SJohan Hedberg if (smp->ltk) { 416970d0f1bSJohan Hedberg list_del_rcu(&smp->ltk->list); 417970d0f1bSJohan Hedberg kfree_rcu(smp->ltk, rcu); 4186f48e260SJohan Hedberg } 4196f48e260SJohan Hedberg 4206f48e260SJohan Hedberg if (smp->slave_ltk) { 421970d0f1bSJohan Hedberg list_del_rcu(&smp->slave_ltk->list); 422970d0f1bSJohan Hedberg kfree_rcu(smp->slave_ltk, rcu); 4236f48e260SJohan Hedberg } 4246f48e260SJohan Hedberg 4256f48e260SJohan Hedberg if (smp->remote_irk) { 426adae20cbSJohan Hedberg list_del_rcu(&smp->remote_irk->list); 427adae20cbSJohan Hedberg kfree_rcu(smp->remote_irk, rcu); 4286f48e260SJohan Hedberg } 4296f48e260SJohan Hedberg } 4306f48e260SJohan Hedberg 4316f48e260SJohan Hedberg chan->data = NULL; 4326f48e260SJohan Hedberg kfree(smp); 4336f48e260SJohan Hedberg hci_conn_drop(conn->hcon); 4346f48e260SJohan Hedberg } 4356f48e260SJohan Hedberg 43684794e11SJohan Hedberg static void smp_failure(struct l2cap_conn *conn, u8 reason) 4374f957a76SBrian Gix { 438bab73cb6SJohan Hedberg struct hci_conn *hcon = conn->hcon; 439b68fda68SJohan Hedberg struct l2cap_chan *chan = conn->smp; 440bab73cb6SJohan Hedberg 44184794e11SJohan Hedberg if (reason) 4424f957a76SBrian Gix smp_send_cmd(conn, SMP_CMD_PAIRING_FAIL, sizeof(reason), 4434f957a76SBrian Gix &reason); 4444f957a76SBrian Gix 445ce39fb4eSMarcel Holtmann clear_bit(HCI_CONN_ENCRYPT_PEND, &hcon->flags); 446e1e930f5SJohan Hedberg mgmt_auth_failed(hcon, HCI_ERROR_AUTH_FAILURE); 447f1c09c07SVinicius Costa Gomes 448fc75cc86SJohan Hedberg if (chan->data) 4494f957a76SBrian Gix smp_chan_destroy(conn); 4504f957a76SBrian Gix } 4514f957a76SBrian Gix 4522b64d153SBrian Gix #define JUST_WORKS 0x00 4532b64d153SBrian Gix #define JUST_CFM 0x01 4542b64d153SBrian Gix #define REQ_PASSKEY 0x02 4552b64d153SBrian Gix #define CFM_PASSKEY 0x03 4562b64d153SBrian Gix #define REQ_OOB 0x04 4572b64d153SBrian Gix #define OVERLAP 0xFF 4582b64d153SBrian Gix 4592b64d153SBrian Gix static const u8 gen_method[5][5] = { 4602b64d153SBrian Gix { JUST_WORKS, JUST_CFM, REQ_PASSKEY, JUST_WORKS, REQ_PASSKEY }, 4612b64d153SBrian Gix { JUST_WORKS, JUST_CFM, REQ_PASSKEY, JUST_WORKS, REQ_PASSKEY }, 4622b64d153SBrian Gix { CFM_PASSKEY, CFM_PASSKEY, REQ_PASSKEY, JUST_WORKS, CFM_PASSKEY }, 4632b64d153SBrian Gix { JUST_WORKS, JUST_CFM, JUST_WORKS, JUST_WORKS, JUST_CFM }, 4642b64d153SBrian Gix { CFM_PASSKEY, CFM_PASSKEY, REQ_PASSKEY, JUST_WORKS, OVERLAP }, 4652b64d153SBrian Gix }; 4662b64d153SBrian Gix 467581370ccSJohan Hedberg static u8 get_auth_method(struct smp_chan *smp, u8 local_io, u8 remote_io) 468581370ccSJohan Hedberg { 4692bcd4003SJohan Hedberg /* If either side has unknown io_caps, use JUST_CFM (which gets 4702bcd4003SJohan Hedberg * converted later to JUST_WORKS if we're initiators. 4712bcd4003SJohan Hedberg */ 472581370ccSJohan Hedberg if (local_io > SMP_IO_KEYBOARD_DISPLAY || 473581370ccSJohan Hedberg remote_io > SMP_IO_KEYBOARD_DISPLAY) 4742bcd4003SJohan Hedberg return JUST_CFM; 475581370ccSJohan Hedberg 476581370ccSJohan Hedberg return gen_method[remote_io][local_io]; 477581370ccSJohan Hedberg } 478581370ccSJohan Hedberg 4792b64d153SBrian Gix static int tk_request(struct l2cap_conn *conn, u8 remote_oob, u8 auth, 4802b64d153SBrian Gix u8 local_io, u8 remote_io) 4812b64d153SBrian Gix { 4822b64d153SBrian Gix struct hci_conn *hcon = conn->hcon; 4835d88cc73SJohan Hedberg struct l2cap_chan *chan = conn->smp; 4845d88cc73SJohan Hedberg struct smp_chan *smp = chan->data; 4852b64d153SBrian Gix u8 method; 4862b64d153SBrian Gix u32 passkey = 0; 4872b64d153SBrian Gix int ret = 0; 4882b64d153SBrian Gix 4892b64d153SBrian Gix /* Initialize key for JUST WORKS */ 4902b64d153SBrian Gix memset(smp->tk, 0, sizeof(smp->tk)); 4914a74d658SJohan Hedberg clear_bit(SMP_FLAG_TK_VALID, &smp->flags); 4922b64d153SBrian Gix 4932b64d153SBrian Gix BT_DBG("tk_request: auth:%d lcl:%d rem:%d", auth, local_io, remote_io); 4942b64d153SBrian Gix 4952bcd4003SJohan Hedberg /* If neither side wants MITM, either "just" confirm an incoming 4962bcd4003SJohan Hedberg * request or use just-works for outgoing ones. The JUST_CFM 4972bcd4003SJohan Hedberg * will be converted to JUST_WORKS if necessary later in this 4982bcd4003SJohan Hedberg * function. If either side has MITM look up the method from the 4992bcd4003SJohan Hedberg * table. 5002bcd4003SJohan Hedberg */ 501581370ccSJohan Hedberg if (!(auth & SMP_AUTH_MITM)) 5022bcd4003SJohan Hedberg method = JUST_CFM; 5032b64d153SBrian Gix else 504581370ccSJohan Hedberg method = get_auth_method(smp, local_io, remote_io); 5052b64d153SBrian Gix 506a82505c7SJohan Hedberg /* Don't confirm locally initiated pairing attempts */ 5074a74d658SJohan Hedberg if (method == JUST_CFM && test_bit(SMP_FLAG_INITIATOR, &smp->flags)) 508a82505c7SJohan Hedberg method = JUST_WORKS; 509a82505c7SJohan Hedberg 51002f3e254SJohan Hedberg /* Don't bother user space with no IO capabilities */ 51102f3e254SJohan Hedberg if (method == JUST_CFM && hcon->io_capability == HCI_IO_NO_INPUT_OUTPUT) 51202f3e254SJohan Hedberg method = JUST_WORKS; 51302f3e254SJohan Hedberg 5142b64d153SBrian Gix /* If Just Works, Continue with Zero TK */ 5152b64d153SBrian Gix if (method == JUST_WORKS) { 5164a74d658SJohan Hedberg set_bit(SMP_FLAG_TK_VALID, &smp->flags); 5172b64d153SBrian Gix return 0; 5182b64d153SBrian Gix } 5192b64d153SBrian Gix 5202b64d153SBrian Gix /* Not Just Works/Confirm results in MITM Authentication */ 5215eb596f5SJohan Hedberg if (method != JUST_CFM) { 5224a74d658SJohan Hedberg set_bit(SMP_FLAG_MITM_AUTH, &smp->flags); 5235eb596f5SJohan Hedberg if (hcon->pending_sec_level < BT_SECURITY_HIGH) 5245eb596f5SJohan Hedberg hcon->pending_sec_level = BT_SECURITY_HIGH; 5255eb596f5SJohan Hedberg } 5262b64d153SBrian Gix 5272b64d153SBrian Gix /* If both devices have Keyoard-Display I/O, the master 5282b64d153SBrian Gix * Confirms and the slave Enters the passkey. 5292b64d153SBrian Gix */ 5302b64d153SBrian Gix if (method == OVERLAP) { 53140bef302SJohan Hedberg if (hcon->role == HCI_ROLE_MASTER) 5322b64d153SBrian Gix method = CFM_PASSKEY; 5332b64d153SBrian Gix else 5342b64d153SBrian Gix method = REQ_PASSKEY; 5352b64d153SBrian Gix } 5362b64d153SBrian Gix 53701ad34d2SJohan Hedberg /* Generate random passkey. */ 5382b64d153SBrian Gix if (method == CFM_PASSKEY) { 539943a732aSJohan Hedberg memset(smp->tk, 0, sizeof(smp->tk)); 5402b64d153SBrian Gix get_random_bytes(&passkey, sizeof(passkey)); 5412b64d153SBrian Gix passkey %= 1000000; 542943a732aSJohan Hedberg put_unaligned_le32(passkey, smp->tk); 5432b64d153SBrian Gix BT_DBG("PassKey: %d", passkey); 5444a74d658SJohan Hedberg set_bit(SMP_FLAG_TK_VALID, &smp->flags); 5452b64d153SBrian Gix } 5462b64d153SBrian Gix 5472b64d153SBrian Gix if (method == REQ_PASSKEY) 548ce39fb4eSMarcel Holtmann ret = mgmt_user_passkey_request(hcon->hdev, &hcon->dst, 549272d90dfSJohan Hedberg hcon->type, hcon->dst_type); 5504eb65e66SJohan Hedberg else if (method == JUST_CFM) 5514eb65e66SJohan Hedberg ret = mgmt_user_confirm_request(hcon->hdev, &hcon->dst, 5524eb65e66SJohan Hedberg hcon->type, hcon->dst_type, 5534eb65e66SJohan Hedberg passkey, 1); 5542b64d153SBrian Gix else 55501ad34d2SJohan Hedberg ret = mgmt_user_passkey_notify(hcon->hdev, &hcon->dst, 556272d90dfSJohan Hedberg hcon->type, hcon->dst_type, 55739adbffeSJohan Hedberg passkey, 0); 5582b64d153SBrian Gix 5592b64d153SBrian Gix return ret; 5602b64d153SBrian Gix } 5612b64d153SBrian Gix 5621cc61144SJohan Hedberg static u8 smp_confirm(struct smp_chan *smp) 5638aab4757SVinicius Costa Gomes { 5648aab4757SVinicius Costa Gomes struct l2cap_conn *conn = smp->conn; 5658aab4757SVinicius Costa Gomes struct smp_cmd_pairing_confirm cp; 5668aab4757SVinicius Costa Gomes int ret; 5678aab4757SVinicius Costa Gomes 5688aab4757SVinicius Costa Gomes BT_DBG("conn %p", conn); 5698aab4757SVinicius Costa Gomes 570e491eaf3SJohan Hedberg ret = smp_c1(smp->tfm_aes, smp->tk, smp->prnd, smp->preq, smp->prsp, 571b1cd5fd9SJohan Hedberg conn->hcon->init_addr_type, &conn->hcon->init_addr, 572943a732aSJohan Hedberg conn->hcon->resp_addr_type, &conn->hcon->resp_addr, 573943a732aSJohan Hedberg cp.confirm_val); 5741cc61144SJohan Hedberg if (ret) 5751cc61144SJohan Hedberg return SMP_UNSPECIFIED; 5768aab4757SVinicius Costa Gomes 5774a74d658SJohan Hedberg clear_bit(SMP_FLAG_CFM_PENDING, &smp->flags); 5782b64d153SBrian Gix 5798aab4757SVinicius Costa Gomes smp_send_cmd(smp->conn, SMP_CMD_PAIRING_CONFIRM, sizeof(cp), &cp); 5808aab4757SVinicius Costa Gomes 581b28b4943SJohan Hedberg if (conn->hcon->out) 582b28b4943SJohan Hedberg SMP_ALLOW_CMD(smp, SMP_CMD_PAIRING_CONFIRM); 583b28b4943SJohan Hedberg else 584b28b4943SJohan Hedberg SMP_ALLOW_CMD(smp, SMP_CMD_PAIRING_RANDOM); 585b28b4943SJohan Hedberg 5861cc61144SJohan Hedberg return 0; 5878aab4757SVinicius Costa Gomes } 5888aab4757SVinicius Costa Gomes 589861580a9SJohan Hedberg static u8 smp_random(struct smp_chan *smp) 5908aab4757SVinicius Costa Gomes { 5918aab4757SVinicius Costa Gomes struct l2cap_conn *conn = smp->conn; 5928aab4757SVinicius Costa Gomes struct hci_conn *hcon = conn->hcon; 593861580a9SJohan Hedberg u8 confirm[16]; 5948aab4757SVinicius Costa Gomes int ret; 5958aab4757SVinicius Costa Gomes 596ec70f36fSJohan Hedberg if (IS_ERR_OR_NULL(smp->tfm_aes)) 597861580a9SJohan Hedberg return SMP_UNSPECIFIED; 5988aab4757SVinicius Costa Gomes 5998aab4757SVinicius Costa Gomes BT_DBG("conn %p %s", conn, conn->hcon->out ? "master" : "slave"); 6008aab4757SVinicius Costa Gomes 601e491eaf3SJohan Hedberg ret = smp_c1(smp->tfm_aes, smp->tk, smp->rrnd, smp->preq, smp->prsp, 602b1cd5fd9SJohan Hedberg hcon->init_addr_type, &hcon->init_addr, 603943a732aSJohan Hedberg hcon->resp_addr_type, &hcon->resp_addr, confirm); 604861580a9SJohan Hedberg if (ret) 605861580a9SJohan Hedberg return SMP_UNSPECIFIED; 6068aab4757SVinicius Costa Gomes 6078aab4757SVinicius Costa Gomes if (memcmp(smp->pcnf, confirm, sizeof(smp->pcnf)) != 0) { 6088aab4757SVinicius Costa Gomes BT_ERR("Pairing failed (confirmation values mismatch)"); 609861580a9SJohan Hedberg return SMP_CONFIRM_FAILED; 6108aab4757SVinicius Costa Gomes } 6118aab4757SVinicius Costa Gomes 6128aab4757SVinicius Costa Gomes if (hcon->out) { 613fe39c7b2SMarcel Holtmann u8 stk[16]; 614fe39c7b2SMarcel Holtmann __le64 rand = 0; 615fe39c7b2SMarcel Holtmann __le16 ediv = 0; 6168aab4757SVinicius Costa Gomes 617e491eaf3SJohan Hedberg smp_s1(smp->tfm_aes, smp->tk, smp->rrnd, smp->prnd, stk); 6188aab4757SVinicius Costa Gomes 619f7aa611aSVinicius Costa Gomes memset(stk + smp->enc_key_size, 0, 620f7aa611aSVinicius Costa Gomes SMP_MAX_ENC_KEY_SIZE - smp->enc_key_size); 6218aab4757SVinicius Costa Gomes 622861580a9SJohan Hedberg if (test_and_set_bit(HCI_CONN_ENCRYPT_PEND, &hcon->flags)) 623861580a9SJohan Hedberg return SMP_UNSPECIFIED; 6248aab4757SVinicius Costa Gomes 6258aab4757SVinicius Costa Gomes hci_le_start_enc(hcon, ediv, rand, stk); 626f7aa611aSVinicius Costa Gomes hcon->enc_key_size = smp->enc_key_size; 627fe59a05fSJohan Hedberg set_bit(HCI_CONN_STK_ENCRYPT, &hcon->flags); 6288aab4757SVinicius Costa Gomes } else { 629fff3490fSJohan Hedberg u8 stk[16], auth; 630fe39c7b2SMarcel Holtmann __le64 rand = 0; 631fe39c7b2SMarcel Holtmann __le16 ediv = 0; 6328aab4757SVinicius Costa Gomes 633943a732aSJohan Hedberg smp_send_cmd(conn, SMP_CMD_PAIRING_RANDOM, sizeof(smp->prnd), 634943a732aSJohan Hedberg smp->prnd); 6358aab4757SVinicius Costa Gomes 636e491eaf3SJohan Hedberg smp_s1(smp->tfm_aes, smp->tk, smp->prnd, smp->rrnd, stk); 6378aab4757SVinicius Costa Gomes 638f7aa611aSVinicius Costa Gomes memset(stk + smp->enc_key_size, 0, 639f7aa611aSVinicius Costa Gomes SMP_MAX_ENC_KEY_SIZE - smp->enc_key_size); 6408aab4757SVinicius Costa Gomes 641fff3490fSJohan Hedberg if (hcon->pending_sec_level == BT_SECURITY_HIGH) 642fff3490fSJohan Hedberg auth = 1; 643fff3490fSJohan Hedberg else 644fff3490fSJohan Hedberg auth = 0; 645fff3490fSJohan Hedberg 6467d5843b7SJohan Hedberg /* Even though there's no _SLAVE suffix this is the 6477d5843b7SJohan Hedberg * slave STK we're adding for later lookup (the master 6487d5843b7SJohan Hedberg * STK never needs to be stored). 6497d5843b7SJohan Hedberg */ 650ce39fb4eSMarcel Holtmann hci_add_ltk(hcon->hdev, &hcon->dst, hcon->dst_type, 6512ceba539SJohan Hedberg SMP_STK, auth, stk, smp->enc_key_size, ediv, rand); 6528aab4757SVinicius Costa Gomes } 6538aab4757SVinicius Costa Gomes 654861580a9SJohan Hedberg return 0; 6558aab4757SVinicius Costa Gomes } 6568aab4757SVinicius Costa Gomes 65744f1a7abSJohan Hedberg static void smp_notify_keys(struct l2cap_conn *conn) 65844f1a7abSJohan Hedberg { 65944f1a7abSJohan Hedberg struct l2cap_chan *chan = conn->smp; 66044f1a7abSJohan Hedberg struct smp_chan *smp = chan->data; 66144f1a7abSJohan Hedberg struct hci_conn *hcon = conn->hcon; 66244f1a7abSJohan Hedberg struct hci_dev *hdev = hcon->hdev; 66344f1a7abSJohan Hedberg struct smp_cmd_pairing *req = (void *) &smp->preq[1]; 66444f1a7abSJohan Hedberg struct smp_cmd_pairing *rsp = (void *) &smp->prsp[1]; 66544f1a7abSJohan Hedberg bool persistent; 66644f1a7abSJohan Hedberg 66744f1a7abSJohan Hedberg if (smp->remote_irk) { 66844f1a7abSJohan Hedberg mgmt_new_irk(hdev, smp->remote_irk); 66944f1a7abSJohan Hedberg /* Now that user space can be considered to know the 67044f1a7abSJohan Hedberg * identity address track the connection based on it 67144f1a7abSJohan Hedberg * from now on. 67244f1a7abSJohan Hedberg */ 67344f1a7abSJohan Hedberg bacpy(&hcon->dst, &smp->remote_irk->bdaddr); 67444f1a7abSJohan Hedberg hcon->dst_type = smp->remote_irk->addr_type; 675f3d82d0cSJohan Hedberg queue_work(hdev->workqueue, &conn->id_addr_update_work); 67644f1a7abSJohan Hedberg 67744f1a7abSJohan Hedberg /* When receiving an indentity resolving key for 67844f1a7abSJohan Hedberg * a remote device that does not use a resolvable 67944f1a7abSJohan Hedberg * private address, just remove the key so that 68044f1a7abSJohan Hedberg * it is possible to use the controller white 68144f1a7abSJohan Hedberg * list for scanning. 68244f1a7abSJohan Hedberg * 68344f1a7abSJohan Hedberg * Userspace will have been told to not store 68444f1a7abSJohan Hedberg * this key at this point. So it is safe to 68544f1a7abSJohan Hedberg * just remove it. 68644f1a7abSJohan Hedberg */ 68744f1a7abSJohan Hedberg if (!bacmp(&smp->remote_irk->rpa, BDADDR_ANY)) { 688adae20cbSJohan Hedberg list_del_rcu(&smp->remote_irk->list); 689adae20cbSJohan Hedberg kfree_rcu(smp->remote_irk, rcu); 69044f1a7abSJohan Hedberg smp->remote_irk = NULL; 69144f1a7abSJohan Hedberg } 69244f1a7abSJohan Hedberg } 69344f1a7abSJohan Hedberg 69444f1a7abSJohan Hedberg /* The LTKs and CSRKs should be persistent only if both sides 69544f1a7abSJohan Hedberg * had the bonding bit set in their authentication requests. 69644f1a7abSJohan Hedberg */ 69744f1a7abSJohan Hedberg persistent = !!((req->auth_req & rsp->auth_req) & SMP_AUTH_BONDING); 69844f1a7abSJohan Hedberg 69944f1a7abSJohan Hedberg if (smp->csrk) { 70044f1a7abSJohan Hedberg smp->csrk->bdaddr_type = hcon->dst_type; 70144f1a7abSJohan Hedberg bacpy(&smp->csrk->bdaddr, &hcon->dst); 70244f1a7abSJohan Hedberg mgmt_new_csrk(hdev, smp->csrk, persistent); 70344f1a7abSJohan Hedberg } 70444f1a7abSJohan Hedberg 70544f1a7abSJohan Hedberg if (smp->slave_csrk) { 70644f1a7abSJohan Hedberg smp->slave_csrk->bdaddr_type = hcon->dst_type; 70744f1a7abSJohan Hedberg bacpy(&smp->slave_csrk->bdaddr, &hcon->dst); 70844f1a7abSJohan Hedberg mgmt_new_csrk(hdev, smp->slave_csrk, persistent); 70944f1a7abSJohan Hedberg } 71044f1a7abSJohan Hedberg 71144f1a7abSJohan Hedberg if (smp->ltk) { 71244f1a7abSJohan Hedberg smp->ltk->bdaddr_type = hcon->dst_type; 71344f1a7abSJohan Hedberg bacpy(&smp->ltk->bdaddr, &hcon->dst); 71444f1a7abSJohan Hedberg mgmt_new_ltk(hdev, smp->ltk, persistent); 71544f1a7abSJohan Hedberg } 71644f1a7abSJohan Hedberg 71744f1a7abSJohan Hedberg if (smp->slave_ltk) { 71844f1a7abSJohan Hedberg smp->slave_ltk->bdaddr_type = hcon->dst_type; 71944f1a7abSJohan Hedberg bacpy(&smp->slave_ltk->bdaddr, &hcon->dst); 72044f1a7abSJohan Hedberg mgmt_new_ltk(hdev, smp->slave_ltk, persistent); 72144f1a7abSJohan Hedberg } 72244f1a7abSJohan Hedberg } 72344f1a7abSJohan Hedberg 724b28b4943SJohan Hedberg static void smp_allow_key_dist(struct smp_chan *smp) 725b28b4943SJohan Hedberg { 726b28b4943SJohan Hedberg /* Allow the first expected phase 3 PDU. The rest of the PDUs 727b28b4943SJohan Hedberg * will be allowed in each PDU handler to ensure we receive 728b28b4943SJohan Hedberg * them in the correct order. 729b28b4943SJohan Hedberg */ 730b28b4943SJohan Hedberg if (smp->remote_key_dist & SMP_DIST_ENC_KEY) 731b28b4943SJohan Hedberg SMP_ALLOW_CMD(smp, SMP_CMD_ENCRYPT_INFO); 732b28b4943SJohan Hedberg else if (smp->remote_key_dist & SMP_DIST_ID_KEY) 733b28b4943SJohan Hedberg SMP_ALLOW_CMD(smp, SMP_CMD_IDENT_INFO); 734b28b4943SJohan Hedberg else if (smp->remote_key_dist & SMP_DIST_SIGN) 735b28b4943SJohan Hedberg SMP_ALLOW_CMD(smp, SMP_CMD_SIGN_INFO); 736b28b4943SJohan Hedberg } 737b28b4943SJohan Hedberg 738d6268e86SJohan Hedberg static void smp_distribute_keys(struct smp_chan *smp) 73944f1a7abSJohan Hedberg { 74044f1a7abSJohan Hedberg struct smp_cmd_pairing *req, *rsp; 74186d1407cSJohan Hedberg struct l2cap_conn *conn = smp->conn; 74244f1a7abSJohan Hedberg struct hci_conn *hcon = conn->hcon; 74344f1a7abSJohan Hedberg struct hci_dev *hdev = hcon->hdev; 74444f1a7abSJohan Hedberg __u8 *keydist; 74544f1a7abSJohan Hedberg 74644f1a7abSJohan Hedberg BT_DBG("conn %p", conn); 74744f1a7abSJohan Hedberg 74844f1a7abSJohan Hedberg rsp = (void *) &smp->prsp[1]; 74944f1a7abSJohan Hedberg 75044f1a7abSJohan Hedberg /* The responder sends its keys first */ 751b28b4943SJohan Hedberg if (hcon->out && (smp->remote_key_dist & KEY_DIST_MASK)) { 752b28b4943SJohan Hedberg smp_allow_key_dist(smp); 75386d1407cSJohan Hedberg return; 754b28b4943SJohan Hedberg } 75544f1a7abSJohan Hedberg 75644f1a7abSJohan Hedberg req = (void *) &smp->preq[1]; 75744f1a7abSJohan Hedberg 75844f1a7abSJohan Hedberg if (hcon->out) { 75944f1a7abSJohan Hedberg keydist = &rsp->init_key_dist; 76044f1a7abSJohan Hedberg *keydist &= req->init_key_dist; 76144f1a7abSJohan Hedberg } else { 76244f1a7abSJohan Hedberg keydist = &rsp->resp_key_dist; 76344f1a7abSJohan Hedberg *keydist &= req->resp_key_dist; 76444f1a7abSJohan Hedberg } 76544f1a7abSJohan Hedberg 76644f1a7abSJohan Hedberg BT_DBG("keydist 0x%x", *keydist); 76744f1a7abSJohan Hedberg 76844f1a7abSJohan Hedberg if (*keydist & SMP_DIST_ENC_KEY) { 76944f1a7abSJohan Hedberg struct smp_cmd_encrypt_info enc; 77044f1a7abSJohan Hedberg struct smp_cmd_master_ident ident; 77144f1a7abSJohan Hedberg struct smp_ltk *ltk; 77244f1a7abSJohan Hedberg u8 authenticated; 77344f1a7abSJohan Hedberg __le16 ediv; 77444f1a7abSJohan Hedberg __le64 rand; 77544f1a7abSJohan Hedberg 77644f1a7abSJohan Hedberg get_random_bytes(enc.ltk, sizeof(enc.ltk)); 77744f1a7abSJohan Hedberg get_random_bytes(&ediv, sizeof(ediv)); 77844f1a7abSJohan Hedberg get_random_bytes(&rand, sizeof(rand)); 77944f1a7abSJohan Hedberg 78044f1a7abSJohan Hedberg smp_send_cmd(conn, SMP_CMD_ENCRYPT_INFO, sizeof(enc), &enc); 78144f1a7abSJohan Hedberg 78244f1a7abSJohan Hedberg authenticated = hcon->sec_level == BT_SECURITY_HIGH; 78344f1a7abSJohan Hedberg ltk = hci_add_ltk(hdev, &hcon->dst, hcon->dst_type, 78444f1a7abSJohan Hedberg SMP_LTK_SLAVE, authenticated, enc.ltk, 78544f1a7abSJohan Hedberg smp->enc_key_size, ediv, rand); 78644f1a7abSJohan Hedberg smp->slave_ltk = ltk; 78744f1a7abSJohan Hedberg 78844f1a7abSJohan Hedberg ident.ediv = ediv; 78944f1a7abSJohan Hedberg ident.rand = rand; 79044f1a7abSJohan Hedberg 79144f1a7abSJohan Hedberg smp_send_cmd(conn, SMP_CMD_MASTER_IDENT, sizeof(ident), &ident); 79244f1a7abSJohan Hedberg 79344f1a7abSJohan Hedberg *keydist &= ~SMP_DIST_ENC_KEY; 79444f1a7abSJohan Hedberg } 79544f1a7abSJohan Hedberg 79644f1a7abSJohan Hedberg if (*keydist & SMP_DIST_ID_KEY) { 79744f1a7abSJohan Hedberg struct smp_cmd_ident_addr_info addrinfo; 79844f1a7abSJohan Hedberg struct smp_cmd_ident_info idinfo; 79944f1a7abSJohan Hedberg 80044f1a7abSJohan Hedberg memcpy(idinfo.irk, hdev->irk, sizeof(idinfo.irk)); 80144f1a7abSJohan Hedberg 80244f1a7abSJohan Hedberg smp_send_cmd(conn, SMP_CMD_IDENT_INFO, sizeof(idinfo), &idinfo); 80344f1a7abSJohan Hedberg 80444f1a7abSJohan Hedberg /* The hci_conn contains the local identity address 80544f1a7abSJohan Hedberg * after the connection has been established. 80644f1a7abSJohan Hedberg * 80744f1a7abSJohan Hedberg * This is true even when the connection has been 80844f1a7abSJohan Hedberg * established using a resolvable random address. 80944f1a7abSJohan Hedberg */ 81044f1a7abSJohan Hedberg bacpy(&addrinfo.bdaddr, &hcon->src); 81144f1a7abSJohan Hedberg addrinfo.addr_type = hcon->src_type; 81244f1a7abSJohan Hedberg 81344f1a7abSJohan Hedberg smp_send_cmd(conn, SMP_CMD_IDENT_ADDR_INFO, sizeof(addrinfo), 81444f1a7abSJohan Hedberg &addrinfo); 81544f1a7abSJohan Hedberg 81644f1a7abSJohan Hedberg *keydist &= ~SMP_DIST_ID_KEY; 81744f1a7abSJohan Hedberg } 81844f1a7abSJohan Hedberg 81944f1a7abSJohan Hedberg if (*keydist & SMP_DIST_SIGN) { 82044f1a7abSJohan Hedberg struct smp_cmd_sign_info sign; 82144f1a7abSJohan Hedberg struct smp_csrk *csrk; 82244f1a7abSJohan Hedberg 82344f1a7abSJohan Hedberg /* Generate a new random key */ 82444f1a7abSJohan Hedberg get_random_bytes(sign.csrk, sizeof(sign.csrk)); 82544f1a7abSJohan Hedberg 82644f1a7abSJohan Hedberg csrk = kzalloc(sizeof(*csrk), GFP_KERNEL); 82744f1a7abSJohan Hedberg if (csrk) { 82844f1a7abSJohan Hedberg csrk->master = 0x00; 82944f1a7abSJohan Hedberg memcpy(csrk->val, sign.csrk, sizeof(csrk->val)); 83044f1a7abSJohan Hedberg } 83144f1a7abSJohan Hedberg smp->slave_csrk = csrk; 83244f1a7abSJohan Hedberg 83344f1a7abSJohan Hedberg smp_send_cmd(conn, SMP_CMD_SIGN_INFO, sizeof(sign), &sign); 83444f1a7abSJohan Hedberg 83544f1a7abSJohan Hedberg *keydist &= ~SMP_DIST_SIGN; 83644f1a7abSJohan Hedberg } 83744f1a7abSJohan Hedberg 83844f1a7abSJohan Hedberg /* If there are still keys to be received wait for them */ 839b28b4943SJohan Hedberg if (smp->remote_key_dist & KEY_DIST_MASK) { 840b28b4943SJohan Hedberg smp_allow_key_dist(smp); 84186d1407cSJohan Hedberg return; 842b28b4943SJohan Hedberg } 84344f1a7abSJohan Hedberg 84444f1a7abSJohan Hedberg set_bit(SMP_FLAG_COMPLETE, &smp->flags); 84544f1a7abSJohan Hedberg smp_notify_keys(conn); 84644f1a7abSJohan Hedberg 84744f1a7abSJohan Hedberg smp_chan_destroy(conn); 84844f1a7abSJohan Hedberg } 84944f1a7abSJohan Hedberg 850b68fda68SJohan Hedberg static void smp_timeout(struct work_struct *work) 851b68fda68SJohan Hedberg { 852b68fda68SJohan Hedberg struct smp_chan *smp = container_of(work, struct smp_chan, 853b68fda68SJohan Hedberg security_timer.work); 854b68fda68SJohan Hedberg struct l2cap_conn *conn = smp->conn; 855b68fda68SJohan Hedberg 856b68fda68SJohan Hedberg BT_DBG("conn %p", conn); 857b68fda68SJohan Hedberg 8581e91c29eSJohan Hedberg hci_disconnect(conn->hcon, HCI_ERROR_REMOTE_USER_TERM); 859b68fda68SJohan Hedberg } 860b68fda68SJohan Hedberg 8618aab4757SVinicius Costa Gomes static struct smp_chan *smp_chan_create(struct l2cap_conn *conn) 8628aab4757SVinicius Costa Gomes { 8635d88cc73SJohan Hedberg struct l2cap_chan *chan = conn->smp; 8648aab4757SVinicius Costa Gomes struct smp_chan *smp; 8658aab4757SVinicius Costa Gomes 866f1560463SMarcel Holtmann smp = kzalloc(sizeof(*smp), GFP_ATOMIC); 867fc75cc86SJohan Hedberg if (!smp) 8688aab4757SVinicius Costa Gomes return NULL; 8698aab4757SVinicius Costa Gomes 8706a7bd103SJohan Hedberg smp->tfm_aes = crypto_alloc_blkcipher("ecb(aes)", 0, CRYPTO_ALG_ASYNC); 8716a7bd103SJohan Hedberg if (IS_ERR(smp->tfm_aes)) { 8726a7bd103SJohan Hedberg BT_ERR("Unable to create ECB crypto context"); 8736a7bd103SJohan Hedberg kfree(smp); 8746a7bd103SJohan Hedberg return NULL; 8756a7bd103SJohan Hedberg } 8766a7bd103SJohan Hedberg 877407cecf6SJohan Hedberg smp->tfm_cmac = crypto_alloc_hash("cmac(aes)", 0, CRYPTO_ALG_ASYNC); 878407cecf6SJohan Hedberg if (IS_ERR(smp->tfm_cmac)) { 879407cecf6SJohan Hedberg BT_ERR("Unable to create CMAC crypto context"); 880407cecf6SJohan Hedberg crypto_free_blkcipher(smp->tfm_aes); 881407cecf6SJohan Hedberg kfree(smp); 882407cecf6SJohan Hedberg return NULL; 883407cecf6SJohan Hedberg } 884407cecf6SJohan Hedberg 8858aab4757SVinicius Costa Gomes smp->conn = conn; 8865d88cc73SJohan Hedberg chan->data = smp; 8878aab4757SVinicius Costa Gomes 888b28b4943SJohan Hedberg SMP_ALLOW_CMD(smp, SMP_CMD_PAIRING_FAIL); 889b28b4943SJohan Hedberg 890b68fda68SJohan Hedberg INIT_DELAYED_WORK(&smp->security_timer, smp_timeout); 891b68fda68SJohan Hedberg 8928aab4757SVinicius Costa Gomes hci_conn_hold(conn->hcon); 8938aab4757SVinicius Costa Gomes 8948aab4757SVinicius Costa Gomes return smp; 8958aab4757SVinicius Costa Gomes } 8968aab4757SVinicius Costa Gomes 8972b64d153SBrian Gix int smp_user_confirm_reply(struct hci_conn *hcon, u16 mgmt_op, __le32 passkey) 8982b64d153SBrian Gix { 899b10e8017SJohan Hedberg struct l2cap_conn *conn = hcon->l2cap_data; 9005d88cc73SJohan Hedberg struct l2cap_chan *chan; 9012b64d153SBrian Gix struct smp_chan *smp; 9022b64d153SBrian Gix u32 value; 903fc75cc86SJohan Hedberg int err; 9042b64d153SBrian Gix 9052b64d153SBrian Gix BT_DBG(""); 9062b64d153SBrian Gix 907fc75cc86SJohan Hedberg if (!conn) 9082b64d153SBrian Gix return -ENOTCONN; 9092b64d153SBrian Gix 9105d88cc73SJohan Hedberg chan = conn->smp; 9115d88cc73SJohan Hedberg if (!chan) 9125d88cc73SJohan Hedberg return -ENOTCONN; 9135d88cc73SJohan Hedberg 914fc75cc86SJohan Hedberg l2cap_chan_lock(chan); 915fc75cc86SJohan Hedberg if (!chan->data) { 916fc75cc86SJohan Hedberg err = -ENOTCONN; 917fc75cc86SJohan Hedberg goto unlock; 918fc75cc86SJohan Hedberg } 919fc75cc86SJohan Hedberg 9205d88cc73SJohan Hedberg smp = chan->data; 9212b64d153SBrian Gix 9222b64d153SBrian Gix switch (mgmt_op) { 9232b64d153SBrian Gix case MGMT_OP_USER_PASSKEY_REPLY: 9242b64d153SBrian Gix value = le32_to_cpu(passkey); 925943a732aSJohan Hedberg memset(smp->tk, 0, sizeof(smp->tk)); 9262b64d153SBrian Gix BT_DBG("PassKey: %d", value); 927943a732aSJohan Hedberg put_unaligned_le32(value, smp->tk); 9282b64d153SBrian Gix /* Fall Through */ 9292b64d153SBrian Gix case MGMT_OP_USER_CONFIRM_REPLY: 9304a74d658SJohan Hedberg set_bit(SMP_FLAG_TK_VALID, &smp->flags); 9312b64d153SBrian Gix break; 9322b64d153SBrian Gix case MGMT_OP_USER_PASSKEY_NEG_REPLY: 9332b64d153SBrian Gix case MGMT_OP_USER_CONFIRM_NEG_REPLY: 93484794e11SJohan Hedberg smp_failure(conn, SMP_PASSKEY_ENTRY_FAILED); 935fc75cc86SJohan Hedberg err = 0; 936fc75cc86SJohan Hedberg goto unlock; 9372b64d153SBrian Gix default: 93884794e11SJohan Hedberg smp_failure(conn, SMP_PASSKEY_ENTRY_FAILED); 939fc75cc86SJohan Hedberg err = -EOPNOTSUPP; 940fc75cc86SJohan Hedberg goto unlock; 9412b64d153SBrian Gix } 9422b64d153SBrian Gix 943fc75cc86SJohan Hedberg err = 0; 944fc75cc86SJohan Hedberg 9452b64d153SBrian Gix /* If it is our turn to send Pairing Confirm, do so now */ 9461cc61144SJohan Hedberg if (test_bit(SMP_FLAG_CFM_PENDING, &smp->flags)) { 9471cc61144SJohan Hedberg u8 rsp = smp_confirm(smp); 9481cc61144SJohan Hedberg if (rsp) 9491cc61144SJohan Hedberg smp_failure(conn, rsp); 9501cc61144SJohan Hedberg } 9512b64d153SBrian Gix 952fc75cc86SJohan Hedberg unlock: 953fc75cc86SJohan Hedberg l2cap_chan_unlock(chan); 954fc75cc86SJohan Hedberg return err; 9552b64d153SBrian Gix } 9562b64d153SBrian Gix 957da85e5e5SVinicius Costa Gomes static u8 smp_cmd_pairing_req(struct l2cap_conn *conn, struct sk_buff *skb) 95888ba43b6SAnderson Briglia { 9593158c50cSVinicius Costa Gomes struct smp_cmd_pairing rsp, *req = (void *) skb->data; 960fc75cc86SJohan Hedberg struct l2cap_chan *chan = conn->smp; 961b3c6410bSJohan Hedberg struct hci_dev *hdev = conn->hcon->hdev; 9628aab4757SVinicius Costa Gomes struct smp_chan *smp; 963c7262e71SJohan Hedberg u8 key_size, auth, sec_level; 9648aab4757SVinicius Costa Gomes int ret; 96588ba43b6SAnderson Briglia 96688ba43b6SAnderson Briglia BT_DBG("conn %p", conn); 96788ba43b6SAnderson Briglia 968c46b98beSJohan Hedberg if (skb->len < sizeof(*req)) 96938e4a915SJohan Hedberg return SMP_INVALID_PARAMS; 970c46b98beSJohan Hedberg 97140bef302SJohan Hedberg if (conn->hcon->role != HCI_ROLE_SLAVE) 9722b64d153SBrian Gix return SMP_CMD_NOTSUPP; 9732b64d153SBrian Gix 974fc75cc86SJohan Hedberg if (!chan->data) 9758aab4757SVinicius Costa Gomes smp = smp_chan_create(conn); 976fc75cc86SJohan Hedberg else 9775d88cc73SJohan Hedberg smp = chan->data; 978d26a2345SVinicius Costa Gomes 979d08fd0e7SAndrei Emeltchenko if (!smp) 980d08fd0e7SAndrei Emeltchenko return SMP_UNSPECIFIED; 981d08fd0e7SAndrei Emeltchenko 982c05b9339SJohan Hedberg /* We didn't start the pairing, so match remote */ 9830edb14deSJohan Hedberg auth = req->auth_req & AUTH_REQ_MASK(hdev); 984c05b9339SJohan Hedberg 985b6ae8457SJohan Hedberg if (!test_bit(HCI_BONDABLE, &hdev->dev_flags) && 986c05b9339SJohan Hedberg (auth & SMP_AUTH_BONDING)) 987b3c6410bSJohan Hedberg return SMP_PAIRING_NOTSUPP; 988b3c6410bSJohan Hedberg 9891c1def09SVinicius Costa Gomes smp->preq[0] = SMP_CMD_PAIRING_REQ; 9901c1def09SVinicius Costa Gomes memcpy(&smp->preq[1], req, sizeof(*req)); 9913158c50cSVinicius Costa Gomes skb_pull(skb, sizeof(*req)); 99288ba43b6SAnderson Briglia 9935be5e275SJohan Hedberg if (conn->hcon->io_capability == HCI_IO_NO_INPUT_OUTPUT) 9941afc2a1aSJohan Hedberg sec_level = BT_SECURITY_MEDIUM; 9951afc2a1aSJohan Hedberg else 996c7262e71SJohan Hedberg sec_level = authreq_to_seclevel(auth); 9971afc2a1aSJohan Hedberg 998c7262e71SJohan Hedberg if (sec_level > conn->hcon->pending_sec_level) 999c7262e71SJohan Hedberg conn->hcon->pending_sec_level = sec_level; 1000fdde0a26SIdo Yariv 100149c922bbSStephen Hemminger /* If we need MITM check that it can be achieved */ 10022ed8f65cSJohan Hedberg if (conn->hcon->pending_sec_level >= BT_SECURITY_HIGH) { 10032ed8f65cSJohan Hedberg u8 method; 10042ed8f65cSJohan Hedberg 10052ed8f65cSJohan Hedberg method = get_auth_method(smp, conn->hcon->io_capability, 10062ed8f65cSJohan Hedberg req->io_capability); 10072ed8f65cSJohan Hedberg if (method == JUST_WORKS || method == JUST_CFM) 10082ed8f65cSJohan Hedberg return SMP_AUTH_REQUIREMENTS; 10092ed8f65cSJohan Hedberg } 10102ed8f65cSJohan Hedberg 10112b64d153SBrian Gix build_pairing_cmd(conn, req, &rsp, auth); 10123158c50cSVinicius Costa Gomes 101365668776SJohan Hedberg if (rsp.auth_req & SMP_AUTH_SC) 101465668776SJohan Hedberg set_bit(SMP_FLAG_SC, &smp->flags); 101565668776SJohan Hedberg 10163158c50cSVinicius Costa Gomes key_size = min(req->max_key_size, rsp.max_key_size); 10173158c50cSVinicius Costa Gomes if (check_enc_key_size(conn, key_size)) 10183158c50cSVinicius Costa Gomes return SMP_ENC_KEY_SIZE; 101988ba43b6SAnderson Briglia 1020e84a6b13SJohan Hedberg get_random_bytes(smp->prnd, sizeof(smp->prnd)); 10218aab4757SVinicius Costa Gomes 10221c1def09SVinicius Costa Gomes smp->prsp[0] = SMP_CMD_PAIRING_RSP; 10231c1def09SVinicius Costa Gomes memcpy(&smp->prsp[1], &rsp, sizeof(rsp)); 1024f01ead31SAnderson Briglia 10253158c50cSVinicius Costa Gomes smp_send_cmd(conn, SMP_CMD_PAIRING_RSP, sizeof(rsp), &rsp); 10263b19146dSJohan Hedberg 10273b19146dSJohan Hedberg clear_bit(SMP_FLAG_INITIATOR, &smp->flags); 10283b19146dSJohan Hedberg 10293b19146dSJohan Hedberg if (test_bit(SMP_FLAG_SC, &smp->flags)) { 10303b19146dSJohan Hedberg SMP_ALLOW_CMD(smp, SMP_CMD_PUBLIC_KEY); 10313b19146dSJohan Hedberg /* Clear bits which are generated but not distributed */ 10323b19146dSJohan Hedberg smp->remote_key_dist &= ~SMP_SC_NO_DIST; 10333b19146dSJohan Hedberg /* Wait for Public Key from Initiating Device */ 10343b19146dSJohan Hedberg return 0; 10353b19146dSJohan Hedberg } else { 1036b28b4943SJohan Hedberg SMP_ALLOW_CMD(smp, SMP_CMD_PAIRING_CONFIRM); 10373b19146dSJohan Hedberg } 1038da85e5e5SVinicius Costa Gomes 10392b64d153SBrian Gix /* Request setup of TK */ 10402b64d153SBrian Gix ret = tk_request(conn, 0, auth, rsp.io_capability, req->io_capability); 10412b64d153SBrian Gix if (ret) 10422b64d153SBrian Gix return SMP_UNSPECIFIED; 10432b64d153SBrian Gix 1044da85e5e5SVinicius Costa Gomes return 0; 104588ba43b6SAnderson Briglia } 104688ba43b6SAnderson Briglia 10473b19146dSJohan Hedberg static u8 sc_send_public_key(struct smp_chan *smp) 10483b19146dSJohan Hedberg { 10493b19146dSJohan Hedberg BT_DBG(""); 10503b19146dSJohan Hedberg 10513b19146dSJohan Hedberg /* Generate local key pair for Secure Connections */ 10523b19146dSJohan Hedberg if (!ecc_make_key(smp->local_pk, smp->local_sk)) 10533b19146dSJohan Hedberg return SMP_UNSPECIFIED; 10543b19146dSJohan Hedberg 10553b19146dSJohan Hedberg BT_DBG("Local Public Key X: %32phN", smp->local_pk); 10563b19146dSJohan Hedberg BT_DBG("Local Public Key Y: %32phN", &smp->local_pk[32]); 10573b19146dSJohan Hedberg BT_DBG("Local Private Key: %32phN", smp->local_sk); 10583b19146dSJohan Hedberg 10593b19146dSJohan Hedberg smp_send_cmd(smp->conn, SMP_CMD_PUBLIC_KEY, 64, smp->local_pk); 10603b19146dSJohan Hedberg 10613b19146dSJohan Hedberg return 0; 10623b19146dSJohan Hedberg } 10633b19146dSJohan Hedberg 1064da85e5e5SVinicius Costa Gomes static u8 smp_cmd_pairing_rsp(struct l2cap_conn *conn, struct sk_buff *skb) 106588ba43b6SAnderson Briglia { 10663158c50cSVinicius Costa Gomes struct smp_cmd_pairing *req, *rsp = (void *) skb->data; 10675d88cc73SJohan Hedberg struct l2cap_chan *chan = conn->smp; 10685d88cc73SJohan Hedberg struct smp_chan *smp = chan->data; 10690edb14deSJohan Hedberg struct hci_dev *hdev = conn->hcon->hdev; 10703a7dbfb8SJohan Hedberg u8 key_size, auth; 10717d24ddccSAnderson Briglia int ret; 107288ba43b6SAnderson Briglia 107388ba43b6SAnderson Briglia BT_DBG("conn %p", conn); 107488ba43b6SAnderson Briglia 1075c46b98beSJohan Hedberg if (skb->len < sizeof(*rsp)) 107638e4a915SJohan Hedberg return SMP_INVALID_PARAMS; 1077c46b98beSJohan Hedberg 107840bef302SJohan Hedberg if (conn->hcon->role != HCI_ROLE_MASTER) 10792b64d153SBrian Gix return SMP_CMD_NOTSUPP; 10802b64d153SBrian Gix 10813158c50cSVinicius Costa Gomes skb_pull(skb, sizeof(*rsp)); 1082da85e5e5SVinicius Costa Gomes 10831c1def09SVinicius Costa Gomes req = (void *) &smp->preq[1]; 10843158c50cSVinicius Costa Gomes 10853158c50cSVinicius Costa Gomes key_size = min(req->max_key_size, rsp->max_key_size); 10863158c50cSVinicius Costa Gomes if (check_enc_key_size(conn, key_size)) 10873158c50cSVinicius Costa Gomes return SMP_ENC_KEY_SIZE; 10883158c50cSVinicius Costa Gomes 10890edb14deSJohan Hedberg auth = rsp->auth_req & AUTH_REQ_MASK(hdev); 1090c05b9339SJohan Hedberg 109165668776SJohan Hedberg if ((req->auth_req & SMP_AUTH_SC) && (auth & SMP_AUTH_SC)) 109265668776SJohan Hedberg set_bit(SMP_FLAG_SC, &smp->flags); 1093d2eb9e10SJohan Hedberg else if (conn->hcon->pending_sec_level > BT_SECURITY_HIGH) 1094d2eb9e10SJohan Hedberg conn->hcon->pending_sec_level = BT_SECURITY_HIGH; 109565668776SJohan Hedberg 109649c922bbSStephen Hemminger /* If we need MITM check that it can be achieved */ 10972ed8f65cSJohan Hedberg if (conn->hcon->pending_sec_level >= BT_SECURITY_HIGH) { 10982ed8f65cSJohan Hedberg u8 method; 10992ed8f65cSJohan Hedberg 11002ed8f65cSJohan Hedberg method = get_auth_method(smp, req->io_capability, 11012ed8f65cSJohan Hedberg rsp->io_capability); 11022ed8f65cSJohan Hedberg if (method == JUST_WORKS || method == JUST_CFM) 11032ed8f65cSJohan Hedberg return SMP_AUTH_REQUIREMENTS; 11042ed8f65cSJohan Hedberg } 11052ed8f65cSJohan Hedberg 1106e84a6b13SJohan Hedberg get_random_bytes(smp->prnd, sizeof(smp->prnd)); 11077d24ddccSAnderson Briglia 11088aab4757SVinicius Costa Gomes smp->prsp[0] = SMP_CMD_PAIRING_RSP; 11098aab4757SVinicius Costa Gomes memcpy(&smp->prsp[1], rsp, sizeof(*rsp)); 11107d24ddccSAnderson Briglia 1111fdcc4becSJohan Hedberg /* Update remote key distribution in case the remote cleared 1112fdcc4becSJohan Hedberg * some bits that we had enabled in our request. 1113fdcc4becSJohan Hedberg */ 1114fdcc4becSJohan Hedberg smp->remote_key_dist &= rsp->resp_key_dist; 1115fdcc4becSJohan Hedberg 11163b19146dSJohan Hedberg if (test_bit(SMP_FLAG_SC, &smp->flags)) { 11173b19146dSJohan Hedberg /* Clear bits which are generated but not distributed */ 11183b19146dSJohan Hedberg smp->remote_key_dist &= ~SMP_SC_NO_DIST; 11193b19146dSJohan Hedberg SMP_ALLOW_CMD(smp, SMP_CMD_PUBLIC_KEY); 11203b19146dSJohan Hedberg return sc_send_public_key(smp); 11213b19146dSJohan Hedberg } 11223b19146dSJohan Hedberg 1123c05b9339SJohan Hedberg auth |= req->auth_req; 11242b64d153SBrian Gix 1125476585ecSJohan Hedberg ret = tk_request(conn, 0, auth, req->io_capability, rsp->io_capability); 11262b64d153SBrian Gix if (ret) 11272b64d153SBrian Gix return SMP_UNSPECIFIED; 11282b64d153SBrian Gix 11294a74d658SJohan Hedberg set_bit(SMP_FLAG_CFM_PENDING, &smp->flags); 11302b64d153SBrian Gix 11312b64d153SBrian Gix /* Can't compose response until we have been confirmed */ 11324a74d658SJohan Hedberg if (test_bit(SMP_FLAG_TK_VALID, &smp->flags)) 11331cc61144SJohan Hedberg return smp_confirm(smp); 1134da85e5e5SVinicius Costa Gomes 1135da85e5e5SVinicius Costa Gomes return 0; 113688ba43b6SAnderson Briglia } 113788ba43b6SAnderson Briglia 1138da85e5e5SVinicius Costa Gomes static u8 smp_cmd_pairing_confirm(struct l2cap_conn *conn, struct sk_buff *skb) 113988ba43b6SAnderson Briglia { 11405d88cc73SJohan Hedberg struct l2cap_chan *chan = conn->smp; 11415d88cc73SJohan Hedberg struct smp_chan *smp = chan->data; 11427d24ddccSAnderson Briglia 114388ba43b6SAnderson Briglia BT_DBG("conn %p %s", conn, conn->hcon->out ? "master" : "slave"); 114488ba43b6SAnderson Briglia 1145c46b98beSJohan Hedberg if (skb->len < sizeof(smp->pcnf)) 114638e4a915SJohan Hedberg return SMP_INVALID_PARAMS; 1147c46b98beSJohan Hedberg 11481c1def09SVinicius Costa Gomes memcpy(smp->pcnf, skb->data, sizeof(smp->pcnf)); 11491c1def09SVinicius Costa Gomes skb_pull(skb, sizeof(smp->pcnf)); 11507d24ddccSAnderson Briglia 1151b28b4943SJohan Hedberg if (conn->hcon->out) { 1152943a732aSJohan Hedberg smp_send_cmd(conn, SMP_CMD_PAIRING_RANDOM, sizeof(smp->prnd), 1153943a732aSJohan Hedberg smp->prnd); 1154b28b4943SJohan Hedberg SMP_ALLOW_CMD(smp, SMP_CMD_PAIRING_RANDOM); 1155b28b4943SJohan Hedberg return 0; 1156b28b4943SJohan Hedberg } 1157b28b4943SJohan Hedberg 1158b28b4943SJohan Hedberg if (test_bit(SMP_FLAG_TK_VALID, &smp->flags)) 11591cc61144SJohan Hedberg return smp_confirm(smp); 1160943a732aSJohan Hedberg else 11614a74d658SJohan Hedberg set_bit(SMP_FLAG_CFM_PENDING, &smp->flags); 1162da85e5e5SVinicius Costa Gomes 1163da85e5e5SVinicius Costa Gomes return 0; 116488ba43b6SAnderson Briglia } 116588ba43b6SAnderson Briglia 1166da85e5e5SVinicius Costa Gomes static u8 smp_cmd_pairing_random(struct l2cap_conn *conn, struct sk_buff *skb) 116788ba43b6SAnderson Briglia { 11685d88cc73SJohan Hedberg struct l2cap_chan *chan = conn->smp; 11695d88cc73SJohan Hedberg struct smp_chan *smp = chan->data; 11707d24ddccSAnderson Briglia 11718aab4757SVinicius Costa Gomes BT_DBG("conn %p", conn); 11727d24ddccSAnderson Briglia 1173c46b98beSJohan Hedberg if (skb->len < sizeof(smp->rrnd)) 117438e4a915SJohan Hedberg return SMP_INVALID_PARAMS; 1175c46b98beSJohan Hedberg 1176943a732aSJohan Hedberg memcpy(smp->rrnd, skb->data, sizeof(smp->rrnd)); 11778aab4757SVinicius Costa Gomes skb_pull(skb, sizeof(smp->rrnd)); 117888ba43b6SAnderson Briglia 1179861580a9SJohan Hedberg return smp_random(smp); 118088ba43b6SAnderson Briglia } 118188ba43b6SAnderson Briglia 1182f81cd823SMarcel Holtmann static bool smp_ltk_encrypt(struct l2cap_conn *conn, u8 sec_level) 1183988c5997SVinicius Costa Gomes { 1184c9839a11SVinicius Costa Gomes struct smp_ltk *key; 1185988c5997SVinicius Costa Gomes struct hci_conn *hcon = conn->hcon; 1186988c5997SVinicius Costa Gomes 1187f3a73d97SJohan Hedberg key = hci_find_ltk(hcon->hdev, &hcon->dst, hcon->dst_type, hcon->role); 1188988c5997SVinicius Costa Gomes if (!key) 1189f81cd823SMarcel Holtmann return false; 1190988c5997SVinicius Costa Gomes 1191a6f7833cSJohan Hedberg if (smp_ltk_sec_level(key) < sec_level) 1192f81cd823SMarcel Holtmann return false; 11934dab7864SJohan Hedberg 119451a8efd7SJohan Hedberg if (test_and_set_bit(HCI_CONN_ENCRYPT_PEND, &hcon->flags)) 1195f81cd823SMarcel Holtmann return true; 1196988c5997SVinicius Costa Gomes 1197c9839a11SVinicius Costa Gomes hci_le_start_enc(hcon, key->ediv, key->rand, key->val); 1198c9839a11SVinicius Costa Gomes hcon->enc_key_size = key->enc_size; 1199988c5997SVinicius Costa Gomes 1200fe59a05fSJohan Hedberg /* We never store STKs for master role, so clear this flag */ 1201fe59a05fSJohan Hedberg clear_bit(HCI_CONN_STK_ENCRYPT, &hcon->flags); 1202fe59a05fSJohan Hedberg 1203f81cd823SMarcel Holtmann return true; 1204988c5997SVinicius Costa Gomes } 1205f1560463SMarcel Holtmann 120635dc6f83SJohan Hedberg bool smp_sufficient_security(struct hci_conn *hcon, u8 sec_level, 120735dc6f83SJohan Hedberg enum smp_key_pref key_pref) 1208854f4727SJohan Hedberg { 1209854f4727SJohan Hedberg if (sec_level == BT_SECURITY_LOW) 1210854f4727SJohan Hedberg return true; 1211854f4727SJohan Hedberg 121235dc6f83SJohan Hedberg /* If we're encrypted with an STK but the caller prefers using 121335dc6f83SJohan Hedberg * LTK claim insufficient security. This way we allow the 121435dc6f83SJohan Hedberg * connection to be re-encrypted with an LTK, even if the LTK 121535dc6f83SJohan Hedberg * provides the same level of security. Only exception is if we 121635dc6f83SJohan Hedberg * don't have an LTK (e.g. because of key distribution bits). 12179ab65d60SJohan Hedberg */ 121835dc6f83SJohan Hedberg if (key_pref == SMP_USE_LTK && 121935dc6f83SJohan Hedberg test_bit(HCI_CONN_STK_ENCRYPT, &hcon->flags) && 1220f3a73d97SJohan Hedberg hci_find_ltk(hcon->hdev, &hcon->dst, hcon->dst_type, hcon->role)) 12219ab65d60SJohan Hedberg return false; 12229ab65d60SJohan Hedberg 1223854f4727SJohan Hedberg if (hcon->sec_level >= sec_level) 1224854f4727SJohan Hedberg return true; 1225854f4727SJohan Hedberg 1226854f4727SJohan Hedberg return false; 1227854f4727SJohan Hedberg } 1228854f4727SJohan Hedberg 1229da85e5e5SVinicius Costa Gomes static u8 smp_cmd_security_req(struct l2cap_conn *conn, struct sk_buff *skb) 123088ba43b6SAnderson Briglia { 123188ba43b6SAnderson Briglia struct smp_cmd_security_req *rp = (void *) skb->data; 123288ba43b6SAnderson Briglia struct smp_cmd_pairing cp; 1233f1cb9af5SVinicius Costa Gomes struct hci_conn *hcon = conn->hcon; 12340edb14deSJohan Hedberg struct hci_dev *hdev = hcon->hdev; 12358aab4757SVinicius Costa Gomes struct smp_chan *smp; 1236c05b9339SJohan Hedberg u8 sec_level, auth; 123788ba43b6SAnderson Briglia 123888ba43b6SAnderson Briglia BT_DBG("conn %p", conn); 123988ba43b6SAnderson Briglia 1240c46b98beSJohan Hedberg if (skb->len < sizeof(*rp)) 124138e4a915SJohan Hedberg return SMP_INVALID_PARAMS; 1242c46b98beSJohan Hedberg 124340bef302SJohan Hedberg if (hcon->role != HCI_ROLE_MASTER) 124486ca9eacSJohan Hedberg return SMP_CMD_NOTSUPP; 124586ca9eacSJohan Hedberg 12460edb14deSJohan Hedberg auth = rp->auth_req & AUTH_REQ_MASK(hdev); 1247c05b9339SJohan Hedberg 12485be5e275SJohan Hedberg if (hcon->io_capability == HCI_IO_NO_INPUT_OUTPUT) 12491afc2a1aSJohan Hedberg sec_level = BT_SECURITY_MEDIUM; 12501afc2a1aSJohan Hedberg else 1251c05b9339SJohan Hedberg sec_level = authreq_to_seclevel(auth); 12521afc2a1aSJohan Hedberg 125335dc6f83SJohan Hedberg if (smp_sufficient_security(hcon, sec_level, SMP_USE_LTK)) 1254854f4727SJohan Hedberg return 0; 1255854f4727SJohan Hedberg 1256c7262e71SJohan Hedberg if (sec_level > hcon->pending_sec_level) 1257c7262e71SJohan Hedberg hcon->pending_sec_level = sec_level; 1258feb45eb5SVinicius Costa Gomes 12594dab7864SJohan Hedberg if (smp_ltk_encrypt(conn, hcon->pending_sec_level)) 1260988c5997SVinicius Costa Gomes return 0; 1261988c5997SVinicius Costa Gomes 12628aab4757SVinicius Costa Gomes smp = smp_chan_create(conn); 1263c29d2444SJohan Hedberg if (!smp) 1264c29d2444SJohan Hedberg return SMP_UNSPECIFIED; 1265d26a2345SVinicius Costa Gomes 1266b6ae8457SJohan Hedberg if (!test_bit(HCI_BONDABLE, &hcon->hdev->dev_flags) && 1267c05b9339SJohan Hedberg (auth & SMP_AUTH_BONDING)) 1268616d55beSJohan Hedberg return SMP_PAIRING_NOTSUPP; 1269616d55beSJohan Hedberg 127088ba43b6SAnderson Briglia skb_pull(skb, sizeof(*rp)); 127188ba43b6SAnderson Briglia 1272da85e5e5SVinicius Costa Gomes memset(&cp, 0, sizeof(cp)); 1273c05b9339SJohan Hedberg build_pairing_cmd(conn, &cp, NULL, auth); 127488ba43b6SAnderson Briglia 12751c1def09SVinicius Costa Gomes smp->preq[0] = SMP_CMD_PAIRING_REQ; 12761c1def09SVinicius Costa Gomes memcpy(&smp->preq[1], &cp, sizeof(cp)); 1277f01ead31SAnderson Briglia 127888ba43b6SAnderson Briglia smp_send_cmd(conn, SMP_CMD_PAIRING_REQ, sizeof(cp), &cp); 1279b28b4943SJohan Hedberg SMP_ALLOW_CMD(smp, SMP_CMD_PAIRING_RSP); 1280f1cb9af5SVinicius Costa Gomes 1281da85e5e5SVinicius Costa Gomes return 0; 128288ba43b6SAnderson Briglia } 128388ba43b6SAnderson Briglia 1284cc110922SVinicius Costa Gomes int smp_conn_security(struct hci_conn *hcon, __u8 sec_level) 1285eb492e01SAnderson Briglia { 1286cc110922SVinicius Costa Gomes struct l2cap_conn *conn = hcon->l2cap_data; 1287c68b7f12SJohan Hedberg struct l2cap_chan *chan; 12880a66cf20SJohan Hedberg struct smp_chan *smp; 12892b64d153SBrian Gix __u8 authreq; 1290fc75cc86SJohan Hedberg int ret; 1291eb492e01SAnderson Briglia 12923a0259bbSVinicius Costa Gomes BT_DBG("conn %p hcon %p level 0x%2.2x", conn, hcon, sec_level); 12933a0259bbSVinicius Costa Gomes 12940a66cf20SJohan Hedberg /* This may be NULL if there's an unexpected disconnection */ 12950a66cf20SJohan Hedberg if (!conn) 12960a66cf20SJohan Hedberg return 1; 12970a66cf20SJohan Hedberg 1298c68b7f12SJohan Hedberg chan = conn->smp; 1299c68b7f12SJohan Hedberg 1300757aee0fSJohan Hedberg if (!test_bit(HCI_LE_ENABLED, &hcon->hdev->dev_flags)) 13012e65c9d2SAndre Guedes return 1; 13022e65c9d2SAndre Guedes 130335dc6f83SJohan Hedberg if (smp_sufficient_security(hcon, sec_level, SMP_USE_LTK)) 1304f1cb9af5SVinicius Costa Gomes return 1; 1305f1cb9af5SVinicius Costa Gomes 1306c7262e71SJohan Hedberg if (sec_level > hcon->pending_sec_level) 1307c7262e71SJohan Hedberg hcon->pending_sec_level = sec_level; 1308c7262e71SJohan Hedberg 130940bef302SJohan Hedberg if (hcon->role == HCI_ROLE_MASTER) 1310c7262e71SJohan Hedberg if (smp_ltk_encrypt(conn, hcon->pending_sec_level)) 1311c7262e71SJohan Hedberg return 0; 1312d26a2345SVinicius Costa Gomes 1313fc75cc86SJohan Hedberg l2cap_chan_lock(chan); 1314fc75cc86SJohan Hedberg 1315fc75cc86SJohan Hedberg /* If SMP is already in progress ignore this request */ 1316fc75cc86SJohan Hedberg if (chan->data) { 1317fc75cc86SJohan Hedberg ret = 0; 1318fc75cc86SJohan Hedberg goto unlock; 1319fc75cc86SJohan Hedberg } 1320d26a2345SVinicius Costa Gomes 13218aab4757SVinicius Costa Gomes smp = smp_chan_create(conn); 1322fc75cc86SJohan Hedberg if (!smp) { 1323fc75cc86SJohan Hedberg ret = 1; 1324fc75cc86SJohan Hedberg goto unlock; 1325fc75cc86SJohan Hedberg } 13262b64d153SBrian Gix 13272b64d153SBrian Gix authreq = seclevel_to_authreq(sec_level); 1328d26a2345SVinicius Costa Gomes 1329d2eb9e10SJohan Hedberg if (test_bit(HCI_SC_ENABLED, &hcon->hdev->dev_flags)) 1330d2eb9e10SJohan Hedberg authreq |= SMP_AUTH_SC; 1331d2eb9e10SJohan Hedberg 133279897d20SJohan Hedberg /* Require MITM if IO Capability allows or the security level 133379897d20SJohan Hedberg * requires it. 13342e233644SJohan Hedberg */ 133579897d20SJohan Hedberg if (hcon->io_capability != HCI_IO_NO_INPUT_OUTPUT || 1336c7262e71SJohan Hedberg hcon->pending_sec_level > BT_SECURITY_MEDIUM) 13372e233644SJohan Hedberg authreq |= SMP_AUTH_MITM; 13382e233644SJohan Hedberg 133940bef302SJohan Hedberg if (hcon->role == HCI_ROLE_MASTER) { 1340d26a2345SVinicius Costa Gomes struct smp_cmd_pairing cp; 1341f01ead31SAnderson Briglia 13422b64d153SBrian Gix build_pairing_cmd(conn, &cp, NULL, authreq); 13431c1def09SVinicius Costa Gomes smp->preq[0] = SMP_CMD_PAIRING_REQ; 13441c1def09SVinicius Costa Gomes memcpy(&smp->preq[1], &cp, sizeof(cp)); 1345f01ead31SAnderson Briglia 1346eb492e01SAnderson Briglia smp_send_cmd(conn, SMP_CMD_PAIRING_REQ, sizeof(cp), &cp); 1347b28b4943SJohan Hedberg SMP_ALLOW_CMD(smp, SMP_CMD_PAIRING_RSP); 1348eb492e01SAnderson Briglia } else { 1349eb492e01SAnderson Briglia struct smp_cmd_security_req cp; 13502b64d153SBrian Gix cp.auth_req = authreq; 1351eb492e01SAnderson Briglia smp_send_cmd(conn, SMP_CMD_SECURITY_REQ, sizeof(cp), &cp); 1352b28b4943SJohan Hedberg SMP_ALLOW_CMD(smp, SMP_CMD_PAIRING_REQ); 1353eb492e01SAnderson Briglia } 1354eb492e01SAnderson Briglia 13554a74d658SJohan Hedberg set_bit(SMP_FLAG_INITIATOR, &smp->flags); 1356fc75cc86SJohan Hedberg ret = 0; 1357edca792cSJohan Hedberg 1358fc75cc86SJohan Hedberg unlock: 1359fc75cc86SJohan Hedberg l2cap_chan_unlock(chan); 1360fc75cc86SJohan Hedberg return ret; 1361eb492e01SAnderson Briglia } 1362eb492e01SAnderson Briglia 13637034b911SVinicius Costa Gomes static int smp_cmd_encrypt_info(struct l2cap_conn *conn, struct sk_buff *skb) 13647034b911SVinicius Costa Gomes { 136516b90839SVinicius Costa Gomes struct smp_cmd_encrypt_info *rp = (void *) skb->data; 13665d88cc73SJohan Hedberg struct l2cap_chan *chan = conn->smp; 13675d88cc73SJohan Hedberg struct smp_chan *smp = chan->data; 136816b90839SVinicius Costa Gomes 1369c46b98beSJohan Hedberg BT_DBG("conn %p", conn); 1370c46b98beSJohan Hedberg 1371c46b98beSJohan Hedberg if (skb->len < sizeof(*rp)) 137238e4a915SJohan Hedberg return SMP_INVALID_PARAMS; 1373c46b98beSJohan Hedberg 1374b28b4943SJohan Hedberg SMP_ALLOW_CMD(smp, SMP_CMD_MASTER_IDENT); 13756131ddc8SJohan Hedberg 137616b90839SVinicius Costa Gomes skb_pull(skb, sizeof(*rp)); 137716b90839SVinicius Costa Gomes 13781c1def09SVinicius Costa Gomes memcpy(smp->tk, rp->ltk, sizeof(smp->tk)); 137916b90839SVinicius Costa Gomes 13807034b911SVinicius Costa Gomes return 0; 13817034b911SVinicius Costa Gomes } 13827034b911SVinicius Costa Gomes 13837034b911SVinicius Costa Gomes static int smp_cmd_master_ident(struct l2cap_conn *conn, struct sk_buff *skb) 13847034b911SVinicius Costa Gomes { 138516b90839SVinicius Costa Gomes struct smp_cmd_master_ident *rp = (void *) skb->data; 13865d88cc73SJohan Hedberg struct l2cap_chan *chan = conn->smp; 13875d88cc73SJohan Hedberg struct smp_chan *smp = chan->data; 1388c9839a11SVinicius Costa Gomes struct hci_dev *hdev = conn->hcon->hdev; 1389c9839a11SVinicius Costa Gomes struct hci_conn *hcon = conn->hcon; 139023d0e128SJohan Hedberg struct smp_ltk *ltk; 1391c9839a11SVinicius Costa Gomes u8 authenticated; 13927034b911SVinicius Costa Gomes 1393c46b98beSJohan Hedberg BT_DBG("conn %p", conn); 1394c46b98beSJohan Hedberg 1395c46b98beSJohan Hedberg if (skb->len < sizeof(*rp)) 139638e4a915SJohan Hedberg return SMP_INVALID_PARAMS; 1397c46b98beSJohan Hedberg 13989747a9f3SJohan Hedberg /* Mark the information as received */ 13999747a9f3SJohan Hedberg smp->remote_key_dist &= ~SMP_DIST_ENC_KEY; 14009747a9f3SJohan Hedberg 1401b28b4943SJohan Hedberg if (smp->remote_key_dist & SMP_DIST_ID_KEY) 1402b28b4943SJohan Hedberg SMP_ALLOW_CMD(smp, SMP_CMD_IDENT_INFO); 1403196332f5SJohan Hedberg else if (smp->remote_key_dist & SMP_DIST_SIGN) 1404196332f5SJohan Hedberg SMP_ALLOW_CMD(smp, SMP_CMD_SIGN_INFO); 1405b28b4943SJohan Hedberg 140616b90839SVinicius Costa Gomes skb_pull(skb, sizeof(*rp)); 140716b90839SVinicius Costa Gomes 1408ce39fb4eSMarcel Holtmann authenticated = (hcon->sec_level == BT_SECURITY_HIGH); 14092ceba539SJohan Hedberg ltk = hci_add_ltk(hdev, &hcon->dst, hcon->dst_type, SMP_LTK, 1410ce39fb4eSMarcel Holtmann authenticated, smp->tk, smp->enc_key_size, 141104124681SGustavo F. Padovan rp->ediv, rp->rand); 141223d0e128SJohan Hedberg smp->ltk = ltk; 1413c6e81e9aSJohan Hedberg if (!(smp->remote_key_dist & KEY_DIST_MASK)) 1414d6268e86SJohan Hedberg smp_distribute_keys(smp); 14157034b911SVinicius Costa Gomes 14167034b911SVinicius Costa Gomes return 0; 14177034b911SVinicius Costa Gomes } 14187034b911SVinicius Costa Gomes 1419fd349c02SJohan Hedberg static int smp_cmd_ident_info(struct l2cap_conn *conn, struct sk_buff *skb) 1420fd349c02SJohan Hedberg { 1421fd349c02SJohan Hedberg struct smp_cmd_ident_info *info = (void *) skb->data; 14225d88cc73SJohan Hedberg struct l2cap_chan *chan = conn->smp; 14235d88cc73SJohan Hedberg struct smp_chan *smp = chan->data; 1424fd349c02SJohan Hedberg 1425fd349c02SJohan Hedberg BT_DBG(""); 1426fd349c02SJohan Hedberg 1427fd349c02SJohan Hedberg if (skb->len < sizeof(*info)) 142838e4a915SJohan Hedberg return SMP_INVALID_PARAMS; 1429fd349c02SJohan Hedberg 1430b28b4943SJohan Hedberg SMP_ALLOW_CMD(smp, SMP_CMD_IDENT_ADDR_INFO); 14316131ddc8SJohan Hedberg 1432fd349c02SJohan Hedberg skb_pull(skb, sizeof(*info)); 1433fd349c02SJohan Hedberg 1434fd349c02SJohan Hedberg memcpy(smp->irk, info->irk, 16); 1435fd349c02SJohan Hedberg 1436fd349c02SJohan Hedberg return 0; 1437fd349c02SJohan Hedberg } 1438fd349c02SJohan Hedberg 1439fd349c02SJohan Hedberg static int smp_cmd_ident_addr_info(struct l2cap_conn *conn, 1440fd349c02SJohan Hedberg struct sk_buff *skb) 1441fd349c02SJohan Hedberg { 1442fd349c02SJohan Hedberg struct smp_cmd_ident_addr_info *info = (void *) skb->data; 14435d88cc73SJohan Hedberg struct l2cap_chan *chan = conn->smp; 14445d88cc73SJohan Hedberg struct smp_chan *smp = chan->data; 1445fd349c02SJohan Hedberg struct hci_conn *hcon = conn->hcon; 1446fd349c02SJohan Hedberg bdaddr_t rpa; 1447fd349c02SJohan Hedberg 1448fd349c02SJohan Hedberg BT_DBG(""); 1449fd349c02SJohan Hedberg 1450fd349c02SJohan Hedberg if (skb->len < sizeof(*info)) 145138e4a915SJohan Hedberg return SMP_INVALID_PARAMS; 1452fd349c02SJohan Hedberg 14539747a9f3SJohan Hedberg /* Mark the information as received */ 14549747a9f3SJohan Hedberg smp->remote_key_dist &= ~SMP_DIST_ID_KEY; 14559747a9f3SJohan Hedberg 1456b28b4943SJohan Hedberg if (smp->remote_key_dist & SMP_DIST_SIGN) 1457b28b4943SJohan Hedberg SMP_ALLOW_CMD(smp, SMP_CMD_SIGN_INFO); 1458b28b4943SJohan Hedberg 1459fd349c02SJohan Hedberg skb_pull(skb, sizeof(*info)); 1460fd349c02SJohan Hedberg 1461a9a58f86SJohan Hedberg /* Strictly speaking the Core Specification (4.1) allows sending 1462a9a58f86SJohan Hedberg * an empty address which would force us to rely on just the IRK 1463a9a58f86SJohan Hedberg * as "identity information". However, since such 1464a9a58f86SJohan Hedberg * implementations are not known of and in order to not over 1465a9a58f86SJohan Hedberg * complicate our implementation, simply pretend that we never 1466a9a58f86SJohan Hedberg * received an IRK for such a device. 1467a9a58f86SJohan Hedberg */ 1468a9a58f86SJohan Hedberg if (!bacmp(&info->bdaddr, BDADDR_ANY)) { 1469a9a58f86SJohan Hedberg BT_ERR("Ignoring IRK with no identity address"); 147031dd624eSJohan Hedberg goto distribute; 1471a9a58f86SJohan Hedberg } 1472a9a58f86SJohan Hedberg 1473fd349c02SJohan Hedberg bacpy(&smp->id_addr, &info->bdaddr); 1474fd349c02SJohan Hedberg smp->id_addr_type = info->addr_type; 1475fd349c02SJohan Hedberg 1476fd349c02SJohan Hedberg if (hci_bdaddr_is_rpa(&hcon->dst, hcon->dst_type)) 1477fd349c02SJohan Hedberg bacpy(&rpa, &hcon->dst); 1478fd349c02SJohan Hedberg else 1479fd349c02SJohan Hedberg bacpy(&rpa, BDADDR_ANY); 1480fd349c02SJohan Hedberg 148123d0e128SJohan Hedberg smp->remote_irk = hci_add_irk(conn->hcon->hdev, &smp->id_addr, 148223d0e128SJohan Hedberg smp->id_addr_type, smp->irk, &rpa); 1483fd349c02SJohan Hedberg 148431dd624eSJohan Hedberg distribute: 1485c6e81e9aSJohan Hedberg if (!(smp->remote_key_dist & KEY_DIST_MASK)) 1486d6268e86SJohan Hedberg smp_distribute_keys(smp); 1487fd349c02SJohan Hedberg 1488fd349c02SJohan Hedberg return 0; 1489fd349c02SJohan Hedberg } 1490fd349c02SJohan Hedberg 14917ee4ea36SMarcel Holtmann static int smp_cmd_sign_info(struct l2cap_conn *conn, struct sk_buff *skb) 14927ee4ea36SMarcel Holtmann { 14937ee4ea36SMarcel Holtmann struct smp_cmd_sign_info *rp = (void *) skb->data; 14945d88cc73SJohan Hedberg struct l2cap_chan *chan = conn->smp; 14955d88cc73SJohan Hedberg struct smp_chan *smp = chan->data; 14967ee4ea36SMarcel Holtmann struct smp_csrk *csrk; 14977ee4ea36SMarcel Holtmann 14987ee4ea36SMarcel Holtmann BT_DBG("conn %p", conn); 14997ee4ea36SMarcel Holtmann 15007ee4ea36SMarcel Holtmann if (skb->len < sizeof(*rp)) 150138e4a915SJohan Hedberg return SMP_INVALID_PARAMS; 15027ee4ea36SMarcel Holtmann 15037ee4ea36SMarcel Holtmann /* Mark the information as received */ 15047ee4ea36SMarcel Holtmann smp->remote_key_dist &= ~SMP_DIST_SIGN; 15057ee4ea36SMarcel Holtmann 15067ee4ea36SMarcel Holtmann skb_pull(skb, sizeof(*rp)); 15077ee4ea36SMarcel Holtmann 15087ee4ea36SMarcel Holtmann csrk = kzalloc(sizeof(*csrk), GFP_KERNEL); 15097ee4ea36SMarcel Holtmann if (csrk) { 15107ee4ea36SMarcel Holtmann csrk->master = 0x01; 15117ee4ea36SMarcel Holtmann memcpy(csrk->val, rp->csrk, sizeof(csrk->val)); 15127ee4ea36SMarcel Holtmann } 15137ee4ea36SMarcel Holtmann smp->csrk = csrk; 1514d6268e86SJohan Hedberg smp_distribute_keys(smp); 15157ee4ea36SMarcel Holtmann 15167ee4ea36SMarcel Holtmann return 0; 15177ee4ea36SMarcel Holtmann } 15187ee4ea36SMarcel Holtmann 1519d8f8edbeSJohan Hedberg static int smp_cmd_public_key(struct l2cap_conn *conn, struct sk_buff *skb) 1520d8f8edbeSJohan Hedberg { 1521d8f8edbeSJohan Hedberg struct smp_cmd_public_key *key = (void *) skb->data; 1522d8f8edbeSJohan Hedberg struct hci_conn *hcon = conn->hcon; 1523d8f8edbeSJohan Hedberg struct l2cap_chan *chan = conn->smp; 1524d8f8edbeSJohan Hedberg struct smp_chan *smp = chan->data; 1525d8f8edbeSJohan Hedberg int err; 1526d8f8edbeSJohan Hedberg 1527d8f8edbeSJohan Hedberg BT_DBG("conn %p", conn); 1528d8f8edbeSJohan Hedberg 1529d8f8edbeSJohan Hedberg if (skb->len < sizeof(*key)) 1530d8f8edbeSJohan Hedberg return SMP_INVALID_PARAMS; 1531d8f8edbeSJohan Hedberg 1532d8f8edbeSJohan Hedberg memcpy(smp->remote_pk, key, 64); 1533d8f8edbeSJohan Hedberg 1534d8f8edbeSJohan Hedberg /* Non-initiating device sends its public key after receiving 1535d8f8edbeSJohan Hedberg * the key from the initiating device. 1536d8f8edbeSJohan Hedberg */ 1537d8f8edbeSJohan Hedberg if (!hcon->out) { 1538d8f8edbeSJohan Hedberg err = sc_send_public_key(smp); 1539d8f8edbeSJohan Hedberg if (err) 1540d8f8edbeSJohan Hedberg return err; 1541d8f8edbeSJohan Hedberg } 1542d8f8edbeSJohan Hedberg 1543d8f8edbeSJohan Hedberg BT_DBG("Remote Public Key X: %32phN", smp->remote_pk); 1544d8f8edbeSJohan Hedberg BT_DBG("Remote Public Key Y: %32phN", &smp->remote_pk[32]); 1545d8f8edbeSJohan Hedberg 1546d8f8edbeSJohan Hedberg if (!ecdh_shared_secret(smp->remote_pk, smp->local_sk, smp->dhkey)) 1547d8f8edbeSJohan Hedberg return SMP_UNSPECIFIED; 1548d8f8edbeSJohan Hedberg 1549d8f8edbeSJohan Hedberg BT_DBG("DHKey %32phN", smp->dhkey); 1550d8f8edbeSJohan Hedberg 1551d8f8edbeSJohan Hedberg set_bit(SMP_FLAG_REMOTE_PK, &smp->flags); 1552d8f8edbeSJohan Hedberg 1553d8f8edbeSJohan Hedberg return 0; 1554d8f8edbeSJohan Hedberg } 1555d8f8edbeSJohan Hedberg 15564befb867SJohan Hedberg static int smp_sig_channel(struct l2cap_chan *chan, struct sk_buff *skb) 1557eb492e01SAnderson Briglia { 15585d88cc73SJohan Hedberg struct l2cap_conn *conn = chan->conn; 15597b9899dbSMarcel Holtmann struct hci_conn *hcon = conn->hcon; 1560b28b4943SJohan Hedberg struct smp_chan *smp; 156192381f5cSMarcel Holtmann __u8 code, reason; 1562eb492e01SAnderson Briglia int err = 0; 1563eb492e01SAnderson Briglia 15647b9899dbSMarcel Holtmann if (hcon->type != LE_LINK) { 15657b9899dbSMarcel Holtmann kfree_skb(skb); 15663432711fSJohan Hedberg return 0; 15677b9899dbSMarcel Holtmann } 15687b9899dbSMarcel Holtmann 15698ae9b984SJohan Hedberg if (skb->len < 1) 157092381f5cSMarcel Holtmann return -EILSEQ; 157192381f5cSMarcel Holtmann 157206ae3314SMarcel Holtmann if (!test_bit(HCI_LE_ENABLED, &hcon->hdev->dev_flags)) { 15732e65c9d2SAndre Guedes reason = SMP_PAIRING_NOTSUPP; 15742e65c9d2SAndre Guedes goto done; 15752e65c9d2SAndre Guedes } 15762e65c9d2SAndre Guedes 157792381f5cSMarcel Holtmann code = skb->data[0]; 1578eb492e01SAnderson Briglia skb_pull(skb, sizeof(code)); 1579eb492e01SAnderson Briglia 1580b28b4943SJohan Hedberg smp = chan->data; 1581b28b4943SJohan Hedberg 1582b28b4943SJohan Hedberg if (code > SMP_CMD_MAX) 1583b28b4943SJohan Hedberg goto drop; 1584b28b4943SJohan Hedberg 158524bd0bd9SJohan Hedberg if (smp && !test_and_clear_bit(code, &smp->allow_cmd)) 1586b28b4943SJohan Hedberg goto drop; 1587b28b4943SJohan Hedberg 1588b28b4943SJohan Hedberg /* If we don't have a context the only allowed commands are 1589b28b4943SJohan Hedberg * pairing request and security request. 15908cf9fa12SJohan Hedberg */ 1591b28b4943SJohan Hedberg if (!smp && code != SMP_CMD_PAIRING_REQ && code != SMP_CMD_SECURITY_REQ) 1592b28b4943SJohan Hedberg goto drop; 15938cf9fa12SJohan Hedberg 1594eb492e01SAnderson Briglia switch (code) { 1595eb492e01SAnderson Briglia case SMP_CMD_PAIRING_REQ: 1596da85e5e5SVinicius Costa Gomes reason = smp_cmd_pairing_req(conn, skb); 1597eb492e01SAnderson Briglia break; 1598eb492e01SAnderson Briglia 1599eb492e01SAnderson Briglia case SMP_CMD_PAIRING_FAIL: 160084794e11SJohan Hedberg smp_failure(conn, 0); 1601da85e5e5SVinicius Costa Gomes err = -EPERM; 1602eb492e01SAnderson Briglia break; 1603eb492e01SAnderson Briglia 1604eb492e01SAnderson Briglia case SMP_CMD_PAIRING_RSP: 1605da85e5e5SVinicius Costa Gomes reason = smp_cmd_pairing_rsp(conn, skb); 160688ba43b6SAnderson Briglia break; 160788ba43b6SAnderson Briglia 160888ba43b6SAnderson Briglia case SMP_CMD_SECURITY_REQ: 1609da85e5e5SVinicius Costa Gomes reason = smp_cmd_security_req(conn, skb); 161088ba43b6SAnderson Briglia break; 161188ba43b6SAnderson Briglia 1612eb492e01SAnderson Briglia case SMP_CMD_PAIRING_CONFIRM: 1613da85e5e5SVinicius Costa Gomes reason = smp_cmd_pairing_confirm(conn, skb); 161488ba43b6SAnderson Briglia break; 161588ba43b6SAnderson Briglia 1616eb492e01SAnderson Briglia case SMP_CMD_PAIRING_RANDOM: 1617da85e5e5SVinicius Costa Gomes reason = smp_cmd_pairing_random(conn, skb); 161888ba43b6SAnderson Briglia break; 161988ba43b6SAnderson Briglia 1620eb492e01SAnderson Briglia case SMP_CMD_ENCRYPT_INFO: 16217034b911SVinicius Costa Gomes reason = smp_cmd_encrypt_info(conn, skb); 16227034b911SVinicius Costa Gomes break; 16237034b911SVinicius Costa Gomes 1624eb492e01SAnderson Briglia case SMP_CMD_MASTER_IDENT: 16257034b911SVinicius Costa Gomes reason = smp_cmd_master_ident(conn, skb); 16267034b911SVinicius Costa Gomes break; 16277034b911SVinicius Costa Gomes 1628eb492e01SAnderson Briglia case SMP_CMD_IDENT_INFO: 1629fd349c02SJohan Hedberg reason = smp_cmd_ident_info(conn, skb); 1630fd349c02SJohan Hedberg break; 1631fd349c02SJohan Hedberg 1632eb492e01SAnderson Briglia case SMP_CMD_IDENT_ADDR_INFO: 1633fd349c02SJohan Hedberg reason = smp_cmd_ident_addr_info(conn, skb); 1634fd349c02SJohan Hedberg break; 1635fd349c02SJohan Hedberg 1636eb492e01SAnderson Briglia case SMP_CMD_SIGN_INFO: 16377ee4ea36SMarcel Holtmann reason = smp_cmd_sign_info(conn, skb); 16387034b911SVinicius Costa Gomes break; 16397034b911SVinicius Costa Gomes 1640d8f8edbeSJohan Hedberg case SMP_CMD_PUBLIC_KEY: 1641d8f8edbeSJohan Hedberg reason = smp_cmd_public_key(conn, skb); 1642d8f8edbeSJohan Hedberg break; 1643d8f8edbeSJohan Hedberg 1644eb492e01SAnderson Briglia default: 1645eb492e01SAnderson Briglia BT_DBG("Unknown command code 0x%2.2x", code); 1646eb492e01SAnderson Briglia reason = SMP_CMD_NOTSUPP; 16473a0259bbSVinicius Costa Gomes goto done; 16483a0259bbSVinicius Costa Gomes } 16493a0259bbSVinicius Costa Gomes 16503a0259bbSVinicius Costa Gomes done: 16519b7b18efSJohan Hedberg if (!err) { 16523a0259bbSVinicius Costa Gomes if (reason) 165384794e11SJohan Hedberg smp_failure(conn, reason); 1654eb492e01SAnderson Briglia kfree_skb(skb); 16559b7b18efSJohan Hedberg } 16569b7b18efSJohan Hedberg 1657eb492e01SAnderson Briglia return err; 1658b28b4943SJohan Hedberg 1659b28b4943SJohan Hedberg drop: 1660b28b4943SJohan Hedberg BT_ERR("%s unexpected SMP command 0x%02x from %pMR", hcon->hdev->name, 1661b28b4943SJohan Hedberg code, &hcon->dst); 1662b28b4943SJohan Hedberg kfree_skb(skb); 1663b28b4943SJohan Hedberg return 0; 1664eb492e01SAnderson Briglia } 16657034b911SVinicius Costa Gomes 166670db83c4SJohan Hedberg static void smp_teardown_cb(struct l2cap_chan *chan, int err) 166770db83c4SJohan Hedberg { 166870db83c4SJohan Hedberg struct l2cap_conn *conn = chan->conn; 166970db83c4SJohan Hedberg 167070db83c4SJohan Hedberg BT_DBG("chan %p", chan); 167170db83c4SJohan Hedberg 1672fc75cc86SJohan Hedberg if (chan->data) 16735d88cc73SJohan Hedberg smp_chan_destroy(conn); 16745d88cc73SJohan Hedberg 167570db83c4SJohan Hedberg conn->smp = NULL; 167670db83c4SJohan Hedberg l2cap_chan_put(chan); 167770db83c4SJohan Hedberg } 167870db83c4SJohan Hedberg 167944f1a7abSJohan Hedberg static void smp_resume_cb(struct l2cap_chan *chan) 168044f1a7abSJohan Hedberg { 1681b68fda68SJohan Hedberg struct smp_chan *smp = chan->data; 168244f1a7abSJohan Hedberg struct l2cap_conn *conn = chan->conn; 168344f1a7abSJohan Hedberg struct hci_conn *hcon = conn->hcon; 168444f1a7abSJohan Hedberg 168544f1a7abSJohan Hedberg BT_DBG("chan %p", chan); 168644f1a7abSJohan Hedberg 168786d1407cSJohan Hedberg if (!smp) 168886d1407cSJohan Hedberg return; 1689b68fda68SJohan Hedberg 169084bc0db5SJohan Hedberg if (!test_bit(HCI_CONN_ENCRYPT, &hcon->flags)) 169184bc0db5SJohan Hedberg return; 169284bc0db5SJohan Hedberg 1693b68fda68SJohan Hedberg cancel_delayed_work(&smp->security_timer); 169486d1407cSJohan Hedberg 1695d6268e86SJohan Hedberg smp_distribute_keys(smp); 169644f1a7abSJohan Hedberg } 169744f1a7abSJohan Hedberg 169870db83c4SJohan Hedberg static void smp_ready_cb(struct l2cap_chan *chan) 169970db83c4SJohan Hedberg { 170070db83c4SJohan Hedberg struct l2cap_conn *conn = chan->conn; 170170db83c4SJohan Hedberg 170270db83c4SJohan Hedberg BT_DBG("chan %p", chan); 170370db83c4SJohan Hedberg 170470db83c4SJohan Hedberg conn->smp = chan; 170570db83c4SJohan Hedberg l2cap_chan_hold(chan); 170670db83c4SJohan Hedberg } 170770db83c4SJohan Hedberg 17084befb867SJohan Hedberg static int smp_recv_cb(struct l2cap_chan *chan, struct sk_buff *skb) 17094befb867SJohan Hedberg { 17104befb867SJohan Hedberg int err; 17114befb867SJohan Hedberg 17124befb867SJohan Hedberg BT_DBG("chan %p", chan); 17134befb867SJohan Hedberg 17144befb867SJohan Hedberg err = smp_sig_channel(chan, skb); 17154befb867SJohan Hedberg if (err) { 1716b68fda68SJohan Hedberg struct smp_chan *smp = chan->data; 17174befb867SJohan Hedberg 1718b68fda68SJohan Hedberg if (smp) 1719b68fda68SJohan Hedberg cancel_delayed_work_sync(&smp->security_timer); 17204befb867SJohan Hedberg 17211e91c29eSJohan Hedberg hci_disconnect(chan->conn->hcon, HCI_ERROR_AUTH_FAILURE); 17224befb867SJohan Hedberg } 17234befb867SJohan Hedberg 17244befb867SJohan Hedberg return err; 17254befb867SJohan Hedberg } 17264befb867SJohan Hedberg 172770db83c4SJohan Hedberg static struct sk_buff *smp_alloc_skb_cb(struct l2cap_chan *chan, 172870db83c4SJohan Hedberg unsigned long hdr_len, 172970db83c4SJohan Hedberg unsigned long len, int nb) 173070db83c4SJohan Hedberg { 173170db83c4SJohan Hedberg struct sk_buff *skb; 173270db83c4SJohan Hedberg 173370db83c4SJohan Hedberg skb = bt_skb_alloc(hdr_len + len, GFP_KERNEL); 173470db83c4SJohan Hedberg if (!skb) 173570db83c4SJohan Hedberg return ERR_PTR(-ENOMEM); 173670db83c4SJohan Hedberg 173770db83c4SJohan Hedberg skb->priority = HCI_PRIO_MAX; 173870db83c4SJohan Hedberg bt_cb(skb)->chan = chan; 173970db83c4SJohan Hedberg 174070db83c4SJohan Hedberg return skb; 174170db83c4SJohan Hedberg } 174270db83c4SJohan Hedberg 174370db83c4SJohan Hedberg static const struct l2cap_ops smp_chan_ops = { 174470db83c4SJohan Hedberg .name = "Security Manager", 174570db83c4SJohan Hedberg .ready = smp_ready_cb, 17465d88cc73SJohan Hedberg .recv = smp_recv_cb, 174770db83c4SJohan Hedberg .alloc_skb = smp_alloc_skb_cb, 174870db83c4SJohan Hedberg .teardown = smp_teardown_cb, 174944f1a7abSJohan Hedberg .resume = smp_resume_cb, 175070db83c4SJohan Hedberg 175170db83c4SJohan Hedberg .new_connection = l2cap_chan_no_new_connection, 175270db83c4SJohan Hedberg .state_change = l2cap_chan_no_state_change, 175370db83c4SJohan Hedberg .close = l2cap_chan_no_close, 175470db83c4SJohan Hedberg .defer = l2cap_chan_no_defer, 175570db83c4SJohan Hedberg .suspend = l2cap_chan_no_suspend, 175670db83c4SJohan Hedberg .set_shutdown = l2cap_chan_no_set_shutdown, 175770db83c4SJohan Hedberg .get_sndtimeo = l2cap_chan_no_get_sndtimeo, 175870db83c4SJohan Hedberg .memcpy_fromiovec = l2cap_chan_no_memcpy_fromiovec, 175970db83c4SJohan Hedberg }; 176070db83c4SJohan Hedberg 176170db83c4SJohan Hedberg static inline struct l2cap_chan *smp_new_conn_cb(struct l2cap_chan *pchan) 176270db83c4SJohan Hedberg { 176370db83c4SJohan Hedberg struct l2cap_chan *chan; 176470db83c4SJohan Hedberg 176570db83c4SJohan Hedberg BT_DBG("pchan %p", pchan); 176670db83c4SJohan Hedberg 176770db83c4SJohan Hedberg chan = l2cap_chan_create(); 176870db83c4SJohan Hedberg if (!chan) 176970db83c4SJohan Hedberg return NULL; 177070db83c4SJohan Hedberg 177170db83c4SJohan Hedberg chan->chan_type = pchan->chan_type; 177270db83c4SJohan Hedberg chan->ops = &smp_chan_ops; 177370db83c4SJohan Hedberg chan->scid = pchan->scid; 177470db83c4SJohan Hedberg chan->dcid = chan->scid; 177570db83c4SJohan Hedberg chan->imtu = pchan->imtu; 177670db83c4SJohan Hedberg chan->omtu = pchan->omtu; 177770db83c4SJohan Hedberg chan->mode = pchan->mode; 177870db83c4SJohan Hedberg 1779abe84903SJohan Hedberg /* Other L2CAP channels may request SMP routines in order to 1780abe84903SJohan Hedberg * change the security level. This means that the SMP channel 1781abe84903SJohan Hedberg * lock must be considered in its own category to avoid lockdep 1782abe84903SJohan Hedberg * warnings. 1783abe84903SJohan Hedberg */ 1784abe84903SJohan Hedberg atomic_set(&chan->nesting, L2CAP_NESTING_SMP); 1785abe84903SJohan Hedberg 178670db83c4SJohan Hedberg BT_DBG("created chan %p", chan); 178770db83c4SJohan Hedberg 178870db83c4SJohan Hedberg return chan; 178970db83c4SJohan Hedberg } 179070db83c4SJohan Hedberg 179170db83c4SJohan Hedberg static const struct l2cap_ops smp_root_chan_ops = { 179270db83c4SJohan Hedberg .name = "Security Manager Root", 179370db83c4SJohan Hedberg .new_connection = smp_new_conn_cb, 179470db83c4SJohan Hedberg 179570db83c4SJohan Hedberg /* None of these are implemented for the root channel */ 179670db83c4SJohan Hedberg .close = l2cap_chan_no_close, 179770db83c4SJohan Hedberg .alloc_skb = l2cap_chan_no_alloc_skb, 179870db83c4SJohan Hedberg .recv = l2cap_chan_no_recv, 179970db83c4SJohan Hedberg .state_change = l2cap_chan_no_state_change, 180070db83c4SJohan Hedberg .teardown = l2cap_chan_no_teardown, 180170db83c4SJohan Hedberg .ready = l2cap_chan_no_ready, 180270db83c4SJohan Hedberg .defer = l2cap_chan_no_defer, 180370db83c4SJohan Hedberg .suspend = l2cap_chan_no_suspend, 180470db83c4SJohan Hedberg .resume = l2cap_chan_no_resume, 180570db83c4SJohan Hedberg .set_shutdown = l2cap_chan_no_set_shutdown, 180670db83c4SJohan Hedberg .get_sndtimeo = l2cap_chan_no_get_sndtimeo, 180770db83c4SJohan Hedberg .memcpy_fromiovec = l2cap_chan_no_memcpy_fromiovec, 180870db83c4SJohan Hedberg }; 180970db83c4SJohan Hedberg 1810711eafe3SJohan Hedberg int smp_register(struct hci_dev *hdev) 1811711eafe3SJohan Hedberg { 181270db83c4SJohan Hedberg struct l2cap_chan *chan; 1813defce9e8SJohan Hedberg struct crypto_blkcipher *tfm_aes; 181470db83c4SJohan Hedberg 1815711eafe3SJohan Hedberg BT_DBG("%s", hdev->name); 1816711eafe3SJohan Hedberg 1817adae20cbSJohan Hedberg tfm_aes = crypto_alloc_blkcipher("ecb(aes)", 0, 0); 1818defce9e8SJohan Hedberg if (IS_ERR(tfm_aes)) { 1819defce9e8SJohan Hedberg int err = PTR_ERR(tfm_aes); 1820711eafe3SJohan Hedberg BT_ERR("Unable to create crypto context"); 1821711eafe3SJohan Hedberg return err; 1822711eafe3SJohan Hedberg } 1823711eafe3SJohan Hedberg 182470db83c4SJohan Hedberg chan = l2cap_chan_create(); 182570db83c4SJohan Hedberg if (!chan) { 1826defce9e8SJohan Hedberg crypto_free_blkcipher(tfm_aes); 182770db83c4SJohan Hedberg return -ENOMEM; 182870db83c4SJohan Hedberg } 182970db83c4SJohan Hedberg 1830defce9e8SJohan Hedberg chan->data = tfm_aes; 1831defce9e8SJohan Hedberg 18325d88cc73SJohan Hedberg l2cap_add_scid(chan, L2CAP_CID_SMP); 183370db83c4SJohan Hedberg 183470db83c4SJohan Hedberg l2cap_chan_set_defaults(chan); 183570db83c4SJohan Hedberg 183670db83c4SJohan Hedberg bacpy(&chan->src, &hdev->bdaddr); 183770db83c4SJohan Hedberg chan->src_type = BDADDR_LE_PUBLIC; 183870db83c4SJohan Hedberg chan->state = BT_LISTEN; 183970db83c4SJohan Hedberg chan->mode = L2CAP_MODE_BASIC; 184070db83c4SJohan Hedberg chan->imtu = L2CAP_DEFAULT_MTU; 184170db83c4SJohan Hedberg chan->ops = &smp_root_chan_ops; 184270db83c4SJohan Hedberg 1843abe84903SJohan Hedberg /* Set correct nesting level for a parent/listening channel */ 1844abe84903SJohan Hedberg atomic_set(&chan->nesting, L2CAP_NESTING_PARENT); 1845abe84903SJohan Hedberg 184670db83c4SJohan Hedberg hdev->smp_data = chan; 184770db83c4SJohan Hedberg 1848711eafe3SJohan Hedberg return 0; 1849711eafe3SJohan Hedberg } 1850711eafe3SJohan Hedberg 1851711eafe3SJohan Hedberg void smp_unregister(struct hci_dev *hdev) 1852711eafe3SJohan Hedberg { 185370db83c4SJohan Hedberg struct l2cap_chan *chan = hdev->smp_data; 1854defce9e8SJohan Hedberg struct crypto_blkcipher *tfm_aes; 185570db83c4SJohan Hedberg 185670db83c4SJohan Hedberg if (!chan) 185770db83c4SJohan Hedberg return; 185870db83c4SJohan Hedberg 185970db83c4SJohan Hedberg BT_DBG("%s chan %p", hdev->name, chan); 1860711eafe3SJohan Hedberg 1861defce9e8SJohan Hedberg tfm_aes = chan->data; 1862defce9e8SJohan Hedberg if (tfm_aes) { 1863defce9e8SJohan Hedberg chan->data = NULL; 1864defce9e8SJohan Hedberg crypto_free_blkcipher(tfm_aes); 1865711eafe3SJohan Hedberg } 186670db83c4SJohan Hedberg 186770db83c4SJohan Hedberg hdev->smp_data = NULL; 186870db83c4SJohan Hedberg l2cap_chan_put(chan); 1869711eafe3SJohan Hedberg } 1870