xref: /openbmc/linux/net/bluetooth/hci_core.c (revision 8035ded4)
11da177e4SLinus Torvalds /*
21da177e4SLinus Torvalds    BlueZ - Bluetooth protocol stack for Linux
31da177e4SLinus Torvalds    Copyright (C) 2000-2001 Qualcomm Incorporated
41da177e4SLinus Torvalds 
51da177e4SLinus Torvalds    Written 2000,2001 by Maxim Krasnyansky <maxk@qualcomm.com>
61da177e4SLinus Torvalds 
71da177e4SLinus Torvalds    This program is free software; you can redistribute it and/or modify
81da177e4SLinus Torvalds    it under the terms of the GNU General Public License version 2 as
91da177e4SLinus Torvalds    published by the Free Software Foundation;
101da177e4SLinus Torvalds 
111da177e4SLinus Torvalds    THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
121da177e4SLinus Torvalds    OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
131da177e4SLinus Torvalds    FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT OF THIRD PARTY RIGHTS.
141da177e4SLinus Torvalds    IN NO EVENT SHALL THE COPYRIGHT HOLDER(S) AND AUTHOR(S) BE LIABLE FOR ANY
151da177e4SLinus Torvalds    CLAIM, OR ANY SPECIAL INDIRECT OR CONSEQUENTIAL DAMAGES, OR ANY DAMAGES
161da177e4SLinus Torvalds    WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
171da177e4SLinus Torvalds    ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
181da177e4SLinus Torvalds    OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
191da177e4SLinus Torvalds 
201da177e4SLinus Torvalds    ALL LIABILITY, INCLUDING LIABILITY FOR INFRINGEMENT OF ANY PATENTS,
211da177e4SLinus Torvalds    COPYRIGHTS, TRADEMARKS OR OTHER RIGHTS, RELATING TO USE OF THIS
221da177e4SLinus Torvalds    SOFTWARE IS DISCLAIMED.
231da177e4SLinus Torvalds */
241da177e4SLinus Torvalds 
251da177e4SLinus Torvalds /* Bluetooth HCI core. */
261da177e4SLinus Torvalds 
2782453021SS.Çağlar Onur #include <linux/jiffies.h>
281da177e4SLinus Torvalds #include <linux/module.h>
291da177e4SLinus Torvalds #include <linux/kmod.h>
301da177e4SLinus Torvalds 
311da177e4SLinus Torvalds #include <linux/types.h>
321da177e4SLinus Torvalds #include <linux/errno.h>
331da177e4SLinus Torvalds #include <linux/kernel.h>
341da177e4SLinus Torvalds #include <linux/sched.h>
351da177e4SLinus Torvalds #include <linux/slab.h>
361da177e4SLinus Torvalds #include <linux/poll.h>
371da177e4SLinus Torvalds #include <linux/fcntl.h>
381da177e4SLinus Torvalds #include <linux/init.h>
391da177e4SLinus Torvalds #include <linux/skbuff.h>
40f48fd9c8SMarcel Holtmann #include <linux/workqueue.h>
411da177e4SLinus Torvalds #include <linux/interrupt.h>
421da177e4SLinus Torvalds #include <linux/notifier.h>
43611b30f7SMarcel Holtmann #include <linux/rfkill.h>
446bd32326SVille Tervo #include <linux/timer.h>
453a0259bbSVinicius Costa Gomes #include <linux/crypto.h>
461da177e4SLinus Torvalds #include <net/sock.h>
471da177e4SLinus Torvalds 
481da177e4SLinus Torvalds #include <asm/system.h>
4970f23020SAndrei Emeltchenko #include <linux/uaccess.h>
501da177e4SLinus Torvalds #include <asm/unaligned.h>
511da177e4SLinus Torvalds 
521da177e4SLinus Torvalds #include <net/bluetooth/bluetooth.h>
531da177e4SLinus Torvalds #include <net/bluetooth/hci_core.h>
541da177e4SLinus Torvalds 
55ab81cbf9SJohan Hedberg #define AUTO_OFF_TIMEOUT 2000
56ab81cbf9SJohan Hedberg 
571da177e4SLinus Torvalds static void hci_cmd_task(unsigned long arg);
581da177e4SLinus Torvalds static void hci_rx_task(unsigned long arg);
591da177e4SLinus Torvalds static void hci_tx_task(unsigned long arg);
601da177e4SLinus Torvalds 
611da177e4SLinus Torvalds static DEFINE_RWLOCK(hci_task_lock);
621da177e4SLinus Torvalds 
631da177e4SLinus Torvalds /* HCI device list */
641da177e4SLinus Torvalds LIST_HEAD(hci_dev_list);
651da177e4SLinus Torvalds DEFINE_RWLOCK(hci_dev_list_lock);
661da177e4SLinus Torvalds 
671da177e4SLinus Torvalds /* HCI callback list */
681da177e4SLinus Torvalds LIST_HEAD(hci_cb_list);
691da177e4SLinus Torvalds DEFINE_RWLOCK(hci_cb_list_lock);
701da177e4SLinus Torvalds 
711da177e4SLinus Torvalds /* HCI protocols */
721da177e4SLinus Torvalds #define HCI_MAX_PROTO	2
731da177e4SLinus Torvalds struct hci_proto *hci_proto[HCI_MAX_PROTO];
741da177e4SLinus Torvalds 
751da177e4SLinus Torvalds /* HCI notifiers list */
76e041c683SAlan Stern static ATOMIC_NOTIFIER_HEAD(hci_notifier);
771da177e4SLinus Torvalds 
781da177e4SLinus Torvalds /* ---- HCI notifications ---- */
791da177e4SLinus Torvalds 
801da177e4SLinus Torvalds int hci_register_notifier(struct notifier_block *nb)
811da177e4SLinus Torvalds {
82e041c683SAlan Stern 	return atomic_notifier_chain_register(&hci_notifier, nb);
831da177e4SLinus Torvalds }
841da177e4SLinus Torvalds 
851da177e4SLinus Torvalds int hci_unregister_notifier(struct notifier_block *nb)
861da177e4SLinus Torvalds {
87e041c683SAlan Stern 	return atomic_notifier_chain_unregister(&hci_notifier, nb);
881da177e4SLinus Torvalds }
891da177e4SLinus Torvalds 
906516455dSMarcel Holtmann static void hci_notify(struct hci_dev *hdev, int event)
911da177e4SLinus Torvalds {
92e041c683SAlan Stern 	atomic_notifier_call_chain(&hci_notifier, event, hdev);
931da177e4SLinus Torvalds }
941da177e4SLinus Torvalds 
951da177e4SLinus Torvalds /* ---- HCI requests ---- */
961da177e4SLinus Torvalds 
9723bb5763SJohan Hedberg void hci_req_complete(struct hci_dev *hdev, __u16 cmd, int result)
981da177e4SLinus Torvalds {
9923bb5763SJohan Hedberg 	BT_DBG("%s command 0x%04x result 0x%2.2x", hdev->name, cmd, result);
10023bb5763SJohan Hedberg 
101a5040efaSJohan Hedberg 	/* If this is the init phase check if the completed command matches
102a5040efaSJohan Hedberg 	 * the last init command, and if not just return.
103a5040efaSJohan Hedberg 	 */
104a5040efaSJohan Hedberg 	if (test_bit(HCI_INIT, &hdev->flags) && hdev->init_last_cmd != cmd)
10523bb5763SJohan Hedberg 		return;
1061da177e4SLinus Torvalds 
1071da177e4SLinus Torvalds 	if (hdev->req_status == HCI_REQ_PEND) {
1081da177e4SLinus Torvalds 		hdev->req_result = result;
1091da177e4SLinus Torvalds 		hdev->req_status = HCI_REQ_DONE;
1101da177e4SLinus Torvalds 		wake_up_interruptible(&hdev->req_wait_q);
1111da177e4SLinus Torvalds 	}
1121da177e4SLinus Torvalds }
1131da177e4SLinus Torvalds 
1141da177e4SLinus Torvalds static void hci_req_cancel(struct hci_dev *hdev, int err)
1151da177e4SLinus Torvalds {
1161da177e4SLinus Torvalds 	BT_DBG("%s err 0x%2.2x", hdev->name, err);
1171da177e4SLinus Torvalds 
1181da177e4SLinus Torvalds 	if (hdev->req_status == HCI_REQ_PEND) {
1191da177e4SLinus Torvalds 		hdev->req_result = err;
1201da177e4SLinus Torvalds 		hdev->req_status = HCI_REQ_CANCELED;
1211da177e4SLinus Torvalds 		wake_up_interruptible(&hdev->req_wait_q);
1221da177e4SLinus Torvalds 	}
1231da177e4SLinus Torvalds }
1241da177e4SLinus Torvalds 
1251da177e4SLinus Torvalds /* Execute request and wait for completion. */
1261da177e4SLinus Torvalds static int __hci_request(struct hci_dev *hdev, void (*req)(struct hci_dev *hdev, unsigned long opt),
1271da177e4SLinus Torvalds 					unsigned long opt, __u32 timeout)
1281da177e4SLinus Torvalds {
1291da177e4SLinus Torvalds 	DECLARE_WAITQUEUE(wait, current);
1301da177e4SLinus Torvalds 	int err = 0;
1311da177e4SLinus Torvalds 
1321da177e4SLinus Torvalds 	BT_DBG("%s start", hdev->name);
1331da177e4SLinus Torvalds 
1341da177e4SLinus Torvalds 	hdev->req_status = HCI_REQ_PEND;
1351da177e4SLinus Torvalds 
1361da177e4SLinus Torvalds 	add_wait_queue(&hdev->req_wait_q, &wait);
1371da177e4SLinus Torvalds 	set_current_state(TASK_INTERRUPTIBLE);
1381da177e4SLinus Torvalds 
1391da177e4SLinus Torvalds 	req(hdev, opt);
1401da177e4SLinus Torvalds 	schedule_timeout(timeout);
1411da177e4SLinus Torvalds 
1421da177e4SLinus Torvalds 	remove_wait_queue(&hdev->req_wait_q, &wait);
1431da177e4SLinus Torvalds 
1441da177e4SLinus Torvalds 	if (signal_pending(current))
1451da177e4SLinus Torvalds 		return -EINTR;
1461da177e4SLinus Torvalds 
1471da177e4SLinus Torvalds 	switch (hdev->req_status) {
1481da177e4SLinus Torvalds 	case HCI_REQ_DONE:
149e175072fSJoe Perches 		err = -bt_to_errno(hdev->req_result);
1501da177e4SLinus Torvalds 		break;
1511da177e4SLinus Torvalds 
1521da177e4SLinus Torvalds 	case HCI_REQ_CANCELED:
1531da177e4SLinus Torvalds 		err = -hdev->req_result;
1541da177e4SLinus Torvalds 		break;
1551da177e4SLinus Torvalds 
1561da177e4SLinus Torvalds 	default:
1571da177e4SLinus Torvalds 		err = -ETIMEDOUT;
1581da177e4SLinus Torvalds 		break;
1593ff50b79SStephen Hemminger 	}
1601da177e4SLinus Torvalds 
161a5040efaSJohan Hedberg 	hdev->req_status = hdev->req_result = 0;
1621da177e4SLinus Torvalds 
1631da177e4SLinus Torvalds 	BT_DBG("%s end: err %d", hdev->name, err);
1641da177e4SLinus Torvalds 
1651da177e4SLinus Torvalds 	return err;
1661da177e4SLinus Torvalds }
1671da177e4SLinus Torvalds 
1681da177e4SLinus Torvalds static inline int hci_request(struct hci_dev *hdev, void (*req)(struct hci_dev *hdev, unsigned long opt),
1691da177e4SLinus Torvalds 					unsigned long opt, __u32 timeout)
1701da177e4SLinus Torvalds {
1711da177e4SLinus Torvalds 	int ret;
1721da177e4SLinus Torvalds 
1737c6a329eSMarcel Holtmann 	if (!test_bit(HCI_UP, &hdev->flags))
1747c6a329eSMarcel Holtmann 		return -ENETDOWN;
1757c6a329eSMarcel Holtmann 
1761da177e4SLinus Torvalds 	/* Serialize all requests */
1771da177e4SLinus Torvalds 	hci_req_lock(hdev);
1781da177e4SLinus Torvalds 	ret = __hci_request(hdev, req, opt, timeout);
1791da177e4SLinus Torvalds 	hci_req_unlock(hdev);
1801da177e4SLinus Torvalds 
1811da177e4SLinus Torvalds 	return ret;
1821da177e4SLinus Torvalds }
1831da177e4SLinus Torvalds 
1841da177e4SLinus Torvalds static void hci_reset_req(struct hci_dev *hdev, unsigned long opt)
1851da177e4SLinus Torvalds {
1861da177e4SLinus Torvalds 	BT_DBG("%s %ld", hdev->name, opt);
1871da177e4SLinus Torvalds 
1881da177e4SLinus Torvalds 	/* Reset device */
189f630cf0dSGustavo F. Padovan 	set_bit(HCI_RESET, &hdev->flags);
190a9de9248SMarcel Holtmann 	hci_send_cmd(hdev, HCI_OP_RESET, 0, NULL);
1911da177e4SLinus Torvalds }
1921da177e4SLinus Torvalds 
1931da177e4SLinus Torvalds static void hci_init_req(struct hci_dev *hdev, unsigned long opt)
1941da177e4SLinus Torvalds {
195b0916ea0SJohan Hedberg 	struct hci_cp_delete_stored_link_key cp;
1961da177e4SLinus Torvalds 	struct sk_buff *skb;
1971ebb9252SMarcel Holtmann 	__le16 param;
19889f2783dSMarcel Holtmann 	__u8 flt_type;
1991da177e4SLinus Torvalds 
2001da177e4SLinus Torvalds 	BT_DBG("%s %ld", hdev->name, opt);
2011da177e4SLinus Torvalds 
2021da177e4SLinus Torvalds 	/* Driver initialization */
2031da177e4SLinus Torvalds 
2041da177e4SLinus Torvalds 	/* Special commands */
2051da177e4SLinus Torvalds 	while ((skb = skb_dequeue(&hdev->driver_init))) {
2060d48d939SMarcel Holtmann 		bt_cb(skb)->pkt_type = HCI_COMMAND_PKT;
2071da177e4SLinus Torvalds 		skb->dev = (void *) hdev;
208c78ae283SMarcel Holtmann 
2091da177e4SLinus Torvalds 		skb_queue_tail(&hdev->cmd_q, skb);
210c78ae283SMarcel Holtmann 		tasklet_schedule(&hdev->cmd_task);
2111da177e4SLinus Torvalds 	}
2121da177e4SLinus Torvalds 	skb_queue_purge(&hdev->driver_init);
2131da177e4SLinus Torvalds 
2141da177e4SLinus Torvalds 	/* Mandatory initialization */
2151da177e4SLinus Torvalds 
2161da177e4SLinus Torvalds 	/* Reset */
217f630cf0dSGustavo F. Padovan 	if (!test_bit(HCI_QUIRK_NO_RESET, &hdev->quirks)) {
218f630cf0dSGustavo F. Padovan 			set_bit(HCI_RESET, &hdev->flags);
219a9de9248SMarcel Holtmann 			hci_send_cmd(hdev, HCI_OP_RESET, 0, NULL);
220f630cf0dSGustavo F. Padovan 	}
2211da177e4SLinus Torvalds 
2221da177e4SLinus Torvalds 	/* Read Local Supported Features */
223a9de9248SMarcel Holtmann 	hci_send_cmd(hdev, HCI_OP_READ_LOCAL_FEATURES, 0, NULL);
2241da177e4SLinus Torvalds 
2251143e5a6SMarcel Holtmann 	/* Read Local Version */
226a9de9248SMarcel Holtmann 	hci_send_cmd(hdev, HCI_OP_READ_LOCAL_VERSION, 0, NULL);
2271143e5a6SMarcel Holtmann 
2281da177e4SLinus Torvalds 	/* Read Buffer Size (ACL mtu, max pkt, etc.) */
229a9de9248SMarcel Holtmann 	hci_send_cmd(hdev, HCI_OP_READ_BUFFER_SIZE, 0, NULL);
2301da177e4SLinus Torvalds 
2311da177e4SLinus Torvalds #if 0
2321da177e4SLinus Torvalds 	/* Host buffer size */
2331da177e4SLinus Torvalds 	{
2341da177e4SLinus Torvalds 		struct hci_cp_host_buffer_size cp;
235aca3192cSYOSHIFUJI Hideaki 		cp.acl_mtu = cpu_to_le16(HCI_MAX_ACL_SIZE);
2361da177e4SLinus Torvalds 		cp.sco_mtu = HCI_MAX_SCO_SIZE;
237aca3192cSYOSHIFUJI Hideaki 		cp.acl_max_pkt = cpu_to_le16(0xffff);
238aca3192cSYOSHIFUJI Hideaki 		cp.sco_max_pkt = cpu_to_le16(0xffff);
239a9de9248SMarcel Holtmann 		hci_send_cmd(hdev, HCI_OP_HOST_BUFFER_SIZE, sizeof(cp), &cp);
2401da177e4SLinus Torvalds 	}
2411da177e4SLinus Torvalds #endif
2421da177e4SLinus Torvalds 
2431da177e4SLinus Torvalds 	/* Read BD Address */
244a9de9248SMarcel Holtmann 	hci_send_cmd(hdev, HCI_OP_READ_BD_ADDR, 0, NULL);
245a9de9248SMarcel Holtmann 
246a9de9248SMarcel Holtmann 	/* Read Class of Device */
247a9de9248SMarcel Holtmann 	hci_send_cmd(hdev, HCI_OP_READ_CLASS_OF_DEV, 0, NULL);
248a9de9248SMarcel Holtmann 
249a9de9248SMarcel Holtmann 	/* Read Local Name */
250a9de9248SMarcel Holtmann 	hci_send_cmd(hdev, HCI_OP_READ_LOCAL_NAME, 0, NULL);
2511da177e4SLinus Torvalds 
2521da177e4SLinus Torvalds 	/* Read Voice Setting */
253a9de9248SMarcel Holtmann 	hci_send_cmd(hdev, HCI_OP_READ_VOICE_SETTING, 0, NULL);
2541da177e4SLinus Torvalds 
2551da177e4SLinus Torvalds 	/* Optional initialization */
2561da177e4SLinus Torvalds 
2571da177e4SLinus Torvalds 	/* Clear Event Filters */
25889f2783dSMarcel Holtmann 	flt_type = HCI_FLT_CLEAR_ALL;
259a9de9248SMarcel Holtmann 	hci_send_cmd(hdev, HCI_OP_SET_EVENT_FLT, 1, &flt_type);
2601da177e4SLinus Torvalds 
2611da177e4SLinus Torvalds 	/* Connection accept timeout ~20 secs */
262aca3192cSYOSHIFUJI Hideaki 	param = cpu_to_le16(0x7d00);
263a9de9248SMarcel Holtmann 	hci_send_cmd(hdev, HCI_OP_WRITE_CA_TIMEOUT, 2, &param);
264b0916ea0SJohan Hedberg 
265b0916ea0SJohan Hedberg 	bacpy(&cp.bdaddr, BDADDR_ANY);
266b0916ea0SJohan Hedberg 	cp.delete_all = 1;
267b0916ea0SJohan Hedberg 	hci_send_cmd(hdev, HCI_OP_DELETE_STORED_LINK_KEY, sizeof(cp), &cp);
2681da177e4SLinus Torvalds }
2691da177e4SLinus Torvalds 
2706ed58ec5SVille Tervo static void hci_le_init_req(struct hci_dev *hdev, unsigned long opt)
2716ed58ec5SVille Tervo {
2726ed58ec5SVille Tervo 	BT_DBG("%s", hdev->name);
2736ed58ec5SVille Tervo 
2746ed58ec5SVille Tervo 	/* Read LE buffer size */
2756ed58ec5SVille Tervo 	hci_send_cmd(hdev, HCI_OP_LE_READ_BUFFER_SIZE, 0, NULL);
2766ed58ec5SVille Tervo }
2776ed58ec5SVille Tervo 
2781da177e4SLinus Torvalds static void hci_scan_req(struct hci_dev *hdev, unsigned long opt)
2791da177e4SLinus Torvalds {
2801da177e4SLinus Torvalds 	__u8 scan = opt;
2811da177e4SLinus Torvalds 
2821da177e4SLinus Torvalds 	BT_DBG("%s %x", hdev->name, scan);
2831da177e4SLinus Torvalds 
2841da177e4SLinus Torvalds 	/* Inquiry and Page scans */
285a9de9248SMarcel Holtmann 	hci_send_cmd(hdev, HCI_OP_WRITE_SCAN_ENABLE, 1, &scan);
2861da177e4SLinus Torvalds }
2871da177e4SLinus Torvalds 
2881da177e4SLinus Torvalds static void hci_auth_req(struct hci_dev *hdev, unsigned long opt)
2891da177e4SLinus Torvalds {
2901da177e4SLinus Torvalds 	__u8 auth = opt;
2911da177e4SLinus Torvalds 
2921da177e4SLinus Torvalds 	BT_DBG("%s %x", hdev->name, auth);
2931da177e4SLinus Torvalds 
2941da177e4SLinus Torvalds 	/* Authentication */
295a9de9248SMarcel Holtmann 	hci_send_cmd(hdev, HCI_OP_WRITE_AUTH_ENABLE, 1, &auth);
2961da177e4SLinus Torvalds }
2971da177e4SLinus Torvalds 
2981da177e4SLinus Torvalds static void hci_encrypt_req(struct hci_dev *hdev, unsigned long opt)
2991da177e4SLinus Torvalds {
3001da177e4SLinus Torvalds 	__u8 encrypt = opt;
3011da177e4SLinus Torvalds 
3021da177e4SLinus Torvalds 	BT_DBG("%s %x", hdev->name, encrypt);
3031da177e4SLinus Torvalds 
304e4e8e37cSMarcel Holtmann 	/* Encryption */
305a9de9248SMarcel Holtmann 	hci_send_cmd(hdev, HCI_OP_WRITE_ENCRYPT_MODE, 1, &encrypt);
3061da177e4SLinus Torvalds }
3071da177e4SLinus Torvalds 
308e4e8e37cSMarcel Holtmann static void hci_linkpol_req(struct hci_dev *hdev, unsigned long opt)
309e4e8e37cSMarcel Holtmann {
310e4e8e37cSMarcel Holtmann 	__le16 policy = cpu_to_le16(opt);
311e4e8e37cSMarcel Holtmann 
312a418b893SMarcel Holtmann 	BT_DBG("%s %x", hdev->name, policy);
313e4e8e37cSMarcel Holtmann 
314e4e8e37cSMarcel Holtmann 	/* Default link policy */
315e4e8e37cSMarcel Holtmann 	hci_send_cmd(hdev, HCI_OP_WRITE_DEF_LINK_POLICY, 2, &policy);
316e4e8e37cSMarcel Holtmann }
317e4e8e37cSMarcel Holtmann 
3181da177e4SLinus Torvalds /* Get HCI device by index.
3191da177e4SLinus Torvalds  * Device is held on return. */
3201da177e4SLinus Torvalds struct hci_dev *hci_dev_get(int index)
3211da177e4SLinus Torvalds {
322*8035ded4SLuiz Augusto von Dentz 	struct hci_dev *hdev = NULL, *d;
3231da177e4SLinus Torvalds 
3241da177e4SLinus Torvalds 	BT_DBG("%d", index);
3251da177e4SLinus Torvalds 
3261da177e4SLinus Torvalds 	if (index < 0)
3271da177e4SLinus Torvalds 		return NULL;
3281da177e4SLinus Torvalds 
3291da177e4SLinus Torvalds 	read_lock(&hci_dev_list_lock);
330*8035ded4SLuiz Augusto von Dentz 	list_for_each_entry(d, &hci_dev_list, list) {
3311da177e4SLinus Torvalds 		if (d->id == index) {
3321da177e4SLinus Torvalds 			hdev = hci_dev_hold(d);
3331da177e4SLinus Torvalds 			break;
3341da177e4SLinus Torvalds 		}
3351da177e4SLinus Torvalds 	}
3361da177e4SLinus Torvalds 	read_unlock(&hci_dev_list_lock);
3371da177e4SLinus Torvalds 	return hdev;
3381da177e4SLinus Torvalds }
3391da177e4SLinus Torvalds 
3401da177e4SLinus Torvalds /* ---- Inquiry support ---- */
3411da177e4SLinus Torvalds static void inquiry_cache_flush(struct hci_dev *hdev)
3421da177e4SLinus Torvalds {
3431da177e4SLinus Torvalds 	struct inquiry_cache *cache = &hdev->inq_cache;
3441da177e4SLinus Torvalds 	struct inquiry_entry *next  = cache->list, *e;
3451da177e4SLinus Torvalds 
3461da177e4SLinus Torvalds 	BT_DBG("cache %p", cache);
3471da177e4SLinus Torvalds 
3481da177e4SLinus Torvalds 	cache->list = NULL;
3491da177e4SLinus Torvalds 	while ((e = next)) {
3501da177e4SLinus Torvalds 		next = e->next;
3511da177e4SLinus Torvalds 		kfree(e);
3521da177e4SLinus Torvalds 	}
3531da177e4SLinus Torvalds }
3541da177e4SLinus Torvalds 
3551da177e4SLinus Torvalds struct inquiry_entry *hci_inquiry_cache_lookup(struct hci_dev *hdev, bdaddr_t *bdaddr)
3561da177e4SLinus Torvalds {
3571da177e4SLinus Torvalds 	struct inquiry_cache *cache = &hdev->inq_cache;
3581da177e4SLinus Torvalds 	struct inquiry_entry *e;
3591da177e4SLinus Torvalds 
3601da177e4SLinus Torvalds 	BT_DBG("cache %p, %s", cache, batostr(bdaddr));
3611da177e4SLinus Torvalds 
3621da177e4SLinus Torvalds 	for (e = cache->list; e; e = e->next)
3631da177e4SLinus Torvalds 		if (!bacmp(&e->data.bdaddr, bdaddr))
3641da177e4SLinus Torvalds 			break;
3651da177e4SLinus Torvalds 	return e;
3661da177e4SLinus Torvalds }
3671da177e4SLinus Torvalds 
3681da177e4SLinus Torvalds void hci_inquiry_cache_update(struct hci_dev *hdev, struct inquiry_data *data)
3691da177e4SLinus Torvalds {
3701da177e4SLinus Torvalds 	struct inquiry_cache *cache = &hdev->inq_cache;
37170f23020SAndrei Emeltchenko 	struct inquiry_entry *ie;
3721da177e4SLinus Torvalds 
3731da177e4SLinus Torvalds 	BT_DBG("cache %p, %s", cache, batostr(&data->bdaddr));
3741da177e4SLinus Torvalds 
37570f23020SAndrei Emeltchenko 	ie = hci_inquiry_cache_lookup(hdev, &data->bdaddr);
37670f23020SAndrei Emeltchenko 	if (!ie) {
3771da177e4SLinus Torvalds 		/* Entry not in the cache. Add new one. */
37870f23020SAndrei Emeltchenko 		ie = kzalloc(sizeof(struct inquiry_entry), GFP_ATOMIC);
37970f23020SAndrei Emeltchenko 		if (!ie)
3801da177e4SLinus Torvalds 			return;
38170f23020SAndrei Emeltchenko 
38270f23020SAndrei Emeltchenko 		ie->next = cache->list;
38370f23020SAndrei Emeltchenko 		cache->list = ie;
3841da177e4SLinus Torvalds 	}
3851da177e4SLinus Torvalds 
38670f23020SAndrei Emeltchenko 	memcpy(&ie->data, data, sizeof(*data));
38770f23020SAndrei Emeltchenko 	ie->timestamp = jiffies;
3881da177e4SLinus Torvalds 	cache->timestamp = jiffies;
3891da177e4SLinus Torvalds }
3901da177e4SLinus Torvalds 
3911da177e4SLinus Torvalds static int inquiry_cache_dump(struct hci_dev *hdev, int num, __u8 *buf)
3921da177e4SLinus Torvalds {
3931da177e4SLinus Torvalds 	struct inquiry_cache *cache = &hdev->inq_cache;
3941da177e4SLinus Torvalds 	struct inquiry_info *info = (struct inquiry_info *) buf;
3951da177e4SLinus Torvalds 	struct inquiry_entry *e;
3961da177e4SLinus Torvalds 	int copied = 0;
3971da177e4SLinus Torvalds 
3981da177e4SLinus Torvalds 	for (e = cache->list; e && copied < num; e = e->next, copied++) {
3991da177e4SLinus Torvalds 		struct inquiry_data *data = &e->data;
4001da177e4SLinus Torvalds 		bacpy(&info->bdaddr, &data->bdaddr);
4011da177e4SLinus Torvalds 		info->pscan_rep_mode	= data->pscan_rep_mode;
4021da177e4SLinus Torvalds 		info->pscan_period_mode	= data->pscan_period_mode;
4031da177e4SLinus Torvalds 		info->pscan_mode	= data->pscan_mode;
4041da177e4SLinus Torvalds 		memcpy(info->dev_class, data->dev_class, 3);
4051da177e4SLinus Torvalds 		info->clock_offset	= data->clock_offset;
4061da177e4SLinus Torvalds 		info++;
4071da177e4SLinus Torvalds 	}
4081da177e4SLinus Torvalds 
4091da177e4SLinus Torvalds 	BT_DBG("cache %p, copied %d", cache, copied);
4101da177e4SLinus Torvalds 	return copied;
4111da177e4SLinus Torvalds }
4121da177e4SLinus Torvalds 
4131da177e4SLinus Torvalds static void hci_inq_req(struct hci_dev *hdev, unsigned long opt)
4141da177e4SLinus Torvalds {
4151da177e4SLinus Torvalds 	struct hci_inquiry_req *ir = (struct hci_inquiry_req *) opt;
4161da177e4SLinus Torvalds 	struct hci_cp_inquiry cp;
4171da177e4SLinus Torvalds 
4181da177e4SLinus Torvalds 	BT_DBG("%s", hdev->name);
4191da177e4SLinus Torvalds 
4201da177e4SLinus Torvalds 	if (test_bit(HCI_INQUIRY, &hdev->flags))
4211da177e4SLinus Torvalds 		return;
4221da177e4SLinus Torvalds 
4231da177e4SLinus Torvalds 	/* Start Inquiry */
4241da177e4SLinus Torvalds 	memcpy(&cp.lap, &ir->lap, 3);
4251da177e4SLinus Torvalds 	cp.length  = ir->length;
4261da177e4SLinus Torvalds 	cp.num_rsp = ir->num_rsp;
427a9de9248SMarcel Holtmann 	hci_send_cmd(hdev, HCI_OP_INQUIRY, sizeof(cp), &cp);
4281da177e4SLinus Torvalds }
4291da177e4SLinus Torvalds 
4301da177e4SLinus Torvalds int hci_inquiry(void __user *arg)
4311da177e4SLinus Torvalds {
4321da177e4SLinus Torvalds 	__u8 __user *ptr = arg;
4331da177e4SLinus Torvalds 	struct hci_inquiry_req ir;
4341da177e4SLinus Torvalds 	struct hci_dev *hdev;
4351da177e4SLinus Torvalds 	int err = 0, do_inquiry = 0, max_rsp;
4361da177e4SLinus Torvalds 	long timeo;
4371da177e4SLinus Torvalds 	__u8 *buf;
4381da177e4SLinus Torvalds 
4391da177e4SLinus Torvalds 	if (copy_from_user(&ir, ptr, sizeof(ir)))
4401da177e4SLinus Torvalds 		return -EFAULT;
4411da177e4SLinus Torvalds 
4425a08ecceSAndrei Emeltchenko 	hdev = hci_dev_get(ir.dev_id);
4435a08ecceSAndrei Emeltchenko 	if (!hdev)
4441da177e4SLinus Torvalds 		return -ENODEV;
4451da177e4SLinus Torvalds 
4461da177e4SLinus Torvalds 	hci_dev_lock_bh(hdev);
4471da177e4SLinus Torvalds 	if (inquiry_cache_age(hdev) > INQUIRY_CACHE_AGE_MAX ||
4481da177e4SLinus Torvalds 				inquiry_cache_empty(hdev) ||
4491da177e4SLinus Torvalds 				ir.flags & IREQ_CACHE_FLUSH) {
4501da177e4SLinus Torvalds 		inquiry_cache_flush(hdev);
4511da177e4SLinus Torvalds 		do_inquiry = 1;
4521da177e4SLinus Torvalds 	}
4531da177e4SLinus Torvalds 	hci_dev_unlock_bh(hdev);
4541da177e4SLinus Torvalds 
45504837f64SMarcel Holtmann 	timeo = ir.length * msecs_to_jiffies(2000);
45670f23020SAndrei Emeltchenko 
45770f23020SAndrei Emeltchenko 	if (do_inquiry) {
45870f23020SAndrei Emeltchenko 		err = hci_request(hdev, hci_inq_req, (unsigned long)&ir, timeo);
45970f23020SAndrei Emeltchenko 		if (err < 0)
4601da177e4SLinus Torvalds 			goto done;
46170f23020SAndrei Emeltchenko 	}
4621da177e4SLinus Torvalds 
4631da177e4SLinus Torvalds 	/* for unlimited number of responses we will use buffer with 255 entries */
4641da177e4SLinus Torvalds 	max_rsp = (ir.num_rsp == 0) ? 255 : ir.num_rsp;
4651da177e4SLinus Torvalds 
4661da177e4SLinus Torvalds 	/* cache_dump can't sleep. Therefore we allocate temp buffer and then
4671da177e4SLinus Torvalds 	 * copy it to the user space.
4681da177e4SLinus Torvalds 	 */
46970f23020SAndrei Emeltchenko 	buf = kmalloc(sizeof(struct inquiry_info) * max_rsp, GFP_KERNEL);
47070f23020SAndrei Emeltchenko 	if (!buf) {
4711da177e4SLinus Torvalds 		err = -ENOMEM;
4721da177e4SLinus Torvalds 		goto done;
4731da177e4SLinus Torvalds 	}
4741da177e4SLinus Torvalds 
4751da177e4SLinus Torvalds 	hci_dev_lock_bh(hdev);
4761da177e4SLinus Torvalds 	ir.num_rsp = inquiry_cache_dump(hdev, max_rsp, buf);
4771da177e4SLinus Torvalds 	hci_dev_unlock_bh(hdev);
4781da177e4SLinus Torvalds 
4791da177e4SLinus Torvalds 	BT_DBG("num_rsp %d", ir.num_rsp);
4801da177e4SLinus Torvalds 
4811da177e4SLinus Torvalds 	if (!copy_to_user(ptr, &ir, sizeof(ir))) {
4821da177e4SLinus Torvalds 		ptr += sizeof(ir);
4831da177e4SLinus Torvalds 		if (copy_to_user(ptr, buf, sizeof(struct inquiry_info) *
4841da177e4SLinus Torvalds 					ir.num_rsp))
4851da177e4SLinus Torvalds 			err = -EFAULT;
4861da177e4SLinus Torvalds 	} else
4871da177e4SLinus Torvalds 		err = -EFAULT;
4881da177e4SLinus Torvalds 
4891da177e4SLinus Torvalds 	kfree(buf);
4901da177e4SLinus Torvalds 
4911da177e4SLinus Torvalds done:
4921da177e4SLinus Torvalds 	hci_dev_put(hdev);
4931da177e4SLinus Torvalds 	return err;
4941da177e4SLinus Torvalds }
4951da177e4SLinus Torvalds 
4961da177e4SLinus Torvalds /* ---- HCI ioctl helpers ---- */
4971da177e4SLinus Torvalds 
4981da177e4SLinus Torvalds int hci_dev_open(__u16 dev)
4991da177e4SLinus Torvalds {
5001da177e4SLinus Torvalds 	struct hci_dev *hdev;
5011da177e4SLinus Torvalds 	int ret = 0;
5021da177e4SLinus Torvalds 
5035a08ecceSAndrei Emeltchenko 	hdev = hci_dev_get(dev);
5045a08ecceSAndrei Emeltchenko 	if (!hdev)
5051da177e4SLinus Torvalds 		return -ENODEV;
5061da177e4SLinus Torvalds 
5071da177e4SLinus Torvalds 	BT_DBG("%s %p", hdev->name, hdev);
5081da177e4SLinus Torvalds 
5091da177e4SLinus Torvalds 	hci_req_lock(hdev);
5101da177e4SLinus Torvalds 
511611b30f7SMarcel Holtmann 	if (hdev->rfkill && rfkill_blocked(hdev->rfkill)) {
512611b30f7SMarcel Holtmann 		ret = -ERFKILL;
513611b30f7SMarcel Holtmann 		goto done;
514611b30f7SMarcel Holtmann 	}
515611b30f7SMarcel Holtmann 
5161da177e4SLinus Torvalds 	if (test_bit(HCI_UP, &hdev->flags)) {
5171da177e4SLinus Torvalds 		ret = -EALREADY;
5181da177e4SLinus Torvalds 		goto done;
5191da177e4SLinus Torvalds 	}
5201da177e4SLinus Torvalds 
5211da177e4SLinus Torvalds 	if (test_bit(HCI_QUIRK_RAW_DEVICE, &hdev->quirks))
5221da177e4SLinus Torvalds 		set_bit(HCI_RAW, &hdev->flags);
5231da177e4SLinus Torvalds 
524943da25dSMarcel Holtmann 	/* Treat all non BR/EDR controllers as raw devices for now */
525943da25dSMarcel Holtmann 	if (hdev->dev_type != HCI_BREDR)
526943da25dSMarcel Holtmann 		set_bit(HCI_RAW, &hdev->flags);
527943da25dSMarcel Holtmann 
5281da177e4SLinus Torvalds 	if (hdev->open(hdev)) {
5291da177e4SLinus Torvalds 		ret = -EIO;
5301da177e4SLinus Torvalds 		goto done;
5311da177e4SLinus Torvalds 	}
5321da177e4SLinus Torvalds 
5331da177e4SLinus Torvalds 	if (!test_bit(HCI_RAW, &hdev->flags)) {
5341da177e4SLinus Torvalds 		atomic_set(&hdev->cmd_cnt, 1);
5351da177e4SLinus Torvalds 		set_bit(HCI_INIT, &hdev->flags);
536a5040efaSJohan Hedberg 		hdev->init_last_cmd = 0;
5371da177e4SLinus Torvalds 
53804837f64SMarcel Holtmann 		ret = __hci_request(hdev, hci_init_req, 0,
53904837f64SMarcel Holtmann 					msecs_to_jiffies(HCI_INIT_TIMEOUT));
5401da177e4SLinus Torvalds 
541eead27daSAndre Guedes 		if (lmp_host_le_capable(hdev))
5426ed58ec5SVille Tervo 			ret = __hci_request(hdev, hci_le_init_req, 0,
5436ed58ec5SVille Tervo 					msecs_to_jiffies(HCI_INIT_TIMEOUT));
5446ed58ec5SVille Tervo 
5451da177e4SLinus Torvalds 		clear_bit(HCI_INIT, &hdev->flags);
5461da177e4SLinus Torvalds 	}
5471da177e4SLinus Torvalds 
5481da177e4SLinus Torvalds 	if (!ret) {
5491da177e4SLinus Torvalds 		hci_dev_hold(hdev);
5501da177e4SLinus Torvalds 		set_bit(HCI_UP, &hdev->flags);
5511da177e4SLinus Torvalds 		hci_notify(hdev, HCI_DEV_UP);
5525add6af8SJohan Hedberg 		if (!test_bit(HCI_SETUP, &hdev->flags))
5535add6af8SJohan Hedberg 			mgmt_powered(hdev->id, 1);
5541da177e4SLinus Torvalds 	} else {
5551da177e4SLinus Torvalds 		/* Init failed, cleanup */
5561da177e4SLinus Torvalds 		tasklet_kill(&hdev->rx_task);
5571da177e4SLinus Torvalds 		tasklet_kill(&hdev->tx_task);
5581da177e4SLinus Torvalds 		tasklet_kill(&hdev->cmd_task);
5591da177e4SLinus Torvalds 
5601da177e4SLinus Torvalds 		skb_queue_purge(&hdev->cmd_q);
5611da177e4SLinus Torvalds 		skb_queue_purge(&hdev->rx_q);
5621da177e4SLinus Torvalds 
5631da177e4SLinus Torvalds 		if (hdev->flush)
5641da177e4SLinus Torvalds 			hdev->flush(hdev);
5651da177e4SLinus Torvalds 
5661da177e4SLinus Torvalds 		if (hdev->sent_cmd) {
5671da177e4SLinus Torvalds 			kfree_skb(hdev->sent_cmd);
5681da177e4SLinus Torvalds 			hdev->sent_cmd = NULL;
5691da177e4SLinus Torvalds 		}
5701da177e4SLinus Torvalds 
5711da177e4SLinus Torvalds 		hdev->close(hdev);
5721da177e4SLinus Torvalds 		hdev->flags = 0;
5731da177e4SLinus Torvalds 	}
5741da177e4SLinus Torvalds 
5751da177e4SLinus Torvalds done:
5761da177e4SLinus Torvalds 	hci_req_unlock(hdev);
5771da177e4SLinus Torvalds 	hci_dev_put(hdev);
5781da177e4SLinus Torvalds 	return ret;
5791da177e4SLinus Torvalds }
5801da177e4SLinus Torvalds 
5811da177e4SLinus Torvalds static int hci_dev_do_close(struct hci_dev *hdev)
5821da177e4SLinus Torvalds {
5831da177e4SLinus Torvalds 	BT_DBG("%s %p", hdev->name, hdev);
5841da177e4SLinus Torvalds 
5851da177e4SLinus Torvalds 	hci_req_cancel(hdev, ENODEV);
5861da177e4SLinus Torvalds 	hci_req_lock(hdev);
5871da177e4SLinus Torvalds 
5881da177e4SLinus Torvalds 	if (!test_and_clear_bit(HCI_UP, &hdev->flags)) {
589b79f44c1SVinicius Costa Gomes 		del_timer_sync(&hdev->cmd_timer);
5901da177e4SLinus Torvalds 		hci_req_unlock(hdev);
5911da177e4SLinus Torvalds 		return 0;
5921da177e4SLinus Torvalds 	}
5931da177e4SLinus Torvalds 
5941da177e4SLinus Torvalds 	/* Kill RX and TX tasks */
5951da177e4SLinus Torvalds 	tasklet_kill(&hdev->rx_task);
5961da177e4SLinus Torvalds 	tasklet_kill(&hdev->tx_task);
5971da177e4SLinus Torvalds 
5981da177e4SLinus Torvalds 	hci_dev_lock_bh(hdev);
5991da177e4SLinus Torvalds 	inquiry_cache_flush(hdev);
6001da177e4SLinus Torvalds 	hci_conn_hash_flush(hdev);
6011da177e4SLinus Torvalds 	hci_dev_unlock_bh(hdev);
6021da177e4SLinus Torvalds 
6031da177e4SLinus Torvalds 	hci_notify(hdev, HCI_DEV_DOWN);
6041da177e4SLinus Torvalds 
6051da177e4SLinus Torvalds 	if (hdev->flush)
6061da177e4SLinus Torvalds 		hdev->flush(hdev);
6071da177e4SLinus Torvalds 
6081da177e4SLinus Torvalds 	/* Reset device */
6091da177e4SLinus Torvalds 	skb_queue_purge(&hdev->cmd_q);
6101da177e4SLinus Torvalds 	atomic_set(&hdev->cmd_cnt, 1);
6111da177e4SLinus Torvalds 	if (!test_bit(HCI_RAW, &hdev->flags)) {
6121da177e4SLinus Torvalds 		set_bit(HCI_INIT, &hdev->flags);
61304837f64SMarcel Holtmann 		__hci_request(hdev, hci_reset_req, 0,
61404837f64SMarcel Holtmann 					msecs_to_jiffies(250));
6151da177e4SLinus Torvalds 		clear_bit(HCI_INIT, &hdev->flags);
6161da177e4SLinus Torvalds 	}
6171da177e4SLinus Torvalds 
6181da177e4SLinus Torvalds 	/* Kill cmd task */
6191da177e4SLinus Torvalds 	tasklet_kill(&hdev->cmd_task);
6201da177e4SLinus Torvalds 
6211da177e4SLinus Torvalds 	/* Drop queues */
6221da177e4SLinus Torvalds 	skb_queue_purge(&hdev->rx_q);
6231da177e4SLinus Torvalds 	skb_queue_purge(&hdev->cmd_q);
6241da177e4SLinus Torvalds 	skb_queue_purge(&hdev->raw_q);
6251da177e4SLinus Torvalds 
6261da177e4SLinus Torvalds 	/* Drop last sent command */
6271da177e4SLinus Torvalds 	if (hdev->sent_cmd) {
628b79f44c1SVinicius Costa Gomes 		del_timer_sync(&hdev->cmd_timer);
6291da177e4SLinus Torvalds 		kfree_skb(hdev->sent_cmd);
6301da177e4SLinus Torvalds 		hdev->sent_cmd = NULL;
6311da177e4SLinus Torvalds 	}
6321da177e4SLinus Torvalds 
6331da177e4SLinus Torvalds 	/* After this point our queues are empty
6341da177e4SLinus Torvalds 	 * and no tasks are scheduled. */
6351da177e4SLinus Torvalds 	hdev->close(hdev);
6361da177e4SLinus Torvalds 
6375add6af8SJohan Hedberg 	mgmt_powered(hdev->id, 0);
6385add6af8SJohan Hedberg 
6391da177e4SLinus Torvalds 	/* Clear flags */
6401da177e4SLinus Torvalds 	hdev->flags = 0;
6411da177e4SLinus Torvalds 
6421da177e4SLinus Torvalds 	hci_req_unlock(hdev);
6431da177e4SLinus Torvalds 
6441da177e4SLinus Torvalds 	hci_dev_put(hdev);
6451da177e4SLinus Torvalds 	return 0;
6461da177e4SLinus Torvalds }
6471da177e4SLinus Torvalds 
6481da177e4SLinus Torvalds int hci_dev_close(__u16 dev)
6491da177e4SLinus Torvalds {
6501da177e4SLinus Torvalds 	struct hci_dev *hdev;
6511da177e4SLinus Torvalds 	int err;
6521da177e4SLinus Torvalds 
65370f23020SAndrei Emeltchenko 	hdev = hci_dev_get(dev);
65470f23020SAndrei Emeltchenko 	if (!hdev)
6551da177e4SLinus Torvalds 		return -ENODEV;
6561da177e4SLinus Torvalds 	err = hci_dev_do_close(hdev);
6571da177e4SLinus Torvalds 	hci_dev_put(hdev);
6581da177e4SLinus Torvalds 	return err;
6591da177e4SLinus Torvalds }
6601da177e4SLinus Torvalds 
6611da177e4SLinus Torvalds int hci_dev_reset(__u16 dev)
6621da177e4SLinus Torvalds {
6631da177e4SLinus Torvalds 	struct hci_dev *hdev;
6641da177e4SLinus Torvalds 	int ret = 0;
6651da177e4SLinus Torvalds 
66670f23020SAndrei Emeltchenko 	hdev = hci_dev_get(dev);
66770f23020SAndrei Emeltchenko 	if (!hdev)
6681da177e4SLinus Torvalds 		return -ENODEV;
6691da177e4SLinus Torvalds 
6701da177e4SLinus Torvalds 	hci_req_lock(hdev);
6711da177e4SLinus Torvalds 	tasklet_disable(&hdev->tx_task);
6721da177e4SLinus Torvalds 
6731da177e4SLinus Torvalds 	if (!test_bit(HCI_UP, &hdev->flags))
6741da177e4SLinus Torvalds 		goto done;
6751da177e4SLinus Torvalds 
6761da177e4SLinus Torvalds 	/* Drop queues */
6771da177e4SLinus Torvalds 	skb_queue_purge(&hdev->rx_q);
6781da177e4SLinus Torvalds 	skb_queue_purge(&hdev->cmd_q);
6791da177e4SLinus Torvalds 
6801da177e4SLinus Torvalds 	hci_dev_lock_bh(hdev);
6811da177e4SLinus Torvalds 	inquiry_cache_flush(hdev);
6821da177e4SLinus Torvalds 	hci_conn_hash_flush(hdev);
6831da177e4SLinus Torvalds 	hci_dev_unlock_bh(hdev);
6841da177e4SLinus Torvalds 
6851da177e4SLinus Torvalds 	if (hdev->flush)
6861da177e4SLinus Torvalds 		hdev->flush(hdev);
6871da177e4SLinus Torvalds 
6881da177e4SLinus Torvalds 	atomic_set(&hdev->cmd_cnt, 1);
6896ed58ec5SVille Tervo 	hdev->acl_cnt = 0; hdev->sco_cnt = 0; hdev->le_cnt = 0;
6901da177e4SLinus Torvalds 
6911da177e4SLinus Torvalds 	if (!test_bit(HCI_RAW, &hdev->flags))
69204837f64SMarcel Holtmann 		ret = __hci_request(hdev, hci_reset_req, 0,
69304837f64SMarcel Holtmann 					msecs_to_jiffies(HCI_INIT_TIMEOUT));
6941da177e4SLinus Torvalds 
6951da177e4SLinus Torvalds done:
6961da177e4SLinus Torvalds 	tasklet_enable(&hdev->tx_task);
6971da177e4SLinus Torvalds 	hci_req_unlock(hdev);
6981da177e4SLinus Torvalds 	hci_dev_put(hdev);
6991da177e4SLinus Torvalds 	return ret;
7001da177e4SLinus Torvalds }
7011da177e4SLinus Torvalds 
7021da177e4SLinus Torvalds int hci_dev_reset_stat(__u16 dev)
7031da177e4SLinus Torvalds {
7041da177e4SLinus Torvalds 	struct hci_dev *hdev;
7051da177e4SLinus Torvalds 	int ret = 0;
7061da177e4SLinus Torvalds 
70770f23020SAndrei Emeltchenko 	hdev = hci_dev_get(dev);
70870f23020SAndrei Emeltchenko 	if (!hdev)
7091da177e4SLinus Torvalds 		return -ENODEV;
7101da177e4SLinus Torvalds 
7111da177e4SLinus Torvalds 	memset(&hdev->stat, 0, sizeof(struct hci_dev_stats));
7121da177e4SLinus Torvalds 
7131da177e4SLinus Torvalds 	hci_dev_put(hdev);
7141da177e4SLinus Torvalds 
7151da177e4SLinus Torvalds 	return ret;
7161da177e4SLinus Torvalds }
7171da177e4SLinus Torvalds 
7181da177e4SLinus Torvalds int hci_dev_cmd(unsigned int cmd, void __user *arg)
7191da177e4SLinus Torvalds {
7201da177e4SLinus Torvalds 	struct hci_dev *hdev;
7211da177e4SLinus Torvalds 	struct hci_dev_req dr;
7221da177e4SLinus Torvalds 	int err = 0;
7231da177e4SLinus Torvalds 
7241da177e4SLinus Torvalds 	if (copy_from_user(&dr, arg, sizeof(dr)))
7251da177e4SLinus Torvalds 		return -EFAULT;
7261da177e4SLinus Torvalds 
72770f23020SAndrei Emeltchenko 	hdev = hci_dev_get(dr.dev_id);
72870f23020SAndrei Emeltchenko 	if (!hdev)
7291da177e4SLinus Torvalds 		return -ENODEV;
7301da177e4SLinus Torvalds 
7311da177e4SLinus Torvalds 	switch (cmd) {
7321da177e4SLinus Torvalds 	case HCISETAUTH:
73304837f64SMarcel Holtmann 		err = hci_request(hdev, hci_auth_req, dr.dev_opt,
73404837f64SMarcel Holtmann 					msecs_to_jiffies(HCI_INIT_TIMEOUT));
7351da177e4SLinus Torvalds 		break;
7361da177e4SLinus Torvalds 
7371da177e4SLinus Torvalds 	case HCISETENCRYPT:
7381da177e4SLinus Torvalds 		if (!lmp_encrypt_capable(hdev)) {
7391da177e4SLinus Torvalds 			err = -EOPNOTSUPP;
7401da177e4SLinus Torvalds 			break;
7411da177e4SLinus Torvalds 		}
7421da177e4SLinus Torvalds 
7431da177e4SLinus Torvalds 		if (!test_bit(HCI_AUTH, &hdev->flags)) {
7441da177e4SLinus Torvalds 			/* Auth must be enabled first */
74504837f64SMarcel Holtmann 			err = hci_request(hdev, hci_auth_req, dr.dev_opt,
74604837f64SMarcel Holtmann 					msecs_to_jiffies(HCI_INIT_TIMEOUT));
7471da177e4SLinus Torvalds 			if (err)
7481da177e4SLinus Torvalds 				break;
7491da177e4SLinus Torvalds 		}
7501da177e4SLinus Torvalds 
75104837f64SMarcel Holtmann 		err = hci_request(hdev, hci_encrypt_req, dr.dev_opt,
75204837f64SMarcel Holtmann 					msecs_to_jiffies(HCI_INIT_TIMEOUT));
7531da177e4SLinus Torvalds 		break;
7541da177e4SLinus Torvalds 
7551da177e4SLinus Torvalds 	case HCISETSCAN:
75604837f64SMarcel Holtmann 		err = hci_request(hdev, hci_scan_req, dr.dev_opt,
75704837f64SMarcel Holtmann 					msecs_to_jiffies(HCI_INIT_TIMEOUT));
7581da177e4SLinus Torvalds 		break;
7591da177e4SLinus Torvalds 
7601da177e4SLinus Torvalds 	case HCISETLINKPOL:
761e4e8e37cSMarcel Holtmann 		err = hci_request(hdev, hci_linkpol_req, dr.dev_opt,
762e4e8e37cSMarcel Holtmann 					msecs_to_jiffies(HCI_INIT_TIMEOUT));
7631da177e4SLinus Torvalds 		break;
7641da177e4SLinus Torvalds 
7651da177e4SLinus Torvalds 	case HCISETLINKMODE:
766e4e8e37cSMarcel Holtmann 		hdev->link_mode = ((__u16) dr.dev_opt) &
767e4e8e37cSMarcel Holtmann 					(HCI_LM_MASTER | HCI_LM_ACCEPT);
768e4e8e37cSMarcel Holtmann 		break;
769e4e8e37cSMarcel Holtmann 
770e4e8e37cSMarcel Holtmann 	case HCISETPTYPE:
771e4e8e37cSMarcel Holtmann 		hdev->pkt_type = (__u16) dr.dev_opt;
7721da177e4SLinus Torvalds 		break;
7731da177e4SLinus Torvalds 
7741da177e4SLinus Torvalds 	case HCISETACLMTU:
7751da177e4SLinus Torvalds 		hdev->acl_mtu  = *((__u16 *) &dr.dev_opt + 1);
7761da177e4SLinus Torvalds 		hdev->acl_pkts = *((__u16 *) &dr.dev_opt + 0);
7771da177e4SLinus Torvalds 		break;
7781da177e4SLinus Torvalds 
7791da177e4SLinus Torvalds 	case HCISETSCOMTU:
7801da177e4SLinus Torvalds 		hdev->sco_mtu  = *((__u16 *) &dr.dev_opt + 1);
7811da177e4SLinus Torvalds 		hdev->sco_pkts = *((__u16 *) &dr.dev_opt + 0);
7821da177e4SLinus Torvalds 		break;
7831da177e4SLinus Torvalds 
7841da177e4SLinus Torvalds 	default:
7851da177e4SLinus Torvalds 		err = -EINVAL;
7861da177e4SLinus Torvalds 		break;
7871da177e4SLinus Torvalds 	}
788e4e8e37cSMarcel Holtmann 
7891da177e4SLinus Torvalds 	hci_dev_put(hdev);
7901da177e4SLinus Torvalds 	return err;
7911da177e4SLinus Torvalds }
7921da177e4SLinus Torvalds 
7931da177e4SLinus Torvalds int hci_get_dev_list(void __user *arg)
7941da177e4SLinus Torvalds {
795*8035ded4SLuiz Augusto von Dentz 	struct hci_dev *hdev;
7961da177e4SLinus Torvalds 	struct hci_dev_list_req *dl;
7971da177e4SLinus Torvalds 	struct hci_dev_req *dr;
7981da177e4SLinus Torvalds 	int n = 0, size, err;
7991da177e4SLinus Torvalds 	__u16 dev_num;
8001da177e4SLinus Torvalds 
8011da177e4SLinus Torvalds 	if (get_user(dev_num, (__u16 __user *) arg))
8021da177e4SLinus Torvalds 		return -EFAULT;
8031da177e4SLinus Torvalds 
8041da177e4SLinus Torvalds 	if (!dev_num || dev_num > (PAGE_SIZE * 2) / sizeof(*dr))
8051da177e4SLinus Torvalds 		return -EINVAL;
8061da177e4SLinus Torvalds 
8071da177e4SLinus Torvalds 	size = sizeof(*dl) + dev_num * sizeof(*dr);
8081da177e4SLinus Torvalds 
80970f23020SAndrei Emeltchenko 	dl = kzalloc(size, GFP_KERNEL);
81070f23020SAndrei Emeltchenko 	if (!dl)
8111da177e4SLinus Torvalds 		return -ENOMEM;
8121da177e4SLinus Torvalds 
8131da177e4SLinus Torvalds 	dr = dl->dev_req;
8141da177e4SLinus Torvalds 
8151da177e4SLinus Torvalds 	read_lock_bh(&hci_dev_list_lock);
816*8035ded4SLuiz Augusto von Dentz 	list_for_each_entry(hdev, &hci_dev_list, list) {
817ab81cbf9SJohan Hedberg 		hci_del_off_timer(hdev);
818c542a06cSJohan Hedberg 
819c542a06cSJohan Hedberg 		if (!test_bit(HCI_MGMT, &hdev->flags))
820c542a06cSJohan Hedberg 			set_bit(HCI_PAIRABLE, &hdev->flags);
821c542a06cSJohan Hedberg 
8221da177e4SLinus Torvalds 		(dr + n)->dev_id  = hdev->id;
8231da177e4SLinus Torvalds 		(dr + n)->dev_opt = hdev->flags;
824c542a06cSJohan Hedberg 
8251da177e4SLinus Torvalds 		if (++n >= dev_num)
8261da177e4SLinus Torvalds 			break;
8271da177e4SLinus Torvalds 	}
8281da177e4SLinus Torvalds 	read_unlock_bh(&hci_dev_list_lock);
8291da177e4SLinus Torvalds 
8301da177e4SLinus Torvalds 	dl->dev_num = n;
8311da177e4SLinus Torvalds 	size = sizeof(*dl) + n * sizeof(*dr);
8321da177e4SLinus Torvalds 
8331da177e4SLinus Torvalds 	err = copy_to_user(arg, dl, size);
8341da177e4SLinus Torvalds 	kfree(dl);
8351da177e4SLinus Torvalds 
8361da177e4SLinus Torvalds 	return err ? -EFAULT : 0;
8371da177e4SLinus Torvalds }
8381da177e4SLinus Torvalds 
8391da177e4SLinus Torvalds int hci_get_dev_info(void __user *arg)
8401da177e4SLinus Torvalds {
8411da177e4SLinus Torvalds 	struct hci_dev *hdev;
8421da177e4SLinus Torvalds 	struct hci_dev_info di;
8431da177e4SLinus Torvalds 	int err = 0;
8441da177e4SLinus Torvalds 
8451da177e4SLinus Torvalds 	if (copy_from_user(&di, arg, sizeof(di)))
8461da177e4SLinus Torvalds 		return -EFAULT;
8471da177e4SLinus Torvalds 
84870f23020SAndrei Emeltchenko 	hdev = hci_dev_get(di.dev_id);
84970f23020SAndrei Emeltchenko 	if (!hdev)
8501da177e4SLinus Torvalds 		return -ENODEV;
8511da177e4SLinus Torvalds 
852ab81cbf9SJohan Hedberg 	hci_del_off_timer(hdev);
853ab81cbf9SJohan Hedberg 
854c542a06cSJohan Hedberg 	if (!test_bit(HCI_MGMT, &hdev->flags))
855c542a06cSJohan Hedberg 		set_bit(HCI_PAIRABLE, &hdev->flags);
856c542a06cSJohan Hedberg 
8571da177e4SLinus Torvalds 	strcpy(di.name, hdev->name);
8581da177e4SLinus Torvalds 	di.bdaddr   = hdev->bdaddr;
859943da25dSMarcel Holtmann 	di.type     = (hdev->bus & 0x0f) | (hdev->dev_type << 4);
8601da177e4SLinus Torvalds 	di.flags    = hdev->flags;
8611da177e4SLinus Torvalds 	di.pkt_type = hdev->pkt_type;
8621da177e4SLinus Torvalds 	di.acl_mtu  = hdev->acl_mtu;
8631da177e4SLinus Torvalds 	di.acl_pkts = hdev->acl_pkts;
8641da177e4SLinus Torvalds 	di.sco_mtu  = hdev->sco_mtu;
8651da177e4SLinus Torvalds 	di.sco_pkts = hdev->sco_pkts;
8661da177e4SLinus Torvalds 	di.link_policy = hdev->link_policy;
8671da177e4SLinus Torvalds 	di.link_mode   = hdev->link_mode;
8681da177e4SLinus Torvalds 
8691da177e4SLinus Torvalds 	memcpy(&di.stat, &hdev->stat, sizeof(di.stat));
8701da177e4SLinus Torvalds 	memcpy(&di.features, &hdev->features, sizeof(di.features));
8711da177e4SLinus Torvalds 
8721da177e4SLinus Torvalds 	if (copy_to_user(arg, &di, sizeof(di)))
8731da177e4SLinus Torvalds 		err = -EFAULT;
8741da177e4SLinus Torvalds 
8751da177e4SLinus Torvalds 	hci_dev_put(hdev);
8761da177e4SLinus Torvalds 
8771da177e4SLinus Torvalds 	return err;
8781da177e4SLinus Torvalds }
8791da177e4SLinus Torvalds 
8801da177e4SLinus Torvalds /* ---- Interface to HCI drivers ---- */
8811da177e4SLinus Torvalds 
882611b30f7SMarcel Holtmann static int hci_rfkill_set_block(void *data, bool blocked)
883611b30f7SMarcel Holtmann {
884611b30f7SMarcel Holtmann 	struct hci_dev *hdev = data;
885611b30f7SMarcel Holtmann 
886611b30f7SMarcel Holtmann 	BT_DBG("%p name %s blocked %d", hdev, hdev->name, blocked);
887611b30f7SMarcel Holtmann 
888611b30f7SMarcel Holtmann 	if (!blocked)
889611b30f7SMarcel Holtmann 		return 0;
890611b30f7SMarcel Holtmann 
891611b30f7SMarcel Holtmann 	hci_dev_do_close(hdev);
892611b30f7SMarcel Holtmann 
893611b30f7SMarcel Holtmann 	return 0;
894611b30f7SMarcel Holtmann }
895611b30f7SMarcel Holtmann 
896611b30f7SMarcel Holtmann static const struct rfkill_ops hci_rfkill_ops = {
897611b30f7SMarcel Holtmann 	.set_block = hci_rfkill_set_block,
898611b30f7SMarcel Holtmann };
899611b30f7SMarcel Holtmann 
9001da177e4SLinus Torvalds /* Alloc HCI device */
9011da177e4SLinus Torvalds struct hci_dev *hci_alloc_dev(void)
9021da177e4SLinus Torvalds {
9031da177e4SLinus Torvalds 	struct hci_dev *hdev;
9041da177e4SLinus Torvalds 
90525ea6db0SMarcel Holtmann 	hdev = kzalloc(sizeof(struct hci_dev), GFP_KERNEL);
9061da177e4SLinus Torvalds 	if (!hdev)
9071da177e4SLinus Torvalds 		return NULL;
9081da177e4SLinus Torvalds 
9090ac7e700SDavid Herrmann 	hci_init_sysfs(hdev);
9101da177e4SLinus Torvalds 	skb_queue_head_init(&hdev->driver_init);
9111da177e4SLinus Torvalds 
9121da177e4SLinus Torvalds 	return hdev;
9131da177e4SLinus Torvalds }
9141da177e4SLinus Torvalds EXPORT_SYMBOL(hci_alloc_dev);
9151da177e4SLinus Torvalds 
9161da177e4SLinus Torvalds /* Free HCI device */
9171da177e4SLinus Torvalds void hci_free_dev(struct hci_dev *hdev)
9181da177e4SLinus Torvalds {
9191da177e4SLinus Torvalds 	skb_queue_purge(&hdev->driver_init);
9201da177e4SLinus Torvalds 
921a91f2e39SMarcel Holtmann 	/* will free via device release */
922a91f2e39SMarcel Holtmann 	put_device(&hdev->dev);
9231da177e4SLinus Torvalds }
9241da177e4SLinus Torvalds EXPORT_SYMBOL(hci_free_dev);
9251da177e4SLinus Torvalds 
926ab81cbf9SJohan Hedberg static void hci_power_on(struct work_struct *work)
927ab81cbf9SJohan Hedberg {
928ab81cbf9SJohan Hedberg 	struct hci_dev *hdev = container_of(work, struct hci_dev, power_on);
929ab81cbf9SJohan Hedberg 
930ab81cbf9SJohan Hedberg 	BT_DBG("%s", hdev->name);
931ab81cbf9SJohan Hedberg 
932ab81cbf9SJohan Hedberg 	if (hci_dev_open(hdev->id) < 0)
933ab81cbf9SJohan Hedberg 		return;
934ab81cbf9SJohan Hedberg 
935ab81cbf9SJohan Hedberg 	if (test_bit(HCI_AUTO_OFF, &hdev->flags))
936ab81cbf9SJohan Hedberg 		mod_timer(&hdev->off_timer,
937ab81cbf9SJohan Hedberg 				jiffies + msecs_to_jiffies(AUTO_OFF_TIMEOUT));
938ab81cbf9SJohan Hedberg 
939ab81cbf9SJohan Hedberg 	if (test_and_clear_bit(HCI_SETUP, &hdev->flags))
940ab81cbf9SJohan Hedberg 		mgmt_index_added(hdev->id);
941ab81cbf9SJohan Hedberg }
942ab81cbf9SJohan Hedberg 
943ab81cbf9SJohan Hedberg static void hci_power_off(struct work_struct *work)
944ab81cbf9SJohan Hedberg {
945ab81cbf9SJohan Hedberg 	struct hci_dev *hdev = container_of(work, struct hci_dev, power_off);
946ab81cbf9SJohan Hedberg 
947ab81cbf9SJohan Hedberg 	BT_DBG("%s", hdev->name);
948ab81cbf9SJohan Hedberg 
949ab81cbf9SJohan Hedberg 	hci_dev_close(hdev->id);
950ab81cbf9SJohan Hedberg }
951ab81cbf9SJohan Hedberg 
952ab81cbf9SJohan Hedberg static void hci_auto_off(unsigned long data)
953ab81cbf9SJohan Hedberg {
954ab81cbf9SJohan Hedberg 	struct hci_dev *hdev = (struct hci_dev *) data;
955ab81cbf9SJohan Hedberg 
956ab81cbf9SJohan Hedberg 	BT_DBG("%s", hdev->name);
957ab81cbf9SJohan Hedberg 
958ab81cbf9SJohan Hedberg 	clear_bit(HCI_AUTO_OFF, &hdev->flags);
959ab81cbf9SJohan Hedberg 
960ab81cbf9SJohan Hedberg 	queue_work(hdev->workqueue, &hdev->power_off);
961ab81cbf9SJohan Hedberg }
962ab81cbf9SJohan Hedberg 
963ab81cbf9SJohan Hedberg void hci_del_off_timer(struct hci_dev *hdev)
964ab81cbf9SJohan Hedberg {
965ab81cbf9SJohan Hedberg 	BT_DBG("%s", hdev->name);
966ab81cbf9SJohan Hedberg 
967ab81cbf9SJohan Hedberg 	clear_bit(HCI_AUTO_OFF, &hdev->flags);
968ab81cbf9SJohan Hedberg 	del_timer(&hdev->off_timer);
969ab81cbf9SJohan Hedberg }
970ab81cbf9SJohan Hedberg 
9712aeb9a1aSJohan Hedberg int hci_uuids_clear(struct hci_dev *hdev)
9722aeb9a1aSJohan Hedberg {
9732aeb9a1aSJohan Hedberg 	struct list_head *p, *n;
9742aeb9a1aSJohan Hedberg 
9752aeb9a1aSJohan Hedberg 	list_for_each_safe(p, n, &hdev->uuids) {
9762aeb9a1aSJohan Hedberg 		struct bt_uuid *uuid;
9772aeb9a1aSJohan Hedberg 
9782aeb9a1aSJohan Hedberg 		uuid = list_entry(p, struct bt_uuid, list);
9792aeb9a1aSJohan Hedberg 
9802aeb9a1aSJohan Hedberg 		list_del(p);
9812aeb9a1aSJohan Hedberg 		kfree(uuid);
9822aeb9a1aSJohan Hedberg 	}
9832aeb9a1aSJohan Hedberg 
9842aeb9a1aSJohan Hedberg 	return 0;
9852aeb9a1aSJohan Hedberg }
9862aeb9a1aSJohan Hedberg 
98755ed8ca1SJohan Hedberg int hci_link_keys_clear(struct hci_dev *hdev)
98855ed8ca1SJohan Hedberg {
98955ed8ca1SJohan Hedberg 	struct list_head *p, *n;
99055ed8ca1SJohan Hedberg 
99155ed8ca1SJohan Hedberg 	list_for_each_safe(p, n, &hdev->link_keys) {
99255ed8ca1SJohan Hedberg 		struct link_key *key;
99355ed8ca1SJohan Hedberg 
99455ed8ca1SJohan Hedberg 		key = list_entry(p, struct link_key, list);
99555ed8ca1SJohan Hedberg 
99655ed8ca1SJohan Hedberg 		list_del(p);
99755ed8ca1SJohan Hedberg 		kfree(key);
99855ed8ca1SJohan Hedberg 	}
99955ed8ca1SJohan Hedberg 
100055ed8ca1SJohan Hedberg 	return 0;
100155ed8ca1SJohan Hedberg }
100255ed8ca1SJohan Hedberg 
100355ed8ca1SJohan Hedberg struct link_key *hci_find_link_key(struct hci_dev *hdev, bdaddr_t *bdaddr)
100455ed8ca1SJohan Hedberg {
100555ed8ca1SJohan Hedberg 	struct link_key *k;
100655ed8ca1SJohan Hedberg 
1007*8035ded4SLuiz Augusto von Dentz 	list_for_each_entry(k, &hdev->link_keys, list)
100855ed8ca1SJohan Hedberg 		if (bacmp(bdaddr, &k->bdaddr) == 0)
100955ed8ca1SJohan Hedberg 			return k;
101055ed8ca1SJohan Hedberg 
101155ed8ca1SJohan Hedberg 	return NULL;
101255ed8ca1SJohan Hedberg }
101355ed8ca1SJohan Hedberg 
1014d25e28abSJohan Hedberg static int hci_persistent_key(struct hci_dev *hdev, struct hci_conn *conn,
1015d25e28abSJohan Hedberg 						u8 key_type, u8 old_key_type)
1016d25e28abSJohan Hedberg {
1017d25e28abSJohan Hedberg 	/* Legacy key */
1018d25e28abSJohan Hedberg 	if (key_type < 0x03)
1019d25e28abSJohan Hedberg 		return 1;
1020d25e28abSJohan Hedberg 
1021d25e28abSJohan Hedberg 	/* Debug keys are insecure so don't store them persistently */
1022d25e28abSJohan Hedberg 	if (key_type == HCI_LK_DEBUG_COMBINATION)
1023d25e28abSJohan Hedberg 		return 0;
1024d25e28abSJohan Hedberg 
1025d25e28abSJohan Hedberg 	/* Changed combination key and there's no previous one */
1026d25e28abSJohan Hedberg 	if (key_type == HCI_LK_CHANGED_COMBINATION && old_key_type == 0xff)
1027d25e28abSJohan Hedberg 		return 0;
1028d25e28abSJohan Hedberg 
1029d25e28abSJohan Hedberg 	/* Security mode 3 case */
1030d25e28abSJohan Hedberg 	if (!conn)
1031d25e28abSJohan Hedberg 		return 1;
1032d25e28abSJohan Hedberg 
1033d25e28abSJohan Hedberg 	/* Neither local nor remote side had no-bonding as requirement */
1034d25e28abSJohan Hedberg 	if (conn->auth_type > 0x01 && conn->remote_auth > 0x01)
1035d25e28abSJohan Hedberg 		return 1;
1036d25e28abSJohan Hedberg 
1037d25e28abSJohan Hedberg 	/* Local side had dedicated bonding as requirement */
1038d25e28abSJohan Hedberg 	if (conn->auth_type == 0x02 || conn->auth_type == 0x03)
1039d25e28abSJohan Hedberg 		return 1;
1040d25e28abSJohan Hedberg 
1041d25e28abSJohan Hedberg 	/* Remote side had dedicated bonding as requirement */
1042d25e28abSJohan Hedberg 	if (conn->remote_auth == 0x02 || conn->remote_auth == 0x03)
1043d25e28abSJohan Hedberg 		return 1;
1044d25e28abSJohan Hedberg 
1045d25e28abSJohan Hedberg 	/* If none of the above criteria match, then don't store the key
1046d25e28abSJohan Hedberg 	 * persistently */
1047d25e28abSJohan Hedberg 	return 0;
1048d25e28abSJohan Hedberg }
1049d25e28abSJohan Hedberg 
105075d262c2SVinicius Costa Gomes struct link_key *hci_find_ltk(struct hci_dev *hdev, __le16 ediv, u8 rand[8])
105175d262c2SVinicius Costa Gomes {
105275d262c2SVinicius Costa Gomes 	struct link_key *k;
105375d262c2SVinicius Costa Gomes 
105475d262c2SVinicius Costa Gomes 	list_for_each_entry(k, &hdev->link_keys, list) {
105575d262c2SVinicius Costa Gomes 		struct key_master_id *id;
105675d262c2SVinicius Costa Gomes 
105775d262c2SVinicius Costa Gomes 		if (k->type != HCI_LK_SMP_LTK)
105875d262c2SVinicius Costa Gomes 			continue;
105975d262c2SVinicius Costa Gomes 
106075d262c2SVinicius Costa Gomes 		if (k->dlen != sizeof(*id))
106175d262c2SVinicius Costa Gomes 			continue;
106275d262c2SVinicius Costa Gomes 
106375d262c2SVinicius Costa Gomes 		id = (void *) &k->data;
106475d262c2SVinicius Costa Gomes 		if (id->ediv == ediv &&
106575d262c2SVinicius Costa Gomes 				(memcmp(rand, id->rand, sizeof(id->rand)) == 0))
106675d262c2SVinicius Costa Gomes 			return k;
106775d262c2SVinicius Costa Gomes 	}
106875d262c2SVinicius Costa Gomes 
106975d262c2SVinicius Costa Gomes 	return NULL;
107075d262c2SVinicius Costa Gomes }
107175d262c2SVinicius Costa Gomes EXPORT_SYMBOL(hci_find_ltk);
107275d262c2SVinicius Costa Gomes 
107375d262c2SVinicius Costa Gomes struct link_key *hci_find_link_key_type(struct hci_dev *hdev,
107475d262c2SVinicius Costa Gomes 					bdaddr_t *bdaddr, u8 type)
107575d262c2SVinicius Costa Gomes {
107675d262c2SVinicius Costa Gomes 	struct link_key *k;
107775d262c2SVinicius Costa Gomes 
107875d262c2SVinicius Costa Gomes 	list_for_each_entry(k, &hdev->link_keys, list)
107975d262c2SVinicius Costa Gomes 		if (k->type == type && bacmp(bdaddr, &k->bdaddr) == 0)
108075d262c2SVinicius Costa Gomes 			return k;
108175d262c2SVinicius Costa Gomes 
108275d262c2SVinicius Costa Gomes 	return NULL;
108375d262c2SVinicius Costa Gomes }
108475d262c2SVinicius Costa Gomes EXPORT_SYMBOL(hci_find_link_key_type);
108575d262c2SVinicius Costa Gomes 
1086d25e28abSJohan Hedberg int hci_add_link_key(struct hci_dev *hdev, struct hci_conn *conn, int new_key,
1087d25e28abSJohan Hedberg 				bdaddr_t *bdaddr, u8 *val, u8 type, u8 pin_len)
108855ed8ca1SJohan Hedberg {
108955ed8ca1SJohan Hedberg 	struct link_key *key, *old_key;
10904df378a1SJohan Hedberg 	u8 old_key_type, persistent;
109155ed8ca1SJohan Hedberg 
109255ed8ca1SJohan Hedberg 	old_key = hci_find_link_key(hdev, bdaddr);
109355ed8ca1SJohan Hedberg 	if (old_key) {
109455ed8ca1SJohan Hedberg 		old_key_type = old_key->type;
109555ed8ca1SJohan Hedberg 		key = old_key;
109655ed8ca1SJohan Hedberg 	} else {
109712adcf3aSJohan Hedberg 		old_key_type = conn ? conn->key_type : 0xff;
109855ed8ca1SJohan Hedberg 		key = kzalloc(sizeof(*key), GFP_ATOMIC);
109955ed8ca1SJohan Hedberg 		if (!key)
110055ed8ca1SJohan Hedberg 			return -ENOMEM;
110155ed8ca1SJohan Hedberg 		list_add(&key->list, &hdev->link_keys);
110255ed8ca1SJohan Hedberg 	}
110355ed8ca1SJohan Hedberg 
110455ed8ca1SJohan Hedberg 	BT_DBG("%s key for %s type %u", hdev->name, batostr(bdaddr), type);
110555ed8ca1SJohan Hedberg 
1106d25e28abSJohan Hedberg 	/* Some buggy controller combinations generate a changed
1107d25e28abSJohan Hedberg 	 * combination key for legacy pairing even when there's no
1108d25e28abSJohan Hedberg 	 * previous key */
1109d25e28abSJohan Hedberg 	if (type == HCI_LK_CHANGED_COMBINATION &&
1110d25e28abSJohan Hedberg 					(!conn || conn->remote_auth == 0xff) &&
1111655fe6ecSJohan Hedberg 					old_key_type == 0xff) {
1112d25e28abSJohan Hedberg 		type = HCI_LK_COMBINATION;
1113655fe6ecSJohan Hedberg 		if (conn)
1114655fe6ecSJohan Hedberg 			conn->key_type = type;
1115655fe6ecSJohan Hedberg 	}
1116d25e28abSJohan Hedberg 
111755ed8ca1SJohan Hedberg 	bacpy(&key->bdaddr, bdaddr);
111855ed8ca1SJohan Hedberg 	memcpy(key->val, val, 16);
111955ed8ca1SJohan Hedberg 	key->pin_len = pin_len;
112055ed8ca1SJohan Hedberg 
1121b6020ba0SWaldemar Rymarkiewicz 	if (type == HCI_LK_CHANGED_COMBINATION)
112255ed8ca1SJohan Hedberg 		key->type = old_key_type;
11234748fed2SJohan Hedberg 	else
11244748fed2SJohan Hedberg 		key->type = type;
11254748fed2SJohan Hedberg 
11264df378a1SJohan Hedberg 	if (!new_key)
11274df378a1SJohan Hedberg 		return 0;
11284df378a1SJohan Hedberg 
11294df378a1SJohan Hedberg 	persistent = hci_persistent_key(hdev, conn, type, old_key_type);
11304df378a1SJohan Hedberg 
11314df378a1SJohan Hedberg 	mgmt_new_key(hdev->id, key, persistent);
11324df378a1SJohan Hedberg 
11334df378a1SJohan Hedberg 	if (!persistent) {
11344df378a1SJohan Hedberg 		list_del(&key->list);
11354df378a1SJohan Hedberg 		kfree(key);
11364df378a1SJohan Hedberg 	}
113755ed8ca1SJohan Hedberg 
113855ed8ca1SJohan Hedberg 	return 0;
113955ed8ca1SJohan Hedberg }
114055ed8ca1SJohan Hedberg 
114175d262c2SVinicius Costa Gomes int hci_add_ltk(struct hci_dev *hdev, int new_key, bdaddr_t *bdaddr,
1142726b4ffcSVinicius Costa Gomes 			u8 key_size, __le16 ediv, u8 rand[8], u8 ltk[16])
114375d262c2SVinicius Costa Gomes {
114475d262c2SVinicius Costa Gomes 	struct link_key *key, *old_key;
114575d262c2SVinicius Costa Gomes 	struct key_master_id *id;
114675d262c2SVinicius Costa Gomes 	u8 old_key_type;
114775d262c2SVinicius Costa Gomes 
114875d262c2SVinicius Costa Gomes 	BT_DBG("%s addr %s", hdev->name, batostr(bdaddr));
114975d262c2SVinicius Costa Gomes 
115075d262c2SVinicius Costa Gomes 	old_key = hci_find_link_key_type(hdev, bdaddr, HCI_LK_SMP_LTK);
115175d262c2SVinicius Costa Gomes 	if (old_key) {
115275d262c2SVinicius Costa Gomes 		key = old_key;
115375d262c2SVinicius Costa Gomes 		old_key_type = old_key->type;
115475d262c2SVinicius Costa Gomes 	} else {
115575d262c2SVinicius Costa Gomes 		key = kzalloc(sizeof(*key) + sizeof(*id), GFP_ATOMIC);
115675d262c2SVinicius Costa Gomes 		if (!key)
115775d262c2SVinicius Costa Gomes 			return -ENOMEM;
115875d262c2SVinicius Costa Gomes 		list_add(&key->list, &hdev->link_keys);
115975d262c2SVinicius Costa Gomes 		old_key_type = 0xff;
116075d262c2SVinicius Costa Gomes 	}
116175d262c2SVinicius Costa Gomes 
116275d262c2SVinicius Costa Gomes 	key->dlen = sizeof(*id);
116375d262c2SVinicius Costa Gomes 
116475d262c2SVinicius Costa Gomes 	bacpy(&key->bdaddr, bdaddr);
116575d262c2SVinicius Costa Gomes 	memcpy(key->val, ltk, sizeof(key->val));
116675d262c2SVinicius Costa Gomes 	key->type = HCI_LK_SMP_LTK;
1167726b4ffcSVinicius Costa Gomes 	key->pin_len = key_size;
116875d262c2SVinicius Costa Gomes 
116975d262c2SVinicius Costa Gomes 	id = (void *) &key->data;
117075d262c2SVinicius Costa Gomes 	id->ediv = ediv;
117175d262c2SVinicius Costa Gomes 	memcpy(id->rand, rand, sizeof(id->rand));
117275d262c2SVinicius Costa Gomes 
117375d262c2SVinicius Costa Gomes 	if (new_key)
117475d262c2SVinicius Costa Gomes 		mgmt_new_key(hdev->id, key, old_key_type);
117575d262c2SVinicius Costa Gomes 
117675d262c2SVinicius Costa Gomes 	return 0;
117775d262c2SVinicius Costa Gomes }
117875d262c2SVinicius Costa Gomes 
117955ed8ca1SJohan Hedberg int hci_remove_link_key(struct hci_dev *hdev, bdaddr_t *bdaddr)
118055ed8ca1SJohan Hedberg {
118155ed8ca1SJohan Hedberg 	struct link_key *key;
118255ed8ca1SJohan Hedberg 
118355ed8ca1SJohan Hedberg 	key = hci_find_link_key(hdev, bdaddr);
118455ed8ca1SJohan Hedberg 	if (!key)
118555ed8ca1SJohan Hedberg 		return -ENOENT;
118655ed8ca1SJohan Hedberg 
118755ed8ca1SJohan Hedberg 	BT_DBG("%s removing %s", hdev->name, batostr(bdaddr));
118855ed8ca1SJohan Hedberg 
118955ed8ca1SJohan Hedberg 	list_del(&key->list);
119055ed8ca1SJohan Hedberg 	kfree(key);
119155ed8ca1SJohan Hedberg 
119255ed8ca1SJohan Hedberg 	return 0;
119355ed8ca1SJohan Hedberg }
119455ed8ca1SJohan Hedberg 
11956bd32326SVille Tervo /* HCI command timer function */
11966bd32326SVille Tervo static void hci_cmd_timer(unsigned long arg)
11976bd32326SVille Tervo {
11986bd32326SVille Tervo 	struct hci_dev *hdev = (void *) arg;
11996bd32326SVille Tervo 
12006bd32326SVille Tervo 	BT_ERR("%s command tx timeout", hdev->name);
12016bd32326SVille Tervo 	atomic_set(&hdev->cmd_cnt, 1);
12026bd32326SVille Tervo 	tasklet_schedule(&hdev->cmd_task);
12036bd32326SVille Tervo }
12046bd32326SVille Tervo 
12052763eda6SSzymon Janc struct oob_data *hci_find_remote_oob_data(struct hci_dev *hdev,
12062763eda6SSzymon Janc 							bdaddr_t *bdaddr)
12072763eda6SSzymon Janc {
12082763eda6SSzymon Janc 	struct oob_data *data;
12092763eda6SSzymon Janc 
12102763eda6SSzymon Janc 	list_for_each_entry(data, &hdev->remote_oob_data, list)
12112763eda6SSzymon Janc 		if (bacmp(bdaddr, &data->bdaddr) == 0)
12122763eda6SSzymon Janc 			return data;
12132763eda6SSzymon Janc 
12142763eda6SSzymon Janc 	return NULL;
12152763eda6SSzymon Janc }
12162763eda6SSzymon Janc 
12172763eda6SSzymon Janc int hci_remove_remote_oob_data(struct hci_dev *hdev, bdaddr_t *bdaddr)
12182763eda6SSzymon Janc {
12192763eda6SSzymon Janc 	struct oob_data *data;
12202763eda6SSzymon Janc 
12212763eda6SSzymon Janc 	data = hci_find_remote_oob_data(hdev, bdaddr);
12222763eda6SSzymon Janc 	if (!data)
12232763eda6SSzymon Janc 		return -ENOENT;
12242763eda6SSzymon Janc 
12252763eda6SSzymon Janc 	BT_DBG("%s removing %s", hdev->name, batostr(bdaddr));
12262763eda6SSzymon Janc 
12272763eda6SSzymon Janc 	list_del(&data->list);
12282763eda6SSzymon Janc 	kfree(data);
12292763eda6SSzymon Janc 
12302763eda6SSzymon Janc 	return 0;
12312763eda6SSzymon Janc }
12322763eda6SSzymon Janc 
12332763eda6SSzymon Janc int hci_remote_oob_data_clear(struct hci_dev *hdev)
12342763eda6SSzymon Janc {
12352763eda6SSzymon Janc 	struct oob_data *data, *n;
12362763eda6SSzymon Janc 
12372763eda6SSzymon Janc 	list_for_each_entry_safe(data, n, &hdev->remote_oob_data, list) {
12382763eda6SSzymon Janc 		list_del(&data->list);
12392763eda6SSzymon Janc 		kfree(data);
12402763eda6SSzymon Janc 	}
12412763eda6SSzymon Janc 
12422763eda6SSzymon Janc 	return 0;
12432763eda6SSzymon Janc }
12442763eda6SSzymon Janc 
12452763eda6SSzymon Janc int hci_add_remote_oob_data(struct hci_dev *hdev, bdaddr_t *bdaddr, u8 *hash,
12462763eda6SSzymon Janc 								u8 *randomizer)
12472763eda6SSzymon Janc {
12482763eda6SSzymon Janc 	struct oob_data *data;
12492763eda6SSzymon Janc 
12502763eda6SSzymon Janc 	data = hci_find_remote_oob_data(hdev, bdaddr);
12512763eda6SSzymon Janc 
12522763eda6SSzymon Janc 	if (!data) {
12532763eda6SSzymon Janc 		data = kmalloc(sizeof(*data), GFP_ATOMIC);
12542763eda6SSzymon Janc 		if (!data)
12552763eda6SSzymon Janc 			return -ENOMEM;
12562763eda6SSzymon Janc 
12572763eda6SSzymon Janc 		bacpy(&data->bdaddr, bdaddr);
12582763eda6SSzymon Janc 		list_add(&data->list, &hdev->remote_oob_data);
12592763eda6SSzymon Janc 	}
12602763eda6SSzymon Janc 
12612763eda6SSzymon Janc 	memcpy(data->hash, hash, sizeof(data->hash));
12622763eda6SSzymon Janc 	memcpy(data->randomizer, randomizer, sizeof(data->randomizer));
12632763eda6SSzymon Janc 
12642763eda6SSzymon Janc 	BT_DBG("%s for %s", hdev->name, batostr(bdaddr));
12652763eda6SSzymon Janc 
12662763eda6SSzymon Janc 	return 0;
12672763eda6SSzymon Janc }
12682763eda6SSzymon Janc 
1269b2a66aadSAntti Julku struct bdaddr_list *hci_blacklist_lookup(struct hci_dev *hdev,
1270b2a66aadSAntti Julku 						bdaddr_t *bdaddr)
1271b2a66aadSAntti Julku {
1272b2a66aadSAntti Julku 	struct bdaddr_list *b;
1273b2a66aadSAntti Julku 
1274*8035ded4SLuiz Augusto von Dentz 	list_for_each_entry(b, &hdev->blacklist, list)
1275b2a66aadSAntti Julku 		if (bacmp(bdaddr, &b->bdaddr) == 0)
1276b2a66aadSAntti Julku 			return b;
1277b2a66aadSAntti Julku 
1278b2a66aadSAntti Julku 	return NULL;
1279b2a66aadSAntti Julku }
1280b2a66aadSAntti Julku 
1281b2a66aadSAntti Julku int hci_blacklist_clear(struct hci_dev *hdev)
1282b2a66aadSAntti Julku {
1283b2a66aadSAntti Julku 	struct list_head *p, *n;
1284b2a66aadSAntti Julku 
1285b2a66aadSAntti Julku 	list_for_each_safe(p, n, &hdev->blacklist) {
1286b2a66aadSAntti Julku 		struct bdaddr_list *b;
1287b2a66aadSAntti Julku 
1288b2a66aadSAntti Julku 		b = list_entry(p, struct bdaddr_list, list);
1289b2a66aadSAntti Julku 
1290b2a66aadSAntti Julku 		list_del(p);
1291b2a66aadSAntti Julku 		kfree(b);
1292b2a66aadSAntti Julku 	}
1293b2a66aadSAntti Julku 
1294b2a66aadSAntti Julku 	return 0;
1295b2a66aadSAntti Julku }
1296b2a66aadSAntti Julku 
1297b2a66aadSAntti Julku int hci_blacklist_add(struct hci_dev *hdev, bdaddr_t *bdaddr)
1298b2a66aadSAntti Julku {
1299b2a66aadSAntti Julku 	struct bdaddr_list *entry;
1300b2a66aadSAntti Julku 
1301b2a66aadSAntti Julku 	if (bacmp(bdaddr, BDADDR_ANY) == 0)
1302b2a66aadSAntti Julku 		return -EBADF;
1303b2a66aadSAntti Julku 
13045e762444SAntti Julku 	if (hci_blacklist_lookup(hdev, bdaddr))
13055e762444SAntti Julku 		return -EEXIST;
1306b2a66aadSAntti Julku 
1307b2a66aadSAntti Julku 	entry = kzalloc(sizeof(struct bdaddr_list), GFP_KERNEL);
13085e762444SAntti Julku 	if (!entry)
13095e762444SAntti Julku 		return -ENOMEM;
1310b2a66aadSAntti Julku 
1311b2a66aadSAntti Julku 	bacpy(&entry->bdaddr, bdaddr);
1312b2a66aadSAntti Julku 
1313b2a66aadSAntti Julku 	list_add(&entry->list, &hdev->blacklist);
1314b2a66aadSAntti Julku 
13155e762444SAntti Julku 	return mgmt_device_blocked(hdev->id, bdaddr);
1316b2a66aadSAntti Julku }
1317b2a66aadSAntti Julku 
1318b2a66aadSAntti Julku int hci_blacklist_del(struct hci_dev *hdev, bdaddr_t *bdaddr)
1319b2a66aadSAntti Julku {
1320b2a66aadSAntti Julku 	struct bdaddr_list *entry;
1321b2a66aadSAntti Julku 
1322a7925bd2SGustavo F. Padovan 	if (bacmp(bdaddr, BDADDR_ANY) == 0) {
13235e762444SAntti Julku 		return hci_blacklist_clear(hdev);
1324a7925bd2SGustavo F. Padovan 	}
1325b2a66aadSAntti Julku 
1326b2a66aadSAntti Julku 	entry = hci_blacklist_lookup(hdev, bdaddr);
1327a7925bd2SGustavo F. Padovan 	if (!entry) {
13285e762444SAntti Julku 		return -ENOENT;
1329a7925bd2SGustavo F. Padovan 	}
1330b2a66aadSAntti Julku 
1331b2a66aadSAntti Julku 	list_del(&entry->list);
1332b2a66aadSAntti Julku 	kfree(entry);
1333b2a66aadSAntti Julku 
13345e762444SAntti Julku 	return mgmt_device_unblocked(hdev->id, bdaddr);
1335b2a66aadSAntti Julku }
1336b2a66aadSAntti Julku 
133735815085SAndre Guedes static void hci_clear_adv_cache(unsigned long arg)
133835815085SAndre Guedes {
133935815085SAndre Guedes 	struct hci_dev *hdev = (void *) arg;
134035815085SAndre Guedes 
134135815085SAndre Guedes 	hci_dev_lock(hdev);
134235815085SAndre Guedes 
134335815085SAndre Guedes 	hci_adv_entries_clear(hdev);
134435815085SAndre Guedes 
134535815085SAndre Guedes 	hci_dev_unlock(hdev);
134635815085SAndre Guedes }
134735815085SAndre Guedes 
134876c8686fSAndre Guedes int hci_adv_entries_clear(struct hci_dev *hdev)
134976c8686fSAndre Guedes {
135076c8686fSAndre Guedes 	struct adv_entry *entry, *tmp;
135176c8686fSAndre Guedes 
135276c8686fSAndre Guedes 	list_for_each_entry_safe(entry, tmp, &hdev->adv_entries, list) {
135376c8686fSAndre Guedes 		list_del(&entry->list);
135476c8686fSAndre Guedes 		kfree(entry);
135576c8686fSAndre Guedes 	}
135676c8686fSAndre Guedes 
135776c8686fSAndre Guedes 	BT_DBG("%s adv cache cleared", hdev->name);
135876c8686fSAndre Guedes 
135976c8686fSAndre Guedes 	return 0;
136076c8686fSAndre Guedes }
136176c8686fSAndre Guedes 
136276c8686fSAndre Guedes struct adv_entry *hci_find_adv_entry(struct hci_dev *hdev, bdaddr_t *bdaddr)
136376c8686fSAndre Guedes {
136476c8686fSAndre Guedes 	struct adv_entry *entry;
136576c8686fSAndre Guedes 
136676c8686fSAndre Guedes 	list_for_each_entry(entry, &hdev->adv_entries, list)
136776c8686fSAndre Guedes 		if (bacmp(bdaddr, &entry->bdaddr) == 0)
136876c8686fSAndre Guedes 			return entry;
136976c8686fSAndre Guedes 
137076c8686fSAndre Guedes 	return NULL;
137176c8686fSAndre Guedes }
137276c8686fSAndre Guedes 
137376c8686fSAndre Guedes static inline int is_connectable_adv(u8 evt_type)
137476c8686fSAndre Guedes {
137576c8686fSAndre Guedes 	if (evt_type == ADV_IND || evt_type == ADV_DIRECT_IND)
137676c8686fSAndre Guedes 		return 1;
137776c8686fSAndre Guedes 
137876c8686fSAndre Guedes 	return 0;
137976c8686fSAndre Guedes }
138076c8686fSAndre Guedes 
138176c8686fSAndre Guedes int hci_add_adv_entry(struct hci_dev *hdev,
138276c8686fSAndre Guedes 					struct hci_ev_le_advertising_info *ev)
138376c8686fSAndre Guedes {
138476c8686fSAndre Guedes 	struct adv_entry *entry;
138576c8686fSAndre Guedes 
138676c8686fSAndre Guedes 	if (!is_connectable_adv(ev->evt_type))
138776c8686fSAndre Guedes 		return -EINVAL;
138876c8686fSAndre Guedes 
138976c8686fSAndre Guedes 	/* Only new entries should be added to adv_entries. So, if
139076c8686fSAndre Guedes 	 * bdaddr was found, don't add it. */
139176c8686fSAndre Guedes 	if (hci_find_adv_entry(hdev, &ev->bdaddr))
139276c8686fSAndre Guedes 		return 0;
139376c8686fSAndre Guedes 
139476c8686fSAndre Guedes 	entry = kzalloc(sizeof(*entry), GFP_ATOMIC);
139576c8686fSAndre Guedes 	if (!entry)
139676c8686fSAndre Guedes 		return -ENOMEM;
139776c8686fSAndre Guedes 
139876c8686fSAndre Guedes 	bacpy(&entry->bdaddr, &ev->bdaddr);
139976c8686fSAndre Guedes 	entry->bdaddr_type = ev->bdaddr_type;
140076c8686fSAndre Guedes 
140176c8686fSAndre Guedes 	list_add(&entry->list, &hdev->adv_entries);
140276c8686fSAndre Guedes 
140376c8686fSAndre Guedes 	BT_DBG("%s adv entry added: address %s type %u", hdev->name,
140476c8686fSAndre Guedes 				batostr(&entry->bdaddr), entry->bdaddr_type);
140576c8686fSAndre Guedes 
140676c8686fSAndre Guedes 	return 0;
140776c8686fSAndre Guedes }
140876c8686fSAndre Guedes 
14091da177e4SLinus Torvalds /* Register HCI device */
14101da177e4SLinus Torvalds int hci_register_dev(struct hci_dev *hdev)
14111da177e4SLinus Torvalds {
14121da177e4SLinus Torvalds 	struct list_head *head = &hci_dev_list, *p;
141333ca954dSDavid Herrmann 	int i, id = 0, error;
14141da177e4SLinus Torvalds 
1415c13854ceSMarcel Holtmann 	BT_DBG("%p name %s bus %d owner %p", hdev, hdev->name,
1416c13854ceSMarcel Holtmann 						hdev->bus, hdev->owner);
14171da177e4SLinus Torvalds 
14181da177e4SLinus Torvalds 	if (!hdev->open || !hdev->close || !hdev->destruct)
14191da177e4SLinus Torvalds 		return -EINVAL;
14201da177e4SLinus Torvalds 
14211da177e4SLinus Torvalds 	write_lock_bh(&hci_dev_list_lock);
14221da177e4SLinus Torvalds 
14231da177e4SLinus Torvalds 	/* Find first available device id */
14241da177e4SLinus Torvalds 	list_for_each(p, &hci_dev_list) {
14251da177e4SLinus Torvalds 		if (list_entry(p, struct hci_dev, list)->id != id)
14261da177e4SLinus Torvalds 			break;
14271da177e4SLinus Torvalds 		head = p; id++;
14281da177e4SLinus Torvalds 	}
14291da177e4SLinus Torvalds 
14301da177e4SLinus Torvalds 	sprintf(hdev->name, "hci%d", id);
14311da177e4SLinus Torvalds 	hdev->id = id;
14321da177e4SLinus Torvalds 	list_add(&hdev->list, head);
14331da177e4SLinus Torvalds 
14341da177e4SLinus Torvalds 	atomic_set(&hdev->refcnt, 1);
14351da177e4SLinus Torvalds 	spin_lock_init(&hdev->lock);
14361da177e4SLinus Torvalds 
14371da177e4SLinus Torvalds 	hdev->flags = 0;
14381da177e4SLinus Torvalds 	hdev->pkt_type  = (HCI_DM1 | HCI_DH1 | HCI_HV1);
14395b7f9909SMarcel Holtmann 	hdev->esco_type = (ESCO_HV1);
14401da177e4SLinus Torvalds 	hdev->link_mode = (HCI_LM_ACCEPT);
144117fa4b9dSJohan Hedberg 	hdev->io_capability = 0x03; /* No Input No Output */
14421da177e4SLinus Torvalds 
144304837f64SMarcel Holtmann 	hdev->idle_timeout = 0;
144404837f64SMarcel Holtmann 	hdev->sniff_max_interval = 800;
144504837f64SMarcel Holtmann 	hdev->sniff_min_interval = 80;
144604837f64SMarcel Holtmann 
14471da177e4SLinus Torvalds 	tasklet_init(&hdev->cmd_task, hci_cmd_task, (unsigned long) hdev);
14481da177e4SLinus Torvalds 	tasklet_init(&hdev->rx_task, hci_rx_task, (unsigned long) hdev);
14491da177e4SLinus Torvalds 	tasklet_init(&hdev->tx_task, hci_tx_task, (unsigned long) hdev);
14501da177e4SLinus Torvalds 
14511da177e4SLinus Torvalds 	skb_queue_head_init(&hdev->rx_q);
14521da177e4SLinus Torvalds 	skb_queue_head_init(&hdev->cmd_q);
14531da177e4SLinus Torvalds 	skb_queue_head_init(&hdev->raw_q);
14541da177e4SLinus Torvalds 
14556bd32326SVille Tervo 	setup_timer(&hdev->cmd_timer, hci_cmd_timer, (unsigned long) hdev);
14566bd32326SVille Tervo 
1457cd4c5391SSuraj Sumangala 	for (i = 0; i < NUM_REASSEMBLY; i++)
1458ef222013SMarcel Holtmann 		hdev->reassembly[i] = NULL;
1459ef222013SMarcel Holtmann 
14601da177e4SLinus Torvalds 	init_waitqueue_head(&hdev->req_wait_q);
1461a6a67efdSThomas Gleixner 	mutex_init(&hdev->req_lock);
14621da177e4SLinus Torvalds 
14631da177e4SLinus Torvalds 	inquiry_cache_init(hdev);
14641da177e4SLinus Torvalds 
14651da177e4SLinus Torvalds 	hci_conn_hash_init(hdev);
14661da177e4SLinus Torvalds 
1467ea4bd8baSDavid Miller 	INIT_LIST_HEAD(&hdev->blacklist);
1468f0358568SJohan Hedberg 
14692aeb9a1aSJohan Hedberg 	INIT_LIST_HEAD(&hdev->uuids);
14702aeb9a1aSJohan Hedberg 
147155ed8ca1SJohan Hedberg 	INIT_LIST_HEAD(&hdev->link_keys);
147255ed8ca1SJohan Hedberg 
14732763eda6SSzymon Janc 	INIT_LIST_HEAD(&hdev->remote_oob_data);
14742763eda6SSzymon Janc 
147576c8686fSAndre Guedes 	INIT_LIST_HEAD(&hdev->adv_entries);
147635815085SAndre Guedes 	setup_timer(&hdev->adv_timer, hci_clear_adv_cache,
147735815085SAndre Guedes 						(unsigned long) hdev);
147876c8686fSAndre Guedes 
1479ab81cbf9SJohan Hedberg 	INIT_WORK(&hdev->power_on, hci_power_on);
1480ab81cbf9SJohan Hedberg 	INIT_WORK(&hdev->power_off, hci_power_off);
1481ab81cbf9SJohan Hedberg 	setup_timer(&hdev->off_timer, hci_auto_off, (unsigned long) hdev);
1482ab81cbf9SJohan Hedberg 
14831da177e4SLinus Torvalds 	memset(&hdev->stat, 0, sizeof(struct hci_dev_stats));
14841da177e4SLinus Torvalds 
14851da177e4SLinus Torvalds 	atomic_set(&hdev->promisc, 0);
14861da177e4SLinus Torvalds 
14871da177e4SLinus Torvalds 	write_unlock_bh(&hci_dev_list_lock);
14881da177e4SLinus Torvalds 
1489f48fd9c8SMarcel Holtmann 	hdev->workqueue = create_singlethread_workqueue(hdev->name);
149033ca954dSDavid Herrmann 	if (!hdev->workqueue) {
149133ca954dSDavid Herrmann 		error = -ENOMEM;
149233ca954dSDavid Herrmann 		goto err;
149333ca954dSDavid Herrmann 	}
1494f48fd9c8SMarcel Holtmann 
149533ca954dSDavid Herrmann 	error = hci_add_sysfs(hdev);
149633ca954dSDavid Herrmann 	if (error < 0)
149733ca954dSDavid Herrmann 		goto err_wqueue;
14981da177e4SLinus Torvalds 
1499611b30f7SMarcel Holtmann 	hdev->rfkill = rfkill_alloc(hdev->name, &hdev->dev,
1500611b30f7SMarcel Holtmann 				RFKILL_TYPE_BLUETOOTH, &hci_rfkill_ops, hdev);
1501611b30f7SMarcel Holtmann 	if (hdev->rfkill) {
1502611b30f7SMarcel Holtmann 		if (rfkill_register(hdev->rfkill) < 0) {
1503611b30f7SMarcel Holtmann 			rfkill_destroy(hdev->rfkill);
1504611b30f7SMarcel Holtmann 			hdev->rfkill = NULL;
1505611b30f7SMarcel Holtmann 		}
1506611b30f7SMarcel Holtmann 	}
1507611b30f7SMarcel Holtmann 
1508ab81cbf9SJohan Hedberg 	set_bit(HCI_AUTO_OFF, &hdev->flags);
1509ab81cbf9SJohan Hedberg 	set_bit(HCI_SETUP, &hdev->flags);
1510ab81cbf9SJohan Hedberg 	queue_work(hdev->workqueue, &hdev->power_on);
1511ab81cbf9SJohan Hedberg 
15121da177e4SLinus Torvalds 	hci_notify(hdev, HCI_DEV_REG);
15131da177e4SLinus Torvalds 
15141da177e4SLinus Torvalds 	return id;
1515f48fd9c8SMarcel Holtmann 
151633ca954dSDavid Herrmann err_wqueue:
151733ca954dSDavid Herrmann 	destroy_workqueue(hdev->workqueue);
151833ca954dSDavid Herrmann err:
1519f48fd9c8SMarcel Holtmann 	write_lock_bh(&hci_dev_list_lock);
1520f48fd9c8SMarcel Holtmann 	list_del(&hdev->list);
1521f48fd9c8SMarcel Holtmann 	write_unlock_bh(&hci_dev_list_lock);
1522f48fd9c8SMarcel Holtmann 
152333ca954dSDavid Herrmann 	return error;
15241da177e4SLinus Torvalds }
15251da177e4SLinus Torvalds EXPORT_SYMBOL(hci_register_dev);
15261da177e4SLinus Torvalds 
15271da177e4SLinus Torvalds /* Unregister HCI device */
152859735631SDavid Herrmann void hci_unregister_dev(struct hci_dev *hdev)
15291da177e4SLinus Torvalds {
1530ef222013SMarcel Holtmann 	int i;
1531ef222013SMarcel Holtmann 
1532c13854ceSMarcel Holtmann 	BT_DBG("%p name %s bus %d", hdev, hdev->name, hdev->bus);
15331da177e4SLinus Torvalds 
15341da177e4SLinus Torvalds 	write_lock_bh(&hci_dev_list_lock);
15351da177e4SLinus Torvalds 	list_del(&hdev->list);
15361da177e4SLinus Torvalds 	write_unlock_bh(&hci_dev_list_lock);
15371da177e4SLinus Torvalds 
15381da177e4SLinus Torvalds 	hci_dev_do_close(hdev);
15391da177e4SLinus Torvalds 
1540cd4c5391SSuraj Sumangala 	for (i = 0; i < NUM_REASSEMBLY; i++)
1541ef222013SMarcel Holtmann 		kfree_skb(hdev->reassembly[i]);
1542ef222013SMarcel Holtmann 
1543ab81cbf9SJohan Hedberg 	if (!test_bit(HCI_INIT, &hdev->flags) &&
1544ab81cbf9SJohan Hedberg 					!test_bit(HCI_SETUP, &hdev->flags))
1545c71e97bfSJohan Hedberg 		mgmt_index_removed(hdev->id);
1546ab81cbf9SJohan Hedberg 
15471da177e4SLinus Torvalds 	hci_notify(hdev, HCI_DEV_UNREG);
15481da177e4SLinus Torvalds 
1549611b30f7SMarcel Holtmann 	if (hdev->rfkill) {
1550611b30f7SMarcel Holtmann 		rfkill_unregister(hdev->rfkill);
1551611b30f7SMarcel Holtmann 		rfkill_destroy(hdev->rfkill);
1552611b30f7SMarcel Holtmann 	}
1553611b30f7SMarcel Holtmann 
1554ce242970SDavid Herrmann 	hci_del_sysfs(hdev);
1555147e2d59SDave Young 
1556c6f3c5f7SGustavo F. Padovan 	hci_del_off_timer(hdev);
155735815085SAndre Guedes 	del_timer(&hdev->adv_timer);
1558c6f3c5f7SGustavo F. Padovan 
1559f48fd9c8SMarcel Holtmann 	destroy_workqueue(hdev->workqueue);
1560f48fd9c8SMarcel Holtmann 
1561e2e0cacbSJohan Hedberg 	hci_dev_lock_bh(hdev);
1562e2e0cacbSJohan Hedberg 	hci_blacklist_clear(hdev);
15632aeb9a1aSJohan Hedberg 	hci_uuids_clear(hdev);
156455ed8ca1SJohan Hedberg 	hci_link_keys_clear(hdev);
15652763eda6SSzymon Janc 	hci_remote_oob_data_clear(hdev);
156676c8686fSAndre Guedes 	hci_adv_entries_clear(hdev);
1567e2e0cacbSJohan Hedberg 	hci_dev_unlock_bh(hdev);
1568e2e0cacbSJohan Hedberg 
15691da177e4SLinus Torvalds 	__hci_dev_put(hdev);
15701da177e4SLinus Torvalds }
15711da177e4SLinus Torvalds EXPORT_SYMBOL(hci_unregister_dev);
15721da177e4SLinus Torvalds 
15731da177e4SLinus Torvalds /* Suspend HCI device */
15741da177e4SLinus Torvalds int hci_suspend_dev(struct hci_dev *hdev)
15751da177e4SLinus Torvalds {
15761da177e4SLinus Torvalds 	hci_notify(hdev, HCI_DEV_SUSPEND);
15771da177e4SLinus Torvalds 	return 0;
15781da177e4SLinus Torvalds }
15791da177e4SLinus Torvalds EXPORT_SYMBOL(hci_suspend_dev);
15801da177e4SLinus Torvalds 
15811da177e4SLinus Torvalds /* Resume HCI device */
15821da177e4SLinus Torvalds int hci_resume_dev(struct hci_dev *hdev)
15831da177e4SLinus Torvalds {
15841da177e4SLinus Torvalds 	hci_notify(hdev, HCI_DEV_RESUME);
15851da177e4SLinus Torvalds 	return 0;
15861da177e4SLinus Torvalds }
15871da177e4SLinus Torvalds EXPORT_SYMBOL(hci_resume_dev);
15881da177e4SLinus Torvalds 
158976bca880SMarcel Holtmann /* Receive frame from HCI drivers */
159076bca880SMarcel Holtmann int hci_recv_frame(struct sk_buff *skb)
159176bca880SMarcel Holtmann {
159276bca880SMarcel Holtmann 	struct hci_dev *hdev = (struct hci_dev *) skb->dev;
159376bca880SMarcel Holtmann 	if (!hdev || (!test_bit(HCI_UP, &hdev->flags)
159476bca880SMarcel Holtmann 				&& !test_bit(HCI_INIT, &hdev->flags))) {
159576bca880SMarcel Holtmann 		kfree_skb(skb);
159676bca880SMarcel Holtmann 		return -ENXIO;
159776bca880SMarcel Holtmann 	}
159876bca880SMarcel Holtmann 
159976bca880SMarcel Holtmann 	/* Incomming skb */
160076bca880SMarcel Holtmann 	bt_cb(skb)->incoming = 1;
160176bca880SMarcel Holtmann 
160276bca880SMarcel Holtmann 	/* Time stamp */
160376bca880SMarcel Holtmann 	__net_timestamp(skb);
160476bca880SMarcel Holtmann 
160576bca880SMarcel Holtmann 	/* Queue frame for rx task */
160676bca880SMarcel Holtmann 	skb_queue_tail(&hdev->rx_q, skb);
1607c78ae283SMarcel Holtmann 	tasklet_schedule(&hdev->rx_task);
1608c78ae283SMarcel Holtmann 
160976bca880SMarcel Holtmann 	return 0;
161076bca880SMarcel Holtmann }
161176bca880SMarcel Holtmann EXPORT_SYMBOL(hci_recv_frame);
161276bca880SMarcel Holtmann 
161333e882a5SSuraj Sumangala static int hci_reassembly(struct hci_dev *hdev, int type, void *data,
16141e429f38SGustavo F. Padovan 						  int count, __u8 index)
161533e882a5SSuraj Sumangala {
161633e882a5SSuraj Sumangala 	int len = 0;
161733e882a5SSuraj Sumangala 	int hlen = 0;
161833e882a5SSuraj Sumangala 	int remain = count;
161933e882a5SSuraj Sumangala 	struct sk_buff *skb;
162033e882a5SSuraj Sumangala 	struct bt_skb_cb *scb;
162133e882a5SSuraj Sumangala 
162233e882a5SSuraj Sumangala 	if ((type < HCI_ACLDATA_PKT || type > HCI_EVENT_PKT) ||
162333e882a5SSuraj Sumangala 				index >= NUM_REASSEMBLY)
162433e882a5SSuraj Sumangala 		return -EILSEQ;
162533e882a5SSuraj Sumangala 
162633e882a5SSuraj Sumangala 	skb = hdev->reassembly[index];
162733e882a5SSuraj Sumangala 
162833e882a5SSuraj Sumangala 	if (!skb) {
162933e882a5SSuraj Sumangala 		switch (type) {
163033e882a5SSuraj Sumangala 		case HCI_ACLDATA_PKT:
163133e882a5SSuraj Sumangala 			len = HCI_MAX_FRAME_SIZE;
163233e882a5SSuraj Sumangala 			hlen = HCI_ACL_HDR_SIZE;
163333e882a5SSuraj Sumangala 			break;
163433e882a5SSuraj Sumangala 		case HCI_EVENT_PKT:
163533e882a5SSuraj Sumangala 			len = HCI_MAX_EVENT_SIZE;
163633e882a5SSuraj Sumangala 			hlen = HCI_EVENT_HDR_SIZE;
163733e882a5SSuraj Sumangala 			break;
163833e882a5SSuraj Sumangala 		case HCI_SCODATA_PKT:
163933e882a5SSuraj Sumangala 			len = HCI_MAX_SCO_SIZE;
164033e882a5SSuraj Sumangala 			hlen = HCI_SCO_HDR_SIZE;
164133e882a5SSuraj Sumangala 			break;
164233e882a5SSuraj Sumangala 		}
164333e882a5SSuraj Sumangala 
16441e429f38SGustavo F. Padovan 		skb = bt_skb_alloc(len, GFP_ATOMIC);
164533e882a5SSuraj Sumangala 		if (!skb)
164633e882a5SSuraj Sumangala 			return -ENOMEM;
164733e882a5SSuraj Sumangala 
164833e882a5SSuraj Sumangala 		scb = (void *) skb->cb;
164933e882a5SSuraj Sumangala 		scb->expect = hlen;
165033e882a5SSuraj Sumangala 		scb->pkt_type = type;
165133e882a5SSuraj Sumangala 
165233e882a5SSuraj Sumangala 		skb->dev = (void *) hdev;
165333e882a5SSuraj Sumangala 		hdev->reassembly[index] = skb;
165433e882a5SSuraj Sumangala 	}
165533e882a5SSuraj Sumangala 
165633e882a5SSuraj Sumangala 	while (count) {
165733e882a5SSuraj Sumangala 		scb = (void *) skb->cb;
165833e882a5SSuraj Sumangala 		len = min(scb->expect, (__u16)count);
165933e882a5SSuraj Sumangala 
166033e882a5SSuraj Sumangala 		memcpy(skb_put(skb, len), data, len);
166133e882a5SSuraj Sumangala 
166233e882a5SSuraj Sumangala 		count -= len;
166333e882a5SSuraj Sumangala 		data += len;
166433e882a5SSuraj Sumangala 		scb->expect -= len;
166533e882a5SSuraj Sumangala 		remain = count;
166633e882a5SSuraj Sumangala 
166733e882a5SSuraj Sumangala 		switch (type) {
166833e882a5SSuraj Sumangala 		case HCI_EVENT_PKT:
166933e882a5SSuraj Sumangala 			if (skb->len == HCI_EVENT_HDR_SIZE) {
167033e882a5SSuraj Sumangala 				struct hci_event_hdr *h = hci_event_hdr(skb);
167133e882a5SSuraj Sumangala 				scb->expect = h->plen;
167233e882a5SSuraj Sumangala 
167333e882a5SSuraj Sumangala 				if (skb_tailroom(skb) < scb->expect) {
167433e882a5SSuraj Sumangala 					kfree_skb(skb);
167533e882a5SSuraj Sumangala 					hdev->reassembly[index] = NULL;
167633e882a5SSuraj Sumangala 					return -ENOMEM;
167733e882a5SSuraj Sumangala 				}
167833e882a5SSuraj Sumangala 			}
167933e882a5SSuraj Sumangala 			break;
168033e882a5SSuraj Sumangala 
168133e882a5SSuraj Sumangala 		case HCI_ACLDATA_PKT:
168233e882a5SSuraj Sumangala 			if (skb->len  == HCI_ACL_HDR_SIZE) {
168333e882a5SSuraj Sumangala 				struct hci_acl_hdr *h = hci_acl_hdr(skb);
168433e882a5SSuraj Sumangala 				scb->expect = __le16_to_cpu(h->dlen);
168533e882a5SSuraj Sumangala 
168633e882a5SSuraj Sumangala 				if (skb_tailroom(skb) < scb->expect) {
168733e882a5SSuraj Sumangala 					kfree_skb(skb);
168833e882a5SSuraj Sumangala 					hdev->reassembly[index] = NULL;
168933e882a5SSuraj Sumangala 					return -ENOMEM;
169033e882a5SSuraj Sumangala 				}
169133e882a5SSuraj Sumangala 			}
169233e882a5SSuraj Sumangala 			break;
169333e882a5SSuraj Sumangala 
169433e882a5SSuraj Sumangala 		case HCI_SCODATA_PKT:
169533e882a5SSuraj Sumangala 			if (skb->len == HCI_SCO_HDR_SIZE) {
169633e882a5SSuraj Sumangala 				struct hci_sco_hdr *h = hci_sco_hdr(skb);
169733e882a5SSuraj Sumangala 				scb->expect = h->dlen;
169833e882a5SSuraj Sumangala 
169933e882a5SSuraj Sumangala 				if (skb_tailroom(skb) < scb->expect) {
170033e882a5SSuraj Sumangala 					kfree_skb(skb);
170133e882a5SSuraj Sumangala 					hdev->reassembly[index] = NULL;
170233e882a5SSuraj Sumangala 					return -ENOMEM;
170333e882a5SSuraj Sumangala 				}
170433e882a5SSuraj Sumangala 			}
170533e882a5SSuraj Sumangala 			break;
170633e882a5SSuraj Sumangala 		}
170733e882a5SSuraj Sumangala 
170833e882a5SSuraj Sumangala 		if (scb->expect == 0) {
170933e882a5SSuraj Sumangala 			/* Complete frame */
171033e882a5SSuraj Sumangala 
171133e882a5SSuraj Sumangala 			bt_cb(skb)->pkt_type = type;
171233e882a5SSuraj Sumangala 			hci_recv_frame(skb);
171333e882a5SSuraj Sumangala 
171433e882a5SSuraj Sumangala 			hdev->reassembly[index] = NULL;
171533e882a5SSuraj Sumangala 			return remain;
171633e882a5SSuraj Sumangala 		}
171733e882a5SSuraj Sumangala 	}
171833e882a5SSuraj Sumangala 
171933e882a5SSuraj Sumangala 	return remain;
172033e882a5SSuraj Sumangala }
172133e882a5SSuraj Sumangala 
1722ef222013SMarcel Holtmann int hci_recv_fragment(struct hci_dev *hdev, int type, void *data, int count)
1723ef222013SMarcel Holtmann {
1724f39a3c06SSuraj Sumangala 	int rem = 0;
1725f39a3c06SSuraj Sumangala 
1726ef222013SMarcel Holtmann 	if (type < HCI_ACLDATA_PKT || type > HCI_EVENT_PKT)
1727ef222013SMarcel Holtmann 		return -EILSEQ;
1728ef222013SMarcel Holtmann 
1729da5f6c37SGustavo F. Padovan 	while (count) {
17301e429f38SGustavo F. Padovan 		rem = hci_reassembly(hdev, type, data, count, type - 1);
1731f39a3c06SSuraj Sumangala 		if (rem < 0)
1732f39a3c06SSuraj Sumangala 			return rem;
1733ef222013SMarcel Holtmann 
1734f39a3c06SSuraj Sumangala 		data += (count - rem);
1735f39a3c06SSuraj Sumangala 		count = rem;
1736f81c6224SJoe Perches 	}
1737ef222013SMarcel Holtmann 
1738f39a3c06SSuraj Sumangala 	return rem;
1739ef222013SMarcel Holtmann }
1740ef222013SMarcel Holtmann EXPORT_SYMBOL(hci_recv_fragment);
1741ef222013SMarcel Holtmann 
174299811510SSuraj Sumangala #define STREAM_REASSEMBLY 0
174399811510SSuraj Sumangala 
174499811510SSuraj Sumangala int hci_recv_stream_fragment(struct hci_dev *hdev, void *data, int count)
174599811510SSuraj Sumangala {
174699811510SSuraj Sumangala 	int type;
174799811510SSuraj Sumangala 	int rem = 0;
174899811510SSuraj Sumangala 
1749da5f6c37SGustavo F. Padovan 	while (count) {
175099811510SSuraj Sumangala 		struct sk_buff *skb = hdev->reassembly[STREAM_REASSEMBLY];
175199811510SSuraj Sumangala 
175299811510SSuraj Sumangala 		if (!skb) {
175399811510SSuraj Sumangala 			struct { char type; } *pkt;
175499811510SSuraj Sumangala 
175599811510SSuraj Sumangala 			/* Start of the frame */
175699811510SSuraj Sumangala 			pkt = data;
175799811510SSuraj Sumangala 			type = pkt->type;
175899811510SSuraj Sumangala 
175999811510SSuraj Sumangala 			data++;
176099811510SSuraj Sumangala 			count--;
176199811510SSuraj Sumangala 		} else
176299811510SSuraj Sumangala 			type = bt_cb(skb)->pkt_type;
176399811510SSuraj Sumangala 
17641e429f38SGustavo F. Padovan 		rem = hci_reassembly(hdev, type, data, count,
17651e429f38SGustavo F. Padovan 							STREAM_REASSEMBLY);
176699811510SSuraj Sumangala 		if (rem < 0)
176799811510SSuraj Sumangala 			return rem;
176899811510SSuraj Sumangala 
176999811510SSuraj Sumangala 		data += (count - rem);
177099811510SSuraj Sumangala 		count = rem;
1771f81c6224SJoe Perches 	}
177299811510SSuraj Sumangala 
177399811510SSuraj Sumangala 	return rem;
177499811510SSuraj Sumangala }
177599811510SSuraj Sumangala EXPORT_SYMBOL(hci_recv_stream_fragment);
177699811510SSuraj Sumangala 
17771da177e4SLinus Torvalds /* ---- Interface to upper protocols ---- */
17781da177e4SLinus Torvalds 
17791da177e4SLinus Torvalds /* Register/Unregister protocols.
17801da177e4SLinus Torvalds  * hci_task_lock is used to ensure that no tasks are running. */
17811da177e4SLinus Torvalds int hci_register_proto(struct hci_proto *hp)
17821da177e4SLinus Torvalds {
17831da177e4SLinus Torvalds 	int err = 0;
17841da177e4SLinus Torvalds 
17851da177e4SLinus Torvalds 	BT_DBG("%p name %s id %d", hp, hp->name, hp->id);
17861da177e4SLinus Torvalds 
17871da177e4SLinus Torvalds 	if (hp->id >= HCI_MAX_PROTO)
17881da177e4SLinus Torvalds 		return -EINVAL;
17891da177e4SLinus Torvalds 
17901da177e4SLinus Torvalds 	write_lock_bh(&hci_task_lock);
17911da177e4SLinus Torvalds 
17921da177e4SLinus Torvalds 	if (!hci_proto[hp->id])
17931da177e4SLinus Torvalds 		hci_proto[hp->id] = hp;
17941da177e4SLinus Torvalds 	else
17951da177e4SLinus Torvalds 		err = -EEXIST;
17961da177e4SLinus Torvalds 
17971da177e4SLinus Torvalds 	write_unlock_bh(&hci_task_lock);
17981da177e4SLinus Torvalds 
17991da177e4SLinus Torvalds 	return err;
18001da177e4SLinus Torvalds }
18011da177e4SLinus Torvalds EXPORT_SYMBOL(hci_register_proto);
18021da177e4SLinus Torvalds 
18031da177e4SLinus Torvalds int hci_unregister_proto(struct hci_proto *hp)
18041da177e4SLinus Torvalds {
18051da177e4SLinus Torvalds 	int err = 0;
18061da177e4SLinus Torvalds 
18071da177e4SLinus Torvalds 	BT_DBG("%p name %s id %d", hp, hp->name, hp->id);
18081da177e4SLinus Torvalds 
18091da177e4SLinus Torvalds 	if (hp->id >= HCI_MAX_PROTO)
18101da177e4SLinus Torvalds 		return -EINVAL;
18111da177e4SLinus Torvalds 
18121da177e4SLinus Torvalds 	write_lock_bh(&hci_task_lock);
18131da177e4SLinus Torvalds 
18141da177e4SLinus Torvalds 	if (hci_proto[hp->id])
18151da177e4SLinus Torvalds 		hci_proto[hp->id] = NULL;
18161da177e4SLinus Torvalds 	else
18171da177e4SLinus Torvalds 		err = -ENOENT;
18181da177e4SLinus Torvalds 
18191da177e4SLinus Torvalds 	write_unlock_bh(&hci_task_lock);
18201da177e4SLinus Torvalds 
18211da177e4SLinus Torvalds 	return err;
18221da177e4SLinus Torvalds }
18231da177e4SLinus Torvalds EXPORT_SYMBOL(hci_unregister_proto);
18241da177e4SLinus Torvalds 
18251da177e4SLinus Torvalds int hci_register_cb(struct hci_cb *cb)
18261da177e4SLinus Torvalds {
18271da177e4SLinus Torvalds 	BT_DBG("%p name %s", cb, cb->name);
18281da177e4SLinus Torvalds 
18291da177e4SLinus Torvalds 	write_lock_bh(&hci_cb_list_lock);
18301da177e4SLinus Torvalds 	list_add(&cb->list, &hci_cb_list);
18311da177e4SLinus Torvalds 	write_unlock_bh(&hci_cb_list_lock);
18321da177e4SLinus Torvalds 
18331da177e4SLinus Torvalds 	return 0;
18341da177e4SLinus Torvalds }
18351da177e4SLinus Torvalds EXPORT_SYMBOL(hci_register_cb);
18361da177e4SLinus Torvalds 
18371da177e4SLinus Torvalds int hci_unregister_cb(struct hci_cb *cb)
18381da177e4SLinus Torvalds {
18391da177e4SLinus Torvalds 	BT_DBG("%p name %s", cb, cb->name);
18401da177e4SLinus Torvalds 
18411da177e4SLinus Torvalds 	write_lock_bh(&hci_cb_list_lock);
18421da177e4SLinus Torvalds 	list_del(&cb->list);
18431da177e4SLinus Torvalds 	write_unlock_bh(&hci_cb_list_lock);
18441da177e4SLinus Torvalds 
18451da177e4SLinus Torvalds 	return 0;
18461da177e4SLinus Torvalds }
18471da177e4SLinus Torvalds EXPORT_SYMBOL(hci_unregister_cb);
18481da177e4SLinus Torvalds 
18491da177e4SLinus Torvalds static int hci_send_frame(struct sk_buff *skb)
18501da177e4SLinus Torvalds {
18511da177e4SLinus Torvalds 	struct hci_dev *hdev = (struct hci_dev *) skb->dev;
18521da177e4SLinus Torvalds 
18531da177e4SLinus Torvalds 	if (!hdev) {
18541da177e4SLinus Torvalds 		kfree_skb(skb);
18551da177e4SLinus Torvalds 		return -ENODEV;
18561da177e4SLinus Torvalds 	}
18571da177e4SLinus Torvalds 
18580d48d939SMarcel Holtmann 	BT_DBG("%s type %d len %d", hdev->name, bt_cb(skb)->pkt_type, skb->len);
18591da177e4SLinus Torvalds 
18601da177e4SLinus Torvalds 	if (atomic_read(&hdev->promisc)) {
18611da177e4SLinus Torvalds 		/* Time stamp */
1862a61bbcf2SPatrick McHardy 		__net_timestamp(skb);
18631da177e4SLinus Torvalds 
1864eec8d2bcSJohan Hedberg 		hci_send_to_sock(hdev, skb, NULL);
18651da177e4SLinus Torvalds 	}
18661da177e4SLinus Torvalds 
18671da177e4SLinus Torvalds 	/* Get rid of skb owner, prior to sending to the driver. */
18681da177e4SLinus Torvalds 	skb_orphan(skb);
18691da177e4SLinus Torvalds 
18701da177e4SLinus Torvalds 	return hdev->send(skb);
18711da177e4SLinus Torvalds }
18721da177e4SLinus Torvalds 
18731da177e4SLinus Torvalds /* Send HCI command */
1874a9de9248SMarcel Holtmann int hci_send_cmd(struct hci_dev *hdev, __u16 opcode, __u32 plen, void *param)
18751da177e4SLinus Torvalds {
18761da177e4SLinus Torvalds 	int len = HCI_COMMAND_HDR_SIZE + plen;
18771da177e4SLinus Torvalds 	struct hci_command_hdr *hdr;
18781da177e4SLinus Torvalds 	struct sk_buff *skb;
18791da177e4SLinus Torvalds 
1880a9de9248SMarcel Holtmann 	BT_DBG("%s opcode 0x%x plen %d", hdev->name, opcode, plen);
18811da177e4SLinus Torvalds 
18821da177e4SLinus Torvalds 	skb = bt_skb_alloc(len, GFP_ATOMIC);
18831da177e4SLinus Torvalds 	if (!skb) {
1884ef222013SMarcel Holtmann 		BT_ERR("%s no memory for command", hdev->name);
18851da177e4SLinus Torvalds 		return -ENOMEM;
18861da177e4SLinus Torvalds 	}
18871da177e4SLinus Torvalds 
18881da177e4SLinus Torvalds 	hdr = (struct hci_command_hdr *) skb_put(skb, HCI_COMMAND_HDR_SIZE);
1889a9de9248SMarcel Holtmann 	hdr->opcode = cpu_to_le16(opcode);
18901da177e4SLinus Torvalds 	hdr->plen   = plen;
18911da177e4SLinus Torvalds 
18921da177e4SLinus Torvalds 	if (plen)
18931da177e4SLinus Torvalds 		memcpy(skb_put(skb, plen), param, plen);
18941da177e4SLinus Torvalds 
18951da177e4SLinus Torvalds 	BT_DBG("skb len %d", skb->len);
18961da177e4SLinus Torvalds 
18970d48d939SMarcel Holtmann 	bt_cb(skb)->pkt_type = HCI_COMMAND_PKT;
18981da177e4SLinus Torvalds 	skb->dev = (void *) hdev;
1899c78ae283SMarcel Holtmann 
1900a5040efaSJohan Hedberg 	if (test_bit(HCI_INIT, &hdev->flags))
1901a5040efaSJohan Hedberg 		hdev->init_last_cmd = opcode;
1902a5040efaSJohan Hedberg 
19031da177e4SLinus Torvalds 	skb_queue_tail(&hdev->cmd_q, skb);
1904c78ae283SMarcel Holtmann 	tasklet_schedule(&hdev->cmd_task);
19051da177e4SLinus Torvalds 
19061da177e4SLinus Torvalds 	return 0;
19071da177e4SLinus Torvalds }
19081da177e4SLinus Torvalds 
19091da177e4SLinus Torvalds /* Get data from the previously sent command */
1910a9de9248SMarcel Holtmann void *hci_sent_cmd_data(struct hci_dev *hdev, __u16 opcode)
19111da177e4SLinus Torvalds {
19121da177e4SLinus Torvalds 	struct hci_command_hdr *hdr;
19131da177e4SLinus Torvalds 
19141da177e4SLinus Torvalds 	if (!hdev->sent_cmd)
19151da177e4SLinus Torvalds 		return NULL;
19161da177e4SLinus Torvalds 
19171da177e4SLinus Torvalds 	hdr = (void *) hdev->sent_cmd->data;
19181da177e4SLinus Torvalds 
1919a9de9248SMarcel Holtmann 	if (hdr->opcode != cpu_to_le16(opcode))
19201da177e4SLinus Torvalds 		return NULL;
19211da177e4SLinus Torvalds 
1922a9de9248SMarcel Holtmann 	BT_DBG("%s opcode 0x%x", hdev->name, opcode);
19231da177e4SLinus Torvalds 
19241da177e4SLinus Torvalds 	return hdev->sent_cmd->data + HCI_COMMAND_HDR_SIZE;
19251da177e4SLinus Torvalds }
19261da177e4SLinus Torvalds 
19271da177e4SLinus Torvalds /* Send ACL data */
19281da177e4SLinus Torvalds static void hci_add_acl_hdr(struct sk_buff *skb, __u16 handle, __u16 flags)
19291da177e4SLinus Torvalds {
19301da177e4SLinus Torvalds 	struct hci_acl_hdr *hdr;
19311da177e4SLinus Torvalds 	int len = skb->len;
19321da177e4SLinus Torvalds 
1933badff6d0SArnaldo Carvalho de Melo 	skb_push(skb, HCI_ACL_HDR_SIZE);
1934badff6d0SArnaldo Carvalho de Melo 	skb_reset_transport_header(skb);
19359c70220bSArnaldo Carvalho de Melo 	hdr = (struct hci_acl_hdr *)skb_transport_header(skb);
1936aca3192cSYOSHIFUJI Hideaki 	hdr->handle = cpu_to_le16(hci_handle_pack(handle, flags));
1937aca3192cSYOSHIFUJI Hideaki 	hdr->dlen   = cpu_to_le16(len);
19381da177e4SLinus Torvalds }
19391da177e4SLinus Torvalds 
19409a9c6a34SGustavo F. Padovan void hci_send_acl(struct hci_conn *conn, struct sk_buff *skb, __u16 flags)
19411da177e4SLinus Torvalds {
19421da177e4SLinus Torvalds 	struct hci_dev *hdev = conn->hdev;
19431da177e4SLinus Torvalds 	struct sk_buff *list;
19441da177e4SLinus Torvalds 
19451da177e4SLinus Torvalds 	BT_DBG("%s conn %p flags 0x%x", hdev->name, conn, flags);
19461da177e4SLinus Torvalds 
19471da177e4SLinus Torvalds 	skb->dev = (void *) hdev;
19480d48d939SMarcel Holtmann 	bt_cb(skb)->pkt_type = HCI_ACLDATA_PKT;
1949e702112fSAndrei Emeltchenko 	hci_add_acl_hdr(skb, conn->handle, flags);
19501da177e4SLinus Torvalds 
195170f23020SAndrei Emeltchenko 	list = skb_shinfo(skb)->frag_list;
195270f23020SAndrei Emeltchenko 	if (!list) {
19531da177e4SLinus Torvalds 		/* Non fragmented */
19541da177e4SLinus Torvalds 		BT_DBG("%s nonfrag skb %p len %d", hdev->name, skb, skb->len);
19551da177e4SLinus Torvalds 
19561da177e4SLinus Torvalds 		skb_queue_tail(&conn->data_q, skb);
19571da177e4SLinus Torvalds 	} else {
19581da177e4SLinus Torvalds 		/* Fragmented */
19591da177e4SLinus Torvalds 		BT_DBG("%s frag %p len %d", hdev->name, skb, skb->len);
19601da177e4SLinus Torvalds 
19611da177e4SLinus Torvalds 		skb_shinfo(skb)->frag_list = NULL;
19621da177e4SLinus Torvalds 
19631da177e4SLinus Torvalds 		/* Queue all fragments atomically */
19641da177e4SLinus Torvalds 		spin_lock_bh(&conn->data_q.lock);
19651da177e4SLinus Torvalds 
19661da177e4SLinus Torvalds 		__skb_queue_tail(&conn->data_q, skb);
1967e702112fSAndrei Emeltchenko 
1968e702112fSAndrei Emeltchenko 		flags &= ~ACL_START;
1969e702112fSAndrei Emeltchenko 		flags |= ACL_CONT;
19701da177e4SLinus Torvalds 		do {
19711da177e4SLinus Torvalds 			skb = list; list = list->next;
19721da177e4SLinus Torvalds 
19731da177e4SLinus Torvalds 			skb->dev = (void *) hdev;
19740d48d939SMarcel Holtmann 			bt_cb(skb)->pkt_type = HCI_ACLDATA_PKT;
1975e702112fSAndrei Emeltchenko 			hci_add_acl_hdr(skb, conn->handle, flags);
19761da177e4SLinus Torvalds 
19771da177e4SLinus Torvalds 			BT_DBG("%s frag %p len %d", hdev->name, skb, skb->len);
19781da177e4SLinus Torvalds 
19791da177e4SLinus Torvalds 			__skb_queue_tail(&conn->data_q, skb);
19801da177e4SLinus Torvalds 		} while (list);
19811da177e4SLinus Torvalds 
19821da177e4SLinus Torvalds 		spin_unlock_bh(&conn->data_q.lock);
19831da177e4SLinus Torvalds 	}
19841da177e4SLinus Torvalds 
1985c78ae283SMarcel Holtmann 	tasklet_schedule(&hdev->tx_task);
19861da177e4SLinus Torvalds }
19871da177e4SLinus Torvalds EXPORT_SYMBOL(hci_send_acl);
19881da177e4SLinus Torvalds 
19891da177e4SLinus Torvalds /* Send SCO data */
19900d861d8bSGustavo F. Padovan void hci_send_sco(struct hci_conn *conn, struct sk_buff *skb)
19911da177e4SLinus Torvalds {
19921da177e4SLinus Torvalds 	struct hci_dev *hdev = conn->hdev;
19931da177e4SLinus Torvalds 	struct hci_sco_hdr hdr;
19941da177e4SLinus Torvalds 
19951da177e4SLinus Torvalds 	BT_DBG("%s len %d", hdev->name, skb->len);
19961da177e4SLinus Torvalds 
1997aca3192cSYOSHIFUJI Hideaki 	hdr.handle = cpu_to_le16(conn->handle);
19981da177e4SLinus Torvalds 	hdr.dlen   = skb->len;
19991da177e4SLinus Torvalds 
2000badff6d0SArnaldo Carvalho de Melo 	skb_push(skb, HCI_SCO_HDR_SIZE);
2001badff6d0SArnaldo Carvalho de Melo 	skb_reset_transport_header(skb);
20029c70220bSArnaldo Carvalho de Melo 	memcpy(skb_transport_header(skb), &hdr, HCI_SCO_HDR_SIZE);
20031da177e4SLinus Torvalds 
20041da177e4SLinus Torvalds 	skb->dev = (void *) hdev;
20050d48d939SMarcel Holtmann 	bt_cb(skb)->pkt_type = HCI_SCODATA_PKT;
2006c78ae283SMarcel Holtmann 
20071da177e4SLinus Torvalds 	skb_queue_tail(&conn->data_q, skb);
2008c78ae283SMarcel Holtmann 	tasklet_schedule(&hdev->tx_task);
20091da177e4SLinus Torvalds }
20101da177e4SLinus Torvalds EXPORT_SYMBOL(hci_send_sco);
20111da177e4SLinus Torvalds 
20121da177e4SLinus Torvalds /* ---- HCI TX task (outgoing data) ---- */
20131da177e4SLinus Torvalds 
20141da177e4SLinus Torvalds /* HCI Connection scheduler */
20151da177e4SLinus Torvalds static inline struct hci_conn *hci_low_sent(struct hci_dev *hdev, __u8 type, int *quote)
20161da177e4SLinus Torvalds {
20171da177e4SLinus Torvalds 	struct hci_conn_hash *h = &hdev->conn_hash;
2018*8035ded4SLuiz Augusto von Dentz 	struct hci_conn *conn = NULL, *c;
20191da177e4SLinus Torvalds 	int num = 0, min = ~0;
20201da177e4SLinus Torvalds 
20211da177e4SLinus Torvalds 	/* We don't have to lock device here. Connections are always
20221da177e4SLinus Torvalds 	 * added and removed with TX task disabled. */
2023*8035ded4SLuiz Augusto von Dentz 	list_for_each_entry(c, &h->list, list) {
2024769be974SMarcel Holtmann 		if (c->type != type || skb_queue_empty(&c->data_q))
20251da177e4SLinus Torvalds 			continue;
2026769be974SMarcel Holtmann 
2027769be974SMarcel Holtmann 		if (c->state != BT_CONNECTED && c->state != BT_CONFIG)
2028769be974SMarcel Holtmann 			continue;
2029769be974SMarcel Holtmann 
20301da177e4SLinus Torvalds 		num++;
20311da177e4SLinus Torvalds 
20321da177e4SLinus Torvalds 		if (c->sent < min) {
20331da177e4SLinus Torvalds 			min  = c->sent;
20341da177e4SLinus Torvalds 			conn = c;
20351da177e4SLinus Torvalds 		}
203652087a79SLuiz Augusto von Dentz 
203752087a79SLuiz Augusto von Dentz 		if (hci_conn_num(hdev, type) == num)
203852087a79SLuiz Augusto von Dentz 			break;
20391da177e4SLinus Torvalds 	}
20401da177e4SLinus Torvalds 
20411da177e4SLinus Torvalds 	if (conn) {
20426ed58ec5SVille Tervo 		int cnt, q;
20436ed58ec5SVille Tervo 
20446ed58ec5SVille Tervo 		switch (conn->type) {
20456ed58ec5SVille Tervo 		case ACL_LINK:
20466ed58ec5SVille Tervo 			cnt = hdev->acl_cnt;
20476ed58ec5SVille Tervo 			break;
20486ed58ec5SVille Tervo 		case SCO_LINK:
20496ed58ec5SVille Tervo 		case ESCO_LINK:
20506ed58ec5SVille Tervo 			cnt = hdev->sco_cnt;
20516ed58ec5SVille Tervo 			break;
20526ed58ec5SVille Tervo 		case LE_LINK:
20536ed58ec5SVille Tervo 			cnt = hdev->le_mtu ? hdev->le_cnt : hdev->acl_cnt;
20546ed58ec5SVille Tervo 			break;
20556ed58ec5SVille Tervo 		default:
20566ed58ec5SVille Tervo 			cnt = 0;
20576ed58ec5SVille Tervo 			BT_ERR("Unknown link type");
20586ed58ec5SVille Tervo 		}
20596ed58ec5SVille Tervo 
20606ed58ec5SVille Tervo 		q = cnt / num;
20611da177e4SLinus Torvalds 		*quote = q ? q : 1;
20621da177e4SLinus Torvalds 	} else
20631da177e4SLinus Torvalds 		*quote = 0;
20641da177e4SLinus Torvalds 
20651da177e4SLinus Torvalds 	BT_DBG("conn %p quote %d", conn, *quote);
20661da177e4SLinus Torvalds 	return conn;
20671da177e4SLinus Torvalds }
20681da177e4SLinus Torvalds 
2069bae1f5d9SVille Tervo static inline void hci_link_tx_to(struct hci_dev *hdev, __u8 type)
20701da177e4SLinus Torvalds {
20711da177e4SLinus Torvalds 	struct hci_conn_hash *h = &hdev->conn_hash;
20721da177e4SLinus Torvalds 	struct hci_conn *c;
20731da177e4SLinus Torvalds 
2074bae1f5d9SVille Tervo 	BT_ERR("%s link tx timeout", hdev->name);
20751da177e4SLinus Torvalds 
20761da177e4SLinus Torvalds 	/* Kill stalled connections */
2077*8035ded4SLuiz Augusto von Dentz 	list_for_each_entry(c, &h->list, list) {
2078bae1f5d9SVille Tervo 		if (c->type == type && c->sent) {
2079bae1f5d9SVille Tervo 			BT_ERR("%s killing stalled connection %s",
20801da177e4SLinus Torvalds 				hdev->name, batostr(&c->dst));
20811da177e4SLinus Torvalds 			hci_acl_disconn(c, 0x13);
20821da177e4SLinus Torvalds 		}
20831da177e4SLinus Torvalds 	}
20841da177e4SLinus Torvalds }
20851da177e4SLinus Torvalds 
20861da177e4SLinus Torvalds static inline void hci_sched_acl(struct hci_dev *hdev)
20871da177e4SLinus Torvalds {
20881da177e4SLinus Torvalds 	struct hci_conn *conn;
20891da177e4SLinus Torvalds 	struct sk_buff *skb;
20901da177e4SLinus Torvalds 	int quote;
20911da177e4SLinus Torvalds 
20921da177e4SLinus Torvalds 	BT_DBG("%s", hdev->name);
20931da177e4SLinus Torvalds 
209452087a79SLuiz Augusto von Dentz 	if (!hci_conn_num(hdev, ACL_LINK))
209552087a79SLuiz Augusto von Dentz 		return;
209652087a79SLuiz Augusto von Dentz 
20971da177e4SLinus Torvalds 	if (!test_bit(HCI_RAW, &hdev->flags)) {
20981da177e4SLinus Torvalds 		/* ACL tx timeout must be longer than maximum
20991da177e4SLinus Torvalds 		 * link supervision timeout (40.9 seconds) */
210082453021SS.Çağlar Onur 		if (!hdev->acl_cnt && time_after(jiffies, hdev->acl_last_tx + HZ * 45))
2101bae1f5d9SVille Tervo 			hci_link_tx_to(hdev, ACL_LINK);
21021da177e4SLinus Torvalds 	}
21031da177e4SLinus Torvalds 
21041da177e4SLinus Torvalds 	while (hdev->acl_cnt && (conn = hci_low_sent(hdev, ACL_LINK, &quote))) {
21051da177e4SLinus Torvalds 		while (quote-- && (skb = skb_dequeue(&conn->data_q))) {
21061da177e4SLinus Torvalds 			BT_DBG("skb %p len %d", skb, skb->len);
210704837f64SMarcel Holtmann 
210814b12d0bSJaikumar Ganesh 			hci_conn_enter_active_mode(conn, bt_cb(skb)->force_active);
210904837f64SMarcel Holtmann 
21101da177e4SLinus Torvalds 			hci_send_frame(skb);
21111da177e4SLinus Torvalds 			hdev->acl_last_tx = jiffies;
21121da177e4SLinus Torvalds 
21131da177e4SLinus Torvalds 			hdev->acl_cnt--;
21141da177e4SLinus Torvalds 			conn->sent++;
21151da177e4SLinus Torvalds 		}
21161da177e4SLinus Torvalds 	}
21171da177e4SLinus Torvalds }
21181da177e4SLinus Torvalds 
21191da177e4SLinus Torvalds /* Schedule SCO */
21201da177e4SLinus Torvalds static inline void hci_sched_sco(struct hci_dev *hdev)
21211da177e4SLinus Torvalds {
21221da177e4SLinus Torvalds 	struct hci_conn *conn;
21231da177e4SLinus Torvalds 	struct sk_buff *skb;
21241da177e4SLinus Torvalds 	int quote;
21251da177e4SLinus Torvalds 
21261da177e4SLinus Torvalds 	BT_DBG("%s", hdev->name);
21271da177e4SLinus Torvalds 
212852087a79SLuiz Augusto von Dentz 	if (!hci_conn_num(hdev, SCO_LINK))
212952087a79SLuiz Augusto von Dentz 		return;
213052087a79SLuiz Augusto von Dentz 
21311da177e4SLinus Torvalds 	while (hdev->sco_cnt && (conn = hci_low_sent(hdev, SCO_LINK, &quote))) {
21321da177e4SLinus Torvalds 		while (quote-- && (skb = skb_dequeue(&conn->data_q))) {
21331da177e4SLinus Torvalds 			BT_DBG("skb %p len %d", skb, skb->len);
21341da177e4SLinus Torvalds 			hci_send_frame(skb);
21351da177e4SLinus Torvalds 
21361da177e4SLinus Torvalds 			conn->sent++;
21371da177e4SLinus Torvalds 			if (conn->sent == ~0)
21381da177e4SLinus Torvalds 				conn->sent = 0;
21391da177e4SLinus Torvalds 		}
21401da177e4SLinus Torvalds 	}
21411da177e4SLinus Torvalds }
21421da177e4SLinus Torvalds 
2143b6a0dc82SMarcel Holtmann static inline void hci_sched_esco(struct hci_dev *hdev)
2144b6a0dc82SMarcel Holtmann {
2145b6a0dc82SMarcel Holtmann 	struct hci_conn *conn;
2146b6a0dc82SMarcel Holtmann 	struct sk_buff *skb;
2147b6a0dc82SMarcel Holtmann 	int quote;
2148b6a0dc82SMarcel Holtmann 
2149b6a0dc82SMarcel Holtmann 	BT_DBG("%s", hdev->name);
2150b6a0dc82SMarcel Holtmann 
215152087a79SLuiz Augusto von Dentz 	if (!hci_conn_num(hdev, ESCO_LINK))
215252087a79SLuiz Augusto von Dentz 		return;
215352087a79SLuiz Augusto von Dentz 
2154b6a0dc82SMarcel Holtmann 	while (hdev->sco_cnt && (conn = hci_low_sent(hdev, ESCO_LINK, &quote))) {
2155b6a0dc82SMarcel Holtmann 		while (quote-- && (skb = skb_dequeue(&conn->data_q))) {
2156b6a0dc82SMarcel Holtmann 			BT_DBG("skb %p len %d", skb, skb->len);
2157b6a0dc82SMarcel Holtmann 			hci_send_frame(skb);
2158b6a0dc82SMarcel Holtmann 
2159b6a0dc82SMarcel Holtmann 			conn->sent++;
2160b6a0dc82SMarcel Holtmann 			if (conn->sent == ~0)
2161b6a0dc82SMarcel Holtmann 				conn->sent = 0;
2162b6a0dc82SMarcel Holtmann 		}
2163b6a0dc82SMarcel Holtmann 	}
2164b6a0dc82SMarcel Holtmann }
2165b6a0dc82SMarcel Holtmann 
21666ed58ec5SVille Tervo static inline void hci_sched_le(struct hci_dev *hdev)
21676ed58ec5SVille Tervo {
21686ed58ec5SVille Tervo 	struct hci_conn *conn;
21696ed58ec5SVille Tervo 	struct sk_buff *skb;
21706ed58ec5SVille Tervo 	int quote, cnt;
21716ed58ec5SVille Tervo 
21726ed58ec5SVille Tervo 	BT_DBG("%s", hdev->name);
21736ed58ec5SVille Tervo 
217452087a79SLuiz Augusto von Dentz 	if (!hci_conn_num(hdev, LE_LINK))
217552087a79SLuiz Augusto von Dentz 		return;
217652087a79SLuiz Augusto von Dentz 
21776ed58ec5SVille Tervo 	if (!test_bit(HCI_RAW, &hdev->flags)) {
21786ed58ec5SVille Tervo 		/* LE tx timeout must be longer than maximum
21796ed58ec5SVille Tervo 		 * link supervision timeout (40.9 seconds) */
2180bae1f5d9SVille Tervo 		if (!hdev->le_cnt && hdev->le_pkts &&
21816ed58ec5SVille Tervo 				time_after(jiffies, hdev->le_last_tx + HZ * 45))
2182bae1f5d9SVille Tervo 			hci_link_tx_to(hdev, LE_LINK);
21836ed58ec5SVille Tervo 	}
21846ed58ec5SVille Tervo 
21856ed58ec5SVille Tervo 	cnt = hdev->le_pkts ? hdev->le_cnt : hdev->acl_cnt;
21866ed58ec5SVille Tervo 	while (cnt && (conn = hci_low_sent(hdev, LE_LINK, &quote))) {
21876ed58ec5SVille Tervo 		while (quote-- && (skb = skb_dequeue(&conn->data_q))) {
21886ed58ec5SVille Tervo 			BT_DBG("skb %p len %d", skb, skb->len);
21896ed58ec5SVille Tervo 
21906ed58ec5SVille Tervo 			hci_send_frame(skb);
21916ed58ec5SVille Tervo 			hdev->le_last_tx = jiffies;
21926ed58ec5SVille Tervo 
21936ed58ec5SVille Tervo 			cnt--;
21946ed58ec5SVille Tervo 			conn->sent++;
21956ed58ec5SVille Tervo 		}
21966ed58ec5SVille Tervo 	}
21976ed58ec5SVille Tervo 	if (hdev->le_pkts)
21986ed58ec5SVille Tervo 		hdev->le_cnt = cnt;
21996ed58ec5SVille Tervo 	else
22006ed58ec5SVille Tervo 		hdev->acl_cnt = cnt;
22016ed58ec5SVille Tervo }
22026ed58ec5SVille Tervo 
22031da177e4SLinus Torvalds static void hci_tx_task(unsigned long arg)
22041da177e4SLinus Torvalds {
22051da177e4SLinus Torvalds 	struct hci_dev *hdev = (struct hci_dev *) arg;
22061da177e4SLinus Torvalds 	struct sk_buff *skb;
22071da177e4SLinus Torvalds 
22081da177e4SLinus Torvalds 	read_lock(&hci_task_lock);
22091da177e4SLinus Torvalds 
22106ed58ec5SVille Tervo 	BT_DBG("%s acl %d sco %d le %d", hdev->name, hdev->acl_cnt,
22116ed58ec5SVille Tervo 		hdev->sco_cnt, hdev->le_cnt);
22121da177e4SLinus Torvalds 
22131da177e4SLinus Torvalds 	/* Schedule queues and send stuff to HCI driver */
22141da177e4SLinus Torvalds 
22151da177e4SLinus Torvalds 	hci_sched_acl(hdev);
22161da177e4SLinus Torvalds 
22171da177e4SLinus Torvalds 	hci_sched_sco(hdev);
22181da177e4SLinus Torvalds 
2219b6a0dc82SMarcel Holtmann 	hci_sched_esco(hdev);
2220b6a0dc82SMarcel Holtmann 
22216ed58ec5SVille Tervo 	hci_sched_le(hdev);
22226ed58ec5SVille Tervo 
22231da177e4SLinus Torvalds 	/* Send next queued raw (unknown type) packet */
22241da177e4SLinus Torvalds 	while ((skb = skb_dequeue(&hdev->raw_q)))
22251da177e4SLinus Torvalds 		hci_send_frame(skb);
22261da177e4SLinus Torvalds 
22271da177e4SLinus Torvalds 	read_unlock(&hci_task_lock);
22281da177e4SLinus Torvalds }
22291da177e4SLinus Torvalds 
223025985edcSLucas De Marchi /* ----- HCI RX task (incoming data processing) ----- */
22311da177e4SLinus Torvalds 
22321da177e4SLinus Torvalds /* ACL data packet */
22331da177e4SLinus Torvalds static inline void hci_acldata_packet(struct hci_dev *hdev, struct sk_buff *skb)
22341da177e4SLinus Torvalds {
22351da177e4SLinus Torvalds 	struct hci_acl_hdr *hdr = (void *) skb->data;
22361da177e4SLinus Torvalds 	struct hci_conn *conn;
22371da177e4SLinus Torvalds 	__u16 handle, flags;
22381da177e4SLinus Torvalds 
22391da177e4SLinus Torvalds 	skb_pull(skb, HCI_ACL_HDR_SIZE);
22401da177e4SLinus Torvalds 
22411da177e4SLinus Torvalds 	handle = __le16_to_cpu(hdr->handle);
22421da177e4SLinus Torvalds 	flags  = hci_flags(handle);
22431da177e4SLinus Torvalds 	handle = hci_handle(handle);
22441da177e4SLinus Torvalds 
22451da177e4SLinus Torvalds 	BT_DBG("%s len %d handle 0x%x flags 0x%x", hdev->name, skb->len, handle, flags);
22461da177e4SLinus Torvalds 
22471da177e4SLinus Torvalds 	hdev->stat.acl_rx++;
22481da177e4SLinus Torvalds 
22491da177e4SLinus Torvalds 	hci_dev_lock(hdev);
22501da177e4SLinus Torvalds 	conn = hci_conn_hash_lookup_handle(hdev, handle);
22511da177e4SLinus Torvalds 	hci_dev_unlock(hdev);
22521da177e4SLinus Torvalds 
22531da177e4SLinus Torvalds 	if (conn) {
22541da177e4SLinus Torvalds 		register struct hci_proto *hp;
22551da177e4SLinus Torvalds 
225614b12d0bSJaikumar Ganesh 		hci_conn_enter_active_mode(conn, bt_cb(skb)->force_active);
225704837f64SMarcel Holtmann 
22581da177e4SLinus Torvalds 		/* Send to upper protocol */
225970f23020SAndrei Emeltchenko 		hp = hci_proto[HCI_PROTO_L2CAP];
226070f23020SAndrei Emeltchenko 		if (hp && hp->recv_acldata) {
22611da177e4SLinus Torvalds 			hp->recv_acldata(conn, skb, flags);
22621da177e4SLinus Torvalds 			return;
22631da177e4SLinus Torvalds 		}
22641da177e4SLinus Torvalds 	} else {
22651da177e4SLinus Torvalds 		BT_ERR("%s ACL packet for unknown connection handle %d",
22661da177e4SLinus Torvalds 			hdev->name, handle);
22671da177e4SLinus Torvalds 	}
22681da177e4SLinus Torvalds 
22691da177e4SLinus Torvalds 	kfree_skb(skb);
22701da177e4SLinus Torvalds }
22711da177e4SLinus Torvalds 
22721da177e4SLinus Torvalds /* SCO data packet */
22731da177e4SLinus Torvalds static inline void hci_scodata_packet(struct hci_dev *hdev, struct sk_buff *skb)
22741da177e4SLinus Torvalds {
22751da177e4SLinus Torvalds 	struct hci_sco_hdr *hdr = (void *) skb->data;
22761da177e4SLinus Torvalds 	struct hci_conn *conn;
22771da177e4SLinus Torvalds 	__u16 handle;
22781da177e4SLinus Torvalds 
22791da177e4SLinus Torvalds 	skb_pull(skb, HCI_SCO_HDR_SIZE);
22801da177e4SLinus Torvalds 
22811da177e4SLinus Torvalds 	handle = __le16_to_cpu(hdr->handle);
22821da177e4SLinus Torvalds 
22831da177e4SLinus Torvalds 	BT_DBG("%s len %d handle 0x%x", hdev->name, skb->len, handle);
22841da177e4SLinus Torvalds 
22851da177e4SLinus Torvalds 	hdev->stat.sco_rx++;
22861da177e4SLinus Torvalds 
22871da177e4SLinus Torvalds 	hci_dev_lock(hdev);
22881da177e4SLinus Torvalds 	conn = hci_conn_hash_lookup_handle(hdev, handle);
22891da177e4SLinus Torvalds 	hci_dev_unlock(hdev);
22901da177e4SLinus Torvalds 
22911da177e4SLinus Torvalds 	if (conn) {
22921da177e4SLinus Torvalds 		register struct hci_proto *hp;
22931da177e4SLinus Torvalds 
22941da177e4SLinus Torvalds 		/* Send to upper protocol */
229570f23020SAndrei Emeltchenko 		hp = hci_proto[HCI_PROTO_SCO];
229670f23020SAndrei Emeltchenko 		if (hp && hp->recv_scodata) {
22971da177e4SLinus Torvalds 			hp->recv_scodata(conn, skb);
22981da177e4SLinus Torvalds 			return;
22991da177e4SLinus Torvalds 		}
23001da177e4SLinus Torvalds 	} else {
23011da177e4SLinus Torvalds 		BT_ERR("%s SCO packet for unknown connection handle %d",
23021da177e4SLinus Torvalds 			hdev->name, handle);
23031da177e4SLinus Torvalds 	}
23041da177e4SLinus Torvalds 
23051da177e4SLinus Torvalds 	kfree_skb(skb);
23061da177e4SLinus Torvalds }
23071da177e4SLinus Torvalds 
23086516455dSMarcel Holtmann static void hci_rx_task(unsigned long arg)
23091da177e4SLinus Torvalds {
23101da177e4SLinus Torvalds 	struct hci_dev *hdev = (struct hci_dev *) arg;
23111da177e4SLinus Torvalds 	struct sk_buff *skb;
23121da177e4SLinus Torvalds 
23131da177e4SLinus Torvalds 	BT_DBG("%s", hdev->name);
23141da177e4SLinus Torvalds 
23151da177e4SLinus Torvalds 	read_lock(&hci_task_lock);
23161da177e4SLinus Torvalds 
23171da177e4SLinus Torvalds 	while ((skb = skb_dequeue(&hdev->rx_q))) {
23181da177e4SLinus Torvalds 		if (atomic_read(&hdev->promisc)) {
23191da177e4SLinus Torvalds 			/* Send copy to the sockets */
2320eec8d2bcSJohan Hedberg 			hci_send_to_sock(hdev, skb, NULL);
23211da177e4SLinus Torvalds 		}
23221da177e4SLinus Torvalds 
23231da177e4SLinus Torvalds 		if (test_bit(HCI_RAW, &hdev->flags)) {
23241da177e4SLinus Torvalds 			kfree_skb(skb);
23251da177e4SLinus Torvalds 			continue;
23261da177e4SLinus Torvalds 		}
23271da177e4SLinus Torvalds 
23281da177e4SLinus Torvalds 		if (test_bit(HCI_INIT, &hdev->flags)) {
23291da177e4SLinus Torvalds 			/* Don't process data packets in this states. */
23300d48d939SMarcel Holtmann 			switch (bt_cb(skb)->pkt_type) {
23311da177e4SLinus Torvalds 			case HCI_ACLDATA_PKT:
23321da177e4SLinus Torvalds 			case HCI_SCODATA_PKT:
23331da177e4SLinus Torvalds 				kfree_skb(skb);
23341da177e4SLinus Torvalds 				continue;
23353ff50b79SStephen Hemminger 			}
23361da177e4SLinus Torvalds 		}
23371da177e4SLinus Torvalds 
23381da177e4SLinus Torvalds 		/* Process frame */
23390d48d939SMarcel Holtmann 		switch (bt_cb(skb)->pkt_type) {
23401da177e4SLinus Torvalds 		case HCI_EVENT_PKT:
23411da177e4SLinus Torvalds 			hci_event_packet(hdev, skb);
23421da177e4SLinus Torvalds 			break;
23431da177e4SLinus Torvalds 
23441da177e4SLinus Torvalds 		case HCI_ACLDATA_PKT:
23451da177e4SLinus Torvalds 			BT_DBG("%s ACL data packet", hdev->name);
23461da177e4SLinus Torvalds 			hci_acldata_packet(hdev, skb);
23471da177e4SLinus Torvalds 			break;
23481da177e4SLinus Torvalds 
23491da177e4SLinus Torvalds 		case HCI_SCODATA_PKT:
23501da177e4SLinus Torvalds 			BT_DBG("%s SCO data packet", hdev->name);
23511da177e4SLinus Torvalds 			hci_scodata_packet(hdev, skb);
23521da177e4SLinus Torvalds 			break;
23531da177e4SLinus Torvalds 
23541da177e4SLinus Torvalds 		default:
23551da177e4SLinus Torvalds 			kfree_skb(skb);
23561da177e4SLinus Torvalds 			break;
23571da177e4SLinus Torvalds 		}
23581da177e4SLinus Torvalds 	}
23591da177e4SLinus Torvalds 
23601da177e4SLinus Torvalds 	read_unlock(&hci_task_lock);
23611da177e4SLinus Torvalds }
23621da177e4SLinus Torvalds 
23631da177e4SLinus Torvalds static void hci_cmd_task(unsigned long arg)
23641da177e4SLinus Torvalds {
23651da177e4SLinus Torvalds 	struct hci_dev *hdev = (struct hci_dev *) arg;
23661da177e4SLinus Torvalds 	struct sk_buff *skb;
23671da177e4SLinus Torvalds 
23681da177e4SLinus Torvalds 	BT_DBG("%s cmd %d", hdev->name, atomic_read(&hdev->cmd_cnt));
23691da177e4SLinus Torvalds 
23701da177e4SLinus Torvalds 	/* Send queued commands */
23715a08ecceSAndrei Emeltchenko 	if (atomic_read(&hdev->cmd_cnt)) {
23725a08ecceSAndrei Emeltchenko 		skb = skb_dequeue(&hdev->cmd_q);
23735a08ecceSAndrei Emeltchenko 		if (!skb)
23745a08ecceSAndrei Emeltchenko 			return;
23755a08ecceSAndrei Emeltchenko 
23761da177e4SLinus Torvalds 		kfree_skb(hdev->sent_cmd);
23771da177e4SLinus Torvalds 
237870f23020SAndrei Emeltchenko 		hdev->sent_cmd = skb_clone(skb, GFP_ATOMIC);
237970f23020SAndrei Emeltchenko 		if (hdev->sent_cmd) {
23801da177e4SLinus Torvalds 			atomic_dec(&hdev->cmd_cnt);
23811da177e4SLinus Torvalds 			hci_send_frame(skb);
23827bdb8a5cSSzymon Janc 			if (test_bit(HCI_RESET, &hdev->flags))
23837bdb8a5cSSzymon Janc 				del_timer(&hdev->cmd_timer);
23847bdb8a5cSSzymon Janc 			else
23856bd32326SVille Tervo 				mod_timer(&hdev->cmd_timer,
23866bd32326SVille Tervo 				  jiffies + msecs_to_jiffies(HCI_CMD_TIMEOUT));
23871da177e4SLinus Torvalds 		} else {
23881da177e4SLinus Torvalds 			skb_queue_head(&hdev->cmd_q, skb);
2389c78ae283SMarcel Holtmann 			tasklet_schedule(&hdev->cmd_task);
23901da177e4SLinus Torvalds 		}
23911da177e4SLinus Torvalds 	}
23921da177e4SLinus Torvalds }
2393