Bluetooth: Add support for resuming socket when SMP is finished

This adds support for resuming the user space traffic when SMP
negotiation is complete.

Signed-off-by: Vinicius Costa Gomes <vinicius.gomes@openbossa.org>
Signed-off-by: Gustavo F. Padovan <padovan@profusion.mobi>
This commit is contained in:
Vinicius Costa Gomes
2011-01-26 21:42:57 -03:00
committed by Gustavo F. Padovan
parent 9b3d67405b
commit f1cb9af557
3 changed files with 76 additions and 43 deletions

View File

@@ -336,9 +336,13 @@ static void smp_cmd_security_req(struct l2cap_conn *conn, struct sk_buff *skb)
{
struct smp_cmd_security_req *rp = (void *) skb->data;
struct smp_cmd_pairing cp;
struct hci_conn *hcon = conn->hcon;
BT_DBG("conn %p", conn);
if (test_bit(HCI_CONN_ENCRYPT_PEND, &hcon->pend))
return;
skb_pull(skb, sizeof(*rp));
memset(&cp, 0, sizeof(cp));
@@ -353,6 +357,20 @@ static void smp_cmd_security_req(struct l2cap_conn *conn, struct sk_buff *skb)
memcpy(&conn->preq[1], &cp, sizeof(cp));
smp_send_cmd(conn, SMP_CMD_PAIRING_REQ, sizeof(cp), &cp);
set_bit(HCI_CONN_ENCRYPT_PEND, &hcon->pend);
}
static __u8 seclevel_to_authreq(__u8 level)
{
switch (level) {
case BT_SECURITY_HIGH:
/* For now we don't support bonding */
return SMP_AUTH_MITM;
default:
return SMP_AUTH_NONE;
}
}
int smp_conn_security(struct l2cap_conn *conn, __u8 sec_level)
@@ -365,21 +383,16 @@ int smp_conn_security(struct l2cap_conn *conn, __u8 sec_level)
if (IS_ERR(hcon->hdev->tfm))
return 1;
switch (sec_level) {
case BT_SECURITY_MEDIUM:
/* Encrypted, no MITM protection */
authreq = HCI_AT_NO_BONDING_MITM;
break;
if (test_bit(HCI_CONN_ENCRYPT_PEND, &hcon->pend))
return 0;
case BT_SECURITY_HIGH:
/* Bonding, MITM protection */
authreq = HCI_AT_GENERAL_BONDING_MITM;
break;
case BT_SECURITY_LOW:
default:
if (sec_level == BT_SECURITY_LOW)
return 1;
}
if (hcon->sec_level >= sec_level)
return 1;
authreq = seclevel_to_authreq(sec_level);
if (hcon->link_mode & HCI_LM_MASTER) {
struct smp_cmd_pairing cp;
@@ -400,6 +413,9 @@ int smp_conn_security(struct l2cap_conn *conn, __u8 sec_level)
smp_send_cmd(conn, SMP_CMD_SECURITY_REQ, sizeof(cp), &cp);
}
hcon->pending_sec_level = sec_level;
set_bit(HCI_CONN_ENCRYPT_PEND, &hcon->pend);
return 0;
}