patch-2.4.21 linux-2.4.21/net/bluetooth/l2cap.c
Next file: linux-2.4.21/net/bluetooth/rfcomm/Config.in
Previous file: linux-2.4.21/net/bluetooth/hci_sock.c
Back to the patch index
Back to the overall index
- Lines: 173
- Date:
2003-06-13 07:51:39.000000000 -0700
- Orig file:
linux-2.4.20/net/bluetooth/l2cap.c
- Orig date:
2002-11-28 15:53:15.000000000 -0800
diff -urN linux-2.4.20/net/bluetooth/l2cap.c linux-2.4.21/net/bluetooth/l2cap.c
@@ -178,69 +178,12 @@
return 0;
}
-int l2cap_connect(struct sock *sk)
-{
- bdaddr_t *src = &bluez_pi(sk)->src;
- bdaddr_t *dst = &bluez_pi(sk)->dst;
- struct l2cap_conn *conn;
- struct hci_conn *hcon;
- struct hci_dev *hdev;
- int err = 0;
-
- BT_DBG("%s -> %s psm 0x%2.2x", batostr(src), batostr(dst), l2cap_pi(sk)->psm);
-
- if (!(hdev = hci_get_route(dst, src)))
- return -EHOSTUNREACH;
-
- hci_dev_lock_bh(hdev);
-
- err = -ENOMEM;
-
- hcon = hci_connect(hdev, ACL_LINK, dst);
- if (!hcon)
- goto done;
-
- conn = l2cap_conn_add(hcon, 0);
- if (!conn) {
- hci_conn_put(hcon);
- goto done;
- }
-
- err = 0;
-
- /* Update source addr of the socket */
- bacpy(src, conn->src);
-
- l2cap_chan_add(conn, sk, NULL);
-
- sk->state = BT_CONNECT;
- l2cap_sock_set_timer(sk, sk->sndtimeo);
-
- if (hcon->state == BT_CONNECTED) {
- if (sk->type == SOCK_SEQPACKET) {
- l2cap_conn_req req;
- req.scid = __cpu_to_le16(l2cap_pi(sk)->scid);
- req.psm = l2cap_pi(sk)->psm;
- l2cap_send_req(conn, L2CAP_CONN_REQ, L2CAP_CONN_REQ_SIZE, &req);
- } else {
- l2cap_sock_clear_timer(sk);
- sk->state = BT_CONNECTED;
- }
- }
-
-done:
- hci_dev_unlock_bh(hdev);
- hci_dev_put(hdev);
- return err;
-}
-
/* -------- Socket interface ---------- */
static struct sock *__l2cap_get_sock_by_addr(__u16 psm, bdaddr_t *src)
{
struct sock *sk;
for (sk = l2cap_sk_list.head; sk; sk = sk->next) {
- if (l2cap_pi(sk)->psm == psm &&
- !bacmp(&bluez_pi(sk)->src, src))
+ if (sk->sport == psm && !bacmp(&bluez_pi(sk)->src, src))
break;
}
return sk;
@@ -432,6 +375,9 @@
if (sock->type != SOCK_SEQPACKET && sock->type != SOCK_DGRAM && sock->type != SOCK_RAW)
return -ESOCKTNOSUPPORT;
+ if (sock->type == SOCK_RAW && !capable(CAP_NET_RAW))
+ return -EPERM;
+
sock->ops = &l2cap_sock_ops;
if (!(sk = l2cap_sock_alloc(sock, protocol, GFP_KERNEL)))
@@ -466,9 +412,9 @@
/* Save source address */
bacpy(&bluez_pi(sk)->src, &la->l2_bdaddr);
l2cap_pi(sk)->psm = la->l2_psm;
+ sk->sport = la->l2_psm;
sk->state = BT_BOUND;
}
-
write_unlock_bh(&l2cap_sk_list.lock);
done:
@@ -476,6 +422,62 @@
return err;
}
+static int l2cap_do_connect(struct sock *sk)
+{
+ bdaddr_t *src = &bluez_pi(sk)->src;
+ bdaddr_t *dst = &bluez_pi(sk)->dst;
+ struct l2cap_conn *conn;
+ struct hci_conn *hcon;
+ struct hci_dev *hdev;
+ int err = 0;
+
+ BT_DBG("%s -> %s psm 0x%2.2x", batostr(src), batostr(dst), l2cap_pi(sk)->psm);
+
+ if (!(hdev = hci_get_route(dst, src)))
+ return -EHOSTUNREACH;
+
+ hci_dev_lock_bh(hdev);
+
+ err = -ENOMEM;
+
+ hcon = hci_connect(hdev, ACL_LINK, dst);
+ if (!hcon)
+ goto done;
+
+ conn = l2cap_conn_add(hcon, 0);
+ if (!conn) {
+ hci_conn_put(hcon);
+ goto done;
+ }
+
+ err = 0;
+
+ /* Update source addr of the socket */
+ bacpy(src, conn->src);
+
+ l2cap_chan_add(conn, sk, NULL);
+
+ sk->state = BT_CONNECT;
+ l2cap_sock_set_timer(sk, sk->sndtimeo);
+
+ if (hcon->state == BT_CONNECTED) {
+ if (sk->type == SOCK_SEQPACKET) {
+ l2cap_conn_req req;
+ req.scid = __cpu_to_le16(l2cap_pi(sk)->scid);
+ req.psm = l2cap_pi(sk)->psm;
+ l2cap_send_req(conn, L2CAP_CONN_REQ, L2CAP_CONN_REQ_SIZE, &req);
+ } else {
+ l2cap_sock_clear_timer(sk);
+ sk->state = BT_CONNECTED;
+ }
+ }
+
+done:
+ hci_dev_unlock_bh(hdev);
+ hci_dev_put(hdev);
+ return err;
+}
+
static int l2cap_sock_connect(struct socket *sock, struct sockaddr *addr, int alen, int flags)
{
struct sockaddr_l2 *la = (struct sockaddr_l2 *) addr;
@@ -521,7 +523,7 @@
bacpy(&bluez_pi(sk)->dst, &la->l2_bdaddr);
l2cap_pi(sk)->psm = la->l2_psm;
- if ((err = l2cap_connect(sk)))
+ if ((err = l2cap_do_connect(sk)))
goto done;
wait:
@@ -1787,7 +1789,7 @@
if (sk->state != BT_LISTEN)
continue;
- if (!bacmp(&bluez_pi(sk)->src, bdaddr)) {
+ if (!bacmp(&bluez_pi(sk)->src, &hdev->bdaddr)) {
lm1 |= (HCI_LM_ACCEPT | l2cap_pi(sk)->link_mode);
exact++;
} else if (!bacmp(&bluez_pi(sk)->src, BDADDR_ANY))
FUNET's LINUX-ADM group, linux-adm@nic.funet.fi
TCL-scripts by Sam Shen (who was at: slshen@lbl.gov)