aboutsummaryrefslogtreecommitdiffstats
path: root/net/bluetooth/l2cap.c
diff options
context:
space:
mode:
authorMarcel Holtmann <marcel@holtmann.org>2009-01-15 15:58:04 -0500
committerMarcel Holtmann <marcel@holtmann.org>2009-02-27 00:14:25 -0500
commit8c1b235594fbab9a13240a1dac12ea9fd99b6440 (patch)
treeeb137a23e0fd8199144a4c3e36902af411e44269 /net/bluetooth/l2cap.c
parentc89b6e6bda4c8021195778f47567d0cc9dbfe7ec (diff)
Bluetooth: Add enhanced security model for Simple Pairing
The current security model is based around the flags AUTH, ENCRYPT and SECURE. Starting with support for the Bluetooth 2.1 specification this is no longer sufficient. The different security levels are now defined as SDP, LOW, MEDIUM and SECURE. Previously it was possible to set each security independently, but this actually doesn't make a lot of sense. For Bluetooth the encryption depends on a previous successful authentication. Also you can only update your existing link key if you successfully created at least one before. And of course the update of link keys without having proper encryption in place is a security issue. The new security levels from the Bluetooth 2.1 specification are now used internally. All old settings are mapped to the new values and this way it ensures that old applications still work. The only limitation is that it is no longer possible to set authentication without also enabling encryption. No application should have done this anyway since this is actually a security issue. Without encryption the integrity of the authentication can't be guaranteed. As default for a new L2CAP or RFCOMM connection, the LOW security level is used. The only exception here are the service discovery sessions on PSM 1 where SDP level is used. To have similar security strength as with a Bluetooth 2.0 and before combination key, the MEDIUM level should be used. This is according to the Bluetooth specification. The MEDIUM level will not require any kind of man-in-the-middle (MITM) protection. Only the HIGH security level will require this. Signed-off-by: Marcel Holtmann <marcel@holtmann.org>
Diffstat (limited to 'net/bluetooth/l2cap.c')
-rw-r--r--net/bluetooth/l2cap.c134
1 files changed, 40 insertions, 94 deletions
diff --git a/net/bluetooth/l2cap.c b/net/bluetooth/l2cap.c
index 123efb46d3f5..eadf09231866 100644
--- a/net/bluetooth/l2cap.c
+++ b/net/bluetooth/l2cap.c
@@ -263,12 +263,17 @@ static inline int l2cap_check_link_mode(struct sock *sk)
263{ 263{
264 struct l2cap_conn *conn = l2cap_pi(sk)->conn; 264 struct l2cap_conn *conn = l2cap_pi(sk)->conn;
265 265
266 if ((l2cap_pi(sk)->link_mode & L2CAP_LM_ENCRYPT) || 266 if (l2cap_pi(sk)->link_mode & L2CAP_LM_SECURE)
267 (l2cap_pi(sk)->link_mode & L2CAP_LM_SECURE)) 267 return hci_conn_security(conn->hcon, BT_SECURITY_HIGH);
268 return hci_conn_encrypt(conn->hcon); 268
269 if (l2cap_pi(sk)->link_mode & L2CAP_LM_ENCRYPT)
270 return hci_conn_security(conn->hcon, BT_SECURITY_MEDIUM);
269 271
270 if (l2cap_pi(sk)->link_mode & L2CAP_LM_AUTH) 272 if (l2cap_pi(sk)->link_mode & L2CAP_LM_AUTH)
271 return hci_conn_auth(conn->hcon); 273 return hci_conn_security(conn->hcon, BT_SECURITY_LOW);
274
275 if (l2cap_pi(sk)->psm == cpu_to_le16(0x0001))
276 return hci_conn_security(conn->hcon, BT_SECURITY_SDP);
272 277
273 return 1; 278 return 1;
274} 279}
@@ -803,6 +808,7 @@ static int l2cap_do_connect(struct sock *sk)
803 struct l2cap_conn *conn; 808 struct l2cap_conn *conn;
804 struct hci_conn *hcon; 809 struct hci_conn *hcon;
805 struct hci_dev *hdev; 810 struct hci_dev *hdev;
811 __u8 sec_level;
806 __u8 auth_type; 812 __u8 auth_type;
807 int err = 0; 813 int err = 0;
808 814
@@ -815,21 +821,37 @@ static int l2cap_do_connect(struct sock *sk)
815 821
816 err = -ENOMEM; 822 err = -ENOMEM;
817 823
818 if (l2cap_pi(sk)->link_mode & L2CAP_LM_AUTH || 824 if (l2cap_pi(sk)->link_mode & L2CAP_LM_SECURE)
819 l2cap_pi(sk)->link_mode & L2CAP_LM_ENCRYPT || 825 sec_level = BT_SECURITY_HIGH;
820 l2cap_pi(sk)->link_mode & L2CAP_LM_SECURE) { 826 else if (l2cap_pi(sk)->psm == cpu_to_le16(0x0001))
821 if (l2cap_pi(sk)->psm == cpu_to_le16(0x0001)) 827 sec_level = BT_SECURITY_SDP;
822 auth_type = HCI_AT_NO_BONDING_MITM; 828 else if (l2cap_pi(sk)->link_mode & L2CAP_LM_ENCRYPT)
829 sec_level = BT_SECURITY_MEDIUM;
830 else
831 sec_level = BT_SECURITY_LOW;
832
833 if (sk->sk_type == SOCK_RAW) {
834 if (l2cap_pi(sk)->link_mode & L2CAP_LM_SECURE)
835 auth_type = HCI_AT_DEDICATED_BONDING_MITM;
836 else if (l2cap_pi(sk)->link_mode & L2CAP_LM_ENCRYPT)
837 auth_type = HCI_AT_DEDICATED_BONDING;
823 else 838 else
824 auth_type = HCI_AT_GENERAL_BONDING_MITM;
825 } else {
826 if (l2cap_pi(sk)->psm == cpu_to_le16(0x0001))
827 auth_type = HCI_AT_NO_BONDING; 839 auth_type = HCI_AT_NO_BONDING;
840 } else if (l2cap_pi(sk)->psm == cpu_to_le16(0x0001)) {
841 if (l2cap_pi(sk)->link_mode & L2CAP_LM_SECURE)
842 auth_type = HCI_AT_NO_BONDING_MITM;
828 else 843 else
844 auth_type = HCI_AT_NO_BONDING;
845 } else {
846 if (l2cap_pi(sk)->link_mode & L2CAP_LM_SECURE)
847 auth_type = HCI_AT_GENERAL_BONDING_MITM;
848 else if (l2cap_pi(sk)->link_mode & L2CAP_LM_ENCRYPT)
829 auth_type = HCI_AT_GENERAL_BONDING; 849 auth_type = HCI_AT_GENERAL_BONDING;
850 else
851 auth_type = HCI_AT_NO_BONDING;
830 } 852 }
831 853
832 hcon = hci_connect(hdev, ACL_LINK, dst, auth_type); 854 hcon = hci_connect(hdev, ACL_LINK, dst, sec_level, auth_type);
833 if (!hcon) 855 if (!hcon)
834 goto done; 856 goto done;
835 857
@@ -1402,11 +1424,6 @@ static void l2cap_chan_ready(struct sock *sk)
1402 */ 1424 */
1403 parent->sk_data_ready(parent, 0); 1425 parent->sk_data_ready(parent, 0);
1404 } 1426 }
1405
1406 if (l2cap_pi(sk)->link_mode & L2CAP_LM_SECURE) {
1407 struct l2cap_conn *conn = l2cap_pi(sk)->conn;
1408 hci_conn_change_link_key(conn->hcon);
1409 }
1410} 1427}
1411 1428
1412/* Copy frame to all raw sockets on that connection */ 1429/* Copy frame to all raw sockets on that connection */
@@ -2323,77 +2340,7 @@ static int l2cap_disconn_ind(struct hci_conn *hcon, u8 reason)
2323 return 0; 2340 return 0;
2324} 2341}
2325 2342
2326static int l2cap_auth_cfm(struct hci_conn *hcon, u8 status) 2343static int l2cap_security_cfm(struct hci_conn *hcon, u8 status, u8 encrypt)
2327{
2328 struct l2cap_chan_list *l;
2329 struct l2cap_conn *conn = hcon->l2cap_data;
2330 struct sock *sk;
2331
2332 if (!conn)
2333 return 0;
2334
2335 l = &conn->chan_list;
2336
2337 BT_DBG("conn %p", conn);
2338
2339 read_lock(&l->lock);
2340
2341 for (sk = l->head; sk; sk = l2cap_pi(sk)->next_c) {
2342 struct l2cap_pinfo *pi = l2cap_pi(sk);
2343
2344 bh_lock_sock(sk);
2345
2346 if ((pi->link_mode & (L2CAP_LM_ENCRYPT | L2CAP_LM_SECURE)) &&
2347 !(hcon->link_mode & HCI_LM_ENCRYPT) &&
2348 !status) {
2349 bh_unlock_sock(sk);
2350 continue;
2351 }
2352
2353 if (sk->sk_state == BT_CONNECT) {
2354 if (!status) {
2355 struct l2cap_conn_req req;
2356 req.scid = cpu_to_le16(l2cap_pi(sk)->scid);
2357 req.psm = l2cap_pi(sk)->psm;
2358
2359 l2cap_pi(sk)->ident = l2cap_get_ident(conn);
2360
2361 l2cap_send_cmd(conn, l2cap_pi(sk)->ident,
2362 L2CAP_CONN_REQ, sizeof(req), &req);
2363 } else {
2364 l2cap_sock_clear_timer(sk);
2365 l2cap_sock_set_timer(sk, HZ / 10);
2366 }
2367 } else if (sk->sk_state == BT_CONNECT2) {
2368 struct l2cap_conn_rsp rsp;
2369 __u16 result;
2370
2371 if (!status) {
2372 sk->sk_state = BT_CONFIG;
2373 result = L2CAP_CR_SUCCESS;
2374 } else {
2375 sk->sk_state = BT_DISCONN;
2376 l2cap_sock_set_timer(sk, HZ / 10);
2377 result = L2CAP_CR_SEC_BLOCK;
2378 }
2379
2380 rsp.scid = cpu_to_le16(l2cap_pi(sk)->dcid);
2381 rsp.dcid = cpu_to_le16(l2cap_pi(sk)->scid);
2382 rsp.result = cpu_to_le16(result);
2383 rsp.status = cpu_to_le16(L2CAP_CS_NO_INFO);
2384 l2cap_send_cmd(conn, l2cap_pi(sk)->ident,
2385 L2CAP_CONN_RSP, sizeof(rsp), &rsp);
2386 }
2387
2388 bh_unlock_sock(sk);
2389 }
2390
2391 read_unlock(&l->lock);
2392
2393 return 0;
2394}
2395
2396static int l2cap_encrypt_cfm(struct hci_conn *hcon, u8 status, u8 encrypt)
2397{ 2344{
2398 struct l2cap_chan_list *l; 2345 struct l2cap_chan_list *l;
2399 struct l2cap_conn *conn = hcon->l2cap_data; 2346 struct l2cap_conn *conn = hcon->l2cap_data;
@@ -2413,10 +2360,10 @@ static int l2cap_encrypt_cfm(struct hci_conn *hcon, u8 status, u8 encrypt)
2413 2360
2414 bh_lock_sock(sk); 2361 bh_lock_sock(sk);
2415 2362
2416 if ((pi->link_mode & (L2CAP_LM_ENCRYPT | L2CAP_LM_SECURE)) && 2363 if (!status && encrypt == 0x00 &&
2364 (pi->link_mode & L2CAP_LM_SECURE) &&
2417 (sk->sk_state == BT_CONNECTED || 2365 (sk->sk_state == BT_CONNECTED ||
2418 sk->sk_state == BT_CONFIG) && 2366 sk->sk_state == BT_CONFIG)) {
2419 !status && encrypt == 0x00) {
2420 __l2cap_sock_close(sk, ECONNREFUSED); 2367 __l2cap_sock_close(sk, ECONNREFUSED);
2421 bh_unlock_sock(sk); 2368 bh_unlock_sock(sk);
2422 continue; 2369 continue;
@@ -2608,8 +2555,7 @@ static struct hci_proto l2cap_hci_proto = {
2608 .connect_ind = l2cap_connect_ind, 2555 .connect_ind = l2cap_connect_ind,
2609 .connect_cfm = l2cap_connect_cfm, 2556 .connect_cfm = l2cap_connect_cfm,
2610 .disconn_ind = l2cap_disconn_ind, 2557 .disconn_ind = l2cap_disconn_ind,
2611 .auth_cfm = l2cap_auth_cfm, 2558 .security_cfm = l2cap_security_cfm,
2612 .encrypt_cfm = l2cap_encrypt_cfm,
2613 .recv_acldata = l2cap_recv_acldata 2559 .recv_acldata = l2cap_recv_acldata
2614}; 2560};
2615 2561