2005-04-16 15:20:36 -07:00
/*
2006-10-03 23:01:26 +02:00
* drivers / usb / core / usb . c
2005-04-16 15:20:36 -07:00
*
* ( C ) Copyright Linus Torvalds 1999
* ( C ) Copyright Johannes Erdfelt 1999 - 2001
* ( C ) Copyright Andreas Gal 1999
* ( C ) Copyright Gregory P . Smith 1999
* ( C ) Copyright Deti Fliegl 1999 ( new USB architecture )
* ( C ) Copyright Randy Dunlap 2000
* ( C ) Copyright David Brownell 2000 - 2004
* ( C ) Copyright Yggdrasil Computing , Inc . 2000
* ( usb_device_id matching changes by Adam J . Richter )
* ( C ) Copyright Greg Kroah - Hartman 2002 - 2003
*
* NOTE ! This is not actually a driver at all , rather this is
* just a collection of helper routines that implement the
* generic USB things that the real drivers can use . .
*
* Think of this as a " USB library " rather than anything else .
* It should be considered a slave , with no callbacks . Callbacks
* are evil .
*/
# include <linux/module.h>
2007-02-20 15:00:53 -05:00
# include <linux/moduleparam.h>
2005-04-16 15:20:36 -07:00
# include <linux/string.h>
# include <linux/bitops.h>
# include <linux/slab.h>
# include <linux/interrupt.h> /* for in_interrupt() */
# include <linux/kmod.h>
# include <linux/init.h>
# include <linux/spinlock.h>
# include <linux/errno.h>
# include <linux/usb.h>
2010-04-24 23:21:52 +02:00
# include <linux/usb/hcd.h>
2006-01-11 15:55:29 +01:00
# include <linux/mutex.h>
2006-09-19 10:14:07 -04:00
# include <linux/workqueue.h>
2009-04-24 14:56:26 -07:00
# include <linux/debugfs.h>
2005-04-16 15:20:36 -07:00
# include <asm/io.h>
2007-10-30 10:35:04 +01:00
# include <linux/scatterlist.h>
2005-04-16 15:20:36 -07:00
# include <linux/mm.h>
# include <linux/dma-mapping.h>
# include "usb.h"
const char * usbcore_name = " usbcore " ;
2012-01-13 09:32:20 +10:30
static bool nousb ; /* Disable USB when built into kernel image */
2005-04-16 15:20:36 -07:00
2014-11-29 23:47:05 +01:00
# ifdef CONFIG_PM
2007-02-20 15:00:53 -05:00
static int usb_autosuspend_delay = 2 ; /* Default delay value,
* in seconds */
2007-03-13 16:39:15 -04:00
module_param_named ( autosuspend , usb_autosuspend_delay , int , 0644 ) ;
2007-02-20 15:00:53 -05:00
MODULE_PARM_DESC ( autosuspend , " default autosuspend delay " ) ;
# else
# define usb_autosuspend_delay 0
# endif
2005-04-16 15:20:36 -07:00
2009-12-03 09:44:34 -08:00
/**
* usb_find_alt_setting ( ) - Given a configuration , find the alternate setting
* for the given interface .
2009-12-13 10:17:16 -08:00
* @ config : the configuration to search ( not necessarily the current config ) .
* @ iface_num : interface number to search in
* @ alt_num : alternate interface setting number to search for .
2009-12-03 09:44:34 -08:00
*
* Search the configuration ' s interface cache for the given alt setting .
2013-08-02 20:10:04 +02:00
*
* Return : The alternate setting , if found . % NULL otherwise .
2009-12-03 09:44:34 -08:00
*/
struct usb_host_interface * usb_find_alt_setting (
struct usb_host_config * config ,
unsigned int iface_num ,
unsigned int alt_num )
{
struct usb_interface_cache * intf_cache = NULL ;
int i ;
for ( i = 0 ; i < config - > desc . bNumInterfaces ; i + + ) {
if ( config - > intf_cache [ i ] - > altsetting [ 0 ] . desc . bInterfaceNumber
= = iface_num ) {
intf_cache = config - > intf_cache [ i ] ;
break ;
}
}
if ( ! intf_cache )
return NULL ;
for ( i = 0 ; i < intf_cache - > num_altsetting ; i + + )
if ( intf_cache - > altsetting [ i ] . desc . bAlternateSetting = = alt_num )
return & intf_cache - > altsetting [ i ] ;
printk ( KERN_DEBUG " Did not find alt setting %u for intf %u, "
" config %u \n " , alt_num , iface_num ,
config - > desc . bConfigurationValue ) ;
return NULL ;
}
EXPORT_SYMBOL_GPL ( usb_find_alt_setting ) ;
2005-04-16 15:20:36 -07:00
/**
* usb_ifnum_to_if - get the interface object with a given interface number
* @ dev : the device whose current configuration is considered
* @ ifnum : the desired interface
*
* This walks the device descriptor for the currently active configuration
2013-08-02 20:10:04 +02:00
* to find the interface object with the particular interface number .
2005-04-16 15:20:36 -07:00
*
* Note that configuration descriptors are not required to assign interface
* numbers sequentially , so that it would be incorrect to assume that
* the first interface in that descriptor corresponds to interface zero .
* This routine helps device drivers avoid such mistakes .
* However , you should make sure that you do the right thing with any
* alternate settings available for this interfaces .
*
* Don ' t call this function unless you are bound to one of the interfaces
* on this device or you have locked the device !
2013-08-02 20:10:04 +02:00
*
* Return : A pointer to the interface that has @ ifnum as interface number ,
* if found . % NULL otherwise .
2005-04-16 15:20:36 -07:00
*/
2006-08-26 23:48:11 -03:00
struct usb_interface * usb_ifnum_to_if ( const struct usb_device * dev ,
unsigned ifnum )
2005-04-16 15:20:36 -07:00
{
struct usb_host_config * config = dev - > actconfig ;
int i ;
if ( ! config )
return NULL ;
for ( i = 0 ; i < config - > desc . bNumInterfaces ; i + + )
if ( config - > interface [ i ] - > altsetting [ 0 ]
. desc . bInterfaceNumber = = ifnum )
return config - > interface [ i ] ;
return NULL ;
}
2008-01-25 11:12:21 -06:00
EXPORT_SYMBOL_GPL ( usb_ifnum_to_if ) ;
2005-04-16 15:20:36 -07:00
/**
2008-02-29 22:03:07 -08:00
* usb_altnum_to_altsetting - get the altsetting structure with a given alternate setting number .
2005-04-16 15:20:36 -07:00
* @ intf : the interface containing the altsetting in question
* @ altnum : the desired alternate setting number
*
* This searches the altsetting array of the specified interface for
2013-08-02 20:10:04 +02:00
* an entry with the correct bAlternateSetting value .
2005-04-16 15:20:36 -07:00
*
* Note that altsettings need not be stored sequentially by number , so
* it would be incorrect to assume that the first altsetting entry in
* the array corresponds to altsetting zero . This routine helps device
* drivers avoid such mistakes .
*
* Don ' t call this function unless you are bound to the intf interface
* or you have locked the device !
2013-08-02 20:10:04 +02:00
*
* Return : A pointer to the entry of the altsetting array of @ intf that
* has @ altnum as the alternate setting number . % NULL if not found .
2005-04-16 15:20:36 -07:00
*/
2008-01-30 15:21:33 -08:00
struct usb_host_interface * usb_altnum_to_altsetting (
const struct usb_interface * intf ,
unsigned int altnum )
2005-04-16 15:20:36 -07:00
{
int i ;
for ( i = 0 ; i < intf - > num_altsetting ; i + + ) {
if ( intf - > altsetting [ i ] . desc . bAlternateSetting = = altnum )
return & intf - > altsetting [ i ] ;
}
return NULL ;
}
2008-01-25 11:12:21 -06:00
EXPORT_SYMBOL_GPL ( usb_altnum_to_altsetting ) ;
2005-04-16 15:20:36 -07:00
2009-12-15 07:47:28 -08:00
struct find_interface_arg {
int minor ;
2009-12-14 21:45:35 -07:00
struct device_driver * drv ;
2009-12-15 07:47:28 -08:00
} ;
2008-01-30 15:21:33 -08:00
static int __find_interface ( struct device * dev , void * data )
2005-03-21 11:09:40 -08:00
{
2009-12-15 07:47:28 -08:00
struct find_interface_arg * arg = data ;
2005-12-21 17:24:54 -08:00
struct usb_interface * intf ;
2005-03-21 11:09:40 -08:00
2009-05-04 19:48:32 +02:00
if ( ! is_usb_interface ( dev ) )
2005-03-21 11:09:40 -08:00
return 0 ;
2009-12-14 21:45:35 -07:00
if ( dev - > driver ! = arg - > drv )
return 0 ;
2005-03-21 11:09:40 -08:00
intf = to_usb_interface ( dev ) ;
2009-12-14 21:45:35 -07:00
return intf - > minor = = arg - > minor ;
2005-03-21 11:09:40 -08:00
}
2005-04-16 15:20:36 -07:00
/**
* usb_find_interface - find usb_interface pointer for driver and device
* @ drv : the driver whose current configuration is considered
* @ minor : the minor number of the desired device
*
2009-11-18 11:02:13 -07:00
* This walks the bus device list and returns a pointer to the interface
2009-12-14 21:45:35 -07:00
* with the matching minor and driver . Note , this only works for devices
* that share the USB major number .
2013-08-02 20:10:04 +02:00
*
* Return : A pointer to the interface with the matching major and @ minor .
2005-04-16 15:20:36 -07:00
*/
struct usb_interface * usb_find_interface ( struct usb_driver * drv , int minor )
{
2009-12-15 07:47:28 -08:00
struct find_interface_arg argb ;
2009-11-18 11:02:13 -07:00
struct device * dev ;
2009-12-15 07:47:28 -08:00
argb . minor = minor ;
2009-12-14 21:45:35 -07:00
argb . drv = & drv - > drvwrap . driver ;
dev = bus_find_device ( & usb_bus_type , NULL , & argb , __find_interface ) ;
2009-11-18 11:02:13 -07:00
/* Drop reference count from bus_find_device */
put_device ( dev ) ;
return dev ? to_usb_interface ( dev ) : NULL ;
2005-04-16 15:20:36 -07:00
}
2008-01-25 11:12:21 -06:00
EXPORT_SYMBOL_GPL ( usb_find_interface ) ;
2005-04-16 15:20:36 -07:00
2013-05-17 12:08:51 -07:00
struct each_dev_arg {
void * data ;
int ( * fn ) ( struct usb_device * , void * ) ;
} ;
static int __each_dev ( struct device * dev , void * data )
{
struct each_dev_arg * arg = ( struct each_dev_arg * ) data ;
/* There are struct usb_interface on the same bus, filter them out */
if ( ! is_usb_device ( dev ) )
return 0 ;
return arg - > fn ( container_of ( dev , struct usb_device , dev ) , arg - > data ) ;
}
/**
* usb_for_each_dev - iterate over all USB devices in the system
* @ data : data pointer that will be handed to the callback function
* @ fn : callback function to be called for each USB device
*
* Iterate over all USB devices and call @ fn for each , passing it @ data . If it
* returns anything other than 0 , we break the iteration prematurely and return
* that value .
*/
int usb_for_each_dev ( void * data , int ( * fn ) ( struct usb_device * , void * ) )
{
struct each_dev_arg arg = { data , fn } ;
return bus_for_each_dev ( & usb_bus_type , NULL , & arg , __each_dev ) ;
}
EXPORT_SYMBOL_GPL ( usb_for_each_dev ) ;
2005-04-16 15:20:36 -07:00
/**
* usb_release_dev - free a usb device structure when all users of it are finished .
* @ dev : device that ' s been disconnected
*
* Will be called only by the device core when all users of this usb device are
* done .
*/
static void usb_release_dev ( struct device * dev )
{
struct usb_device * udev ;
2009-04-27 19:57:26 -07:00
struct usb_hcd * hcd ;
2005-04-16 15:20:36 -07:00
udev = to_usb_device ( dev ) ;
2009-04-27 19:57:26 -07:00
hcd = bus_to_hcd ( udev - > bus ) ;
2005-04-16 15:20:36 -07:00
usb_destroy_configuration ( udev ) ;
2011-09-23 14:19:47 -07:00
usb_release_bos_descriptor ( udev ) ;
2009-04-27 19:57:26 -07:00
usb_put_hcd ( hcd ) ;
2005-04-16 15:20:36 -07:00
kfree ( udev - > product ) ;
kfree ( udev - > manufacturer ) ;
kfree ( udev - > serial ) ;
kfree ( udev ) ;
}
2007-11-06 15:01:52 -05:00
static int usb_dev_uevent ( struct device * dev , struct kobj_uevent_env * env )
{
struct usb_device * usb_dev ;
usb_dev = to_usb_device ( dev ) ;
if ( add_uevent_var ( env , " BUSNUM=%03d " , usb_dev - > bus - > busnum ) )
return - ENOMEM ;
if ( add_uevent_var ( env , " DEVNUM=%03d " , usb_dev - > devnum ) )
return - ENOMEM ;
return 0 ;
}
2006-08-30 15:47:02 -04:00
# ifdef CONFIG_PM
2008-08-12 14:34:10 -04:00
/* USB device Power-Management thunks.
* There ' s no need to distinguish here between quiescing a USB device
* and powering it down ; the generic_suspend ( ) routine takes care of
* it by skipping the usb_port_suspend ( ) call for a quiesce . And for
* USB interfaces there ' s no difference at all .
*/
static int usb_dev_prepare ( struct device * dev )
{
return 0 ; /* Implement eventually? */
}
static void usb_dev_complete ( struct device * dev )
{
/* Currently used only for rebinding interfaces */
2012-01-11 08:38:35 +01:00
usb_resume_complete ( dev ) ;
2008-08-12 14:34:10 -04:00
}
static int usb_dev_suspend ( struct device * dev )
{
return usb_suspend ( dev , PMSG_SUSPEND ) ;
}
static int usb_dev_resume ( struct device * dev )
{
2008-11-25 16:39:18 -05:00
return usb_resume ( dev , PMSG_RESUME ) ;
2008-08-12 14:34:10 -04:00
}
static int usb_dev_freeze ( struct device * dev )
{
return usb_suspend ( dev , PMSG_FREEZE ) ;
}
static int usb_dev_thaw ( struct device * dev )
{
2008-11-25 16:39:18 -05:00
return usb_resume ( dev , PMSG_THAW ) ;
2008-08-12 14:34:10 -04:00
}
static int usb_dev_poweroff ( struct device * dev )
{
return usb_suspend ( dev , PMSG_HIBERNATE ) ;
}
static int usb_dev_restore ( struct device * dev )
{
2008-11-25 16:39:18 -05:00
return usb_resume ( dev , PMSG_RESTORE ) ;
2008-08-12 14:34:10 -04:00
}
2009-12-14 18:00:08 -08:00
static const struct dev_pm_ops usb_device_pm_ops = {
2008-08-12 14:34:10 -04:00
. prepare = usb_dev_prepare ,
. complete = usb_dev_complete ,
. suspend = usb_dev_suspend ,
. resume = usb_dev_resume ,
. freeze = usb_dev_freeze ,
. thaw = usb_dev_thaw ,
. poweroff = usb_dev_poweroff ,
. restore = usb_dev_restore ,
2011-03-18 19:55:36 +01:00
. runtime_suspend = usb_runtime_suspend ,
. runtime_resume = usb_runtime_resume ,
. runtime_idle = usb_runtime_idle ,
2008-08-12 14:34:10 -04:00
} ;
2006-11-13 15:02:04 -05:00
# endif /* CONFIG_PM */
2006-08-30 15:47:02 -04:00
2009-04-30 15:23:42 +02:00
2013-04-06 09:56:00 -07:00
static char * usb_devnode ( struct device * dev ,
2013-04-11 11:43:29 -07:00
umode_t * mode , kuid_t * uid , kgid_t * gid )
2009-04-30 15:23:42 +02:00
{
struct usb_device * usb_dev ;
usb_dev = to_usb_device ( dev ) ;
return kasprintf ( GFP_KERNEL , " bus/usb/%03d/%03d " ,
usb_dev - > bus - > busnum , usb_dev - > devnum ) ;
}
2008-08-12 14:34:10 -04:00
struct device_type usb_device_type = {
. name = " usb_device " ,
. release = usb_release_dev ,
. uevent = usb_dev_uevent ,
2009-09-18 23:01:12 +02:00
. devnode = usb_devnode ,
2010-08-05 13:12:14 -04:00
# ifdef CONFIG_PM
2008-08-12 14:34:10 -04:00
. pm = & usb_device_pm_ops ,
2010-08-05 13:12:14 -04:00
# endif
2008-08-12 14:34:10 -04:00
} ;
2007-07-31 20:34:00 -07:00
/* Returns 1 if @usb_bus is WUSB, 0 otherwise */
static unsigned usb_bus_is_wusb ( struct usb_bus * bus )
{
struct usb_hcd * hcd = container_of ( bus , struct usb_hcd , self ) ;
return hcd - > wireless ;
}
2005-04-16 15:20:36 -07:00
/**
* usb_alloc_dev - usb device constructor ( usbcore - internal )
* @ parent : hub to which device is connected ; null to allocate a root hub
* @ bus : bus used to access the device
* @ port1 : one - based index of port ; ignored for root hubs
2007-01-23 15:55:28 -05:00
* Context : ! in_interrupt ( )
2005-04-16 15:20:36 -07:00
*
* Only hub drivers ( including virtual root hub drivers for host
* controllers ) should ever call this .
*
* This call may not be used in a non - sleeping context .
2013-08-02 20:10:04 +02:00
*
* Return : On success , a pointer to the allocated usb device . % NULL on
* failure .
2005-04-16 15:20:36 -07:00
*/
2008-01-30 15:21:33 -08:00
struct usb_device * usb_alloc_dev ( struct usb_device * parent ,
struct usb_bus * bus , unsigned port1 )
2005-04-16 15:20:36 -07:00
{
struct usb_device * dev ;
2012-10-06 15:23:17 +08:00
struct usb_hcd * usb_hcd = bus_to_hcd ( bus ) ;
2007-07-31 20:34:00 -07:00
unsigned root_hub = 0 ;
2005-04-16 15:20:36 -07:00
2005-10-24 15:38:24 -04:00
dev = kzalloc ( sizeof ( * dev ) , GFP_KERNEL ) ;
2005-04-16 15:20:36 -07:00
if ( ! dev )
return NULL ;
2012-10-06 15:23:17 +08:00
if ( ! usb_get_hcd ( usb_hcd ) ) {
2005-04-16 15:20:36 -07:00
kfree ( dev ) ;
return NULL ;
}
2009-04-27 19:57:26 -07:00
/* Root hubs aren't true devices, so don't allocate HCD resources */
if ( usb_hcd - > driver - > alloc_dev & & parent & &
! usb_hcd - > driver - > alloc_dev ( usb_hcd , dev ) ) {
usb_put_hcd ( bus_to_hcd ( bus ) ) ;
kfree ( dev ) ;
return NULL ;
}
2005-04-16 15:20:36 -07:00
device_initialize ( & dev - > dev ) ;
dev - > dev . bus = & usb_bus_type ;
2007-03-13 15:59:31 +01:00
dev - > dev . type = & usb_device_type ;
2008-04-30 15:37:19 -04:00
dev - > dev . groups = usb_device_groups ;
2005-04-16 15:20:36 -07:00
dev - > dev . dma_mask = bus - > controller - > dma_mask ;
2007-07-09 12:03:09 -07:00
set_dev_node ( & dev - > dev , dev_to_node ( bus - > controller ) ) ;
2005-04-16 15:20:36 -07:00
dev - > state = USB_STATE_ATTACHED ;
2012-07-03 23:22:38 -07:00
dev - > lpm_disable_count = 1 ;
2007-10-03 14:56:03 -07:00
atomic_set ( & dev - > urbnum , 0 ) ;
2005-04-16 15:20:36 -07:00
INIT_LIST_HEAD ( & dev - > ep0 . urb_list ) ;
dev - > ep0 . desc . bLength = USB_DT_ENDPOINT_SIZE ;
dev - > ep0 . desc . bDescriptorType = USB_DT_ENDPOINT ;
/* ep0 maxpacket comes later, from device descriptor */
2009-04-08 17:36:28 +00:00
usb_enable_endpoint ( dev , & dev - > ep0 , false ) ;
2007-09-10 11:34:26 -04:00
dev - > can_submit = 1 ;
2005-04-16 15:20:36 -07:00
/* Save readable and stable topology id, distinguishing devices
* by location for diagnostics , tools , driver model , etc . The
* string is a path along hub ports , from the root . Each device ' s
* dev - > devpath will be stable until USB is re - cabled , and hubs
2008-05-02 06:02:41 +02:00
* are often labeled with these port numbers . The name isn ' t
2005-04-16 15:20:36 -07:00
* as stable : bus - > busnum changes easily from modprobe order ,
* cardbus or pci hotplugging , and so on .
*/
2007-01-23 15:55:28 -05:00
if ( unlikely ( ! parent ) ) {
dev - > devpath [ 0 ] = ' 0 ' ;
2009-04-27 19:54:49 -07:00
dev - > route = 0 ;
2005-04-16 15:20:36 -07:00
dev - > dev . parent = bus - > controller ;
2008-05-02 06:02:41 +02:00
dev_set_name ( & dev - > dev , " usb%d " , bus - > busnum ) ;
2007-07-31 20:34:00 -07:00
root_hub = 1 ;
2005-04-16 15:20:36 -07:00
} else {
/* match any labeling on the hubs; it's one-based */
2009-04-27 19:54:49 -07:00
if ( parent - > devpath [ 0 ] = = ' 0 ' ) {
2007-01-23 15:55:28 -05:00
snprintf ( dev - > devpath , sizeof dev - > devpath ,
2005-04-16 15:20:36 -07:00
" %d " , port1 ) ;
2009-04-27 19:54:49 -07:00
/* Root ports are not counted in route string */
dev - > route = 0 ;
} else {
2007-01-23 15:55:28 -05:00
snprintf ( dev - > devpath , sizeof dev - > devpath ,
2005-04-16 15:20:36 -07:00
" %s.%d " , parent - > devpath , port1 ) ;
2009-09-04 10:53:17 -07:00
/* Route string assumes hubs have less than 16 ports */
if ( port1 < 15 )
dev - > route = parent - > route +
( port1 < < ( ( parent - > level - 1 ) * 4 ) ) ;
else
dev - > route = parent - > route +
( 15 < < ( ( parent - > level - 1 ) * 4 ) ) ;
2009-04-27 19:54:49 -07:00
}
2005-04-16 15:20:36 -07:00
dev - > dev . parent = & parent - > dev ;
2008-05-02 06:02:41 +02:00
dev_set_name ( & dev - > dev , " %d-%s " , bus - > busnum , dev - > devpath ) ;
2005-04-16 15:20:36 -07:00
/* hub driver sets up TT records */
}
2005-11-23 12:09:52 -05:00
dev - > portnum = port1 ;
2005-04-16 15:20:36 -07:00
dev - > bus = bus ;
dev - > parent = parent ;
INIT_LIST_HEAD ( & dev - > filelist ) ;
2006-08-30 15:47:02 -04:00
# ifdef CONFIG_PM
2010-11-15 15:57:51 -05:00
pm_runtime_set_autosuspend_delay ( & dev - > dev ,
usb_autosuspend_delay * 1000 ) ;
2007-12-21 16:54:15 -08:00
dev - > connect_time = jiffies ;
dev - > active_duration = - jiffies ;
2006-08-30 15:47:02 -04:00
# endif
2007-07-31 20:34:00 -07:00
if ( root_hub ) /* Root hub always ok [and always wired] */
dev - > authorized = 1 ;
else {
dev - > authorized = usb_hcd - > authorized_default ;
2013-10-10 23:41:27 +02:00
dev - > wusb = usb_bus_is_wusb ( bus ) ? 1 : 0 ;
2007-07-31 20:34:00 -07:00
}
2005-04-16 15:20:36 -07:00
return dev ;
}
2014-07-14 19:27:48 +05:30
EXPORT_SYMBOL_GPL ( usb_alloc_dev ) ;
2005-04-16 15:20:36 -07:00
/**
* usb_get_dev - increments the reference count of the usb device structure
* @ dev : the device being referenced
*
* Each live reference to a device should be refcounted .
*
* Drivers for USB interfaces should normally record such references in
* their probe ( ) methods , when they bind to an interface , and release
* them by calling usb_put_dev ( ) , in their disconnect ( ) methods .
*
2013-08-02 20:10:04 +02:00
* Return : A pointer to the device with the incremented reference counter .
2005-04-16 15:20:36 -07:00
*/
struct usb_device * usb_get_dev ( struct usb_device * dev )
{
if ( dev )
get_device ( & dev - > dev ) ;
return dev ;
}
2008-01-25 11:12:21 -06:00
EXPORT_SYMBOL_GPL ( usb_get_dev ) ;
2005-04-16 15:20:36 -07:00
/**
* usb_put_dev - release a use of the usb device structure
* @ dev : device that ' s been disconnected
*
* Must be called when a user of a device is finished with it . When the last
* user of the device calls this function , the memory of the device is freed .
*/
void usb_put_dev ( struct usb_device * dev )
{
if ( dev )
put_device ( & dev - > dev ) ;
}
2008-01-25 11:12:21 -06:00
EXPORT_SYMBOL_GPL ( usb_put_dev ) ;
2005-04-16 15:20:36 -07:00
/**
* usb_get_intf - increments the reference count of the usb interface structure
* @ intf : the interface being referenced
*
* Each live reference to a interface must be refcounted .
*
* Drivers for USB interfaces should normally record such references in
* their probe ( ) methods , when they bind to an interface , and release
* them by calling usb_put_intf ( ) , in their disconnect ( ) methods .
*
2013-08-02 20:10:04 +02:00
* Return : A pointer to the interface with the incremented reference counter .
2005-04-16 15:20:36 -07:00
*/
struct usb_interface * usb_get_intf ( struct usb_interface * intf )
{
if ( intf )
get_device ( & intf - > dev ) ;
return intf ;
}
2008-01-25 11:12:21 -06:00
EXPORT_SYMBOL_GPL ( usb_get_intf ) ;
2005-04-16 15:20:36 -07:00
/**
* usb_put_intf - release a use of the usb interface structure
* @ intf : interface that ' s been decremented
*
* Must be called when a user of an interface is finished with it . When the
* last user of the interface calls this function , the memory of the interface
* is freed .
*/
void usb_put_intf ( struct usb_interface * intf )
{
if ( intf )
put_device ( & intf - > dev ) ;
}
2008-01-25 11:12:21 -06:00
EXPORT_SYMBOL_GPL ( usb_put_intf ) ;
2005-04-16 15:20:36 -07:00
/* USB device locking
*
2005-11-17 17:10:32 -05:00
* USB devices and interfaces are locked using the semaphore in their
* embedded struct device . The hub driver guarantees that whenever a
* device is connected or disconnected , drivers are called with the
* USB device locked as well as their particular interface .
2005-04-16 15:20:36 -07:00
*
* Complications arise when several devices are to be locked at the same
* time . Only hub - aware drivers that are part of usbcore ever have to
2005-11-17 17:10:32 -05:00
* do this ; nobody else needs to worry about it . The rule for locking
* is simple :
2005-04-16 15:20:36 -07:00
*
* When locking both a device and its parent , always lock the
* the parent first .
*/
/**
2008-02-29 22:03:07 -08:00
* usb_lock_device_for_reset - cautiously acquire the lock for a usb device structure
2005-04-16 15:20:36 -07:00
* @ udev : device that ' s being locked
* @ iface : interface bound to the driver making the request ( optional )
*
* Attempts to acquire the device lock , but fails if the device is
* NOTATTACHED or SUSPENDED , or if iface is specified and the interface
* is neither BINDING nor BOUND . Rather than sleeping to wait for the
* lock , the routine polls repeatedly . This is to prevent deadlock with
* disconnect ; in some drivers ( such as usb - storage ) the disconnect ( )
2005-08-11 10:15:39 -04:00
* or suspend ( ) method will block waiting for a device reset to complete .
2005-04-16 15:20:36 -07:00
*
2013-08-02 20:10:04 +02:00
* Return : A negative error code for failure , otherwise 0.
2005-04-16 15:20:36 -07:00
*/
int usb_lock_device_for_reset ( struct usb_device * udev ,
2006-08-26 23:48:11 -03:00
const struct usb_interface * iface )
2005-04-16 15:20:36 -07:00
{
2005-08-11 10:15:39 -04:00
unsigned long jiffies_expire = jiffies + HZ ;
2005-04-16 15:20:36 -07:00
if ( udev - > state = = USB_STATE_NOTATTACHED )
return - ENODEV ;
if ( udev - > state = = USB_STATE_SUSPENDED )
return - EHOSTUNREACH ;
2008-11-04 11:29:27 -05:00
if ( iface & & ( iface - > condition = = USB_INTERFACE_UNBINDING | |
iface - > condition = = USB_INTERFACE_UNBOUND ) )
return - EINTR ;
2005-04-16 15:20:36 -07:00
2010-01-29 20:39:02 +00:00
while ( ! usb_trylock_device ( udev ) ) {
2005-08-11 10:15:39 -04:00
/* If we can't acquire the lock after waiting one second,
* we ' re probably deadlocked */
if ( time_after ( jiffies , jiffies_expire ) )
return - EBUSY ;
2005-04-16 15:20:36 -07:00
msleep ( 15 ) ;
if ( udev - > state = = USB_STATE_NOTATTACHED )
return - ENODEV ;
if ( udev - > state = = USB_STATE_SUSPENDED )
return - EHOSTUNREACH ;
2008-11-04 11:29:27 -05:00
if ( iface & & ( iface - > condition = = USB_INTERFACE_UNBINDING | |
iface - > condition = = USB_INTERFACE_UNBOUND ) )
2005-04-16 15:20:36 -07:00
return - EINTR ;
}
2008-11-04 11:29:27 -05:00
return 0 ;
2005-04-16 15:20:36 -07:00
}
2008-01-25 11:12:21 -06:00
EXPORT_SYMBOL_GPL ( usb_lock_device_for_reset ) ;
2005-04-16 15:20:36 -07:00
/**
* usb_get_current_frame_number - return current bus frame number
* @ dev : the device whose bus is being queried
*
2013-08-02 20:10:04 +02:00
* Return : The current frame number for the USB host controller used
* with the given USB device . This can be used when scheduling
2005-04-16 15:20:36 -07:00
* isochronous requests .
*
2013-08-02 20:10:04 +02:00
* Note : Different kinds of host controller have different " scheduling
* horizons " . While one type might support scheduling only 32 frames
* into the future , others could support scheduling up to 1024 frames
* into the future .
*
2005-04-16 15:20:36 -07:00
*/
int usb_get_current_frame_number ( struct usb_device * dev )
{
2007-01-23 15:55:28 -05:00
return usb_hcd_get_frame_number ( dev ) ;
2005-04-16 15:20:36 -07:00
}
2008-01-25 11:12:21 -06:00
EXPORT_SYMBOL_GPL ( usb_get_current_frame_number ) ;
2005-04-16 15:20:36 -07:00
/*-------------------------------------------------------------------*/
/*
* __usb_get_extra_descriptor ( ) finds a descriptor of specific type in the
* extra field of the interface and endpoint descriptor structs .
*/
int __usb_get_extra_descriptor ( char * buffer , unsigned size ,
2008-01-30 15:21:33 -08:00
unsigned char type , void * * ptr )
2005-04-16 15:20:36 -07:00
{
struct usb_descriptor_header * header ;
while ( size > = sizeof ( struct usb_descriptor_header ) ) {
header = ( struct usb_descriptor_header * ) buffer ;
if ( header - > bLength < 2 ) {
printk ( KERN_ERR
" %s: bogus descriptor, type %d length %d \n " ,
usbcore_name ,
2008-01-30 15:21:33 -08:00
header - > bDescriptorType ,
2005-04-16 15:20:36 -07:00
header - > bLength ) ;
return - 1 ;
}
if ( header - > bDescriptorType = = type ) {
* ptr = header ;
return 0 ;
}
buffer + = header - > bLength ;
size - = header - > bLength ;
}
return - 1 ;
}
2008-01-25 11:12:21 -06:00
EXPORT_SYMBOL_GPL ( __usb_get_extra_descriptor ) ;
2005-04-16 15:20:36 -07:00
/**
2010-04-12 13:17:25 +02:00
* usb_alloc_coherent - allocate dma - consistent buffer for URB_NO_xxx_DMA_MAP
2005-04-16 15:20:36 -07:00
* @ dev : device the buffer will be used with
* @ size : requested buffer size
* @ mem_flags : affect whether allocation may block
* @ dma : used to return DMA address of buffer
*
2013-08-02 20:10:04 +02:00
* Return : Either null ( indicating no buffer could be allocated ) , or the
* cpu - space pointer to a buffer that may be used to perform DMA to the
2005-04-16 15:20:36 -07:00
* specified device . Such cpu - space buffers are returned along with the DMA
* address ( through the pointer provided ) .
*
2013-08-02 20:10:04 +02:00
* Note :
2005-04-16 15:20:36 -07:00
* These buffers are used with URB_NO_xxx_DMA_MAP set in urb - > transfer_flags
2007-07-01 23:33:12 -07:00
* to avoid behaviors like using " DMA bounce buffers " , or thrashing IOMMU
* hardware during URB completion / resubmit . The implementation varies between
2005-04-16 15:20:36 -07:00
* platforms , depending on details of how DMA will work to this device .
2007-07-01 23:33:12 -07:00
* Using these buffers also eliminates cacheline sharing problems on
* architectures where CPU caches are not DMA - coherent . On systems without
* bus - snooping caches , these buffers are uncached .
2005-04-16 15:20:36 -07:00
*
2010-04-12 13:17:25 +02:00
* When the buffer is no longer used , free it with usb_free_coherent ( ) .
2005-04-16 15:20:36 -07:00
*/
2010-04-12 13:17:25 +02:00
void * usb_alloc_coherent ( struct usb_device * dev , size_t size , gfp_t mem_flags ,
dma_addr_t * dma )
2005-04-16 15:20:36 -07:00
{
2006-08-30 11:27:36 -04:00
if ( ! dev | | ! dev - > bus )
2005-04-16 15:20:36 -07:00
return NULL ;
2007-01-23 15:55:28 -05:00
return hcd_buffer_alloc ( dev - > bus , size , mem_flags , dma ) ;
2005-04-16 15:20:36 -07:00
}
2010-04-12 13:17:25 +02:00
EXPORT_SYMBOL_GPL ( usb_alloc_coherent ) ;
2005-04-16 15:20:36 -07:00
/**
2010-04-12 13:17:25 +02:00
* usb_free_coherent - free memory allocated with usb_alloc_coherent ( )
2005-04-16 15:20:36 -07:00
* @ dev : device the buffer was used with
* @ size : requested buffer size
* @ addr : CPU address of buffer
* @ dma : DMA address of buffer
*
* This reclaims an I / O buffer , letting it be reused . The memory must have
2010-04-12 13:17:25 +02:00
* been allocated using usb_alloc_coherent ( ) , and the parameters must match
2007-07-01 23:33:12 -07:00
* those provided in that allocation request .
2005-04-16 15:20:36 -07:00
*/
2010-04-12 13:17:25 +02:00
void usb_free_coherent ( struct usb_device * dev , size_t size , void * addr ,
dma_addr_t dma )
2005-04-16 15:20:36 -07:00
{
2006-08-30 11:27:36 -04:00
if ( ! dev | | ! dev - > bus )
2006-08-01 22:33:34 -04:00
return ;
if ( ! addr )
return ;
2007-01-23 15:55:28 -05:00
hcd_buffer_free ( dev - > bus , size , addr , dma ) ;
2005-04-16 15:20:36 -07:00
}
2010-04-12 13:17:25 +02:00
EXPORT_SYMBOL_GPL ( usb_free_coherent ) ;
2005-04-16 15:20:36 -07:00
/**
* usb_buffer_map - create DMA mapping ( s ) for an urb
* @ urb : urb whose transfer_buffer / setup_packet will be mapped
*
2013-08-02 20:10:04 +02:00
* URB_NO_TRANSFER_DMA_MAP is added to urb - > transfer_flags if the operation
* succeeds . If the device is connected to this system through a non - DMA
* controller , this operation always succeeds .
2005-04-16 15:20:36 -07:00
*
* This call would normally be used for an urb which is reused , perhaps
* as the target of a large periodic transfer , with usb_buffer_dmasync ( )
* calls to synchronize memory and dma state .
*
* Reverse the effect of this call with usb_buffer_unmap ( ) .
2013-08-02 20:10:04 +02:00
*
* Return : Either % NULL ( indicating no buffer could be mapped ) , or @ urb .
*
2005-04-16 15:20:36 -07:00
*/
#if 0
2007-01-23 15:55:28 -05:00
struct urb * usb_buffer_map ( struct urb * urb )
2005-04-16 15:20:36 -07:00
{
struct usb_bus * bus ;
struct device * controller ;
if ( ! urb
| | ! urb - > dev
| | ! ( bus = urb - > dev - > bus )
| | ! ( controller = bus - > controller ) )
return NULL ;
if ( controller - > dma_mask ) {
2007-01-23 15:55:28 -05:00
urb - > transfer_dma = dma_map_single ( controller ,
2005-04-16 15:20:36 -07:00
urb - > transfer_buffer , urb - > transfer_buffer_length ,
2007-01-23 15:55:28 -05:00
usb_pipein ( urb - > pipe )
2005-04-16 15:20:36 -07:00
? DMA_FROM_DEVICE : DMA_TO_DEVICE ) ;
2008-01-30 15:21:33 -08:00
/* FIXME generic api broken like pci, can't report errors */
/* if (urb->transfer_dma == DMA_ADDR_INVALID) return 0; */
2005-04-16 15:20:36 -07:00
} else
urb - > transfer_dma = ~ 0 ;
2010-03-05 15:10:17 -05:00
urb - > transfer_flags | = URB_NO_TRANSFER_DMA_MAP ;
2005-04-16 15:20:36 -07:00
return urb ;
}
2008-01-25 11:12:21 -06:00
EXPORT_SYMBOL_GPL ( usb_buffer_map ) ;
2005-04-16 15:20:36 -07:00
# endif /* 0 */
/* XXX DISABLED, no users currently. If you wish to re-enable this
* XXX please determine whether the sync is to transfer ownership of
* XXX the buffer from device to cpu or vice verse , and thusly use the
* XXX appropriate _for_ { cpu , device } ( ) method . - DaveM
*/
#if 0
/**
* usb_buffer_dmasync - synchronize DMA and CPU view of buffer ( s )
* @ urb : urb whose transfer_buffer / setup_packet will be synchronized
*/
2007-01-23 15:55:28 -05:00
void usb_buffer_dmasync ( struct urb * urb )
2005-04-16 15:20:36 -07:00
{
struct usb_bus * bus ;
struct device * controller ;
if ( ! urb
| | ! ( urb - > transfer_flags & URB_NO_TRANSFER_DMA_MAP )
| | ! urb - > dev
| | ! ( bus = urb - > dev - > bus )
| | ! ( controller = bus - > controller ) )
return ;
if ( controller - > dma_mask ) {
2009-05-28 10:10:44 +09:00
dma_sync_single_for_cpu ( controller ,
2005-04-16 15:20:36 -07:00
urb - > transfer_dma , urb - > transfer_buffer_length ,
2007-01-23 15:55:28 -05:00
usb_pipein ( urb - > pipe )
2005-04-16 15:20:36 -07:00
? DMA_FROM_DEVICE : DMA_TO_DEVICE ) ;
2007-01-23 15:55:28 -05:00
if ( usb_pipecontrol ( urb - > pipe ) )
2009-05-28 10:10:44 +09:00
dma_sync_single_for_cpu ( controller ,
2005-04-16 15:20:36 -07:00
urb - > setup_dma ,
2007-01-23 15:55:28 -05:00
sizeof ( struct usb_ctrlrequest ) ,
2005-04-16 15:20:36 -07:00
DMA_TO_DEVICE ) ;
}
}
2008-01-25 11:12:21 -06:00
EXPORT_SYMBOL_GPL ( usb_buffer_dmasync ) ;
2005-04-16 15:20:36 -07:00
# endif
/**
* usb_buffer_unmap - free DMA mapping ( s ) for an urb
* @ urb : urb whose transfer_buffer will be unmapped
*
* Reverses the effect of usb_buffer_map ( ) .
*/
#if 0
2007-01-23 15:55:28 -05:00
void usb_buffer_unmap ( struct urb * urb )
2005-04-16 15:20:36 -07:00
{
struct usb_bus * bus ;
struct device * controller ;
if ( ! urb
| | ! ( urb - > transfer_flags & URB_NO_TRANSFER_DMA_MAP )
| | ! urb - > dev
| | ! ( bus = urb - > dev - > bus )
| | ! ( controller = bus - > controller ) )
return ;
if ( controller - > dma_mask ) {
2007-01-23 15:55:28 -05:00
dma_unmap_single ( controller ,
2005-04-16 15:20:36 -07:00
urb - > transfer_dma , urb - > transfer_buffer_length ,
2007-01-23 15:55:28 -05:00
usb_pipein ( urb - > pipe )
2005-04-16 15:20:36 -07:00
? DMA_FROM_DEVICE : DMA_TO_DEVICE ) ;
}
2010-03-05 15:10:17 -05:00
urb - > transfer_flags & = ~ URB_NO_TRANSFER_DMA_MAP ;
2005-04-16 15:20:36 -07:00
}
2008-01-25 11:12:21 -06:00
EXPORT_SYMBOL_GPL ( usb_buffer_unmap ) ;
2005-04-16 15:20:36 -07:00
# endif /* 0 */
2010-04-02 13:27:28 -04:00
#if 0
2005-04-16 15:20:36 -07:00
/**
* usb_buffer_map_sg - create scatterlist DMA mapping ( s ) for an endpoint
* @ dev : device to which the scatterlist will be mapped
2007-07-30 17:07:21 -04:00
* @ is_in : mapping transfer direction
2005-04-16 15:20:36 -07:00
* @ sg : the scatterlist to map
* @ nents : the number of entries in the scatterlist
*
2013-08-02 20:10:04 +02:00
* Return : Either < 0 ( indicating no buffers could be mapped ) , or the
* number of DMA mapping array entries in the scatterlist .
2005-04-16 15:20:36 -07:00
*
2013-08-02 20:10:04 +02:00
* Note :
2005-04-16 15:20:36 -07:00
* The caller is responsible for placing the resulting DMA addresses from
* the scatterlist into URB transfer buffer pointers , and for setting the
* URB_NO_TRANSFER_DMA_MAP transfer flag in each of those URBs .
*
* Top I / O rates come from queuing URBs , instead of waiting for each one
* to complete before starting the next I / O . This is particularly easy
* to do with scatterlists . Just allocate and submit one URB for each DMA
* mapping entry returned , stopping on the first error or when all succeed .
* Better yet , use the usb_sg_ * ( ) calls , which do that ( and more ) for you .
*
* This call would normally be used when translating scatterlist requests ,
* rather than usb_buffer_map ( ) , since on some hardware ( with IOMMUs ) it
* may be able to coalesce mappings for improved I / O efficiency .
*
* Reverse the effect of this call with usb_buffer_unmap_sg ( ) .
*/
2007-07-30 17:07:21 -04:00
int usb_buffer_map_sg ( const struct usb_device * dev , int is_in ,
2006-08-26 23:48:11 -03:00
struct scatterlist * sg , int nents )
2005-04-16 15:20:36 -07:00
{
struct usb_bus * bus ;
struct device * controller ;
if ( ! dev
| | ! ( bus = dev - > bus )
| | ! ( controller = bus - > controller )
| | ! controller - > dma_mask )
2009-08-22 20:24:49 +02:00
return - EINVAL ;
2005-04-16 15:20:36 -07:00
2008-01-30 15:21:33 -08:00
/* FIXME generic api broken like pci, can't report errors */
2007-01-23 15:55:28 -05:00
return dma_map_sg ( controller , sg , nents ,
2009-08-22 20:24:49 +02:00
is_in ? DMA_FROM_DEVICE : DMA_TO_DEVICE ) ? : - ENOMEM ;
2005-04-16 15:20:36 -07:00
}
2008-01-25 11:12:21 -06:00
EXPORT_SYMBOL_GPL ( usb_buffer_map_sg ) ;
2010-04-02 13:27:28 -04:00
# endif
2005-04-16 15:20:36 -07:00
/* XXX DISABLED, no users currently. If you wish to re-enable this
* XXX please determine whether the sync is to transfer ownership of
* XXX the buffer from device to cpu or vice verse , and thusly use the
* XXX appropriate _for_ { cpu , device } ( ) method . - DaveM
*/
#if 0
/**
* usb_buffer_dmasync_sg - synchronize DMA and CPU view of scatterlist buffer ( s )
* @ dev : device to which the scatterlist will be mapped
2007-07-30 17:07:21 -04:00
* @ is_in : mapping transfer direction
2005-04-16 15:20:36 -07:00
* @ sg : the scatterlist to synchronize
* @ n_hw_ents : the positive return value from usb_buffer_map_sg
*
* Use this when you are re - using a scatterlist ' s data buffers for
* another USB request .
*/
2007-07-30 17:07:21 -04:00
void usb_buffer_dmasync_sg ( const struct usb_device * dev , int is_in ,
2006-08-26 23:48:11 -03:00
struct scatterlist * sg , int n_hw_ents )
2005-04-16 15:20:36 -07:00
{
struct usb_bus * bus ;
struct device * controller ;
if ( ! dev
| | ! ( bus = dev - > bus )
| | ! ( controller = bus - > controller )
| | ! controller - > dma_mask )
return ;
2009-05-28 10:10:44 +09:00
dma_sync_sg_for_cpu ( controller , sg , n_hw_ents ,
is_in ? DMA_FROM_DEVICE : DMA_TO_DEVICE ) ;
2005-04-16 15:20:36 -07:00
}
2008-01-25 11:12:21 -06:00
EXPORT_SYMBOL_GPL ( usb_buffer_dmasync_sg ) ;
2005-04-16 15:20:36 -07:00
# endif
2010-04-02 13:27:28 -04:00
#if 0
2005-04-16 15:20:36 -07:00
/**
* usb_buffer_unmap_sg - free DMA mapping ( s ) for a scatterlist
* @ dev : device to which the scatterlist will be mapped
2007-07-30 17:07:21 -04:00
* @ is_in : mapping transfer direction
2005-04-16 15:20:36 -07:00
* @ sg : the scatterlist to unmap
* @ n_hw_ents : the positive return value from usb_buffer_map_sg
*
* Reverses the effect of usb_buffer_map_sg ( ) .
*/
2007-07-30 17:07:21 -04:00
void usb_buffer_unmap_sg ( const struct usb_device * dev , int is_in ,
2006-08-26 23:48:11 -03:00
struct scatterlist * sg , int n_hw_ents )
2005-04-16 15:20:36 -07:00
{
struct usb_bus * bus ;
struct device * controller ;
if ( ! dev
| | ! ( bus = dev - > bus )
| | ! ( controller = bus - > controller )
| | ! controller - > dma_mask )
return ;
2007-01-23 15:55:28 -05:00
dma_unmap_sg ( controller , sg , n_hw_ents ,
2007-07-30 17:07:21 -04:00
is_in ? DMA_FROM_DEVICE : DMA_TO_DEVICE ) ;
2005-04-16 15:20:36 -07:00
}
2008-01-25 11:12:21 -06:00
EXPORT_SYMBOL_GPL ( usb_buffer_unmap_sg ) ;
2010-04-02 13:27:28 -04:00
# endif
2005-04-16 15:20:36 -07:00
2008-11-22 13:01:06 +10:30
/* To disable USB, kernel command line is 'nousb' not 'usbcore.nousb' */
# ifdef MODULE
module_param ( nousb , bool , 0444 ) ;
# else
core_param ( nousb , nousb , bool , 0444 ) ;
# endif
2005-04-16 15:20:36 -07:00
/*
* for external read access to < nousb >
*/
int usb_disabled ( void )
{
return nousb ;
}
2008-01-25 11:12:21 -06:00
EXPORT_SYMBOL_GPL ( usb_disabled ) ;
2005-04-16 15:20:36 -07:00
2008-12-05 14:10:34 -05:00
/*
* Notifications of device and interface registration
*/
static int usb_bus_notify ( struct notifier_block * nb , unsigned long action ,
void * data )
{
struct device * dev = data ;
switch ( action ) {
case BUS_NOTIFY_ADD_DEVICE :
if ( dev - > type = = & usb_device_type )
( void ) usb_create_sysfs_dev_files ( to_usb_device ( dev ) ) ;
else if ( dev - > type = = & usb_if_device_type )
2011-04-14 17:47:09 +02:00
usb_create_sysfs_intf_files ( to_usb_interface ( dev ) ) ;
2008-12-05 14:10:34 -05:00
break ;
case BUS_NOTIFY_DEL_DEVICE :
if ( dev - > type = = & usb_device_type )
usb_remove_sysfs_dev_files ( to_usb_device ( dev ) ) ;
else if ( dev - > type = = & usb_if_device_type )
usb_remove_sysfs_intf_files ( to_usb_interface ( dev ) ) ;
break ;
}
return 0 ;
}
static struct notifier_block usb_bus_nb = {
. notifier_call = usb_bus_notify ,
} ;
2009-04-24 14:56:26 -07:00
struct dentry * usb_debug_root ;
EXPORT_SYMBOL_GPL ( usb_debug_root ) ;
2009-12-04 15:47:42 +02:00
static struct dentry * usb_debug_devices ;
2009-04-24 15:16:04 -07:00
2009-04-24 14:56:26 -07:00
static int usb_debugfs_init ( void )
{
usb_debug_root = debugfs_create_dir ( " usb " , NULL ) ;
if ( ! usb_debug_root )
return - ENOENT ;
2009-04-24 15:16:04 -07:00
usb_debug_devices = debugfs_create_file ( " devices " , 0444 ,
usb_debug_root , NULL ,
& usbfs_devices_fops ) ;
if ( ! usb_debug_devices ) {
debugfs_remove ( usb_debug_root ) ;
usb_debug_root = NULL ;
return - ENOENT ;
}
2009-04-24 14:56:26 -07:00
return 0 ;
}
static void usb_debugfs_cleanup ( void )
{
2009-04-24 15:16:04 -07:00
debugfs_remove ( usb_debug_devices ) ;
2009-04-24 14:56:26 -07:00
debugfs_remove ( usb_debug_root ) ;
}
2005-04-16 15:20:36 -07:00
/*
* Init
*/
static int __init usb_init ( void )
{
int retval ;
2015-03-20 09:04:40 +05:30
if ( usb_disabled ( ) ) {
2007-01-23 15:55:28 -05:00
pr_info ( " %s: USB support disabled \n " , usbcore_name ) ;
2005-04-16 15:20:36 -07:00
return 0 ;
}
2014-12-05 15:13:54 +01:00
usb_init_pool_max ( ) ;
2005-04-16 15:20:36 -07:00
2009-04-24 14:56:26 -07:00
retval = usb_debugfs_init ( ) ;
if ( retval )
goto out ;
2012-05-16 14:11:15 +02:00
usb_acpi_register ( ) ;
2005-04-16 15:20:36 -07:00
retval = bus_register ( & usb_bus_type ) ;
2008-01-30 15:21:33 -08:00
if ( retval )
2006-09-19 10:14:07 -04:00
goto bus_register_failed ;
2008-12-05 14:10:34 -05:00
retval = bus_register_notifier ( & usb_bus_type , & usb_bus_nb ) ;
if ( retval )
goto bus_notifier_failed ;
2005-04-16 15:20:36 -07:00
retval = usb_major_init ( ) ;
if ( retval )
goto major_init_failed ;
2005-07-31 01:05:53 +02:00
retval = usb_register ( & usbfs_driver ) ;
if ( retval )
goto driver_register_failed ;
2007-03-13 15:59:31 +01:00
retval = usb_devio_init ( ) ;
2005-07-31 01:05:53 +02:00
if ( retval )
2007-03-13 15:59:31 +01:00
goto usb_devio_init_failed ;
2005-04-16 15:20:36 -07:00
retval = usb_hub_init ( ) ;
if ( retval )
goto hub_init_failed ;
2006-07-01 22:08:49 -04:00
retval = usb_register_device_driver ( & usb_generic_driver , THIS_MODULE ) ;
2005-04-16 15:20:36 -07:00
if ( ! retval )
goto out ;
usb_hub_cleanup ( ) ;
hub_init_failed :
2007-03-13 15:59:31 +01:00
usb_devio_cleanup ( ) ;
usb_devio_init_failed :
2005-07-31 01:05:53 +02:00
usb_deregister ( & usbfs_driver ) ;
driver_register_failed :
usb_major_cleanup ( ) ;
2005-04-16 15:20:36 -07:00
major_init_failed :
2008-12-05 14:10:34 -05:00
bus_unregister_notifier ( & usb_bus_type , & usb_bus_nb ) ;
bus_notifier_failed :
2005-04-16 15:20:36 -07:00
bus_unregister ( & usb_bus_type ) ;
2006-09-19 10:14:07 -04:00
bus_register_failed :
2012-05-11 16:08:27 +08:00
usb_acpi_unregister ( ) ;
2010-01-08 12:57:28 -05:00
usb_debugfs_cleanup ( ) ;
2005-04-16 15:20:36 -07:00
out :
return retval ;
}
/*
* Cleanup
*/
static void __exit usb_exit ( void )
{
/* This will matter if shutdown/reboot does exitcalls. */
2015-03-20 09:04:40 +05:30
if ( usb_disabled ( ) )
2005-04-16 15:20:36 -07:00
return ;
2006-07-01 22:08:49 -04:00
usb_deregister_device_driver ( & usb_generic_driver ) ;
2005-04-16 15:20:36 -07:00
usb_major_cleanup ( ) ;
2005-07-31 01:05:53 +02:00
usb_deregister ( & usbfs_driver ) ;
2007-03-13 15:59:31 +01:00
usb_devio_cleanup ( ) ;
2005-04-16 15:20:36 -07:00
usb_hub_cleanup ( ) ;
2008-12-05 14:10:34 -05:00
bus_unregister_notifier ( & usb_bus_type , & usb_bus_nb ) ;
2005-04-16 15:20:36 -07:00
bus_unregister ( & usb_bus_type ) ;
2012-05-11 16:08:27 +08:00
usb_acpi_unregister ( ) ;
2009-04-24 14:56:26 -07:00
usb_debugfs_cleanup ( ) ;
2005-04-16 15:20:36 -07:00
}
subsys_initcall ( usb_init ) ;
module_exit ( usb_exit ) ;
MODULE_LICENSE ( " GPL " ) ;