diff options
author | John W. Linville <linville@tuxdriver.com> | 2013-04-29 15:31:57 -0400 |
---|---|---|
committer | John W. Linville <linville@tuxdriver.com> | 2013-04-29 15:31:57 -0400 |
commit | 17a2911f3395d66694fcbd2e8970015904d9b034 (patch) | |
tree | c93e40197d4614b5183f86f0335c5c7abcee31aa /net/bluetooth | |
parent | 94dace10142790ddeb0a3a7b8b33d9540d30c79f (diff) | |
parent | a8a48e60a468084ef6ec23c78e8903c9e0ba7a4c (diff) |
Merge branch 'master' of git://git.kernel.org/pub/scm/linux/kernel/git/linville/wireless-next into for-davem
Diffstat (limited to 'net/bluetooth')
-rw-r--r-- | net/bluetooth/hci_core.c | 29 | ||||
-rw-r--r-- | net/bluetooth/l2cap_core.c | 7 | ||||
-rw-r--r-- | net/bluetooth/mgmt.c | 8 |
3 files changed, 32 insertions, 12 deletions
diff --git a/net/bluetooth/hci_core.c b/net/bluetooth/hci_core.c index ce82265f5619..33843c5c4939 100644 --- a/net/bluetooth/hci_core.c +++ b/net/bluetooth/hci_core.c | |||
@@ -79,7 +79,8 @@ static void hci_req_cancel(struct hci_dev *hdev, int err) | |||
79 | } | 79 | } |
80 | } | 80 | } |
81 | 81 | ||
82 | struct sk_buff *hci_get_cmd_complete(struct hci_dev *hdev, u16 opcode, u8 event) | 82 | static struct sk_buff *hci_get_cmd_complete(struct hci_dev *hdev, u16 opcode, |
83 | u8 event) | ||
83 | { | 84 | { |
84 | struct hci_ev_cmd_complete *ev; | 85 | struct hci_ev_cmd_complete *ev; |
85 | struct hci_event_hdr *hdr; | 86 | struct hci_event_hdr *hdr; |
@@ -134,7 +135,7 @@ failed: | |||
134 | } | 135 | } |
135 | 136 | ||
136 | struct sk_buff *__hci_cmd_sync_ev(struct hci_dev *hdev, u16 opcode, u32 plen, | 137 | struct sk_buff *__hci_cmd_sync_ev(struct hci_dev *hdev, u16 opcode, u32 plen, |
137 | void *param, u8 event, u32 timeout) | 138 | const void *param, u8 event, u32 timeout) |
138 | { | 139 | { |
139 | DECLARE_WAITQUEUE(wait, current); | 140 | DECLARE_WAITQUEUE(wait, current); |
140 | struct hci_request req; | 141 | struct hci_request req; |
@@ -188,7 +189,7 @@ struct sk_buff *__hci_cmd_sync_ev(struct hci_dev *hdev, u16 opcode, u32 plen, | |||
188 | EXPORT_SYMBOL(__hci_cmd_sync_ev); | 189 | EXPORT_SYMBOL(__hci_cmd_sync_ev); |
189 | 190 | ||
190 | struct sk_buff *__hci_cmd_sync(struct hci_dev *hdev, u16 opcode, u32 plen, | 191 | struct sk_buff *__hci_cmd_sync(struct hci_dev *hdev, u16 opcode, u32 plen, |
191 | void *param, u32 timeout) | 192 | const void *param, u32 timeout) |
192 | { | 193 | { |
193 | return __hci_cmd_sync_ev(hdev, opcode, plen, param, 0, timeout); | 194 | return __hci_cmd_sync_ev(hdev, opcode, plen, param, 0, timeout); |
194 | } | 195 | } |
@@ -377,6 +378,8 @@ static void bredr_setup(struct hci_request *req) | |||
377 | 378 | ||
378 | static void le_setup(struct hci_request *req) | 379 | static void le_setup(struct hci_request *req) |
379 | { | 380 | { |
381 | struct hci_dev *hdev = req->hdev; | ||
382 | |||
380 | /* Read LE Buffer Size */ | 383 | /* Read LE Buffer Size */ |
381 | hci_req_add(req, HCI_OP_LE_READ_BUFFER_SIZE, 0, NULL); | 384 | hci_req_add(req, HCI_OP_LE_READ_BUFFER_SIZE, 0, NULL); |
382 | 385 | ||
@@ -391,6 +394,10 @@ static void le_setup(struct hci_request *req) | |||
391 | 394 | ||
392 | /* Read LE Supported States */ | 395 | /* Read LE Supported States */ |
393 | hci_req_add(req, HCI_OP_LE_READ_SUPPORTED_STATES, 0, NULL); | 396 | hci_req_add(req, HCI_OP_LE_READ_SUPPORTED_STATES, 0, NULL); |
397 | |||
398 | /* LE-only controllers have LE implicitly enabled */ | ||
399 | if (!lmp_bredr_capable(hdev)) | ||
400 | set_bit(HCI_LE_ENABLED, &hdev->dev_flags); | ||
394 | } | 401 | } |
395 | 402 | ||
396 | static u8 hci_get_inquiry_mode(struct hci_dev *hdev) | 403 | static u8 hci_get_inquiry_mode(struct hci_dev *hdev) |
@@ -574,6 +581,10 @@ static void hci_set_le_support(struct hci_request *req) | |||
574 | struct hci_dev *hdev = req->hdev; | 581 | struct hci_dev *hdev = req->hdev; |
575 | struct hci_cp_write_le_host_supported cp; | 582 | struct hci_cp_write_le_host_supported cp; |
576 | 583 | ||
584 | /* LE-only devices do not support explicit enablement */ | ||
585 | if (!lmp_bredr_capable(hdev)) | ||
586 | return; | ||
587 | |||
577 | memset(&cp, 0, sizeof(cp)); | 588 | memset(&cp, 0, sizeof(cp)); |
578 | 589 | ||
579 | if (test_bit(HCI_LE_ENABLED, &hdev->dev_flags)) { | 590 | if (test_bit(HCI_LE_ENABLED, &hdev->dev_flags)) { |
@@ -2602,7 +2613,7 @@ int hci_req_run(struct hci_request *req, hci_req_complete_t complete) | |||
2602 | } | 2613 | } |
2603 | 2614 | ||
2604 | static struct sk_buff *hci_prepare_cmd(struct hci_dev *hdev, u16 opcode, | 2615 | static struct sk_buff *hci_prepare_cmd(struct hci_dev *hdev, u16 opcode, |
2605 | u32 plen, void *param) | 2616 | u32 plen, const void *param) |
2606 | { | 2617 | { |
2607 | int len = HCI_COMMAND_HDR_SIZE + plen; | 2618 | int len = HCI_COMMAND_HDR_SIZE + plen; |
2608 | struct hci_command_hdr *hdr; | 2619 | struct hci_command_hdr *hdr; |
@@ -2628,7 +2639,8 @@ static struct sk_buff *hci_prepare_cmd(struct hci_dev *hdev, u16 opcode, | |||
2628 | } | 2639 | } |
2629 | 2640 | ||
2630 | /* Send HCI command */ | 2641 | /* Send HCI command */ |
2631 | int hci_send_cmd(struct hci_dev *hdev, __u16 opcode, __u32 plen, void *param) | 2642 | int hci_send_cmd(struct hci_dev *hdev, __u16 opcode, __u32 plen, |
2643 | const void *param) | ||
2632 | { | 2644 | { |
2633 | struct sk_buff *skb; | 2645 | struct sk_buff *skb; |
2634 | 2646 | ||
@@ -2652,8 +2664,8 @@ int hci_send_cmd(struct hci_dev *hdev, __u16 opcode, __u32 plen, void *param) | |||
2652 | } | 2664 | } |
2653 | 2665 | ||
2654 | /* Queue a command to an asynchronous HCI request */ | 2666 | /* Queue a command to an asynchronous HCI request */ |
2655 | void hci_req_add_ev(struct hci_request *req, u16 opcode, u32 plen, void *param, | 2667 | void hci_req_add_ev(struct hci_request *req, u16 opcode, u32 plen, |
2656 | u8 event) | 2668 | const void *param, u8 event) |
2657 | { | 2669 | { |
2658 | struct hci_dev *hdev = req->hdev; | 2670 | struct hci_dev *hdev = req->hdev; |
2659 | struct sk_buff *skb; | 2671 | struct sk_buff *skb; |
@@ -2682,7 +2694,8 @@ void hci_req_add_ev(struct hci_request *req, u16 opcode, u32 plen, void *param, | |||
2682 | skb_queue_tail(&req->cmd_q, skb); | 2694 | skb_queue_tail(&req->cmd_q, skb); |
2683 | } | 2695 | } |
2684 | 2696 | ||
2685 | void hci_req_add(struct hci_request *req, u16 opcode, u32 plen, void *param) | 2697 | void hci_req_add(struct hci_request *req, u16 opcode, u32 plen, |
2698 | const void *param) | ||
2686 | { | 2699 | { |
2687 | hci_req_add_ev(req, opcode, plen, param, 0); | 2700 | hci_req_add_ev(req, opcode, plen, param, 0); |
2688 | } | 2701 | } |
diff --git a/net/bluetooth/l2cap_core.c b/net/bluetooth/l2cap_core.c index eae1d9f90b68..a76d1ac0321b 100644 --- a/net/bluetooth/l2cap_core.c +++ b/net/bluetooth/l2cap_core.c | |||
@@ -6314,12 +6314,13 @@ drop: | |||
6314 | kfree_skb(skb); | 6314 | kfree_skb(skb); |
6315 | } | 6315 | } |
6316 | 6316 | ||
6317 | static void l2cap_att_channel(struct l2cap_conn *conn, u16 cid, | 6317 | static void l2cap_att_channel(struct l2cap_conn *conn, |
6318 | struct sk_buff *skb) | 6318 | struct sk_buff *skb) |
6319 | { | 6319 | { |
6320 | struct l2cap_chan *chan; | 6320 | struct l2cap_chan *chan; |
6321 | 6321 | ||
6322 | chan = l2cap_global_chan_by_scid(0, cid, conn->src, conn->dst); | 6322 | chan = l2cap_global_chan_by_scid(0, L2CAP_CID_LE_DATA, |
6323 | conn->src, conn->dst); | ||
6323 | if (!chan) | 6324 | if (!chan) |
6324 | goto drop; | 6325 | goto drop; |
6325 | 6326 | ||
@@ -6368,7 +6369,7 @@ static void l2cap_recv_frame(struct l2cap_conn *conn, struct sk_buff *skb) | |||
6368 | break; | 6369 | break; |
6369 | 6370 | ||
6370 | case L2CAP_CID_LE_DATA: | 6371 | case L2CAP_CID_LE_DATA: |
6371 | l2cap_att_channel(conn, cid, skb); | 6372 | l2cap_att_channel(conn, skb); |
6372 | break; | 6373 | break; |
6373 | 6374 | ||
6374 | case L2CAP_CID_SMP: | 6375 | case L2CAP_CID_SMP: |
diff --git a/net/bluetooth/mgmt.c b/net/bluetooth/mgmt.c index 4c830c62ef74..35fef22703e9 100644 --- a/net/bluetooth/mgmt.c +++ b/net/bluetooth/mgmt.c | |||
@@ -1351,6 +1351,11 @@ static int set_le(struct sock *sk, struct hci_dev *hdev, void *data, u16 len) | |||
1351 | return cmd_status(sk, hdev->id, MGMT_OP_SET_LE, | 1351 | return cmd_status(sk, hdev->id, MGMT_OP_SET_LE, |
1352 | MGMT_STATUS_INVALID_PARAMS); | 1352 | MGMT_STATUS_INVALID_PARAMS); |
1353 | 1353 | ||
1354 | /* LE-only devices do not allow toggling LE on/off */ | ||
1355 | if (!lmp_bredr_capable(hdev)) | ||
1356 | return cmd_status(sk, hdev->id, MGMT_OP_SET_LE, | ||
1357 | MGMT_STATUS_REJECTED); | ||
1358 | |||
1354 | hci_dev_lock(hdev); | 1359 | hci_dev_lock(hdev); |
1355 | 1360 | ||
1356 | val = !!cp->val; | 1361 | val = !!cp->val; |
@@ -3347,7 +3352,8 @@ static int powered_update_hci(struct hci_dev *hdev) | |||
3347 | hci_req_add(&req, HCI_OP_WRITE_SSP_MODE, 1, &ssp); | 3352 | hci_req_add(&req, HCI_OP_WRITE_SSP_MODE, 1, &ssp); |
3348 | } | 3353 | } |
3349 | 3354 | ||
3350 | if (test_bit(HCI_LE_ENABLED, &hdev->dev_flags)) { | 3355 | if (test_bit(HCI_LE_ENABLED, &hdev->dev_flags) && |
3356 | lmp_bredr_capable(hdev)) { | ||
3351 | struct hci_cp_write_le_host_supported cp; | 3357 | struct hci_cp_write_le_host_supported cp; |
3352 | 3358 | ||
3353 | cp.le = 1; | 3359 | cp.le = 1; |