78 #include <linux/module.h>
80 #include <linux/kernel.h>
81 #include <linux/types.h>
82 #include <linux/errno.h>
84 #include <linux/slab.h>
86 #include <linux/device.h>
89 #include <asm/unaligned.h>
90 #include <asm/byteorder.h>
91 #include <asm/uaccess.h>
97 #define KSDAZZLE_VENDOR_ID 0x07d0
98 #define KSDAZZLE_PRODUCT_ID 0x4100
109 #define KINGSUN_MTT 0x07
110 #define KINGSUN_REQ_RECV 0x01
111 #define KINGSUN_REQ_SEND 0x09
113 #define KINGSUN_SND_FIFO_SIZE 2048
114 #define KINGSUN_RCV_MAX 2048
122 #define KS_DATA_5_BITS 0x00
123 #define KS_DATA_6_BITS 0x01
124 #define KS_DATA_7_BITS 0x02
125 #define KS_DATA_8_BITS 0x03
127 #define KS_STOP_BITS_1 0x00
128 #define KS_STOP_BITS_2 0x08
130 #define KS_PAR_DISABLE 0x00
131 #define KS_PAR_EVEN 0x10
132 #define KS_PAR_ODD 0x30
133 #define KS_RESET 0x80
135 #define KINGSUN_EP_IN 0
136 #define KINGSUN_EP_OUT 1
168 static void ksdazzle_speed_irq(
struct urb *
urb)
171 if (urb->status != 0)
173 "ksdazzle_speed_irq: urb asynchronously failed - %d\n",
178 static int ksdazzle_change_speed(
struct ksdazzle_cb *kingsun,
unsigned speed)
180 static unsigned int supported_speeds[] = { 2400, 9600, 19200, 38400,
181 57600, 115200, 576000, 1152000, 4000000, 0
190 for (i = 0; supported_speeds[
i] && supported_speeds[
i] != speed; i++) ;
191 if (supported_speeds[i] == 0)
200 usb_sndctrlpipe(kingsun->
usbdev, 0),
204 ksdazzle_speed_irq, kingsun);
212 static void ksdazzle_send_irq(
struct urb *
urb);
213 static int ksdazzle_submit_tx_fragment(
struct ksdazzle_cb *kingsun)
215 unsigned int wraplen;
230 kingsun->
tx_payload, 8, ksdazzle_send_irq, kingsun, 1);
231 kingsun->
tx_urb->status = 0;
240 static void ksdazzle_send_irq(
struct urb *
urb)
247 if (!netif_running(kingsun->
netdev)) {
249 "ksdazzle_send_irq: Network not running!\n");
254 if (urb->status != 0) {
256 "ksdazzle_send_irq: urb asynchronously failed - %d\n",
275 if ((ret = ksdazzle_submit_tx_fragment(kingsun)) != 0) {
277 "ksdazzle_send_irq: failed tx_urb submit: %d\n",
284 netdev->
stats.tx_errors++;
285 netif_start_queue(netdev);
293 ksdazzle_change_speed(kingsun,
296 netif_wake_queue(netdev);
308 unsigned int wraplen;
311 netif_stop_queue(netdev);
314 SKB_LINEAR_ASSERT(skb);
316 kingsun = netdev_priv(netdev);
318 spin_lock(&kingsun->
lock);
319 kingsun->
new_speed = irda_get_next_speed(skb);
326 if ((ret = ksdazzle_submit_tx_fragment(kingsun)) != 0) {
328 "ksdazzle_hard_xmit: failed tx_urb submit: %d\n", ret);
334 netdev->
stats.tx_errors++;
335 netif_start_queue(netdev);
338 netdev->
stats.tx_packets++;
344 spin_unlock(&kingsun->
lock);
350 static void ksdazzle_rcv_irq(
struct urb *urb)
356 if (!netif_running(netdev)) {
362 if (urb->status != 0) {
364 "ksdazzle_rcv_irq: urb asynchronously failed - %d\n",
370 if (urb->actual_length > 0) {
374 for (i = 0; i < urb->actual_length; i++) {
394 static int ksdazzle_net_open(
struct net_device *netdev)
428 err = ksdazzle_change_speed(kingsun, 9600);
438 if (!kingsun->
irlap) {
449 kingsun->
rx_urb->status = 0;
452 dev_err(&kingsun->
usbdev->dev,
"first urb-submit failed: %d\n", err);
456 netif_start_queue(netdev);
492 static int ksdazzle_net_close(
struct net_device *netdev)
497 netif_stop_queue(netdev);
543 if (netif_device_present(kingsun->
netdev))
544 return ksdazzle_change_speed(kingsun,
553 if (netif_running(kingsun->
netdev))
570 .ndo_start_xmit = ksdazzle_hard_xmit,
571 .ndo_open = ksdazzle_net_open,
572 .ndo_stop = ksdazzle_net_close,
573 .ndo_do_ioctl = ksdazzle_net_ioctl,
587 struct usb_device *
dev = interface_to_usbdev(intf);
591 int pipe, maxp_in, maxp_out;
598 interface = intf->cur_altsetting;
599 if (interface->desc.bNumEndpoints != 2) {
600 dev_err(&intf->dev,
"ksdazzle: expected 2 endpoints, found %d\n",
601 interface->desc.bNumEndpoints);
605 if (!usb_endpoint_is_int_in(endpoint)) {
607 "ksdazzle: endpoint 0 is not interrupt IN\n");
612 pipe = usb_rcvintpipe(dev, ep_in);
613 maxp_in = usb_maxpacket(dev, pipe, usb_pipeout(pipe));
614 if (maxp_in > 255 || maxp_in <= 1) {
616 "ksdazzle: endpoint 0 has max packet size %d not in range [2..255]\n",
622 if (!usb_endpoint_is_int_out(endpoint)) {
624 "ksdazzle: endpoint 1 is not interrupt OUT\n");
629 pipe = usb_sndintpipe(dev, ep_out);
630 maxp_out = usb_maxpacket(dev, pipe, usb_pipeout(pipe));
638 kingsun = netdev_priv(net);
641 kingsun->
ep_in = ep_in;
685 "Vendor: %x, Product: %x\n",
686 dev->devnum,
le16_to_cpu(dev->descriptor.idVendor),
696 kingsun->
qos.baud_rate.bits =
708 dev_info(&net->
dev,
"IrDA: Registered KingSun/Dazzle device %s\n",
711 usb_set_intfdata(intf, kingsun);
737 struct ksdazzle_cb *kingsun = usb_get_intfdata(intf);
762 usb_set_intfdata(intf,
NULL);
769 struct ksdazzle_cb *kingsun = usb_get_intfdata(intf);
784 struct ksdazzle_cb *kingsun = usb_get_intfdata(intf);
799 static struct usb_driver irda_driver = {
800 .name =
"ksdazzle-sir",
801 .probe = ksdazzle_probe,
802 .disconnect = ksdazzle_disconnect,
805 .suspend = ksdazzle_suspend,
806 .resume = ksdazzle_resume,