[PATCH 3/5] USB suspend and hibernation support for Siano's SMS chip-set based devices.

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



This patch provides USB suspend and hibernation support for Siano's SMS chipset based USB device

Signed-off-by: Uri Shkolnik <uris@xxxxxxxxxxxx> hibernation



      
This patch provides USB suspend and hibernation support for Siano's SMS chipset based USB device

Signed-off-by: Uri Shkolnik <uris@xxxxxxxxxxxx> hibernation

diff -uNr v4l-dvb-c5f976cab011/linux/drivers/media/dvb/siano/smsusb.c v4l-dvb-c5f976cab011_0003/linux/drivers/media/dvb/siano/smsusb.c
--- v4l-dvb-c5f976cab011/linux/drivers/media/dvb/siano/smsusb.c	2008-11-16 15:40:21.000000000 +0200
+++ v4l-dvb-c5f976cab011_0003/linux/drivers/media/dvb/siano/smsusb.c	2008-11-18 18:26:04.000000000 +0200
@@ -1,23 +1,23 @@
-/*
- *  Driver for the Siano SMS1xxx USB dongle
- *
- *  author: Anatoly Greenblat
- *
- *  Copyright (c), 2005-2008 Siano Mobile Silicon, Inc.
- *
- *  This program is free software; you can redistribute it and/or modify
- *  it under the terms of the GNU General Public License version 2 as
- *  published by the Free Software Foundation;
- *
- *  Software distributed under the License is distributed on an "AS IS"
- *  basis, WITHOUT WARRANTY OF ANY KIND, either express or implied.
- *
- *  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., 675 Mass Ave, Cambridge, MA 02139, USA.
- */
+/****************************************************************
+
+Siano Mobile Silicon, Inc.
+MDTV receiver kernel modules.
+Copyright (C) 2006-2008, Uri Shkolnik
+
+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, see <http://www.gnu.org/licenses/>.
+
+****************************************************************/
 
 #include <linux/kernel.h>
 #include <linux/init.h>
@@ -37,7 +37,7 @@
 
 struct smsusb_urb_t {
 	struct smscore_buffer_t *cb;
-	struct smsusb_device_t	*dev;
+	struct smsusb_device_t *dev;
 
 	struct urb urb;
 };
@@ -46,10 +46,10 @@
 	struct usb_device *udev;
 	struct smscore_device_t *coredev;
 
-	struct smsusb_urb_t 	surbs[MAX_URBS];
+	struct smsusb_urb_t surbs[MAX_URBS];
 
-	int		response_alignment;
-	int		buffer_size;
+	int response_alignment;
+	int buffer_size;
 };
 
 static int smsusb_submit_urb(struct smsusb_device_t *dev,
@@ -61,7 +61,7 @@
 static void smsusb_onresponse(struct urb *urb, struct pt_regs *regs)
 #endif
 {
-	struct smsusb_urb_t *surb = (struct smsusb_urb_t *) urb->context;
+	struct smsusb_urb_t *surb = (struct smsusb_urb_t *)urb->context;
 	struct smsusb_device_t *dev = surb->dev;
 
 	if (urb->status < 0) {
@@ -71,7 +71,7 @@
 	}
 
 	if (urb->actual_length > 0) {
-		struct SmsMsgHdr_ST *phdr = (struct SmsMsgHdr_ST *) surb->cb->p;
+		struct SmsMsgHdr_ST *phdr = (struct SmsMsgHdr_ST *)surb->cb->p;
 
 		if (urb->actual_length >= phdr->msgLength) {
 			surb->cb->size = phdr->msgLength;
@@ -80,11 +80,11 @@
 			    (phdr->msgFlags & MSG_HDR_FLAG_SPLIT_MSG)) {
 
 				surb->cb->offset =
-					dev->response_alignment +
-					((phdr->msgFlags >> 8) & 3);
+				    dev->response_alignment +
+				    ((phdr->msgFlags >> 8) & 3);
 
 				/* sanity check */
-				if (((int) phdr->msgLength +
+				if (((int)phdr->msgLength +
 				     surb->cb->offset) > urb->actual_length) {
 					sms_err("invalid response "
 						"msglen %d offset %d "
@@ -97,7 +97,7 @@
 
 				/* move buffer pointer and
 				 * copy header to its new location */
-				memcpy((char *) phdr + surb->cb->offset,
+				memcpy((char *)phdr + surb->cb->offset,
 				       phdr, sizeof(struct SmsMsgHdr_ST));
 			} else
 				surb->cb->offset = 0;
@@ -126,15 +126,11 @@
 		}
 	}
 
-	usb_fill_bulk_urb(
-		&surb->urb,
-		dev->udev,
-		usb_rcvbulkpipe(dev->udev, 0x81),
-		surb->cb->p,
-		dev->buffer_size,
-		smsusb_onresponse,
-		surb
-	);
+	usb_fill_bulk_urb(&surb->urb,
+			  dev->udev,
+			  usb_rcvbulkpipe(dev->udev, 0x81),
+			  surb->cb->p,
+			  dev->buffer_size, smsusb_onresponse, surb);
 	surb->urb.transfer_dma = surb->cb->phys;
 	surb->urb.transfer_flags |= URB_NO_TRANSFER_DMA_MAP;
 
@@ -173,7 +169,7 @@
 
 static int smsusb_sendrequest(void *context, void *buffer, size_t size)
 {
-	struct smsusb_device_t *dev = (struct smsusb_device_t *) context;
+	struct smsusb_device_t *dev = (struct smsusb_device_t *)context;
 	int dummy;
 
 	return usb_bulk_msg(dev->udev, usb_sndbulkpipe(dev->udev, 2),
@@ -230,14 +226,14 @@
 		rc = usb_bulk_msg(udev, usb_sndbulkpipe(udev, 2),
 				  fw_buffer, fw->size, &dummy, 1000);
 
-		sms_info("sent %zd(%d) bytes, rc %d", fw->size, dummy, rc);
+		sms_info("sent %d(%d) bytes, rc %d", fw->size, dummy, rc);
 
 		kfree(fw_buffer);
 	} else {
 		sms_err("failed to allocate firmware buffer");
 		rc = -ENOMEM;
 	}
-	sms_info("read FW %s, size=%zd", fw_filename, fw->size);
+	sms_info("read FW %s, size=%d", fw_filename, fw->size);
 
 	release_firmware(fw);
 
@@ -247,7 +243,7 @@
 static void smsusb1_detectmode(void *context, int *mode)
 {
 	char *product_string =
-		((struct smsusb_device_t *) context)->udev->product;
+	    ((struct smsusb_device_t *)context)->udev->product;
 
 	*mode = DEVICE_MODE_NONE;
 
@@ -269,7 +265,8 @@
 static int smsusb1_setmode(void *context, int mode)
 {
 	struct SmsMsgHdr_ST Msg = { MSG_SW_RELOAD_REQ, 0, HIF_TASK,
-			     sizeof(struct SmsMsgHdr_ST), 0 };
+		sizeof(struct SmsMsgHdr_ST), 0
+	};
 
 	if (mode < DEVICE_MODE_DVBT || mode > DEVICE_MODE_DVBT_BDA) {
 		sms_err("invalid firmware id specified %d", mode);
@@ -282,7 +279,7 @@
 static void smsusb_term_device(struct usb_interface *intf)
 {
 	struct smsusb_device_t *dev =
-		(struct smsusb_device_t *) usb_get_intfdata(intf);
+	    (struct smsusb_device_t *)usb_get_intfdata(intf);
 
 	if (dev) {
 		smsusb_stop_streaming(dev);
@@ -333,8 +330,8 @@
 	case SMS_VEGA:
 		dev->buffer_size = USB2_BUFFER_SIZE;
 		dev->response_alignment =
-			dev->udev->ep_in[1]->desc.wMaxPacketSize -
-			sizeof(struct SmsMsgHdr_ST);
+		    dev->udev->ep_in[1]->desc.wMaxPacketSize -
+		    sizeof(struct SmsMsgHdr_ST);
 
 		params.flags |= SMS_DEVICE_FAMILY2;
 		break;
@@ -395,8 +392,9 @@
 	rc = usb_clear_halt(udev, usb_rcvbulkpipe(udev, 0x02));
 
 	if (intf->num_altsetting > 0) {
-		rc = usb_set_interface(
-			udev, intf->cur_altsetting->desc.bInterfaceNumber, 0);
+		rc = usb_set_interface(udev,
+				       intf->cur_altsetting->desc.
+				       bInterfaceNumber, 0);
 		if (rc < 0) {
 			sms_err("usb_set_interface failed, rc %d", rc);
 			return rc;
@@ -404,12 +402,13 @@
 	}
 
 	sms_info("smsusb_probe %d",
-	       intf->cur_altsetting->desc.bInterfaceNumber);
+		 intf->cur_altsetting->desc.bInterfaceNumber);
 	for (i = 0; i < intf->cur_altsetting->desc.bNumEndpoints; i++)
 		sms_info("endpoint %d %02x %02x %d", i,
-		       intf->cur_altsetting->endpoint[i].desc.bEndpointAddress,
-		       intf->cur_altsetting->endpoint[i].desc.bmAttributes,
-		       intf->cur_altsetting->endpoint[i].desc.wMaxPacketSize);
+			 intf->cur_altsetting->endpoint[i].desc.
+			 bEndpointAddress,
+			 intf->cur_altsetting->endpoint[i].desc.bmAttributes,
+			 intf->cur_altsetting->endpoint[i].desc.wMaxPacketSize);
 
 	if ((udev->actconfig->desc.bNumInterfaces == 2) &&
 	    (intf->cur_altsetting->desc.bInterfaceNumber == 0)) {
@@ -421,9 +420,9 @@
 		snprintf(devpath, sizeof(devpath), "usb\\%d-%s",
 			 udev->bus->busnum, udev->devpath);
 		sms_info("stellar device was found.");
-		return smsusb1_load_firmware(
-				udev, smscore_registry_getmode(devpath),
-				id->driver_info);
+		return smsusb1_load_firmware(udev,
+					     smscore_registry_getmode(devpath),
+					     id->driver_info);
 	}
 
 	rc = smsusb_init_device(intf, id->driver_info);
@@ -436,11 +435,55 @@
 	smsusb_term_device(intf);
 }
 
+static int smsusb_suspend(struct usb_interface *intf, pm_message_t msg)
+{
+	struct smsusb_device_t *dev =
+	    (struct smsusb_device_t *)usb_get_intfdata(intf);
+	printk(KERN_INFO "%s  Entering status %d.\n", __func__, msg.event);
+	smsusb_stop_streaming(dev);
+	return 0;
+}
+
+static int smsusb_resume(struct usb_interface *intf)
+{
+	int rc, i;
+	struct smsusb_device_t *dev =
+	    (struct smsusb_device_t *)usb_get_intfdata(intf);
+	struct usb_device *udev = interface_to_usbdev(intf);
+
+	printk(KERN_INFO "%s  Entering.\n", __func__);
+	usb_clear_halt(udev, usb_rcvbulkpipe(udev, 0x81));
+	usb_clear_halt(udev, usb_rcvbulkpipe(udev, 0x02));
+
+	for (i = 0; i < intf->cur_altsetting->desc.bNumEndpoints; i++)
+		printk(KERN_INFO "endpoint %d %02x %02x %d\n", i,
+		       intf->cur_altsetting->endpoint[i].desc.bEndpointAddress,
+		       intf->cur_altsetting->endpoint[i].desc.bmAttributes,
+		       intf->cur_altsetting->endpoint[i].desc.wMaxPacketSize);
+
+	if (intf->num_altsetting > 0) {
+		rc = usb_set_interface(udev,
+				       intf->cur_altsetting->desc.
+				       bInterfaceNumber, 0);
+		if (rc < 0) {
+			printk(KERN_INFO
+			       "%s usb_set_interface failed, rc %d\n",
+			       __func__, rc);
+			return rc;
+		}
+	}
+
+	smsusb_start_streaming(dev);
+	return 0;
+}
+
 static struct usb_driver smsusb_driver = {
-	.name			= "sms1xxx",
-	.probe			= smsusb_probe,
-	.disconnect		= smsusb_disconnect,
-	.id_table		= smsusb_id_table,
+	.name = "smsusb",
+	.probe = smsusb_probe,
+	.disconnect = smsusb_disconnect,
+	.suspend = smsusb_suspend,
+	.resume = smsusb_resume,
+	.id_table = smsusb_id_table,
 };
 
 int smsusb_register(void)
@@ -461,3 +504,6 @@
 	usb_deregister(&smsusb_driver);
 }
 
+MODULE_DESCRIPTION("Driver for the Siano SMS1xxx USB dongle");
+MODULE_AUTHOR("Siano Mobile Silicon, INC. (uris@xxxxxxxxxxxx)");
+MODULE_LICENSE("GPL");
_______________________________________________
linux-dvb mailing list
linux-dvb@xxxxxxxxxxx
http://www.linuxtv.org/cgi-bin/mailman/listinfo/linux-dvb

[Index of Archives]     [Linux Media]     [Video 4 Linux]     [Asterisk]     [Samba]     [Xorg]     [Xfree86]     [Linux USB]

  Powered by Linux