• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*****************************************************************************
2 *
3 * Filename:      kingsun-sir.c
4 * Version:       0.1.1
5 * Description:   Irda KingSun/DonShine USB Dongle
6 * Status:        Experimental
7 * Author:        Alex Villacís Lasso <a_villacis@palosanto.com>
8 *
9 *  	Based on stir4200 and mcs7780 drivers, with (strange?) differences
10 *
11 *	This program is free software; you can redistribute it and/or modify
12 *	it under the terms of the GNU General Public License as published by
13 *	the Free Software Foundation; either version 2 of the License.
14 *
15 *	This program is distributed in the hope that it will be useful,
16 *	but WITHOUT ANY WARRANTY; without even the implied warranty of
17 *	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18 *	GNU General Public License for more details.
19 *
20 *	You should have received a copy of the GNU General Public License
21 *	along with this program; if not, write to the Free Software
22 *	Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
23 *
24 *****************************************************************************/
25 
26 /*
27  * This is my current (2007-04-25) understanding of how this dongle is supposed
28  * to work. This is based on reverse-engineering and examination of the packet
29  * data sent and received by the WinXP driver using USBSnoopy. Feel free to
30  * update here as more of this dongle is known:
31  *
32  * General: Unlike the other USB IrDA dongles, this particular dongle exposes,
33  * not two bulk (in and out) endpoints, but two *interrupt* ones. This dongle,
34  * like the bulk based ones (stir4200.c and mcs7780.c), requires polling in
35  * order to receive data.
36  * Transmission: Just like stir4200, this dongle uses a raw stream of data,
37  * which needs to be wrapped and escaped in a similar way as in stir4200.c.
38  * Reception: Poll-based, as in stir4200. Each read returns the contents of a
39  * 8-byte buffer, of which the first byte (LSB) indicates the number of bytes
40  * (1-7) of valid data contained within the remaining 7 bytes. For example, if
41  * the buffer had the following contents:
42  *  06 ff ff ff c0 01 04 aa
43  * This means that (06) there are 6 bytes of valid data. The byte 0xaa at the
44  * end is garbage (left over from a previous reception) and is discarded.
45  * If a read returns an "impossible" value as the length of valid data (such as
46  * 0x36) in the first byte, then the buffer is uninitialized (as is the case of
47  * first plug-in) and its contents should be discarded. There is currently no
48  * evidence that the top 5 bits of the 1st byte of the buffer can have values
49  * other than 0 once reception begins.
50  * Once valid bytes are collected, the assembled stream is a sequence of
51  * wrapped IrDA frames that is unwrapped and unescaped as in stir4200.c.
52  * BIG FAT WARNING: the dongle does *not* reset the RX buffer in any way after
53  * a successful read from the host, which means that in absence of further
54  * reception, repeated reads from the dongle will return the exact same
55  * contents repeatedly. Attempts to be smart and cache a previous read seem
56  * to result in corrupted packets, so this driver depends on the unwrap logic
57  * to sort out any repeated reads.
58  * Speed change: no commands observed so far to change speed, assumed fixed
59  * 9600bps (SIR).
60  */
61 
62 #include <linux/module.h>
63 #include <linux/moduleparam.h>
64 #include <linux/kernel.h>
65 #include <linux/types.h>
66 #include <linux/errno.h>
67 #include <linux/slab.h>
68 #include <linux/usb.h>
69 #include <linux/device.h>
70 #include <linux/crc32.h>
71 
72 #include <asm/unaligned.h>
73 #include <asm/byteorder.h>
74 #include <asm/uaccess.h>
75 
76 #include <net/irda/irda.h>
77 #include <net/irda/wrapper.h>
78 #include <net/irda/crc.h>
79 
80 /*
81  * According to lsusb, 0x07c0 is assigned to
82  * "Code Mercenaries Hard- und Software GmbH"
83  */
84 #define KING_VENDOR_ID 0x07c0
85 #define KING_PRODUCT_ID 0x4200
86 
87 /* These are the currently known USB ids */
88 static struct usb_device_id dongles[] = {
89     /* KingSun Co,Ltd  IrDA/USB Bridge */
90     { USB_DEVICE(KING_VENDOR_ID, KING_PRODUCT_ID) },
91     { }
92 };
93 
94 MODULE_DEVICE_TABLE(usb, dongles);
95 
96 #define KINGSUN_MTT 0x07
97 
98 #define KINGSUN_FIFO_SIZE		4096
99 #define KINGSUN_EP_IN			0
100 #define KINGSUN_EP_OUT			1
101 
102 struct kingsun_cb {
103 	struct usb_device *usbdev;      /* init: probe_irda */
104 	struct net_device *netdev;      /* network layer */
105 	struct irlap_cb   *irlap;       /* The link layer we are binded to */
106 
107 	struct qos_info   qos;
108 
109 	__u8		  *in_buf;	/* receive buffer */
110 	__u8		  *out_buf;	/* transmit buffer */
111 	__u8		  max_rx;	/* max. atomic read from dongle
112 					   (usually 8), also size of in_buf */
113 	__u8		  max_tx;	/* max. atomic write to dongle
114 					   (usually 8) */
115 
116 	iobuff_t  	  rx_buff;	/* receive unwrap state machine */
117 	struct timeval	  rx_time;
118 	spinlock_t lock;
119 	int receiving;
120 
121 	__u8 ep_in;
122 	__u8 ep_out;
123 
124 	struct urb	 *tx_urb;
125 	struct urb	 *rx_urb;
126 };
127 
128 /* Callback transmission routine */
kingsun_send_irq(struct urb * urb)129 static void kingsun_send_irq(struct urb *urb)
130 {
131 	struct kingsun_cb *kingsun = urb->context;
132 	struct net_device *netdev = kingsun->netdev;
133 
134 	/* in process of stopping, just drop data */
135 	if (!netif_running(kingsun->netdev)) {
136 		dev_err(&kingsun->usbdev->dev,
137 			"kingsun_send_irq: Network not running!\n");
138 		return;
139 	}
140 
141 	/* unlink, shutdown, unplug, other nasties */
142 	if (urb->status != 0) {
143 		dev_err(&kingsun->usbdev->dev,
144 			"kingsun_send_irq: urb asynchronously failed - %d\n",
145 			urb->status);
146 	}
147 	netif_wake_queue(netdev);
148 }
149 
150 /*
151  * Called from net/core when new frame is available.
152  */
kingsun_hard_xmit(struct sk_buff * skb,struct net_device * netdev)153 static netdev_tx_t kingsun_hard_xmit(struct sk_buff *skb,
154 					   struct net_device *netdev)
155 {
156 	struct kingsun_cb *kingsun;
157 	int wraplen;
158 	int ret = 0;
159 
160 	netif_stop_queue(netdev);
161 
162 	/* the IRDA wrapping routines don't deal with non linear skb */
163 	SKB_LINEAR_ASSERT(skb);
164 
165 	kingsun = netdev_priv(netdev);
166 
167 	spin_lock(&kingsun->lock);
168 
169 	/* Append data to the end of whatever data remains to be transmitted */
170 	wraplen = async_wrap_skb(skb,
171 		kingsun->out_buf,
172 		KINGSUN_FIFO_SIZE);
173 
174 	/* Calculate how much data can be transmitted in this urb */
175 	usb_fill_int_urb(kingsun->tx_urb, kingsun->usbdev,
176 		usb_sndintpipe(kingsun->usbdev, kingsun->ep_out),
177 		kingsun->out_buf, wraplen, kingsun_send_irq,
178 		kingsun, 1);
179 
180 	if ((ret = usb_submit_urb(kingsun->tx_urb, GFP_ATOMIC))) {
181 		dev_err(&kingsun->usbdev->dev,
182 			"kingsun_hard_xmit: failed tx_urb submit: %d\n", ret);
183 		switch (ret) {
184 		case -ENODEV:
185 		case -EPIPE:
186 			break;
187 		default:
188 			netdev->stats.tx_errors++;
189 			netif_start_queue(netdev);
190 		}
191 	} else {
192 		netdev->stats.tx_packets++;
193 		netdev->stats.tx_bytes += skb->len;
194 	}
195 
196 	dev_kfree_skb(skb);
197 	spin_unlock(&kingsun->lock);
198 
199 	return NETDEV_TX_OK;
200 }
201 
202 /* Receive callback function */
kingsun_rcv_irq(struct urb * urb)203 static void kingsun_rcv_irq(struct urb *urb)
204 {
205 	struct kingsun_cb *kingsun = urb->context;
206 	int ret;
207 
208 	/* in process of stopping, just drop data */
209 	if (!netif_running(kingsun->netdev)) {
210 		kingsun->receiving = 0;
211 		return;
212 	}
213 
214 	/* unlink, shutdown, unplug, other nasties */
215 	if (urb->status != 0) {
216 		dev_err(&kingsun->usbdev->dev,
217 			"kingsun_rcv_irq: urb asynchronously failed - %d\n",
218 			urb->status);
219 		kingsun->receiving = 0;
220 		return;
221 	}
222 
223 	if (urb->actual_length == kingsun->max_rx) {
224 		__u8 *bytes = urb->transfer_buffer;
225 		int i;
226 
227 		/* The very first byte in the buffer indicates the length of
228 		   valid data in the read. This byte must be in the range
229 		   1..kingsun->max_rx -1 . Values outside this range indicate
230 		   an uninitialized Rx buffer when the dongle has just been
231 		   plugged in. */
232 		if (bytes[0] >= 1 && bytes[0] < kingsun->max_rx) {
233 			for (i = 1; i <= bytes[0]; i++) {
234 				async_unwrap_char(kingsun->netdev,
235 						  &kingsun->netdev->stats,
236 						  &kingsun->rx_buff, bytes[i]);
237 			}
238 			do_gettimeofday(&kingsun->rx_time);
239 			kingsun->receiving =
240 				(kingsun->rx_buff.state != OUTSIDE_FRAME)
241 				? 1 : 0;
242 		}
243 	} else if (urb->actual_length > 0) {
244 		dev_err(&kingsun->usbdev->dev,
245 			"%s(): Unexpected response length, expected %d got %d\n",
246 			__func__, kingsun->max_rx, urb->actual_length);
247 	}
248 	/* This urb has already been filled in kingsun_net_open */
249 	ret = usb_submit_urb(urb, GFP_ATOMIC);
250 }
251 
252 /*
253  * Function kingsun_net_open (dev)
254  *
255  *    Network device is taken up. Usually this is done by "ifconfig irda0 up"
256  */
kingsun_net_open(struct net_device * netdev)257 static int kingsun_net_open(struct net_device *netdev)
258 {
259 	struct kingsun_cb *kingsun = netdev_priv(netdev);
260 	int err = -ENOMEM;
261 	char hwname[16];
262 
263 	/* At this point, urbs are NULL, and skb is NULL (see kingsun_probe) */
264 	kingsun->receiving = 0;
265 
266 	/* Initialize for SIR to copy data directly into skb.  */
267 	kingsun->rx_buff.in_frame = FALSE;
268 	kingsun->rx_buff.state = OUTSIDE_FRAME;
269 	kingsun->rx_buff.truesize = IRDA_SKB_MAX_MTU;
270 	kingsun->rx_buff.skb = dev_alloc_skb(IRDA_SKB_MAX_MTU);
271 	if (!kingsun->rx_buff.skb)
272 		goto free_mem;
273 
274 	skb_reserve(kingsun->rx_buff.skb, 1);
275 	kingsun->rx_buff.head = kingsun->rx_buff.skb->data;
276 	do_gettimeofday(&kingsun->rx_time);
277 
278 	kingsun->rx_urb = usb_alloc_urb(0, GFP_KERNEL);
279 	if (!kingsun->rx_urb)
280 		goto free_mem;
281 
282 	kingsun->tx_urb = usb_alloc_urb(0, GFP_KERNEL);
283 	if (!kingsun->tx_urb)
284 		goto free_mem;
285 
286 	/*
287 	 * Now that everything should be initialized properly,
288 	 * Open new IrLAP layer instance to take care of us...
289 	 */
290 	sprintf(hwname, "usb#%d", kingsun->usbdev->devnum);
291 	kingsun->irlap = irlap_open(netdev, &kingsun->qos, hwname);
292 	if (!kingsun->irlap) {
293 		dev_err(&kingsun->usbdev->dev, "irlap_open failed\n");
294 		goto free_mem;
295 	}
296 
297 	/* Start first reception */
298 	usb_fill_int_urb(kingsun->rx_urb, kingsun->usbdev,
299 			  usb_rcvintpipe(kingsun->usbdev, kingsun->ep_in),
300 			  kingsun->in_buf, kingsun->max_rx,
301 			  kingsun_rcv_irq, kingsun, 1);
302 	kingsun->rx_urb->status = 0;
303 	err = usb_submit_urb(kingsun->rx_urb, GFP_KERNEL);
304 	if (err) {
305 		dev_err(&kingsun->usbdev->dev,
306 			"first urb-submit failed: %d\n", err);
307 		goto close_irlap;
308 	}
309 
310 	netif_start_queue(netdev);
311 
312 	/* Situation at this point:
313 	   - all work buffers allocated
314 	   - urbs allocated and ready to fill
315 	   - max rx packet known (in max_rx)
316 	   - unwrap state machine initialized, in state outside of any frame
317 	   - receive request in progress
318 	   - IrLAP layer started, about to hand over packets to send
319 	 */
320 
321 	return 0;
322 
323  close_irlap:
324 	irlap_close(kingsun->irlap);
325  free_mem:
326 	if (kingsun->tx_urb) {
327 		usb_free_urb(kingsun->tx_urb);
328 		kingsun->tx_urb = NULL;
329 	}
330 	if (kingsun->rx_urb) {
331 		usb_free_urb(kingsun->rx_urb);
332 		kingsun->rx_urb = NULL;
333 	}
334 	if (kingsun->rx_buff.skb) {
335 		kfree_skb(kingsun->rx_buff.skb);
336 		kingsun->rx_buff.skb = NULL;
337 		kingsun->rx_buff.head = NULL;
338 	}
339 	return err;
340 }
341 
342 /*
343  * Function kingsun_net_close (kingsun)
344  *
345  *    Network device is taken down. Usually this is done by
346  *    "ifconfig irda0 down"
347  */
kingsun_net_close(struct net_device * netdev)348 static int kingsun_net_close(struct net_device *netdev)
349 {
350 	struct kingsun_cb *kingsun = netdev_priv(netdev);
351 
352 	/* Stop transmit processing */
353 	netif_stop_queue(netdev);
354 
355 	/* Mop up receive && transmit urb's */
356 	usb_kill_urb(kingsun->tx_urb);
357 	usb_kill_urb(kingsun->rx_urb);
358 
359 	usb_free_urb(kingsun->tx_urb);
360 	usb_free_urb(kingsun->rx_urb);
361 
362 	kingsun->tx_urb = NULL;
363 	kingsun->rx_urb = NULL;
364 
365 	kfree_skb(kingsun->rx_buff.skb);
366 	kingsun->rx_buff.skb = NULL;
367 	kingsun->rx_buff.head = NULL;
368 	kingsun->rx_buff.in_frame = FALSE;
369 	kingsun->rx_buff.state = OUTSIDE_FRAME;
370 	kingsun->receiving = 0;
371 
372 	/* Stop and remove instance of IrLAP */
373 	if (kingsun->irlap)
374 		irlap_close(kingsun->irlap);
375 
376 	kingsun->irlap = NULL;
377 
378 	return 0;
379 }
380 
381 /*
382  * IOCTLs : Extra out-of-band network commands...
383  */
kingsun_net_ioctl(struct net_device * netdev,struct ifreq * rq,int cmd)384 static int kingsun_net_ioctl(struct net_device *netdev, struct ifreq *rq,
385 			     int cmd)
386 {
387 	struct if_irda_req *irq = (struct if_irda_req *) rq;
388 	struct kingsun_cb *kingsun = netdev_priv(netdev);
389 	int ret = 0;
390 
391 	switch (cmd) {
392 	case SIOCSBANDWIDTH: /* Set bandwidth */
393 		if (!capable(CAP_NET_ADMIN))
394 			return -EPERM;
395 
396 		/* Check if the device is still there */
397 		if (netif_device_present(kingsun->netdev))
398 			/* No observed commands for speed change */
399 			ret = -EOPNOTSUPP;
400 		break;
401 
402 	case SIOCSMEDIABUSY: /* Set media busy */
403 		if (!capable(CAP_NET_ADMIN))
404 			return -EPERM;
405 
406 		/* Check if the IrDA stack is still there */
407 		if (netif_running(kingsun->netdev))
408 			irda_device_set_media_busy(kingsun->netdev, TRUE);
409 		break;
410 
411 	case SIOCGRECEIVING:
412 		/* Only approximately true */
413 		irq->ifr_receiving = kingsun->receiving;
414 		break;
415 
416 	default:
417 		ret = -EOPNOTSUPP;
418 	}
419 
420 	return ret;
421 }
422 
423 static const struct net_device_ops kingsun_ops = {
424 	.ndo_start_xmit	     = kingsun_hard_xmit,
425 	.ndo_open            = kingsun_net_open,
426 	.ndo_stop            = kingsun_net_close,
427 	.ndo_do_ioctl        = kingsun_net_ioctl,
428 };
429 
430 /*
431  * This routine is called by the USB subsystem for each new device
432  * in the system. We need to check if the device is ours, and in
433  * this case start handling it.
434  */
kingsun_probe(struct usb_interface * intf,const struct usb_device_id * id)435 static int kingsun_probe(struct usb_interface *intf,
436 		      const struct usb_device_id *id)
437 {
438 	struct usb_host_interface *interface;
439 	struct usb_endpoint_descriptor *endpoint;
440 
441 	struct usb_device *dev = interface_to_usbdev(intf);
442 	struct kingsun_cb *kingsun = NULL;
443 	struct net_device *net = NULL;
444 	int ret = -ENOMEM;
445 	int pipe, maxp_in, maxp_out;
446 	__u8 ep_in;
447 	__u8 ep_out;
448 
449 	/* Check that there really are two interrupt endpoints.
450 	   Check based on the one in drivers/usb/input/usbmouse.c
451 	 */
452 	interface = intf->cur_altsetting;
453 	if (interface->desc.bNumEndpoints != 2) {
454 		dev_err(&intf->dev,
455 			"kingsun-sir: expected 2 endpoints, found %d\n",
456 			interface->desc.bNumEndpoints);
457 		return -ENODEV;
458 	}
459 	endpoint = &interface->endpoint[KINGSUN_EP_IN].desc;
460 	if (!usb_endpoint_is_int_in(endpoint)) {
461 		dev_err(&intf->dev,
462 			"kingsun-sir: endpoint 0 is not interrupt IN\n");
463 		return -ENODEV;
464 	}
465 
466 	ep_in = endpoint->bEndpointAddress;
467 	pipe = usb_rcvintpipe(dev, ep_in);
468 	maxp_in = usb_maxpacket(dev, pipe, usb_pipeout(pipe));
469 	if (maxp_in > 255 || maxp_in <= 1) {
470 		dev_err(&intf->dev,
471 			"endpoint 0 has max packet size %d not in range\n",
472 			maxp_in);
473 		return -ENODEV;
474 	}
475 
476 	endpoint = &interface->endpoint[KINGSUN_EP_OUT].desc;
477 	if (!usb_endpoint_is_int_out(endpoint)) {
478 		dev_err(&intf->dev,
479 			"kingsun-sir: endpoint 1 is not interrupt OUT\n");
480 		return -ENODEV;
481 	}
482 
483 	ep_out = endpoint->bEndpointAddress;
484 	pipe = usb_sndintpipe(dev, ep_out);
485 	maxp_out = usb_maxpacket(dev, pipe, usb_pipeout(pipe));
486 
487 	/* Allocate network device container. */
488 	net = alloc_irdadev(sizeof(*kingsun));
489 	if(!net)
490 		goto err_out1;
491 
492 	SET_NETDEV_DEV(net, &intf->dev);
493 	kingsun = netdev_priv(net);
494 	kingsun->irlap = NULL;
495 	kingsun->tx_urb = NULL;
496 	kingsun->rx_urb = NULL;
497 	kingsun->ep_in = ep_in;
498 	kingsun->ep_out = ep_out;
499 	kingsun->in_buf = NULL;
500 	kingsun->out_buf = NULL;
501 	kingsun->max_rx = (__u8)maxp_in;
502 	kingsun->max_tx = (__u8)maxp_out;
503 	kingsun->netdev = net;
504 	kingsun->usbdev = dev;
505 	kingsun->rx_buff.in_frame = FALSE;
506 	kingsun->rx_buff.state = OUTSIDE_FRAME;
507 	kingsun->rx_buff.skb = NULL;
508 	kingsun->receiving = 0;
509 	spin_lock_init(&kingsun->lock);
510 
511 	/* Allocate input buffer */
512 	kingsun->in_buf = kmalloc(kingsun->max_rx, GFP_KERNEL);
513 	if (!kingsun->in_buf)
514 		goto free_mem;
515 
516 	/* Allocate output buffer */
517 	kingsun->out_buf = kmalloc(KINGSUN_FIFO_SIZE, GFP_KERNEL);
518 	if (!kingsun->out_buf)
519 		goto free_mem;
520 
521 	printk(KERN_INFO "KingSun/DonShine IRDA/USB found at address %d, "
522 		"Vendor: %x, Product: %x\n",
523 	       dev->devnum, le16_to_cpu(dev->descriptor.idVendor),
524 	       le16_to_cpu(dev->descriptor.idProduct));
525 
526 	/* Initialize QoS for this device */
527 	irda_init_max_qos_capabilies(&kingsun->qos);
528 
529 	/* That's the Rx capability. */
530 	kingsun->qos.baud_rate.bits       &= IR_9600;
531 	kingsun->qos.min_turn_time.bits   &= KINGSUN_MTT;
532 	irda_qos_bits_to_value(&kingsun->qos);
533 
534 	/* Override the network functions we need to use */
535 	net->netdev_ops = &kingsun_ops;
536 
537 	ret = register_netdev(net);
538 	if (ret != 0)
539 		goto free_mem;
540 
541 	dev_info(&net->dev, "IrDA: Registered KingSun/DonShine device %s\n",
542 		 net->name);
543 
544 	usb_set_intfdata(intf, kingsun);
545 
546 	/* Situation at this point:
547 	   - all work buffers allocated
548 	   - urbs not allocated, set to NULL
549 	   - max rx packet known (in max_rx)
550 	   - unwrap state machine (partially) initialized, but skb == NULL
551 	 */
552 
553 	return 0;
554 
555 free_mem:
556 	kfree(kingsun->out_buf);
557 	kfree(kingsun->in_buf);
558 	free_netdev(net);
559 err_out1:
560 	return ret;
561 }
562 
563 /*
564  * The current device is removed, the USB layer tell us to shut it down...
565  */
kingsun_disconnect(struct usb_interface * intf)566 static void kingsun_disconnect(struct usb_interface *intf)
567 {
568 	struct kingsun_cb *kingsun = usb_get_intfdata(intf);
569 
570 	if (!kingsun)
571 		return;
572 
573 	unregister_netdev(kingsun->netdev);
574 
575 	/* Mop up receive && transmit urb's */
576 	if (kingsun->tx_urb != NULL) {
577 		usb_kill_urb(kingsun->tx_urb);
578 		usb_free_urb(kingsun->tx_urb);
579 		kingsun->tx_urb = NULL;
580 	}
581 	if (kingsun->rx_urb != NULL) {
582 		usb_kill_urb(kingsun->rx_urb);
583 		usb_free_urb(kingsun->rx_urb);
584 		kingsun->rx_urb = NULL;
585 	}
586 
587 	kfree(kingsun->out_buf);
588 	kfree(kingsun->in_buf);
589 	free_netdev(kingsun->netdev);
590 
591 	usb_set_intfdata(intf, NULL);
592 }
593 
594 #ifdef CONFIG_PM
595 /* USB suspend, so power off the transmitter/receiver */
kingsun_suspend(struct usb_interface * intf,pm_message_t message)596 static int kingsun_suspend(struct usb_interface *intf, pm_message_t message)
597 {
598 	struct kingsun_cb *kingsun = usb_get_intfdata(intf);
599 
600 	netif_device_detach(kingsun->netdev);
601 	if (kingsun->tx_urb != NULL) usb_kill_urb(kingsun->tx_urb);
602 	if (kingsun->rx_urb != NULL) usb_kill_urb(kingsun->rx_urb);
603 	return 0;
604 }
605 
606 /* Coming out of suspend, so reset hardware */
kingsun_resume(struct usb_interface * intf)607 static int kingsun_resume(struct usb_interface *intf)
608 {
609 	struct kingsun_cb *kingsun = usb_get_intfdata(intf);
610 
611 	if (kingsun->rx_urb != NULL)
612 		usb_submit_urb(kingsun->rx_urb, GFP_KERNEL);
613 	netif_device_attach(kingsun->netdev);
614 
615 	return 0;
616 }
617 #endif
618 
619 /*
620  * USB device callbacks
621  */
622 static struct usb_driver irda_driver = {
623 	.name		= "kingsun-sir",
624 	.probe		= kingsun_probe,
625 	.disconnect	= kingsun_disconnect,
626 	.id_table	= dongles,
627 #ifdef CONFIG_PM
628 	.suspend	= kingsun_suspend,
629 	.resume		= kingsun_resume,
630 #endif
631 };
632 
633 module_usb_driver(irda_driver);
634 
635 MODULE_AUTHOR("Alex Villacís Lasso <a_villacis@palosanto.com>");
636 MODULE_DESCRIPTION("IrDA-USB Dongle Driver for KingSun/DonShine");
637 MODULE_LICENSE("GPL");
638