bfusb.c 16.7 KB
Newer Older
L
Linus Torvalds 已提交
1 2 3 4
/*
 *
 *  AVM BlueFRITZ! USB driver
 *
5
 *  Copyright (C) 2003-2006  Marcel Holtmann <marcel@holtmann.org>
L
Linus Torvalds 已提交
6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40
 *
 *
 *  This program is free software; you can redistribute it and/or modify
 *  it under the terms of the GNU General Public License as published by
 *  the Free Software Foundation; either version 2 of the License, or
 *  (at your option) any later version.
 *
 *  This program is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *  GNU General Public License for more details.
 *
 *  You should have received a copy of the GNU General Public License
 *  along with this program; if not, write to the Free Software
 *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 *
 */

#include <linux/module.h>

#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/slab.h>
#include <linux/types.h>
#include <linux/errno.h>
#include <linux/skbuff.h>

#include <linux/device.h>
#include <linux/firmware.h>

#include <linux/usb.h>

#include <net/bluetooth/bluetooth.h>
#include <net/bluetooth/hci_core.h>

41
#define VERSION "1.2"
L
Linus Torvalds 已提交
42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63

static struct usb_driver bfusb_driver;

static struct usb_device_id bfusb_table[] = {
	/* AVM BlueFRITZ! USB */
	{ USB_DEVICE(0x057c, 0x2200) },

	{ }	/* Terminating entry */
};

MODULE_DEVICE_TABLE(usb, bfusb_table);

#define BFUSB_MAX_BLOCK_SIZE	256

#define BFUSB_BLOCK_TIMEOUT	3000

#define BFUSB_TX_PROCESS	1
#define BFUSB_TX_WAKEUP		2

#define BFUSB_MAX_BULK_TX	2
#define BFUSB_MAX_BULK_RX	2

64
struct bfusb_data {
L
Linus Torvalds 已提交
65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85
	struct hci_dev		*hdev;

	unsigned long		state;

	struct usb_device	*udev;

	unsigned int		bulk_in_ep;
	unsigned int		bulk_out_ep;
	unsigned int		bulk_pkt_size;

	rwlock_t		lock;

	struct sk_buff_head	transmit_q;

	struct sk_buff		*reassembly;

	atomic_t		pending_tx;
	struct sk_buff_head	pending_q;
	struct sk_buff_head	completed_q;
};

86
struct bfusb_data_scb {
L
Linus Torvalds 已提交
87 88 89
	struct urb *urb;
};

90 91
static void bfusb_tx_complete(struct urb *urb);
static void bfusb_rx_complete(struct urb *urb);
L
Linus Torvalds 已提交
92

93
static struct urb *bfusb_get_completed(struct bfusb_data *data)
L
Linus Torvalds 已提交
94 95 96 97
{
	struct sk_buff *skb;
	struct urb *urb = NULL;

98
	BT_DBG("bfusb %p", data);
L
Linus Torvalds 已提交
99

100
	skb = skb_dequeue(&data->completed_q);
L
Linus Torvalds 已提交
101
	if (skb) {
102
		urb = ((struct bfusb_data_scb *) skb->cb)->urb;
L
Linus Torvalds 已提交
103 104 105 106 107 108
		kfree_skb(skb);
	}

	return urb;
}

109
static void bfusb_unlink_urbs(struct bfusb_data *data)
L
Linus Torvalds 已提交
110 111 112 113
{
	struct sk_buff *skb;
	struct urb *urb;

114
	BT_DBG("bfusb %p", data);
L
Linus Torvalds 已提交
115

116 117
	while ((skb = skb_dequeue(&data->pending_q))) {
		urb = ((struct bfusb_data_scb *) skb->cb)->urb;
L
Linus Torvalds 已提交
118
		usb_kill_urb(urb);
119
		skb_queue_tail(&data->completed_q, skb);
L
Linus Torvalds 已提交
120 121
	}

122
	while ((urb = bfusb_get_completed(data)))
L
Linus Torvalds 已提交
123 124 125
		usb_free_urb(urb);
}

126
static int bfusb_send_bulk(struct bfusb_data *data, struct sk_buff *skb)
L
Linus Torvalds 已提交
127
{
128 129
	struct bfusb_data_scb *scb = (void *) skb->cb;
	struct urb *urb = bfusb_get_completed(data);
L
Linus Torvalds 已提交
130 131
	int err, pipe;

132
	BT_DBG("bfusb %p skb %p len %d", data, skb, skb->len);
L
Linus Torvalds 已提交
133 134 135 136

	if (!urb && !(urb = usb_alloc_urb(0, GFP_ATOMIC)))
		return -ENOMEM;

137
	pipe = usb_sndbulkpipe(data->udev, data->bulk_out_ep);
L
Linus Torvalds 已提交
138

139
	usb_fill_bulk_urb(urb, data->udev, pipe, skb->data, skb->len,
L
Linus Torvalds 已提交
140 141 142 143
			bfusb_tx_complete, skb);

	scb->urb = urb;

144
	skb_queue_tail(&data->pending_q, skb);
L
Linus Torvalds 已提交
145 146 147 148

	err = usb_submit_urb(urb, GFP_ATOMIC);
	if (err) {
		BT_ERR("%s bulk tx submit failed urb %p err %d", 
149 150
					data->hdev->name, urb, err);
		skb_unlink(skb, &data->pending_q);
L
Linus Torvalds 已提交
151 152
		usb_free_urb(urb);
	} else
153
		atomic_inc(&data->pending_tx);
L
Linus Torvalds 已提交
154 155 156 157

	return err;
}

158
static void bfusb_tx_wakeup(struct bfusb_data *data)
L
Linus Torvalds 已提交
159 160 161
{
	struct sk_buff *skb;

162
	BT_DBG("bfusb %p", data);
L
Linus Torvalds 已提交
163

164 165
	if (test_and_set_bit(BFUSB_TX_PROCESS, &data->state)) {
		set_bit(BFUSB_TX_WAKEUP, &data->state);
L
Linus Torvalds 已提交
166 167 168 169
		return;
	}

	do {
170
		clear_bit(BFUSB_TX_WAKEUP, &data->state);
L
Linus Torvalds 已提交
171

172 173 174 175
		while ((atomic_read(&data->pending_tx) < BFUSB_MAX_BULK_TX) &&
				(skb = skb_dequeue(&data->transmit_q))) {
			if (bfusb_send_bulk(data, skb) < 0) {
				skb_queue_head(&data->transmit_q, skb);
L
Linus Torvalds 已提交
176 177 178 179
				break;
			}
		}

180
	} while (test_bit(BFUSB_TX_WAKEUP, &data->state));
L
Linus Torvalds 已提交
181

182
	clear_bit(BFUSB_TX_PROCESS, &data->state);
L
Linus Torvalds 已提交
183 184
}

185
static void bfusb_tx_complete(struct urb *urb)
L
Linus Torvalds 已提交
186 187
{
	struct sk_buff *skb = (struct sk_buff *) urb->context;
188
	struct bfusb_data *data = (struct bfusb_data *) skb->dev;
L
Linus Torvalds 已提交
189

190
	BT_DBG("bfusb %p urb %p skb %p len %d", data, urb, skb, skb->len);
L
Linus Torvalds 已提交
191

192
	atomic_dec(&data->pending_tx);
L
Linus Torvalds 已提交
193

194
	if (!test_bit(HCI_RUNNING, &data->hdev->flags))
L
Linus Torvalds 已提交
195 196 197
		return;

	if (!urb->status)
198
		data->hdev->stat.byte_tx += skb->len;
L
Linus Torvalds 已提交
199
	else
200
		data->hdev->stat.err_tx++;
L
Linus Torvalds 已提交
201

202
	read_lock(&data->lock);
L
Linus Torvalds 已提交
203

204 205
	skb_unlink(skb, &data->pending_q);
	skb_queue_tail(&data->completed_q, skb);
L
Linus Torvalds 已提交
206

207
	bfusb_tx_wakeup(data);
L
Linus Torvalds 已提交
208

209
	read_unlock(&data->lock);
L
Linus Torvalds 已提交
210 211 212
}


213
static int bfusb_rx_submit(struct bfusb_data *data, struct urb *urb)
L
Linus Torvalds 已提交
214
{
215
	struct bfusb_data_scb *scb;
L
Linus Torvalds 已提交
216 217 218
	struct sk_buff *skb;
	int err, pipe, size = HCI_MAX_FRAME_SIZE + 32;

219
	BT_DBG("bfusb %p urb %p", data, urb);
L
Linus Torvalds 已提交
220 221 222 223

	if (!urb && !(urb = usb_alloc_urb(0, GFP_ATOMIC)))
		return -ENOMEM;

224 225
	skb = bt_skb_alloc(size, GFP_ATOMIC);
	if (!skb) {
L
Linus Torvalds 已提交
226 227 228 229
		usb_free_urb(urb);
		return -ENOMEM;
	}

230
	skb->dev = (void *) data;
L
Linus Torvalds 已提交
231

232
	scb = (struct bfusb_data_scb *) skb->cb;
L
Linus Torvalds 已提交
233 234
	scb->urb = urb;

235
	pipe = usb_rcvbulkpipe(data->udev, data->bulk_in_ep);
L
Linus Torvalds 已提交
236

237
	usb_fill_bulk_urb(urb, data->udev, pipe, skb->data, size,
L
Linus Torvalds 已提交
238 239
			bfusb_rx_complete, skb);

240
	skb_queue_tail(&data->pending_q, skb);
L
Linus Torvalds 已提交
241 242 243 244

	err = usb_submit_urb(urb, GFP_ATOMIC);
	if (err) {
		BT_ERR("%s bulk rx submit failed urb %p err %d",
245 246
					data->hdev->name, urb, err);
		skb_unlink(skb, &data->pending_q);
L
Linus Torvalds 已提交
247 248 249 250 251 252 253
		kfree_skb(skb);
		usb_free_urb(urb);
	}

	return err;
}

254
static inline int bfusb_recv_block(struct bfusb_data *data, int hdr, unsigned char *buf, int len)
L
Linus Torvalds 已提交
255
{
256
	BT_DBG("bfusb %p hdr 0x%02x data %p len %d", data, hdr, buf, len);
L
Linus Torvalds 已提交
257 258

	if (hdr & 0x10) {
259 260 261 262
		BT_ERR("%s error in block", data->hdev->name);
		if (data->reassembly)
			kfree_skb(data->reassembly);
		data->reassembly = NULL;
L
Linus Torvalds 已提交
263 264 265 266 267 268 269 270
		return -EIO;
	}

	if (hdr & 0x04) {
		struct sk_buff *skb;
		unsigned char pkt_type;
		int pkt_len = 0;

271 272 273 274
		if (data->reassembly) {
			BT_ERR("%s unexpected start block", data->hdev->name);
			kfree_skb(data->reassembly);
			data->reassembly = NULL;
L
Linus Torvalds 已提交
275 276 277
		}

		if (len < 1) {
278
			BT_ERR("%s no packet type found", data->hdev->name);
L
Linus Torvalds 已提交
279 280 281
			return -EPROTO;
		}

282
		pkt_type = *buf++; len--;
L
Linus Torvalds 已提交
283 284 285 286

		switch (pkt_type) {
		case HCI_EVENT_PKT:
			if (len >= HCI_EVENT_HDR_SIZE) {
287
				struct hci_event_hdr *hdr = (struct hci_event_hdr *) buf;
L
Linus Torvalds 已提交
288 289
				pkt_len = HCI_EVENT_HDR_SIZE + hdr->plen;
			} else {
290
				BT_ERR("%s event block is too short", data->hdev->name);
L
Linus Torvalds 已提交
291 292 293 294 295 296
				return -EILSEQ;
			}
			break;

		case HCI_ACLDATA_PKT:
			if (len >= HCI_ACL_HDR_SIZE) {
297
				struct hci_acl_hdr *hdr = (struct hci_acl_hdr *) buf;
L
Linus Torvalds 已提交
298 299
				pkt_len = HCI_ACL_HDR_SIZE + __le16_to_cpu(hdr->dlen);
			} else {
300
				BT_ERR("%s data block is too short", data->hdev->name);
L
Linus Torvalds 已提交
301 302 303 304 305 306
				return -EILSEQ;
			}
			break;

		case HCI_SCODATA_PKT:
			if (len >= HCI_SCO_HDR_SIZE) {
307
				struct hci_sco_hdr *hdr = (struct hci_sco_hdr *) buf;
L
Linus Torvalds 已提交
308 309
				pkt_len = HCI_SCO_HDR_SIZE + hdr->dlen;
			} else {
310
				BT_ERR("%s audio block is too short", data->hdev->name);
L
Linus Torvalds 已提交
311 312 313 314 315 316 317
				return -EILSEQ;
			}
			break;
		}

		skb = bt_skb_alloc(pkt_len, GFP_ATOMIC);
		if (!skb) {
318
			BT_ERR("%s no memory for the packet", data->hdev->name);
L
Linus Torvalds 已提交
319 320 321
			return -ENOMEM;
		}

322
		skb->dev = (void *) data->hdev;
323
		bt_cb(skb)->pkt_type = pkt_type;
L
Linus Torvalds 已提交
324

325
		data->reassembly = skb;
L
Linus Torvalds 已提交
326
	} else {
327 328
		if (!data->reassembly) {
			BT_ERR("%s unexpected continuation block", data->hdev->name);
L
Linus Torvalds 已提交
329 330 331 332 333
			return -EIO;
		}
	}

	if (len > 0)
334
		memcpy(skb_put(data->reassembly, len), buf, len);
L
Linus Torvalds 已提交
335 336

	if (hdr & 0x08) {
337 338
		hci_recv_frame(data->reassembly);
		data->reassembly = NULL;
L
Linus Torvalds 已提交
339 340 341 342 343
	}

	return 0;
}

344
static void bfusb_rx_complete(struct urb *urb)
L
Linus Torvalds 已提交
345 346
{
	struct sk_buff *skb = (struct sk_buff *) urb->context;
347
	struct bfusb_data *data = (struct bfusb_data *) skb->dev;
L
Linus Torvalds 已提交
348 349 350 351
	unsigned char *buf = urb->transfer_buffer;
	int count = urb->actual_length;
	int err, hdr, len;

352
	BT_DBG("bfusb %p urb %p skb %p len %d", data, urb, skb, skb->len);
L
Linus Torvalds 已提交
353

354
	read_lock(&data->lock);
L
Linus Torvalds 已提交
355

356
	if (!test_bit(HCI_RUNNING, &data->hdev->flags))
L
Linus Torvalds 已提交
357 358 359 360 361
		goto unlock;

	if (urb->status || !count)
		goto resubmit;

362
	data->hdev->stat.byte_rx += count;
L
Linus Torvalds 已提交
363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380

	skb_put(skb, count);

	while (count) {
		hdr = buf[0] | (buf[1] << 8);

		if (hdr & 0x4000) {
			len = 0;
			count -= 2;
			buf   += 2;
		} else {
			len = (buf[2] == 0) ? 256 : buf[2];
			count -= 3;
			buf   += 3;
		}

		if (count < len) {
			BT_ERR("%s block extends over URB buffer ranges",
381
					data->hdev->name);
L
Linus Torvalds 已提交
382 383 384
		}

		if ((hdr & 0xe1) == 0xc1)
385
			bfusb_recv_block(data, hdr, buf, len);
L
Linus Torvalds 已提交
386 387 388 389 390

		count -= len;
		buf   += len;
	}

391
	skb_unlink(skb, &data->pending_q);
L
Linus Torvalds 已提交
392 393
	kfree_skb(skb);

394
	bfusb_rx_submit(data, urb);
L
Linus Torvalds 已提交
395

396
	read_unlock(&data->lock);
L
Linus Torvalds 已提交
397 398 399 400

	return;

resubmit:
401
	urb->dev = data->udev;
L
Linus Torvalds 已提交
402 403 404 405

	err = usb_submit_urb(urb, GFP_ATOMIC);
	if (err) {
		BT_ERR("%s bulk resubmit failed urb %p err %d",
406
					data->hdev->name, urb, err);
L
Linus Torvalds 已提交
407 408 409
	}

unlock:
410
	read_unlock(&data->lock);
L
Linus Torvalds 已提交
411 412 413 414
}

static int bfusb_open(struct hci_dev *hdev)
{
415
	struct bfusb_data *data = hdev->driver_data;
L
Linus Torvalds 已提交
416 417 418
	unsigned long flags;
	int i, err;

419
	BT_DBG("hdev %p bfusb %p", hdev, data);
L
Linus Torvalds 已提交
420 421 422 423

	if (test_and_set_bit(HCI_RUNNING, &hdev->flags))
		return 0;

424
	write_lock_irqsave(&data->lock, flags);
L
Linus Torvalds 已提交
425

426
	err = bfusb_rx_submit(data, NULL);
L
Linus Torvalds 已提交
427 428
	if (!err) {
		for (i = 1; i < BFUSB_MAX_BULK_RX; i++)
429
			bfusb_rx_submit(data, NULL);
L
Linus Torvalds 已提交
430 431 432 433
	} else {
		clear_bit(HCI_RUNNING, &hdev->flags);
	}

434
	write_unlock_irqrestore(&data->lock, flags);
L
Linus Torvalds 已提交
435 436 437 438 439 440

	return err;
}

static int bfusb_flush(struct hci_dev *hdev)
{
441
	struct bfusb_data *data = hdev->driver_data;
L
Linus Torvalds 已提交
442

443
	BT_DBG("hdev %p bfusb %p", hdev, data);
L
Linus Torvalds 已提交
444

445
	skb_queue_purge(&data->transmit_q);
L
Linus Torvalds 已提交
446 447 448 449 450 451

	return 0;
}

static int bfusb_close(struct hci_dev *hdev)
{
452
	struct bfusb_data *data = hdev->driver_data;
L
Linus Torvalds 已提交
453 454
	unsigned long flags;

455
	BT_DBG("hdev %p bfusb %p", hdev, data);
L
Linus Torvalds 已提交
456 457 458 459

	if (!test_and_clear_bit(HCI_RUNNING, &hdev->flags))
		return 0;

460 461
	write_lock_irqsave(&data->lock, flags);
	write_unlock_irqrestore(&data->lock, flags);
L
Linus Torvalds 已提交
462

463
	bfusb_unlink_urbs(data);
L
Linus Torvalds 已提交
464 465 466 467 468 469 470 471
	bfusb_flush(hdev);

	return 0;
}

static int bfusb_send_frame(struct sk_buff *skb)
{
	struct hci_dev *hdev = (struct hci_dev *) skb->dev;
472
	struct bfusb_data *data;
L
Linus Torvalds 已提交
473 474 475 476
	struct sk_buff *nskb;
	unsigned char buf[3];
	int sent = 0, size, count;

477
	BT_DBG("hdev %p skb %p type %d len %d", hdev, skb, bt_cb(skb)->pkt_type, skb->len);
L
Linus Torvalds 已提交
478 479 480 481 482 483 484 485 486

	if (!hdev) {
		BT_ERR("Frame for unknown HCI device (hdev=NULL)");
		return -ENODEV;
	}

	if (!test_bit(HCI_RUNNING, &hdev->flags))
		return -EBUSY;

487
	data = hdev->driver_data;
L
Linus Torvalds 已提交
488

489
	switch (bt_cb(skb)->pkt_type) {
L
Linus Torvalds 已提交
490 491 492 493 494 495 496 497 498 499 500 501
	case HCI_COMMAND_PKT:
		hdev->stat.cmd_tx++;
		break;
	case HCI_ACLDATA_PKT:
		hdev->stat.acl_tx++;
		break;
	case HCI_SCODATA_PKT:
		hdev->stat.sco_tx++;
		break;
	};

	/* Prepend skb with frame type */
502
	memcpy(skb_push(skb, 1), &bt_cb(skb)->pkt_type, 1);
L
Linus Torvalds 已提交
503 504 505 506

	count = skb->len;

	/* Max HCI frame size seems to be 1511 + 1 */
507 508
	nskb = bt_skb_alloc(count + 32, GFP_ATOMIC);
	if (!nskb) {
L
Linus Torvalds 已提交
509 510 511 512
		BT_ERR("Can't allocate memory for new packet");
		return -ENOMEM;
	}

513
	nskb->dev = (void *) data;
L
Linus Torvalds 已提交
514 515 516 517 518 519 520 521 522

	while (count) {
		size = min_t(uint, count, BFUSB_MAX_BLOCK_SIZE);

		buf[0] = 0xc1 | ((sent == 0) ? 0x04 : 0) | ((count == size) ? 0x08 : 0);
		buf[1] = 0x00;
		buf[2] = (size == BFUSB_MAX_BLOCK_SIZE) ? 0 : size;

		memcpy(skb_put(nskb, 3), buf, 3);
523
		skb_copy_from_linear_data_offset(skb, sent, skb_put(nskb, size), size);
L
Linus Torvalds 已提交
524 525 526 527 528 529

		sent  += size;
		count -= size;
	}

	/* Don't send frame with multiple size of bulk max packet */
530
	if ((nskb->len % data->bulk_pkt_size) == 0) {
L
Linus Torvalds 已提交
531 532 533 534 535
		buf[0] = 0xdd;
		buf[1] = 0x00;
		memcpy(skb_put(nskb, 2), buf, 2);
	}

536
	read_lock(&data->lock);
L
Linus Torvalds 已提交
537

538 539
	skb_queue_tail(&data->transmit_q, nskb);
	bfusb_tx_wakeup(data);
L
Linus Torvalds 已提交
540

541
	read_unlock(&data->lock);
L
Linus Torvalds 已提交
542 543 544 545 546 547 548 549

	kfree_skb(skb);

	return 0;
}

static void bfusb_destruct(struct hci_dev *hdev)
{
550
	struct bfusb_data *data = hdev->driver_data;
L
Linus Torvalds 已提交
551

552
	BT_DBG("hdev %p bfusb %p", hdev, data);
L
Linus Torvalds 已提交
553

554
	kfree(data);
L
Linus Torvalds 已提交
555 556 557 558 559 560 561
}

static int bfusb_ioctl(struct hci_dev *hdev, unsigned int cmd, unsigned long arg)
{
	return -ENOIOCTLCMD;
}

562 563
static int bfusb_load_firmware(struct bfusb_data *data,
			       const unsigned char *firmware, int count)
L
Linus Torvalds 已提交
564 565 566 567
{
	unsigned char *buf;
	int err, pipe, len, size, sent = 0;

568
	BT_DBG("bfusb %p udev %p", data, data->udev);
L
Linus Torvalds 已提交
569 570 571

	BT_INFO("BlueFRITZ! USB loading firmware");

572
	pipe = usb_sndctrlpipe(data->udev, 0);
L
Linus Torvalds 已提交
573

574
	if (usb_control_msg(data->udev, pipe, USB_REQ_SET_CONFIGURATION,
L
Linus Torvalds 已提交
575 576 577 578 579
				0, 1, 0, NULL, 0, USB_CTRL_SET_TIMEOUT) < 0) {
		BT_ERR("Can't change to loading configuration");
		return -EBUSY;
	}

580
	data->udev->toggle[0] = data->udev->toggle[1] = 0;
L
Linus Torvalds 已提交
581 582 583 584 585 586 587

	buf = kmalloc(BFUSB_MAX_BLOCK_SIZE + 3, GFP_ATOMIC);
	if (!buf) {
		BT_ERR("Can't allocate memory chunk for firmware");
		return -ENOMEM;
	}

588
	pipe = usb_sndbulkpipe(data->udev, data->bulk_out_ep);
L
Linus Torvalds 已提交
589 590 591 592 593 594

	while (count) {
		size = min_t(uint, count, BFUSB_MAX_BLOCK_SIZE + 3);

		memcpy(buf, firmware + sent, size);

595
		err = usb_bulk_msg(data->udev, pipe, buf, size,
L
Linus Torvalds 已提交
596 597 598 599 600 601 602 603 604 605 606
					&len, BFUSB_BLOCK_TIMEOUT);

		if (err || (len != size)) {
			BT_ERR("Error in firmware loading");
			goto error;
		}

		sent  += size;
		count -= size;
	}

607 608 609
	err = usb_bulk_msg(data->udev, pipe, NULL, 0,
					&len, BFUSB_BLOCK_TIMEOUT);
	if (err < 0) {
L
Linus Torvalds 已提交
610 611 612 613
		BT_ERR("Error in null packet request");
		goto error;
	}

614
	pipe = usb_sndctrlpipe(data->udev, 0);
L
Linus Torvalds 已提交
615

616 617 618
	err = usb_control_msg(data->udev, pipe, USB_REQ_SET_CONFIGURATION,
				0, 2, 0, NULL, 0, USB_CTRL_SET_TIMEOUT);
	if (err < 0) {
L
Linus Torvalds 已提交
619 620 621 622
		BT_ERR("Can't change to running configuration");
		goto error;
	}

623
	data->udev->toggle[0] = data->udev->toggle[1] = 0;
L
Linus Torvalds 已提交
624 625 626 627 628 629 630 631 632

	BT_INFO("BlueFRITZ! USB device ready");

	kfree(buf);
	return 0;

error:
	kfree(buf);

633
	pipe = usb_sndctrlpipe(data->udev, 0);
L
Linus Torvalds 已提交
634

635
	usb_control_msg(data->udev, pipe, USB_REQ_SET_CONFIGURATION,
L
Linus Torvalds 已提交
636 637 638 639 640 641 642 643 644 645 646 647
				0, 0, 0, NULL, 0, USB_CTRL_SET_TIMEOUT);

	return err;
}

static int bfusb_probe(struct usb_interface *intf, const struct usb_device_id *id)
{
	const struct firmware *firmware;
	struct usb_device *udev = interface_to_usbdev(intf);
	struct usb_host_endpoint *bulk_out_ep;
	struct usb_host_endpoint *bulk_in_ep;
	struct hci_dev *hdev;
648
	struct bfusb_data *data;
L
Linus Torvalds 已提交
649 650 651 652 653 654 655 656 657 658 659 660 661 662 663 664

	BT_DBG("intf %p id %p", intf, id);

	/* Check number of endpoints */
	if (intf->cur_altsetting->desc.bNumEndpoints < 2)
		return -EIO;

	bulk_out_ep = &intf->cur_altsetting->endpoint[0];
	bulk_in_ep  = &intf->cur_altsetting->endpoint[1];

	if (!bulk_out_ep || !bulk_in_ep) {
		BT_ERR("Bulk endpoints not found");
		goto done;
	}

	/* Initialize control structure and load firmware */
665 666
	data = kzalloc(sizeof(struct bfusb_data), GFP_KERNEL);
	if (!data) {
L
Linus Torvalds 已提交
667 668 669 670
		BT_ERR("Can't allocate memory for control structure");
		goto done;
	}

671 672 673 674
	data->udev = udev;
	data->bulk_in_ep    = bulk_in_ep->desc.bEndpointAddress;
	data->bulk_out_ep   = bulk_out_ep->desc.bEndpointAddress;
	data->bulk_pkt_size = le16_to_cpu(bulk_out_ep->desc.wMaxPacketSize);
L
Linus Torvalds 已提交
675

676
	rwlock_init(&data->lock);
L
Linus Torvalds 已提交
677

678
	data->reassembly = NULL;
L
Linus Torvalds 已提交
679

680 681 682
	skb_queue_head_init(&data->transmit_q);
	skb_queue_head_init(&data->pending_q);
	skb_queue_head_init(&data->completed_q);
L
Linus Torvalds 已提交
683 684 685 686 687 688

	if (request_firmware(&firmware, "bfubase.frm", &udev->dev) < 0) {
		BT_ERR("Firmware request failed");
		goto error;
	}

689
	BT_DBG("firmware data %p size %zu", firmware->data, firmware->size);
L
Linus Torvalds 已提交
690

691
	if (bfusb_load_firmware(data, firmware->data, firmware->size) < 0) {
L
Linus Torvalds 已提交
692 693 694 695 696 697 698 699 700 701 702 703 704
		BT_ERR("Firmware loading failed");
		goto release;
	}

	release_firmware(firmware);

	/* Initialize and register HCI device */
	hdev = hci_alloc_dev();
	if (!hdev) {
		BT_ERR("Can't allocate HCI device");
		goto error;
	}

705
	data->hdev = hdev;
L
Linus Torvalds 已提交
706 707

	hdev->type = HCI_USB;
708
	hdev->driver_data = data;
L
Linus Torvalds 已提交
709 710 711 712 713 714 715 716 717 718 719 720 721 722 723 724 725
	SET_HCIDEV_DEV(hdev, &intf->dev);

	hdev->open     = bfusb_open;
	hdev->close    = bfusb_close;
	hdev->flush    = bfusb_flush;
	hdev->send     = bfusb_send_frame;
	hdev->destruct = bfusb_destruct;
	hdev->ioctl    = bfusb_ioctl;

	hdev->owner = THIS_MODULE;

	if (hci_register_dev(hdev) < 0) {
		BT_ERR("Can't register HCI device");
		hci_free_dev(hdev);
		goto error;
	}

726
	usb_set_intfdata(intf, data);
L
Linus Torvalds 已提交
727 728 729 730 731 732 733

	return 0;

release:
	release_firmware(firmware);

error:
734
	kfree(data);
L
Linus Torvalds 已提交
735 736 737 738 739 740 741

done:
	return -EIO;
}

static void bfusb_disconnect(struct usb_interface *intf)
{
742 743
	struct bfusb_data *data = usb_get_intfdata(intf);
	struct hci_dev *hdev = data->hdev;
L
Linus Torvalds 已提交
744 745 746 747 748 749 750 751 752 753 754 755 756 757 758 759 760 761 762 763 764 765 766 767 768 769 770 771 772

	BT_DBG("intf %p", intf);

	if (!hdev)
		return;

	usb_set_intfdata(intf, NULL);

	bfusb_close(hdev);

	if (hci_unregister_dev(hdev) < 0)
		BT_ERR("Can't unregister HCI device %s", hdev->name);

	hci_free_dev(hdev);
}

static struct usb_driver bfusb_driver = {
	.name		= "bfusb",
	.probe		= bfusb_probe,
	.disconnect	= bfusb_disconnect,
	.id_table	= bfusb_table,
};

static int __init bfusb_init(void)
{
	int err;

	BT_INFO("BlueFRITZ! USB driver ver %s", VERSION);

773 774
	err = usb_register(&bfusb_driver);
	if (err < 0)
L
Linus Torvalds 已提交
775 776 777 778 779 780 781 782 783 784 785 786 787 788 789 790 791
		BT_ERR("Failed to register BlueFRITZ! USB driver");

	return err;
}

static void __exit bfusb_exit(void)
{
	usb_deregister(&bfusb_driver);
}

module_init(bfusb_init);
module_exit(bfusb_exit);

MODULE_AUTHOR("Marcel Holtmann <marcel@holtmann.org>");
MODULE_DESCRIPTION("BlueFRITZ! USB driver ver " VERSION);
MODULE_VERSION(VERSION);
MODULE_LICENSE("GPL");
792
MODULE_FIRMWARE("bfubase.frm");