aboutsummaryrefslogtreecommitdiffstats
path: root/net
diff options
context:
space:
mode:
authorJohan Hedberg <johan.hedberg@intel.com>2014-06-17 06:07:37 -0400
committerMarcel Holtmann <marcel@holtmann.org>2014-06-20 07:53:38 -0400
commitc7262e711ae6e466baeb9ddc21d678c878469b1f (patch)
treecee6f759689de12132f84a4bc5ca05359a6f6ba7 /net
parenta2b23bacb315d3873ed90029fd2b68c95de734c0 (diff)
Bluetooth: Fix overriding higher security level in SMP
When we receive a pairing request or an internal request to start pairing we shouldn't blindly overwrite the existing pending_sec_level value as that may actually be higher than the new one. This patch fixes the SMP code to only overwrite the value in case the new one is higher than the old. Signed-off-by: Johan Hedberg <johan.hedberg@intel.com> Signed-off-by: Marcel Holtmann <marcel@holtmann.org>
Diffstat (limited to 'net')
-rw-r--r--net/bluetooth/smp.c23
1 files changed, 14 insertions, 9 deletions
diff --git a/net/bluetooth/smp.c b/net/bluetooth/smp.c
index f2829a7932e2..0189ec8b68d1 100644
--- a/net/bluetooth/smp.c
+++ b/net/bluetooth/smp.c
@@ -669,7 +669,7 @@ static u8 smp_cmd_pairing_req(struct l2cap_conn *conn, struct sk_buff *skb)
669{ 669{
670 struct smp_cmd_pairing rsp, *req = (void *) skb->data; 670 struct smp_cmd_pairing rsp, *req = (void *) skb->data;
671 struct smp_chan *smp; 671 struct smp_chan *smp;
672 u8 key_size, auth; 672 u8 key_size, auth, sec_level;
673 int ret; 673 int ret;
674 674
675 BT_DBG("conn %p", conn); 675 BT_DBG("conn %p", conn);
@@ -695,7 +695,9 @@ static u8 smp_cmd_pairing_req(struct l2cap_conn *conn, struct sk_buff *skb)
695 /* We didn't start the pairing, so match remote */ 695 /* We didn't start the pairing, so match remote */
696 auth = req->auth_req; 696 auth = req->auth_req;
697 697
698 conn->hcon->pending_sec_level = authreq_to_seclevel(auth); 698 sec_level = authreq_to_seclevel(auth);
699 if (sec_level > conn->hcon->pending_sec_level)
700 conn->hcon->pending_sec_level = sec_level;
699 701
700 build_pairing_cmd(conn, req, &rsp, auth); 702 build_pairing_cmd(conn, req, &rsp, auth);
701 703
@@ -838,6 +840,7 @@ static u8 smp_cmd_security_req(struct l2cap_conn *conn, struct sk_buff *skb)
838 struct smp_cmd_pairing cp; 840 struct smp_cmd_pairing cp;
839 struct hci_conn *hcon = conn->hcon; 841 struct hci_conn *hcon = conn->hcon;
840 struct smp_chan *smp; 842 struct smp_chan *smp;
843 u8 sec_level;
841 844
842 BT_DBG("conn %p", conn); 845 BT_DBG("conn %p", conn);
843 846
@@ -847,7 +850,9 @@ static u8 smp_cmd_security_req(struct l2cap_conn *conn, struct sk_buff *skb)
847 if (!(conn->hcon->link_mode & HCI_LM_MASTER)) 850 if (!(conn->hcon->link_mode & HCI_LM_MASTER))
848 return SMP_CMD_NOTSUPP; 851 return SMP_CMD_NOTSUPP;
849 852
850 hcon->pending_sec_level = authreq_to_seclevel(rp->auth_req); 853 sec_level = authreq_to_seclevel(rp->auth_req);
854 if (sec_level > hcon->pending_sec_level)
855 hcon->pending_sec_level = sec_level;
851 856
852 if (smp_ltk_encrypt(conn, hcon->pending_sec_level)) 857 if (smp_ltk_encrypt(conn, hcon->pending_sec_level))
853 return 0; 858 return 0;
@@ -901,9 +906,12 @@ int smp_conn_security(struct hci_conn *hcon, __u8 sec_level)
901 if (smp_sufficient_security(hcon, sec_level)) 906 if (smp_sufficient_security(hcon, sec_level))
902 return 1; 907 return 1;
903 908
909 if (sec_level > hcon->pending_sec_level)
910 hcon->pending_sec_level = sec_level;
911
904 if (hcon->link_mode & HCI_LM_MASTER) 912 if (hcon->link_mode & HCI_LM_MASTER)
905 if (smp_ltk_encrypt(conn, sec_level)) 913 if (smp_ltk_encrypt(conn, hcon->pending_sec_level))
906 goto done; 914 return 0;
907 915
908 if (test_and_set_bit(HCI_CONN_LE_SMP_PEND, &hcon->flags)) 916 if (test_and_set_bit(HCI_CONN_LE_SMP_PEND, &hcon->flags))
909 return 0; 917 return 0;
@@ -918,7 +926,7 @@ int smp_conn_security(struct hci_conn *hcon, __u8 sec_level)
918 * requires it. 926 * requires it.
919 */ 927 */
920 if (hcon->io_capability != HCI_IO_NO_INPUT_OUTPUT || 928 if (hcon->io_capability != HCI_IO_NO_INPUT_OUTPUT ||
921 sec_level > BT_SECURITY_MEDIUM) 929 hcon->pending_sec_level > BT_SECURITY_MEDIUM)
922 authreq |= SMP_AUTH_MITM; 930 authreq |= SMP_AUTH_MITM;
923 931
924 if (hcon->link_mode & HCI_LM_MASTER) { 932 if (hcon->link_mode & HCI_LM_MASTER) {
@@ -937,9 +945,6 @@ int smp_conn_security(struct hci_conn *hcon, __u8 sec_level)
937 945
938 set_bit(SMP_FLAG_INITIATOR, &smp->flags); 946 set_bit(SMP_FLAG_INITIATOR, &smp->flags);
939 947
940done:
941 hcon->pending_sec_level = sec_level;
942
943 return 0; 948 return 0;
944} 949}
945 950