diff options
Diffstat (limited to 'net/bluetooth/smp.c')
-rw-r--r-- | net/bluetooth/smp.c | 29 |
1 files changed, 25 insertions, 4 deletions
diff --git a/net/bluetooth/smp.c b/net/bluetooth/smp.c index 3a7b0773536b..73f7211d0431 100644 --- a/net/bluetooth/smp.c +++ b/net/bluetooth/smp.c | |||
@@ -2422,30 +2422,51 @@ unlock: | |||
2422 | return ret; | 2422 | return ret; |
2423 | } | 2423 | } |
2424 | 2424 | ||
2425 | void smp_cancel_pairing(struct hci_conn *hcon) | 2425 | int smp_cancel_and_remove_pairing(struct hci_dev *hdev, bdaddr_t *bdaddr, |
2426 | u8 addr_type) | ||
2426 | { | 2427 | { |
2427 | struct l2cap_conn *conn = hcon->l2cap_data; | 2428 | struct hci_conn *hcon; |
2429 | struct l2cap_conn *conn; | ||
2428 | struct l2cap_chan *chan; | 2430 | struct l2cap_chan *chan; |
2429 | struct smp_chan *smp; | 2431 | struct smp_chan *smp; |
2432 | int err; | ||
2433 | |||
2434 | err = hci_remove_ltk(hdev, bdaddr, addr_type); | ||
2435 | hci_remove_irk(hdev, bdaddr, addr_type); | ||
2436 | |||
2437 | hcon = hci_conn_hash_lookup_le(hdev, bdaddr, addr_type); | ||
2438 | if (!hcon) | ||
2439 | goto done; | ||
2430 | 2440 | ||
2441 | conn = hcon->l2cap_data; | ||
2431 | if (!conn) | 2442 | if (!conn) |
2432 | return; | 2443 | goto done; |
2433 | 2444 | ||
2434 | chan = conn->smp; | 2445 | chan = conn->smp; |
2435 | if (!chan) | 2446 | if (!chan) |
2436 | return; | 2447 | goto done; |
2437 | 2448 | ||
2438 | l2cap_chan_lock(chan); | 2449 | l2cap_chan_lock(chan); |
2439 | 2450 | ||
2440 | smp = chan->data; | 2451 | smp = chan->data; |
2441 | if (smp) { | 2452 | if (smp) { |
2453 | /* Set keys to NULL to make sure smp_failure() does not try to | ||
2454 | * remove and free already invalidated rcu list entries. */ | ||
2455 | smp->ltk = NULL; | ||
2456 | smp->slave_ltk = NULL; | ||
2457 | smp->remote_irk = NULL; | ||
2458 | |||
2442 | if (test_bit(SMP_FLAG_COMPLETE, &smp->flags)) | 2459 | if (test_bit(SMP_FLAG_COMPLETE, &smp->flags)) |
2443 | smp_failure(conn, 0); | 2460 | smp_failure(conn, 0); |
2444 | else | 2461 | else |
2445 | smp_failure(conn, SMP_UNSPECIFIED); | 2462 | smp_failure(conn, SMP_UNSPECIFIED); |
2463 | err = 0; | ||
2446 | } | 2464 | } |
2447 | 2465 | ||
2448 | l2cap_chan_unlock(chan); | 2466 | l2cap_chan_unlock(chan); |
2467 | |||
2468 | done: | ||
2469 | return err; | ||
2449 | } | 2470 | } |
2450 | 2471 | ||
2451 | static int smp_cmd_encrypt_info(struct l2cap_conn *conn, struct sk_buff *skb) | 2472 | static int smp_cmd_encrypt_info(struct l2cap_conn *conn, struct sk_buff *skb) |