Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
L
linux
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
Analytics
Analytics
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Commits
Issue Boards
Open sidebar
Kirill Smelkov
linux
Commits
5bc21855
Commit
5bc21855
authored
Jul 06, 2002
by
Anton Altaparmakov
Browse files
Options
Browse Files
Download
Plain Diff
Merge cantab.net:/usr/src/bklinux-2.5 into cantab.net:/usr/src/tng
parents
ea51ad20
7970f12d
Changes
35
Hide whitespace changes
Inline
Side-by-side
Showing
35 changed files
with
648 additions
and
923 deletions
+648
-923
Documentation/DocBook/Makefile
Documentation/DocBook/Makefile
+1
-0
Documentation/DocBook/kernel-api.tmpl
Documentation/DocBook/kernel-api.tmpl
+1
-0
Makefile
Makefile
+1
-1
arch/i386/boot/Makefile
arch/i386/boot/Makefile
+1
-1
drivers/ide/probe.c
drivers/ide/probe.c
+0
-12
drivers/usb/class/bluetty.c
drivers/usb/class/bluetty.c
+2
-3
drivers/usb/class/printer.c
drivers/usb/class/printer.c
+5
-18
drivers/usb/core/Makefile
drivers/usb/core/Makefile
+3
-3
drivers/usb/core/file.c
drivers/usb/core/file.c
+182
-0
drivers/usb/core/inode.c
drivers/usb/core/inode.c
+0
-19
drivers/usb/core/usb.c
drivers/usb/core/usb.c
+20
-213
drivers/usb/host/Config.help
drivers/usb/host/Config.help
+2
-41
drivers/usb/host/Config.in
drivers/usb/host/Config.in
+3
-17
drivers/usb/host/ohci-dbg.c
drivers/usb/host/ohci-dbg.c
+2
-0
drivers/usb/host/ohci-hcd.c
drivers/usb/host/ohci-hcd.c
+10
-2
drivers/usb/host/uhci-hcd.c
drivers/usb/host/uhci-hcd.c
+8
-30
drivers/usb/host/usb-uhci-hcd.c
drivers/usb/host/usb-uhci-hcd.c
+6
-12
drivers/usb/host/usb-uhci-q.c
drivers/usb/host/usb-uhci-q.c
+1
-57
drivers/usb/image/mdc800.c
drivers/usb/image/mdc800.c
+4
-5
drivers/usb/image/scanner.c
drivers/usb/image/scanner.c
+5
-14
drivers/usb/input/hiddev.c
drivers/usb/input/hiddev.c
+7
-15
drivers/usb/media/dabusb.c
drivers/usb/media/dabusb.c
+4
-12
drivers/usb/misc/auerswald.c
drivers/usb/misc/auerswald.c
+5
-20
drivers/usb/misc/brlvger.c
drivers/usb/misc/brlvger.c
+4
-18
drivers/usb/misc/rio500.c
drivers/usb/misc/rio500.c
+14
-4
drivers/usb/net/pegasus.c
drivers/usb/net/pegasus.c
+162
-117
drivers/usb/net/pegasus.h
drivers/usb/net/pegasus.h
+5
-12
drivers/usb/net/rtl8150.c
drivers/usb/net/rtl8150.c
+21
-28
drivers/usb/storage/transport.c
drivers/usb/storage/transport.c
+27
-74
drivers/usb/storage/usb.c
drivers/usb/storage/usb.c
+120
-133
drivers/usb/storage/usb.h
drivers/usb/storage/usb.h
+1
-0
drivers/usb/usb-skeleton.c
drivers/usb/usb-skeleton.c
+9
-20
fs/binfmt_elf.c
fs/binfmt_elf.c
+2
-2
fs/reiserfs/buffer2.c
fs/reiserfs/buffer2.c
+7
-0
include/linux/usb.h
include/linux/usb.h
+3
-20
No files found.
Documentation/DocBook/Makefile
View file @
5bc21855
...
...
@@ -120,6 +120,7 @@ APISOURCES := $(TOPDIR)/drivers/media/video/videodev.c \
$(TOPDIR)
/drivers/usb/core/urb.c
\
$(TOPDIR)
/drivers/usb/core/message.c
\
$(TOPDIR)
/drivers/usb/core/config.c
\
$(TOPDIR)
/drivers/usb/core/file.c
\
$(TOPDIR)
/drivers/usb/core/usb.c
\
$(TOPDIR)
/drivers/video/fbmem.c
\
$(TOPDIR)
/drivers/video/fbcmap.c
\
...
...
Documentation/DocBook/kernel-api.tmpl
View file @
5bc21855
...
...
@@ -285,6 +285,7 @@
!Edrivers/usb/core/urb.c
!Edrivers/usb/core/config.c
!Edrivers/usb/core/message.c
!Edrivers/usb/core/file.c
!Edrivers/usb/core/usb.c
</sect1>
...
...
Makefile
View file @
5bc21855
VERSION
=
2
PATCHLEVEL
=
5
SUBLEVEL
=
2
4
SUBLEVEL
=
2
5
EXTRAVERSION
=
# *DOCUMENTATION*
...
...
arch/i386/boot/Makefile
View file @
5bc21855
...
...
@@ -79,7 +79,7 @@ install: $(BOOTIMAGE)
clean
:
@
echo
'Cleaning up (boot)'
@
rm
-f
tools/build
@
rm
-f
tools/build
vmlinux.bin bvmlinux.bin
@
rm
-f
setup bootsect zImage compressed/vmlinux.out
@
rm
-f
bsetup bbootsect bzImage compressed/bvmlinux.out
@
$(MAKE)
-C
compressed clean
...
...
drivers/ide/probe.c
View file @
5bc21855
...
...
@@ -1173,18 +1173,6 @@ static void channel_init(struct ata_channel *ch)
gd
->
next
=
NULL
;
/* linked list of major devs */
gd
->
fops
=
ide_fops
;
/* file operations */
gd
->
de_arr
=
kmalloc
(
sizeof
(
*
gd
->
de_arr
)
*
MAX_DRIVES
,
GFP_KERNEL
);
if
(
gd
->
de_arr
)
memset
(
gd
->
de_arr
,
0
,
sizeof
(
*
gd
->
de_arr
)
*
MAX_DRIVES
);
else
goto
err_kmalloc_gd_de_arr
;
gd
->
flags
=
kmalloc
(
sizeof
(
*
gd
->
flags
)
*
MAX_DRIVES
,
GFP_KERNEL
);
if
(
gd
->
flags
)
memset
(
gd
->
flags
,
0
,
sizeof
(
*
gd
->
flags
)
*
MAX_DRIVES
);
else
goto
err_kmalloc_gd_flags
;
ch
->
gd
=
gd
;
add_gendisk
(
gd
);
...
...
drivers/usb/class/bluetty.c
View file @
5bc21855
...
...
@@ -1151,7 +1151,8 @@ static void * usb_bluetooth_probe(struct usb_device *dev, unsigned int ifnum,
endpoint
=
bulk_out_endpoint
[
0
];
bluetooth
->
bulk_out_endpointAddress
=
endpoint
->
bEndpointAddress
;
bluetooth
->
bulk_out_buffer_size
=
endpoint
->
wMaxPacketSize
*
2
;
/* create our write urb pool */
for
(
i
=
0
;
i
<
NUM_BULK_URBS
;
++
i
)
{
struct
urb
*
urb
=
usb_alloc_urb
(
0
,
GFP_KERNEL
);
...
...
@@ -1166,8 +1167,6 @@ static void * usb_bluetooth_probe(struct usb_device *dev, unsigned int ifnum,
}
bluetooth
->
write_urb_pool
[
i
]
=
urb
;
}
bluetooth
->
bulk_out_buffer_size
=
endpoint
->
wMaxPacketSize
*
2
;
endpoint
=
interrupt_in_endpoint
[
0
];
bluetooth
->
interrupt_in_urb
=
usb_alloc_urb
(
0
,
GFP_KERNEL
);
...
...
drivers/usb/class/printer.c
View file @
5bc21855
...
...
@@ -372,7 +372,7 @@ static void usblp_cleanup (struct usblp *usblp)
{
devfs_unregister
(
usblp
->
devfs
);
usblp_table
[
usblp
->
minor
]
=
NULL
;
usb_deregister_dev
(
&
usblp_driver
,
1
,
usblp
->
minor
);
usb_deregister_dev
(
1
,
usblp
->
minor
);
info
(
"usblp%d: removed"
,
usblp
->
minor
);
kfree
(
usblp
->
writeurb
->
transfer_buffer
);
...
...
@@ -812,20 +812,10 @@ static void *usblp_probe(struct usb_device *dev, unsigned int ifnum,
init_waitqueue_head
(
&
usblp
->
wait
);
usblp
->
ifnum
=
ifnum
;
retval
=
usb_register_dev
(
&
usblp_
driver
,
1
,
&
usblp
->
minor
);
retval
=
usb_register_dev
(
&
usblp_
fops
,
USBLP_MINOR_BASE
,
1
,
&
usblp
->
minor
);
if
(
retval
)
{
if
(
retval
!=
-
ENODEV
)
{
err
(
"Not able to get a minor for this device."
);
goto
abort
;
}
/* Look for a free usblp_table entry on our own. */
while
(
usblp_table
[
usblp
->
minor
])
{
usblp
->
minor
++
;
if
(
usblp
->
minor
>=
USBLP_MINORS
)
{
err
(
"no more free usblp devices"
);
goto
abort
;
}
}
err
(
"Not able to get a minor for this device."
);
goto
abort
;
}
usblp
->
writeurb
=
usb_alloc_urb
(
0
,
GFP_KERNEL
);
...
...
@@ -901,7 +891,7 @@ static void *usblp_probe(struct usb_device *dev, unsigned int ifnum,
return
usblp
;
abort_minor:
usb_deregister_dev
(
&
usblp_driver
,
1
,
usblp
->
minor
);
usb_deregister_dev
(
1
,
usblp
->
minor
);
abort:
if
(
usblp
)
{
usb_free_urb
(
usblp
->
writeurb
);
...
...
@@ -1111,9 +1101,6 @@ static struct usb_driver usblp_driver = {
name:
"usblp"
,
probe:
usblp_probe
,
disconnect:
usblp_disconnect
,
fops:
&
usblp_fops
,
minor:
USBLP_MINOR_BASE
,
num_minors:
USBLP_MINORS
,
id_table:
usblp_ids
,
};
...
...
drivers/usb/core/Makefile
View file @
5bc21855
...
...
@@ -2,17 +2,17 @@
# Makefile for USB Core files and filesystem
#
export-objs
:=
usb.o hcd.o hcd-pci.o urb.o message.o config.o
export-objs
:=
usb.o hcd.o hcd-pci.o urb.o message.o config.o
file.o
usbcore-objs
:=
usb.o usb-debug.o hub.o hcd.o urb.o message.o
\
config.o
config.o
file.o
ifeq
($(CONFIG_PCI),y)
usbcore-objs
+=
hcd-pci.o
endif
ifeq
($(CONFIG_USB_DEVICEFS),y)
usbcore-objs
+=
devio.o inode.o d
rivers.o d
evices.o
usbcore-objs
+=
devio.o inode.o devices.o
endif
obj-$(CONFIG_USB)
+=
usbcore.o
...
...
drivers/usb/core/file.c
0 → 100644
View file @
5bc21855
/*
* drivers/usb/file.c
*
* (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-2001 (kernel hotplug, usb_device_id,
more docs, etc)
* (C) Copyright Yggdrasil Computing, Inc. 2000
* (usb_device_id matching changes by Adam J. Richter)
* (C) Copyright Greg Kroah-Hartman 2002
*
*/
#include <linux/config.h>
#include <linux/module.h>
#include <linux/devfs_fs_kernel.h>
#include <linux/spinlock.h>
#include <linux/errno.h>
#ifdef CONFIG_USB_DEBUG
#define DEBUG
#else
#undef DEBUG
#endif
#include <linux/usb.h>
devfs_handle_t
usb_devfs_handle
;
/* /dev/usb dir. */
EXPORT_SYMBOL
(
usb_devfs_handle
);
#define MAX_USB_MINORS 256
static
struct
file_operations
*
usb_minors
[
MAX_USB_MINORS
];
static
spinlock_t
minor_lock
=
SPIN_LOCK_UNLOCKED
;
static
int
usb_open
(
struct
inode
*
inode
,
struct
file
*
file
)
{
int
minor
=
minor
(
inode
->
i_rdev
);
struct
file_operations
*
c
;
int
err
=
-
ENODEV
;
struct
file_operations
*
old_fops
,
*
new_fops
=
NULL
;
spin_lock
(
&
minor_lock
);
c
=
usb_minors
[
minor
];
spin_unlock
(
&
minor_lock
);
if
(
!
c
||
!
(
new_fops
=
fops_get
(
c
)))
return
err
;
old_fops
=
file
->
f_op
;
file
->
f_op
=
new_fops
;
/* Curiouser and curiouser... NULL ->open() as "no device" ? */
if
(
file
->
f_op
->
open
)
err
=
file
->
f_op
->
open
(
inode
,
file
);
if
(
err
)
{
fops_put
(
file
->
f_op
);
file
->
f_op
=
fops_get
(
old_fops
);
}
fops_put
(
old_fops
);
return
err
;
}
static
struct
file_operations
usb_fops
=
{
owner:
THIS_MODULE
,
open:
usb_open
,
};
int
usb_major_init
(
void
)
{
if
(
devfs_register_chrdev
(
USB_MAJOR
,
"usb"
,
&
usb_fops
))
{
err
(
"unable to get major %d for usb devices"
,
USB_MAJOR
);
return
-
EBUSY
;
}
usb_devfs_handle
=
devfs_mk_dir
(
NULL
,
"usb"
,
NULL
);
return
0
;
}
void
usb_major_cleanup
(
void
)
{
devfs_unregister
(
usb_devfs_handle
);
devfs_unregister_chrdev
(
USB_MAJOR
,
"usb"
);
}
/**
* usb_register_dev - register a USB device, and ask for a minor number
* @fops: the file operations for this USB device
* @minor: the requested starting minor for this device.
* @num_minors: number of minor numbers requested for this device
* @start_minor: place to put the new starting minor number
*
* This should be called by all USB drivers that use the USB major number.
* If CONFIG_USB_DYNAMIC_MINORS is enabled, the minor number will be
* dynamically allocated out of the list of available ones. If it is not
* enabled, the minor number will be based on the next available free minor,
* starting at the requested @minor.
*
* usb_deregister_dev() must be called when the driver is done with
* the minor numbers given out by this function.
*
* Returns -EINVAL if something bad happens with trying to register a
* device, and 0 on success, alone with a value that the driver should
* use in start_minor.
*/
int
usb_register_dev
(
struct
file_operations
*
fops
,
int
minor
,
int
num_minors
,
int
*
start_minor
)
{
int
i
;
int
j
;
int
good_spot
;
int
retval
=
-
EINVAL
;
#ifdef CONFIG_USB_DYNAMIC_MINORS
/*
* We don't care what the device tries to start at, we want to start
* at zero to pack the devices into the smallest available space with
* no holes in the minor range.
*/
minor
=
0
;
#endif
dbg
(
"asking for %d minors, starting at %d"
,
num_minors
,
minor
);
if
(
fops
==
NULL
)
goto
exit
;
*
start_minor
=
0
;
spin_lock
(
&
minor_lock
);
for
(
i
=
minor
;
i
<
MAX_USB_MINORS
;
++
i
)
{
if
(
usb_minors
[
i
])
continue
;
good_spot
=
1
;
for
(
j
=
1
;
j
<=
num_minors
-
1
;
++
j
)
if
(
usb_minors
[
i
+
j
])
{
good_spot
=
0
;
break
;
}
if
(
good_spot
==
0
)
continue
;
*
start_minor
=
i
;
dbg
(
"found a minor chunk free, starting at %d"
,
i
);
for
(
i
=
*
start_minor
;
i
<
(
*
start_minor
+
num_minors
);
++
i
)
usb_minors
[
i
]
=
fops
;
retval
=
0
;
goto
exit
;
}
exit:
spin_unlock
(
&
minor_lock
);
return
retval
;
}
EXPORT_SYMBOL
(
usb_register_dev
);
/**
* usb_deregister_dev - deregister a USB device's dynamic minor.
* @num_minors: number of minor numbers to put back.
* @start_minor: the starting minor number
*
* Used in conjunction with usb_register_dev(). This function is called
* when the USB driver is finished with the minor numbers gotten from a
* call to usb_register_dev() (usually when the device is disconnected
* from the system.)
*
* This should be called by all drivers that use the USB major number.
*/
void
usb_deregister_dev
(
int
num_minors
,
int
start_minor
)
{
int
i
;
dbg
(
"removing %d minors starting at %d"
,
num_minors
,
start_minor
);
spin_lock
(
&
minor_lock
);
for
(
i
=
start_minor
;
i
<
(
start_minor
+
num_minors
);
++
i
)
usb_minors
[
i
]
=
NULL
;
spin_unlock
(
&
minor_lock
);
}
EXPORT_SYMBOL
(
usb_deregister_dev
);
drivers/usb/core/inode.c
View file @
5bc21855
...
...
@@ -48,7 +48,6 @@ static spinlock_t mount_lock = SPIN_LOCK_UNLOCKED;
static
int
mount_count
;
/* = 0 */
static
struct
dentry
*
devices_dentry
;
static
struct
dentry
*
drivers_dentry
;
static
int
num_buses
;
/* = 0 */
static
uid_t
devuid
;
/* = 0 */
...
...
@@ -548,16 +547,6 @@ static int create_special_files (void)
return
-
ENODEV
;
}
drivers_dentry
=
fs_create_file
(
"drivers"
,
listmode
|
S_IFREG
,
NULL
,
NULL
,
&
usbdevfs_drivers_fops
,
listuid
,
listgid
);
if
(
drivers_dentry
==
NULL
)
{
err
(
"Unable to create drivers usbfs file"
);
return
-
ENODEV
;
}
return
0
;
}
...
...
@@ -565,10 +554,7 @@ static void remove_special_files (void)
{
if
(
devices_dentry
)
fs_remove_file
(
devices_dentry
);
if
(
drivers_dentry
)
fs_remove_file
(
drivers_dentry
);
devices_dentry
=
NULL
;
drivers_dentry
=
NULL
;
remove_mount
();
}
...
...
@@ -581,11 +567,6 @@ void usbfs_update_special (void)
if
(
inode
)
inode
->
i_atime
=
inode
->
i_mtime
=
inode
->
i_ctime
=
CURRENT_TIME
;
}
if
(
drivers_dentry
)
{
inode
=
devices_dentry
->
d_inode
;
if
(
inode
)
inode
->
i_atime
=
inode
->
i_mtime
=
inode
->
i_ctime
=
CURRENT_TIME
;
}
}
void
usbfs_add_bus
(
struct
usb_bus
*
bus
)
...
...
drivers/usb/core/usb.c
View file @
5bc21855
...
...
@@ -30,7 +30,6 @@
#include <linux/interrupt.h>
/* for in_interrupt() */
#include <linux/kmod.h>
#include <linux/init.h>
#include <linux/devfs_fs_kernel.h>
#include <linux/spinlock.h>
#include <linux/errno.h>
...
...
@@ -45,6 +44,8 @@
extern
int
usb_hub_init
(
void
);
extern
void
usb_hub_cleanup
(
void
);
extern
int
usb_major_init
(
void
);
extern
void
usb_major_cleanup
(
void
);
/*
* Prototypes for the device driver probing/loading functions
...
...
@@ -58,75 +59,23 @@ static void usb_check_support(struct usb_device *);
*/
LIST_HEAD
(
usb_driver_list
);
devfs_handle_t
usb_devfs_handle
;
/* /dev/usb dir. */
#define MAX_USB_MINORS 256
static
struct
usb_driver
*
usb_minors
[
MAX_USB_MINORS
];
static
spinlock_t
minor_lock
=
SPIN_LOCK_UNLOCKED
;
static
int
usb_register_minors
(
struct
usb_driver
*
driver
,
int
num_minors
,
int
start_minor
)
{
int
i
;
dbg
(
"registering %d minors, starting at %d"
,
num_minors
,
start_minor
);
if
(
start_minor
+
num_minors
>=
MAX_USB_MINORS
)
return
-
EINVAL
;
spin_lock
(
&
minor_lock
);
for
(
i
=
start_minor
;
i
<
(
start_minor
+
num_minors
);
++
i
)
if
(
usb_minors
[
i
])
{
spin_unlock
(
&
minor_lock
);
err
(
"minor %d is already in use, error registering %s driver"
,
i
,
driver
->
name
);
return
-
EINVAL
;
}
for
(
i
=
start_minor
;
i
<
(
start_minor
+
num_minors
);
++
i
)
usb_minors
[
i
]
=
driver
;
spin_unlock
(
&
minor_lock
);
return
0
;
}
static
void
usb_deregister_minors
(
struct
usb_driver
*
driver
,
int
num_minors
,
int
start_minor
)
{
int
i
;
dbg
(
"%s is removing %d minors starting at %d"
,
driver
->
name
,
num_minors
,
start_minor
);
spin_lock
(
&
minor_lock
);
for
(
i
=
start_minor
;
i
<
(
start_minor
+
num_minors
);
++
i
)
usb_minors
[
i
]
=
NULL
;
spin_unlock
(
&
minor_lock
);
}
/**
*
usb_register - register a USB driver
*
@new_driver: USB operations for the driver
*
usb_register - register a USB driver
*
@new_driver: USB operations for the driver
*
* Registers a USB driver with the USB core. The list of unattached
* interfaces will be rescanned whenever a new driver is added, allowing
* the new driver to attach to any recognized devices.
* Returns a negative error code on failure and 0 on success.
* Registers a USB driver with the USB core. The list of unattached
* interfaces will be rescanned whenever a new driver is added, allowing
* the new driver to attach to any recognized devices.
* Returns a negative error code on failure and 0 on success.
*
* NOTE: if you want your driver to use the USB major number, you must call
* usb_register_dev() to enable that functionality. This function no longer
* takes care of that.
*/
int
usb_register
(
struct
usb_driver
*
new_driver
)
{
int
retval
=
0
;
if
((
new_driver
->
fops
)
&&
(
new_driver
->
num_minors
==
0
))
{
err
(
"%s driver must specify num_minors"
,
new_driver
->
name
);
return
-
EINVAL
;
}
#ifndef CONFIG_USB_DYNAMIC_MINORS
if
(
new_driver
->
fops
!=
NULL
)
{
retval
=
usb_register_minors
(
new_driver
,
new_driver
->
num_minors
,
new_driver
->
minor
);
if
(
retval
)
return
retval
;
}
#endif
info
(
"registered new driver %s"
,
new_driver
->
name
);
...
...
@@ -143,92 +92,6 @@ int usb_register(struct usb_driver *new_driver)
}
/**
* usb_register_dev - register a USB device, and ask for a minor number
* @new_driver: USB operations for the driver
* @num_minors: number of minor numbers requested for this device
* @start_minor: place to put the new starting minor number
*
* Used to ask the USB core for a new minor number for a device that has
* just showed up. This is used to dynamically allocate minor numbers
* from the pool of USB reserved minor numbers.
*
* This should be called by all drivers that use the USB major number.
* This only returns a good value of CONFIG_USB_DYNAMIC_MINORS is
* selected by the user.
*
* usb_deregister_dev() should be called when the driver is done with
* the minor numbers given out by this function.
*
* Returns -ENODEV if CONFIG_USB_DYNAMIC_MINORS is not enabled in this
* kernel, -EINVAL if something bad happens with trying to register a
* device, and 0 on success, alone with a value that the driver should
* use in start_minor.
*/
#ifdef CONFIG_USB_DYNAMIC_MINORS
int
usb_register_dev
(
struct
usb_driver
*
new_driver
,
int
num_minors
,
int
*
start_minor
)
{
int
i
;
int
j
;
int
good_spot
;
int
retval
=
-
EINVAL
;
dbg
(
"%s is asking for %d minors"
,
new_driver
->
name
,
num_minors
);
if
(
new_driver
->
fops
==
NULL
)
goto
exit
;
*
start_minor
=
0
;
spin_lock
(
&
minor_lock
);
for
(
i
=
0
;
i
<
MAX_USB_MINORS
;
++
i
)
{
if
(
usb_minors
[
i
])
continue
;
good_spot
=
1
;
for
(
j
=
1
;
j
<=
num_minors
-
1
;
++
j
)
if
(
usb_minors
[
i
+
j
])
{
good_spot
=
0
;
break
;
}
if
(
good_spot
==
0
)
continue
;
*
start_minor
=
i
;
spin_unlock
(
&
minor_lock
);
retval
=
usb_register_minors
(
new_driver
,
num_minors
,
*
start_minor
);
if
(
retval
)
{
/* someone snuck in here, so let's start looking all over again */
spin_lock
(
&
minor_lock
);
i
=
0
;
continue
;
}
goto
exit
;
}
spin_unlock
(
&
minor_lock
);
exit:
return
retval
;
}
/**
* usb_deregister_dev - deregister a USB device's dynamic minor.
* @driver: USB operations for the driver
* @num_minors: number of minor numbers to put back.
* @start_minor: the starting minor number
*
* Used in conjunction with usb_register_dev(). This function is called
* when the USB driver is finished with the minor numbers gotten from a
* call to usb_register_dev() (usually when the device is disconnected
* from the system.)
*
* This should be called by all drivers that use the USB major number.
*/
void
usb_deregister_dev
(
struct
usb_driver
*
driver
,
int
num_minors
,
int
start_minor
)
{
usb_deregister_minors
(
driver
,
num_minors
,
start_minor
);
}
#endif
/* CONFIG_USB_DYNAMIC_MINORS */
/**
* usb_scan_devices - scans all unclaimed USB interfaces
* Context: !in_interrupt ()
...
...
@@ -298,11 +161,15 @@ static void usb_drivers_purge(struct usb_driver *driver,struct usb_device *dev)
}
/**
*
usb_deregister - unregister a USB driver
*
@driver: USB operations of the driver to unregister
*
Context: !in_interrupt ()
*
usb_deregister - unregister a USB driver
*
@driver: USB operations of the driver to unregister
*
Context: !in_interrupt ()
*
* Unlinks the specified driver from the internal USB driver list.
* Unlinks the specified driver from the internal USB driver list.
*
* NOTE: If you called usb_register_dev(), you still need to call
* usb_deregister_dev() to clean up your driver's allocated minor numbers,
* this * call will no longer do it for you.
*/
void
usb_deregister
(
struct
usb_driver
*
driver
)
{
...
...
@@ -310,11 +177,6 @@ void usb_deregister(struct usb_driver *driver)
info
(
"deregistering driver %s"
,
driver
->
name
);
#ifndef CONFIG_USB_DYNAMIC_MINORS
if
(
driver
->
fops
!=
NULL
)
usb_deregister_minors
(
driver
,
driver
->
num_minors
,
driver
->
minor
);
#endif
/*
* first we remove the driver, to be sure it doesn't get used by
* another thread while we are stepping through removing entries
...
...
@@ -1357,55 +1219,6 @@ int usb_new_device(struct usb_device *dev)
return
0
;
}
static
int
usb_open
(
struct
inode
*
inode
,
struct
file
*
file
)
{
int
minor
=
minor
(
inode
->
i_rdev
);
struct
usb_driver
*
c
;
int
err
=
-
ENODEV
;
struct
file_operations
*
old_fops
,
*
new_fops
=
NULL
;
spin_lock
(
&
minor_lock
);
c
=
usb_minors
[
minor
];
spin_unlock
(
&
minor_lock
);
if
(
!
c
||
!
(
new_fops
=
fops_get
(
c
->
fops
)))
return
err
;
old_fops
=
file
->
f_op
;
file
->
f_op
=
new_fops
;
/* Curiouser and curiouser... NULL ->open() as "no device" ? */
if
(
file
->
f_op
->
open
)
err
=
file
->
f_op
->
open
(
inode
,
file
);
if
(
err
)
{
fops_put
(
file
->
f_op
);
file
->
f_op
=
fops_get
(
old_fops
);
}
fops_put
(
old_fops
);
return
err
;
}
static
struct
file_operations
usb_fops
=
{
owner:
THIS_MODULE
,
open:
usb_open
,
};
int
usb_major_init
(
void
)
{
if
(
devfs_register_chrdev
(
USB_MAJOR
,
"usb"
,
&
usb_fops
))
{
err
(
"unable to get major %d for usb devices"
,
USB_MAJOR
);
return
-
EBUSY
;
}
usb_devfs_handle
=
devfs_mk_dir
(
NULL
,
"usb"
,
NULL
);
return
0
;
}
void
usb_major_cleanup
(
void
)
{
devfs_unregister
(
usb_devfs_handle
);
devfs_unregister_chrdev
(
USB_MAJOR
,
"usb"
);
}
#ifdef CONFIG_PROC_FS
struct
list_head
*
usb_driver_get_list
(
void
)
...
...
@@ -1463,11 +1276,6 @@ EXPORT_SYMBOL(usb_register);
EXPORT_SYMBOL
(
usb_deregister
);
EXPORT_SYMBOL
(
usb_scan_devices
);
#ifdef CONFIG_USB_DYNAMIC_MINORS
EXPORT_SYMBOL
(
usb_register_dev
);
EXPORT_SYMBOL
(
usb_deregister_dev
);
#endif
EXPORT_SYMBOL
(
usb_alloc_dev
);
EXPORT_SYMBOL
(
usb_free_dev
);
EXPORT_SYMBOL
(
usb_get_dev
);
...
...
@@ -1489,5 +1297,4 @@ EXPORT_SYMBOL(__usb_get_extra_descriptor);
EXPORT_SYMBOL
(
usb_get_current_frame_number
);
EXPORT_SYMBOL
(
usb_devfs_handle
);
MODULE_LICENSE
(
"GPL"
);
drivers/usb/host/Config.help
View file @
5bc21855
...
...
@@ -36,26 +36,7 @@ CONFIG_USB_OHCI_HCD
The module will be called ohci-hcd.o. If you want to compile it
as a module, say M here and read <file:Documentation/modules.txt>.
CONFIG_USB_UHCI
The Universal Host Controller Interface is a standard by Intel for
accessing the USB hardware in the PC (which is also called the USB
host controller). If your USB host controller conforms to this
standard, you may want to say Y, but see below. All recent boards
with Intel PCI chipsets (like intel 430TX, 440FX, 440LX, 440BX,
i810, i820) conform to this standard. Also all VIA PCI chipsets
(like VIA VP2, VP3, MVP3, Apollo Pro, Apollo Pro II or Apollo Pro
133).
Currently there exist two drivers for UHCI host controllers: this
one and the so-called JE driver, which you can get from
"UHCI alternate (JE) support", below. You need only one.
This code is also available as a module ( = code which can be
inserted in and removed from the running kernel whenever you want).
The module will be called usb-uhci.o. If you want to compile it as a
module, say M here and read <file:Documentation/modules.txt>.
CONFIG_USB_UHCI_ALT
CONFIG_USB_UHCI_HCD_ALT
The Universal Host Controller Interface is a standard by Intel for
accessing the USB hardware in the PC (which is also called the USB
host controller). If your USB host controller conforms to this
...
...
@@ -65,31 +46,11 @@ CONFIG_USB_UHCI_ALT
(like VIA VP2, VP3, MVP3, Apollo Pro, Apollo Pro II or Apollo Pro
133). If unsure, say Y.
Currently there exist two drivers for UHCI host controllers: this
so-called JE driver, and the one you get from "UHCI support", above.
You need only one.
This code is also available as a module ( = code which can be
inserted in and removed from the running kernel whenever you want).
The module will be called uhci.o. If you want to compile it as a
The module will be called uhci
-hcd
.o. If you want to compile it as a
module, say M here and read <file:Documentation/modules.txt>.
CONFIG_USB_OHCI
The Open Host Controller Interface is a standard by
Compaq/Microsoft/National for accessing the USB PC hardware (also
called USB host controller). If your USB host controller conforms to
this standard, say Y. The USB host controllers on most non-Intel
architectures and on several x86 compatibles with non-Intel chipsets
-- like SiS (aktual 610, 610 and so on) or ALi (ALi IV, ALi V,
Aladdin Pro..) -- conform to this standard.
You may want to read <file:Documentation/usb/ohci.txt>.
This code is also available as a module ( = code which can be
inserted in and removed from the running kernel whenever you want).
The module will be called usb-ohci.o. If you want to compile it
as a module, say M here and read <file:Documentation/modules.txt>.
CONFIG_USB_SL811HS
Say Y here if you have a SL811HS USB host controller in your system.
...
...
drivers/usb/host/Config.in
View file @
5bc21855
...
...
@@ -2,23 +2,9 @@
# USB Host Controller Drivers
#
comment 'USB Host Controller Drivers'
dep_tristate ' EHCI HCD (USB 2.0) support (EXPERIMENTAL)' CONFIG_USB_EHCI_HCD $CONFIG_USB $CONFIG_EXPERIMENTAL
dep_tristate ' OHCI HCD support (EXPERIMENTAL)' CONFIG_USB_OHCI_HCD $CONFIG_USB $CONFIG_EXPERIMENTAL
if [ "$CONFIG_USB_UHCI_HCD_ALT" != "y" ]; then
dep_tristate ' UHCI HCD (most Intel and VIA) support (EXPERIMENTAL)' CONFIG_USB_UHCI_HCD $CONFIG_USB $CONFIG_EXPERIMENTAL
fi
if [ "$CONFIG_USB_UHCI_HCD" != "y" ]; then
dep_tristate ' UHCI HCD Alternate (most Intel and VIA) support (EXPERIMENTAL)' CONFIG_USB_UHCI_HCD_ALT $CONFIG_USB $CONFIG_EXPERIMENTAL
fi
#if [ "$CONFIG_USB_UHCI_ALT" != "y" ]; then
# dep_tristate ' UHCI (Intel PIIX4, VIA, ...) support' CONFIG_USB_UHCI $CONFIG_USB
#fi
#if [ "$CONFIG_USB_UHCI" != "y" ]; then
# dep_tristate ' UHCI Alternate Driver (JE) support' CONFIG_USB_UHCI_ALT $CONFIG_USB
#else
# define_bool CONFIG_USB_UHCI_ALT n
#fi
#dep_tristate ' OHCI (Compaq, iMacs, OPTi, SiS, ALi, ...) support' CONFIG_USB_OHCI $CONFIG_USB
dep_tristate ' EHCI HCD (USB 2.0) support' CONFIG_USB_EHCI_HCD $CONFIG_USB
dep_tristate ' OHCI HCD support' CONFIG_USB_OHCI_HCD $CONFIG_USB
dep_tristate ' UHCI HCD (most Intel and VIA) support' CONFIG_USB_UHCI_HCD_ALT $CONFIG_USB
if [ "$CONFIG_ARM" = "y" ]; then
dep_tristate ' SA1111 OHCI-compatible host interface support' CONFIG_USB_OHCI_SA1111 $CONFIG_USB
dep_tristate ' SL811HS support' CONFIG_USB_SL811HS $CONFIG_USB
...
...
drivers/usb/host/ohci-dbg.c
View file @
5bc21855
...
...
@@ -190,6 +190,8 @@ static void ohci_dump_roothub (struct ohci_hcd *controller, int verbose)
__u32
temp
,
ndp
,
i
;
temp
=
roothub_a
(
controller
);
if
(
temp
==
~
(
u32
)
0
)
return
;
ndp
=
(
temp
&
RH_A_NDP
);
if
(
verbose
)
{
...
...
drivers/usb/host/ohci-hcd.c
View file @
5bc21855
...
...
@@ -502,11 +502,19 @@ static void ohci_irq (struct usb_hcd *hcd)
if
((
ohci
->
hcca
->
done_head
!=
0
)
&&
!
(
le32_to_cpup
(
&
ohci
->
hcca
->
done_head
)
&
0x01
))
{
ints
=
OHCI_INTR_WDH
;
}
else
if
((
ints
=
(
readl
(
&
regs
->
intrstatus
)
&
readl
(
&
regs
->
intrenable
)))
==
0
)
{
/* cardbus/... hardware gone before remove() */
}
else
if
((
ints
=
readl
(
&
regs
->
intrstatus
))
==
~
(
u32
)
0
)
{
ohci
->
disabled
++
;
err
(
"%s device removed!"
,
hcd
->
self
.
bus_name
);
return
;
/* interrupt for some other device? */
}
else
if
((
ints
&=
readl
(
&
regs
->
intrenable
))
==
0
)
{
return
;
}
// dbg ("Interrupt: %x frame: %x", ints, le16_to_cpu (ohci->hcca->frame_no));
if
(
ints
&
OHCI_INTR_UE
)
{
...
...
drivers/usb/host/uhci-hcd.c
View file @
5bc21855
...
...
@@ -1665,37 +1665,15 @@ static int uhci_urb_dequeue(struct usb_hcd *hcd, struct urb *urb)
uhci_unlink_generic
(
uhci
,
urb
);
if
(
urb
->
transfer_flags
&
USB_ASYNC_UNLINK
)
{
urbp
->
status
=
urb
->
status
=
-
ECONNABORTED
;
spin_lock
(
&
uhci
->
urb_remove_list_lock
);
spin_lock
(
&
uhci
->
urb_remove_list_lock
);
/* If we're the first, set the next interrupt bit */
if
(
list_empty
(
&
uhci
->
urb_remove_list
))
uhci_set_next_interrupt
(
uhci
);
list_add
(
&
urbp
->
urb_list
,
&
uhci
->
urb_remove_list
);
spin_unlock
(
&
uhci
->
urb_remove_list_lock
);
spin_unlock_irqrestore
(
&
uhci
->
urb_list_lock
,
flags
);
}
else
{
urb
->
status
=
-
ENOENT
;
spin_unlock_irqrestore
(
&
uhci
->
urb_list_lock
,
flags
);
if
(
in_interrupt
())
{
/* wait at least 1 frame */
static
int
errorcount
=
10
;
if
(
errorcount
--
)
dbg
(
"uhci_urb_dequeue called from interrupt for urb %p"
,
urb
);
udelay
(
1000
);
}
else
schedule_timeout
(
1
+
1
*
HZ
/
1000
);
uhci_finish_urb
(
hcd
,
urb
);
}
/* If we're the first, set the next interrupt bit */
if
(
list_empty
(
&
uhci
->
urb_remove_list
))
uhci_set_next_interrupt
(
uhci
);
list_add
(
&
urbp
->
urb_list
,
&
uhci
->
urb_remove_list
);
spin_unlock
(
&
uhci
->
urb_remove_list_lock
);
spin_unlock_irqrestore
(
&
uhci
->
urb_list_lock
,
flags
);
return
0
;
}
...
...
@@ -1788,7 +1766,7 @@ static void stall_callback(unsigned long ptr)
tmp
=
tmp
->
next
;
u
->
transfer_flags
|=
USB_
ASYNC_UNLINK
|
USB_
TIMEOUT_KILLED
;
u
->
transfer_flags
|=
USB_TIMEOUT_KILLED
;
uhci_urb_dequeue
(
hcd
,
u
);
}
...
...
drivers/usb/host/usb-uhci-hcd.c
View file @
5bc21855
...
...
@@ -271,21 +271,15 @@ static int uhci_urb_enqueue (struct usb_hcd *hcd, struct urb *urb, int mem_flags
static
int
uhci_urb_dequeue
(
struct
usb_hcd
*
hcd
,
struct
urb
*
urb
)
{
unsigned
long
flags
=
0
;
struct
uhci_hcd
*
uhci
;
struct
uhci_hcd
*
uhci
=
hcd_to_uhci
(
hcd
);
int
ret
;
dbg
(
"uhci_urb_dequeue called for %p"
,
urb
);
uhci
=
hcd_to_uhci
(
hcd
);
if
(
urb
->
transfer_flags
&
USB_ASYNC_UNLINK
)
{
int
ret
;
spin_lock_irqsave
(
&
uhci
->
urb_list_lock
,
flags
);
ret
=
uhci_unlink_urb_async
(
uhci
,
urb
,
UNLINK_ASYNC_STORE_URB
);
spin_unlock_irqrestore
(
&
uhci
->
urb_list_lock
,
flags
);
return
ret
;
}
else
return
uhci_unlink_urb_sync
(
uhci
,
urb
);
spin_lock_irqsave
(
&
uhci
->
urb_list_lock
,
flags
);
ret
=
uhci_unlink_urb_async
(
uhci
,
urb
,
UNLINK_ASYNC_STORE_URB
);
spin_unlock_irqrestore
(
&
uhci
->
urb_list_lock
,
flags
);
return
ret
;
}
/*--------------------------------------------------------------------------*/
static
int
uhci_get_frame
(
struct
usb_hcd
*
hcd
)
...
...
drivers/usb/host/usb-uhci-q.c
View file @
5bc21855
...
...
@@ -541,22 +541,6 @@ static void uhci_clean_iso_step1(struct uhci_hcd *uhci, urb_priv_t *urb_priv)
}
}
/*-------------------------------------------------------------------*/
static
void
uhci_clean_iso_step2
(
struct
uhci_hcd
*
uhci
,
urb_priv_t
*
urb_priv
)
{
struct
list_head
*
p
;
uhci_desc_t
*
td
;
int
now
=
UHCI_GET_CURRENT_FRAME
(
uhci
);
dbg
(
"uhci_clean_iso_step2"
);
while
((
p
=
urb_priv
->
desc_list
.
next
)
!=
&
urb_priv
->
desc_list
)
{
td
=
list_entry
(
p
,
uhci_desc_t
,
desc_list
);
list_del
(
p
);
INIT_LIST_HEAD
(
&
td
->
horizontal
);
list_add_tail
(
&
td
->
horizontal
,
&
uhci
->
free_desc_td
);
td
->
last_used
=
now
;
}
}
/*-------------------------------------------------------------------*/
/* mode: CLEAN_TRANSFER_NO_DELETION: unlink but no deletion mark (step 1 of async_unlink)
CLEAN_TRANSFER_REGULAR: regular (unlink/delete-mark)
CLEAN_TRANSFER_DELETION_MARK: deletion mark for QH (step 2 of async_unlink)
...
...
@@ -759,44 +743,6 @@ static int uhci_unlink_urb_async (struct uhci_hcd *uhci, struct urb *urb, int mo
return
0
;
// completion will follow
}
/*-------------------------------------------------------------------*/
// kills an urb by unlinking descriptors and waiting for at least one frame
static
int
uhci_unlink_urb_sync
(
struct
uhci_hcd
*
uhci
,
struct
urb
*
urb
)
{
uhci_desc_t
*
qh
;
urb_priv_t
*
urb_priv
;
unsigned
long
flags
=
0
;
spin_lock_irqsave
(
&
uhci
->
urb_list_lock
,
flags
);
// err("uhci_unlink_urb_sync %p, %i",urb,urb->status);
// move descriptors out the the running chains, dequeue urb
uhci_unlink_urb_async
(
uhci
,
urb
,
UNLINK_ASYNC_DONT_STORE
);
urb_priv
=
urb
->
hcpriv
;
spin_unlock_irqrestore
(
&
uhci
->
urb_list_lock
,
flags
);
// cleanup the rest
switch
(
usb_pipetype
(
urb
->
pipe
))
{
case
PIPE_INTERRUPT
:
case
PIPE_ISOCHRONOUS
:
uhci_wait_ms
(
1
);
uhci_clean_iso_step2
(
uhci
,
urb_priv
);
break
;
case
PIPE_BULK
:
case
PIPE_CONTROL
:
qh
=
list_entry
(
urb_priv
->
desc_list
.
next
,
uhci_desc_t
,
desc_list
);
uhci_clean_transfer
(
uhci
,
urb
,
qh
,
CLEAN_TRANSFER_DELETION_MARK
);
uhci_wait_ms
(
1
);
}
urb
->
status
=
-
ENOENT
;
// mark urb as killed
finish_urb
(
uhci
,
urb
);
return
0
;
}
/*-------------------------------------------------------------------*/
// unlink urbs for specific device or all devices
static
void
uhci_unlink_urbs
(
struct
uhci_hcd
*
uhci
,
struct
usb_device
*
usb_dev
,
int
remove_all
)
{
...
...
@@ -816,8 +762,6 @@ static void uhci_unlink_urbs(struct uhci_hcd *uhci, struct usb_device *usb_dev,
// err("unlink urb: %p, dev %p, ud %p", urb, usb_dev,urb->dev);
//urb->transfer_flags |=USB_ASYNC_UNLINK;
if
(
remove_all
||
(
usb_dev
==
urb
->
dev
))
{
spin_unlock_irqrestore
(
&
uhci
->
urb_list_lock
,
flags
);
err
(
"forced removing of queued URB %p due to disconnect"
,
urb
);
...
...
@@ -850,7 +794,7 @@ static void uhci_check_timeouts(struct uhci_hcd *uhci)
type
=
usb_pipetype
(
urb
->
pipe
);
if
(
urb
->
timeout
&&
time_after
(
jiffies
,
hcpriv
->
started
+
urb
->
timeout
))
{
urb
->
transfer_flags
|=
USB_TIMEOUT_KILLED
|
USB_ASYNC_UNLINK
;
urb
->
transfer_flags
|=
USB_TIMEOUT_KILLED
;
async_dbg
(
"uhci_check_timeout: timeout for %p"
,
urb
);
uhci_unlink_urb_async
(
uhci
,
urb
,
UNLINK_ASYNC_STORE_URB
);
}
...
...
drivers/usb/image/mdc800.c
View file @
5bc21855
...
...
@@ -401,6 +401,7 @@ static void mdc800_usb_download_notify (struct urb *urb)
***************************************************************************/
static
struct
usb_driver
mdc800_usb_driver
;
static
struct
file_operations
mdc800_device_ops
;
/*
* Callback to search the Mustek MDC800 on the USB Bus
...
...
@@ -476,7 +477,7 @@ static void* mdc800_usb_probe (struct usb_device *dev ,unsigned int ifnum,
down
(
&
mdc800
->
io_lock
);
retval
=
usb_register_dev
(
&
mdc800_
usb_driver
,
1
,
&
mdc800
->
minor
);
retval
=
usb_register_dev
(
&
mdc800_
device_ops
,
MDC800_DEVICE_MINOR_BASE
,
1
,
&
mdc800
->
minor
);
if
(
retval
&&
(
retval
!=
-
ENODEV
))
{
err
(
"Not able to get a minor for this device."
);
return
0
;
...
...
@@ -537,7 +538,7 @@ static void mdc800_usb_disconnect (struct usb_device *dev,void* ptr)
if
(
mdc800
->
state
==
NOT_CONNECTED
)
return
;
usb_deregister_dev
(
&
mdc800_usb_driver
,
1
,
mdc800
->
minor
);
usb_deregister_dev
(
1
,
mdc800
->
minor
);
mdc800
->
state
=
NOT_CONNECTED
;
...
...
@@ -942,12 +943,10 @@ MODULE_DEVICE_TABLE (usb, mdc800_table);
*/
static
struct
usb_driver
mdc800_usb_driver
=
{
owner:
THIS_MODULE
,
name:
"mdc800"
,
probe:
mdc800_usb_probe
,
disconnect:
mdc800_usb_disconnect
,
fops:
&
mdc800_device_ops
,
minor:
MDC800_DEVICE_MINOR_BASE
,
num_minors:
1
,
id_table:
mdc800_table
};
...
...
drivers/usb/image/scanner.c
View file @
5bc21855
...
...
@@ -971,17 +971,11 @@ probe_scanner(struct usb_device *dev, unsigned int ifnum,
down
(
&
scn_mutex
);
retval
=
usb_register_dev
(
&
scanner_driver
,
1
,
&
scn_minor
);
retval
=
usb_register_dev
(
&
usb_scanner_fops
,
SCN_BASE_MNR
,
1
,
&
scn_minor
);
if
(
retval
)
{
if
(
retval
!=
-
ENODEV
)
{
err
(
"Not able to get a minor for this device."
);
up
(
&
scn_mutex
);
return
NULL
;
}
for
(
scn_minor
=
0
;
scn_minor
<
SCN_MAX_MNR
;
scn_minor
++
)
{
if
(
!
p_scn_table
[
scn_minor
])
break
;
}
err
(
"Not able to get a minor for this device."
);
up
(
&
scn_mutex
);
return
NULL
;
}
/* Check to make sure that the last slot isn't already taken */
...
...
@@ -1112,7 +1106,7 @@ disconnect_scanner(struct usb_device *dev, void *ptr)
dbg
(
"disconnect_scanner: De-allocating minor:%d"
,
scn
->
scn_minor
);
devfs_unregister
(
scn
->
devfs
);
usb_deregister_dev
(
&
scanner_driver
,
1
,
scn
->
scn_minor
);
usb_deregister_dev
(
1
,
scn
->
scn_minor
);
p_scn_table
[
scn
->
scn_minor
]
=
NULL
;
usb_free_urb
(
scn
->
scn_irq
);
up
(
&
(
scn
->
sem
));
...
...
@@ -1125,9 +1119,6 @@ usb_driver scanner_driver = {
name:
"usbscanner"
,
probe:
probe_scanner
,
disconnect:
disconnect_scanner
,
fops:
&
usb_scanner_fops
,
minor:
SCN_BASE_MNR
,
num_minors:
SCN_MAX_MNR
,
id_table:
NULL
,
/* This would be scanner_device_ids, but we
need to check every USB device, in case
we match a user defined vendor/product ID. */
...
...
drivers/usb/input/hiddev.c
View file @
5bc21855
...
...
@@ -193,7 +193,7 @@ static int hiddev_fasync(int fd, struct file *file, int on)
static
void
hiddev_cleanup
(
struct
hiddev
*
hiddev
)
{
devfs_unregister
(
hiddev
->
devfs
);
usb_deregister_dev
(
&
hiddev_driver
,
1
,
hiddev
->
minor
);
usb_deregister_dev
(
1
,
hiddev
->
minor
);
hiddev_table
[
hiddev
->
minor
]
=
NULL
;
kfree
(
hiddev
);
}
...
...
@@ -626,21 +626,16 @@ int hiddev_connect(struct hid_device *hid)
if
(
i
==
hid
->
maxapplication
)
return
-
1
;
retval
=
usb_register_dev
(
&
hiddev_
driver
,
1
,
&
minor
);
retval
=
usb_register_dev
(
&
hiddev_
fops
,
HIDDEV_MINOR_BASE
,
1
,
&
minor
);
if
(
retval
)
{
if
(
retval
!=
-
ENODEV
)
{
err
(
"Not able to get a minor for this device."
);
return
-
1
;
}
for
(
minor
=
0
;
minor
<
HIDDEV_MINORS
&&
hiddev_table
[
minor
];
minor
++
);
if
(
minor
==
HIDDEV_MINORS
)
{
printk
(
KERN_ERR
"hiddev: no more free hiddev devices
\n
"
);
return
-
1
;
}
err
(
"Not able to get a minor for this device."
);
return
-
1
;
}
if
(
!
(
hiddev
=
kmalloc
(
sizeof
(
struct
hiddev
),
GFP_KERNEL
)))
if
(
!
(
hiddev
=
kmalloc
(
sizeof
(
struct
hiddev
),
GFP_KERNEL
)))
{
usb_deregister_dev
(
1
,
minor
);
return
-
1
;
}
memset
(
hiddev
,
0
,
sizeof
(
struct
hiddev
));
init_waitqueue_head
(
&
hiddev
->
wait
);
...
...
@@ -708,9 +703,6 @@ static void *hiddev_usbd_probe(struct usb_device *dev, unsigned int ifnum,
static
/* const */
struct
usb_driver
hiddev_driver
=
{
name:
"hiddev"
,
probe:
hiddev_usbd_probe
,
fops:
&
hiddev_fops
,
minor:
HIDDEV_MINOR_BASE
,
num_minors:
HIDDEV_MINORS
,
};
int
__init
hiddev_init
(
void
)
...
...
drivers/usb/media/dabusb.c
View file @
5bc21855
...
...
@@ -742,14 +742,9 @@ static void *dabusb_probe (struct usb_device *usbdev, unsigned int ifnum,
if
(
ifnum
!=
_DABUSB_IF
&&
usbdev
->
descriptor
.
idProduct
==
0x9999
)
return
NULL
;
retval
=
usb_register_dev
(
&
dabusb_driver
,
1
,
&
devnum
);
if
(
retval
)
{
if
(
retval
!=
-
ENODEV
)
return
NULL
;
devnum
=
dabusb_find_struct
();
if
(
devnum
==
-
1
)
return
NULL
;
}
retval
=
usb_register_dev
(
&
dabusb_fops
,
DABUSB_MINOR
,
1
,
&
devnum
);
if
(
retval
)
return
NULL
;
s
=
&
dabusb
[
devnum
];
...
...
@@ -791,7 +786,7 @@ static void dabusb_disconnect (struct usb_device *usbdev, void *ptr)
dbg
(
"dabusb_disconnect"
);
usb_deregister_dev
(
&
dabusb_driver
,
1
,
s
->
devnum
);
usb_deregister_dev
(
1
,
s
->
devnum
);
s
->
remove_pending
=
1
;
wake_up
(
&
s
->
wait
);
if
(
s
->
state
==
_started
)
...
...
@@ -814,9 +809,6 @@ static struct usb_driver dabusb_driver =
name:
"dabusb"
,
probe:
dabusb_probe
,
disconnect:
dabusb_disconnect
,
fops:
&
dabusb_fops
,
minor:
DABUSB_MINOR
,
num_minors:
NRDABUSB
,
id_table:
dabusb_ids
,
};
...
...
drivers/usb/misc/auerswald.c
View file @
5bc21855
...
...
@@ -1948,23 +1948,11 @@ static void *auerswald_probe (struct usb_device *usbdev, unsigned int ifnum,
init_waitqueue_head
(
&
cp
->
bufferwait
);
down
(
&
dev_table_mutex
);
ret
=
usb_register_dev
(
&
auerswald_
driver
,
1
,
&
dtindex
);
ret
=
usb_register_dev
(
&
auerswald_
fops
,
AUER_MINOR_BASE
,
1
,
&
dtindex
);
if
(
ret
)
{
if
(
ret
!=
-
ENODEV
)
{
err
(
"Not able to get a minor for this device."
);
up
(
&
dev_table_mutex
);
goto
pfail
;
}
/* find a free slot in the device table */
for
(
dtindex
=
0
;
dtindex
<
AUER_MAX_DEVICES
;
++
dtindex
)
{
if
(
dev_table
[
dtindex
]
==
NULL
)
break
;
}
if
(
dtindex
>=
AUER_MAX_DEVICES
)
{
err
(
"more than %d devices plugged in, can not handle this device"
,
AUER_MAX_DEVICES
);
up
(
&
dev_table_mutex
);
goto
pfail
;
}
err
(
"Not able to get a minor for this device."
);
up
(
&
dev_table_mutex
);
goto
pfail
;
}
/* Give the device a name */
...
...
@@ -2096,7 +2084,7 @@ static void auerswald_disconnect (struct usb_device *usbdev, void *driver_contex
devfs_unregister
(
cp
->
devfs
);
/* give back our USB minor number */
usb_deregister_dev
(
&
auerswald_driver
,
1
,
cp
->
dtindex
);
usb_deregister_dev
(
1
,
cp
->
dtindex
);
/* Stop the interrupt endpoint */
auerswald_int_release
(
cp
);
...
...
@@ -2153,9 +2141,6 @@ static struct usb_driver auerswald_driver = {
name:
"auerswald"
,
probe:
auerswald_probe
,
disconnect:
auerswald_disconnect
,
fops:
&
auerswald_fops
,
minor:
AUER_MINOR_BASE
,
num_minors:
AUER_MAX_DEVICES
,
id_table:
auerswald_ids
,
};
...
...
drivers/usb/misc/brlvger.c
View file @
5bc21855
...
...
@@ -246,9 +246,6 @@ static struct usb_driver brlvger_driver =
name:
"brlvger"
,
probe:
brlvger_probe
,
disconnect:
brlvger_disconnect
,
fops:
&
brlvger_fops
,
minor:
BRLVGER_MINOR
,
num_minors:
MAX_NR_BRLVGER_DEVS
,
id_table:
brlvger_ids
,
};
...
...
@@ -316,21 +313,10 @@ brlvger_probe (struct usb_device *dev, unsigned ifnum,
down
(
&
reserve_sem
);
retval
=
usb_register_dev
(
&
brlvger_
driver
,
1
,
&
i
);
retval
=
usb_register_dev
(
&
brlvger_
fops
,
BRLVGER_MINOR
,
1
,
&
i
);
if
(
retval
)
{
if
(
retval
!=
-
ENODEV
)
{
err
(
"Not able to get a minor for this device."
);
goto
error
;
}
for
(
i
=
0
;
i
<
MAX_NR_BRLVGER_DEVS
;
i
++
)
if
(
display_table
[
i
]
==
NULL
)
break
;
if
(
i
==
MAX_NR_BRLVGER_DEVS
)
{
err
(
"This driver cannot handle more than %d "
"braille displays"
,
MAX_NR_BRLVGER_DEVS
);
goto
error
;
}
err
(
"Not able to get a minor for this device."
);
goto
error
;
}
if
(
!
(
priv
=
kmalloc
(
sizeof
*
priv
,
GFP_KERNEL
))
){
...
...
@@ -431,7 +417,7 @@ brlvger_disconnect(struct usb_device *dev, void *ptr)
info
(
"Display %d disconnecting"
,
priv
->
subminor
);
devfs_unregister
(
priv
->
devfs
);
usb_deregister_dev
(
&
brlvger_driver
,
1
,
priv
->
subminor
);
usb_deregister_dev
(
1
,
priv
->
subminor
);
down
(
&
disconnect_sem
);
display_table
[
priv
->
subminor
]
=
NULL
;
...
...
drivers/usb/misc/rio500.c
View file @
5bc21855
...
...
@@ -49,7 +49,11 @@
#define DRIVER_AUTHOR "Cesar Miquel <miquel@df.uba.ar>"
#define DRIVER_DESC "USB Rio 500 driver"
#define RIO_MINOR 64
#ifdef CONFIG_USB_DYNAMIC_MINORS
#define RIO_MINOR 0
#else
#define RIO_MINOR 64
#endif
/* stall/wait timeout for rio */
#define NAK_TIMEOUT (HZ)
...
...
@@ -65,6 +69,7 @@ struct rio_usb_data {
unsigned
int
ifnum
;
/* Interface number of the USB device */
int
isopen
;
/* nz if open */
int
present
;
/* Device is present on the bus */
int
minor
;
/* minor number assigned to us */
char
*
obuf
,
*
ibuf
;
/* transfer buffers */
char
bulk_in_ep
,
bulk_out_ep
;
/* Endpoint assignments */
wait_queue_head_t
wait_q
;
/* for timeouts */
...
...
@@ -449,9 +454,16 @@ static void *probe_rio(struct usb_device *dev, unsigned int ifnum,
const
struct
usb_device_id
*
id
)
{
struct
rio_usb_data
*
rio
=
&
rio_instance
;
int
retval
;
info
(
"USB Rio found at address %d"
,
dev
->
devnum
);
retval
=
usb_register_dev
(
&
usb_rio_fops
,
RIO_MINOR
,
1
,
&
rio
->
minor
);
if
(
retval
)
{
err
(
"Not able to get a minor for this device."
);
return
NULL
;
}
rio
->
present
=
1
;
rio
->
rio_dev
=
dev
;
...
...
@@ -486,6 +498,7 @@ static void disconnect_rio(struct usb_device *dev, void *ptr)
struct
rio_usb_data
*
rio
=
(
struct
rio_usb_data
*
)
ptr
;
devfs_unregister
(
rio
->
devfs
);
usb_deregister_dev
(
1
,
rio
->
minor
);
down
(
&
(
rio
->
lock
));
if
(
rio
->
isopen
)
{
...
...
@@ -515,9 +528,6 @@ static struct usb_driver rio_driver = {
name:
"rio500"
,
probe:
probe_rio
,
disconnect:
disconnect_rio
,
fops:
&
usb_rio_fops
,
minor:
RIO_MINOR
,
num_minors:
1
,
id_table:
rio_table
,
};
...
...
drivers/usb/net/pegasus.c
View file @
5bc21855
/*
** Pegasus: USB 10/100Mbps/HomePNA (1Mbps) Controller
**
** Copyright (c) 1999-2002 Petko Manolov (petkan@users.sourceforge.net)
**
**
** ChangeLog:
** .... Most of the time spend reading sources & docs.
** v0.2.x First official release for the Linux kernel.
** v0.3.0 Beutified and structured, some bugs fixed.
** v0.3.x URBifying bulk requests and bugfixing. First relatively
** stable release. Still can touch device's registers only
** from top-halves.
** v0.4.0 Control messages remained unurbified are now URBs.
** Now we can touch the HW at any time.
** v0.4.9 Control urbs again use process context to wait. Argh...
** Some long standing bugs (enable_net_traffic) fixed.
** Also nasty trick about resubmiting control urb from
** interrupt context used. Please let me know how it
** behaves. Pegasus II support added since this version.
** TODO: suppressing HCD warnings spewage on disconnect.
** v0.4.13 Ethernet address is now set at probe(), not at open()
** time as this seems to break dhcpd.
** v0.5.0 branch to 2.5.x kernels
** v0.5.1 ethtool support added
*/
/*
* 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.
* Copyright (c) 1999-2002 Petko Manolov (petkan@users.sourceforge.net)
*
* 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.
* 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.
*
* 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
* ChangeLog:
* .... Most of the time spent on reading sources & docs.
* v0.2.x First official release for the Linux kernel.
* v0.3.0 Beutified and structured, some bugs fixed.
* v0.3.x URBifying bulk requests and bugfixing. First relatively
* stable release. Still can touch device's registers only
* from top-halves.
* v0.4.0 Control messages remained unurbified are now URBs.
* Now we can touch the HW at any time.
* v0.4.9 Control urbs again use process context to wait. Argh...
* Some long standing bugs (enable_net_traffic) fixed.
* Also nasty trick about resubmiting control urb from
* interrupt context used. Please let me know how it
* behaves. Pegasus II support added since this version.
* TODO: suppressing HCD warnings spewage on disconnect.
* v0.4.13 Ethernet address is now set at probe(), not at open()
* time as this seems to break dhcpd.
* v0.5.0 branch to 2.5.x kernels
* v0.5.1 ethtool support added
* v0.5.5 rx socket buffers are in a pool and the their allocation
* is out of the interrupt routine.
*/
#include <linux/sched.h>
#include <linux/slab.h>
#include <linux/init.h>
...
...
@@ -58,14 +46,13 @@
/*
* Version Information
*/
#define DRIVER_VERSION "v0.5.
4 (2002/04/11
)"
#define DRIVER_VERSION "v0.5.
6 (2002/06/23
)"
#define DRIVER_AUTHOR "Petko Manolov <petkan@users.sourceforge.net>"
#define DRIVER_DESC "Pegasus/Pegasus II USB Ethernet driver"
static
const
char
driver_name
[]
=
"pegasus"
;
#define PEGASUS_USE_INTR
#define PEGASUS_WRITE_EEPROM
#undef PEGASUS_WRITE_EEPROM
#define BMSR_MEDIA (BMSR_10HALF | BMSR_10FULL | BMSR_100HALF | \
BMSR_100FULL | BMSR_ANEGCAPABLE)
...
...
@@ -499,13 +486,57 @@ static int enable_net_traffic(struct net_device *dev, struct usb_device *usb)
return
0
;
}
static
void
fill_skb_pool
(
pegasus_t
*
pegasus
)
{
int
i
;
for
(
i
=
0
;
i
<
RX_SKBS
;
i
++
)
{
if
(
pegasus
->
rx_pool
[
i
])
continue
;
pegasus
->
rx_pool
[
i
]
=
dev_alloc_skb
(
PEGASUS_MTU
+
2
);
/*
** we give up if the allocation fail. the tasklet will be
** rescheduled again anyway...
*/
if
(
pegasus
->
rx_pool
[
i
]
==
NULL
)
return
;
pegasus
->
rx_pool
[
i
]
->
dev
=
pegasus
->
net
;
skb_reserve
(
pegasus
->
rx_pool
[
i
],
2
);
}
}
static
void
free_skb_pool
(
pegasus_t
*
pegasus
)
{
int
i
;
for
(
i
=
0
;
i
<
RX_SKBS
;
i
++
)
{
if
(
pegasus
->
rx_pool
[
i
])
{
dev_kfree_skb
(
pegasus
->
rx_pool
[
i
]);
pegasus
->
rx_pool
[
i
]
=
NULL
;
}
}
}
static
inline
struct
sk_buff
*
pull_skb
(
pegasus_t
*
pegasus
)
{
int
i
;
struct
sk_buff
*
skb
;
for
(
i
=
0
;
i
<
RX_SKBS
;
i
++
)
{
if
(
likely
(
pegasus
->
rx_pool
[
i
]
!=
NULL
))
{
skb
=
pegasus
->
rx_pool
[
i
];
pegasus
->
rx_pool
[
i
]
=
NULL
;
return
skb
;
}
}
return
NULL
;
}
static
void
read_bulk_callback
(
struct
urb
*
urb
)
{
pegasus_t
*
pegasus
=
urb
->
context
;
struct
net_device
*
net
;
int
count
=
urb
->
actual_length
;
int
rx_status
;
struct
sk_buff
*
skb
;
int
rx_status
,
count
=
urb
->
actual_length
;
__u16
pkt_len
;
if
(
!
pegasus
||
!
(
pegasus
->
flags
&
PEGASUS_RUNNING
))
...
...
@@ -519,7 +550,7 @@ static void read_bulk_callback(struct urb *urb)
case
0
:
break
;
case
-
ETIMEDOUT
:
dbg
(
"
reset MAC"
);
dbg
(
"
%s: reset MAC"
,
net
->
name
);
pegasus
->
flags
&=
~
PEGASUS_RX_BUSY
;
break
;
case
-
ENOENT
:
...
...
@@ -546,23 +577,24 @@ static void read_bulk_callback(struct urb *urb)
}
pkt_len
=
(
rx_status
&
0xfff
)
-
8
;
if
(
!
pegasus
->
rx_skb
)
goto
tl_sched
;
if
(
pegasus
->
rx_skb
==
NULL
)
printk
(
"%s: rx_skb == NULL
\n
"
,
__FUNCTION__
);
/*
** we are sure at this point pegasus->rx_skb != NULL
** so we go ahead and pass up the packet.
*/
skb_put
(
pegasus
->
rx_skb
,
pkt_len
);
pegasus
->
rx_skb
->
protocol
=
eth_type_trans
(
pegasus
->
rx_skb
,
net
);
netif_rx
(
pegasus
->
rx_skb
);
if
(
!
(
skb
=
dev_alloc_skb
(
PEGASUS_MTU
+
2
)))
{
pegasus
->
rx_skb
=
NULL
;
goto
tl_sched
;
}
skb
->
dev
=
net
;
skb_reserve
(
skb
,
2
);
pegasus
->
rx_skb
=
skb
;
pegasus
->
stats
.
rx_packets
++
;
pegasus
->
stats
.
rx_bytes
+=
pkt_len
;
spin_lock
(
&
pegasus
->
rx_pool_lock
);
pegasus
->
rx_skb
=
pull_skb
(
pegasus
);
spin_unlock
(
&
pegasus
->
rx_pool_lock
);
if
(
pegasus
->
rx_skb
==
NULL
)
goto
tl_sched
;
goon:
FILL_BULK_URB
(
pegasus
->
rx_urb
,
pegasus
->
usb
,
usb_rcvbulkpipe
(
pegasus
->
usb
,
1
),
...
...
@@ -587,11 +619,19 @@ static void rx_fixup(unsigned long data)
pegasus
=
(
pegasus_t
*
)
data
;
spin_lock_irq
(
&
pegasus
->
rx_pool_lock
);
fill_skb_pool
(
pegasus
);
spin_unlock_irq
(
&
pegasus
->
rx_pool_lock
);
if
(
pegasus
->
flags
&
PEGASUS_RX_URB_FAIL
)
if
(
pegasus
->
rx_skb
)
goto
try_again
;
if
(
!
(
pegasus
->
rx_skb
=
dev_alloc_skb
(
PEGASUS_MTU
+
2
)))
{
if
(
pegasus
->
rx_skb
==
NULL
)
{
spin_lock_irq
(
&
pegasus
->
rx_pool_lock
);
pegasus
->
rx_skb
=
pull_skb
(
pegasus
);
spin_unlock_irq
(
&
pegasus
->
rx_pool_lock
);
}
if
(
pegasus
->
rx_skb
==
NULL
)
{
warn
(
"wow, low on memory"
);
tasklet_schedule
(
&
pegasus
->
rx_tl
);
return
;
}
...
...
@@ -625,7 +665,6 @@ static void write_bulk_callback(struct urb *urb)
netif_wake_queue
(
pegasus
->
net
);
}
#ifdef PEGASUS_USE_INTR
static
void
intr_callback
(
struct
urb
*
urb
)
{
pegasus_t
*
pegasus
=
urb
->
context
;
...
...
@@ -662,7 +701,6 @@ static void intr_callback(struct urb *urb)
}
}
}
#endif
static
void
pegasus_tx_timeout
(
struct
net_device
*
net
)
{
...
...
@@ -748,15 +786,62 @@ static void set_carrier(struct net_device *net)
}
static
void
free_all_urbs
(
pegasus_t
*
pegasus
)
{
usb_free_urb
(
pegasus
->
intr_urb
);
usb_free_urb
(
pegasus
->
tx_urb
);
usb_free_urb
(
pegasus
->
rx_urb
);
usb_free_urb
(
pegasus
->
ctrl_urb
);
}
static
void
unlink_all_urbs
(
pegasus_t
*
pegasus
)
{
usb_unlink_urb
(
pegasus
->
intr_urb
);
usb_unlink_urb
(
pegasus
->
tx_urb
);
usb_unlink_urb
(
pegasus
->
rx_urb
);
usb_unlink_urb
(
pegasus
->
ctrl_urb
);
}
static
int
alloc_urbs
(
pegasus_t
*
pegasus
)
{
pegasus
->
ctrl_urb
=
usb_alloc_urb
(
0
,
GFP_KERNEL
);
if
(
!
pegasus
->
ctrl_urb
)
{
return
0
;
}
pegasus
->
rx_urb
=
usb_alloc_urb
(
0
,
GFP_KERNEL
);
if
(
!
pegasus
->
rx_urb
)
{
usb_free_urb
(
pegasus
->
ctrl_urb
);
return
0
;
}
pegasus
->
tx_urb
=
usb_alloc_urb
(
0
,
GFP_KERNEL
);
if
(
!
pegasus
->
tx_urb
)
{
usb_free_urb
(
pegasus
->
rx_urb
);
usb_free_urb
(
pegasus
->
ctrl_urb
);
return
0
;
}
pegasus
->
intr_urb
=
usb_alloc_urb
(
0
,
GFP_KERNEL
);
if
(
!
pegasus
->
intr_urb
)
{
usb_free_urb
(
pegasus
->
tx_urb
);
usb_free_urb
(
pegasus
->
rx_urb
);
usb_free_urb
(
pegasus
->
ctrl_urb
);
return
0
;
}
return
1
;
}
static
int
pegasus_open
(
struct
net_device
*
net
)
{
pegasus_t
*
pegasus
=
(
pegasus_t
*
)
net
->
priv
;
int
res
;
if
(
!
(
pegasus
->
rx_skb
=
dev_alloc_skb
(
PEGASUS_MTU
+
2
)))
if
(
pegasus
->
rx_skb
==
NULL
)
pegasus
->
rx_skb
=
pull_skb
(
pegasus
);
/*
** Note: no point to free the pool. it is empty :-)
*/
if
(
!
pegasus
->
rx_skb
)
return
-
ENOMEM
;
pegasus
->
rx_skb
->
dev
=
net
;
skb_reserve
(
pegasus
->
rx_skb
,
2
);
down
(
&
pegasus
->
sem
);
FILL_BULK_URB
(
pegasus
->
rx_urb
,
pegasus
->
usb
,
...
...
@@ -765,19 +850,20 @@ static int pegasus_open(struct net_device *net)
read_bulk_callback
,
pegasus
);
if
((
res
=
usb_submit_urb
(
pegasus
->
rx_urb
,
GFP_KERNEL
)))
warn
(
"%s: failed rx_urb %d"
,
__FUNCTION__
,
res
);
#ifdef PEGASUS_USE_INTR
FILL_INT_URB
(
pegasus
->
intr_urb
,
pegasus
->
usb
,
usb_rcvintpipe
(
pegasus
->
usb
,
3
),
pegasus
->
intr_buff
,
sizeof
(
pegasus
->
intr_buff
),
intr_callback
,
pegasus
,
pegasus
->
intr_interval
);
if
((
res
=
usb_submit_urb
(
pegasus
->
intr_urb
,
GFP_KERNEL
)))
warn
(
"%s: failed intr_urb %d"
,
__FUNCTION__
,
res
);
#endif
netif_start_queue
(
net
);
pegasus
->
flags
|=
PEGASUS_RUNNING
;
if
((
res
=
enable_net_traffic
(
net
,
pegasus
->
usb
)))
{
err
(
"can't enable_net_traffic() - %d"
,
res
);
res
=
-
EIO
;
usb_unlink_urb
(
pegasus
->
rx_urb
);
usb_unlink_urb
(
pegasus
->
intr_urb
);
free_skb_pool
(
pegasus
);
goto
exit
;
}
set_carrier
(
net
);
...
...
@@ -797,13 +883,7 @@ static int pegasus_close(struct net_device *net)
netif_stop_queue
(
net
);
if
(
!
(
pegasus
->
flags
&
PEGASUS_UNPLUG
))
disable_net_traffic
(
pegasus
);
usb_unlink_urb
(
pegasus
->
rx_urb
);
usb_unlink_urb
(
pegasus
->
tx_urb
);
usb_unlink_urb
(
pegasus
->
ctrl_urb
);
#ifdef PEGASUS_USE_INTR
usb_unlink_urb
(
pegasus
->
intr_urb
);
#endif
unlink_all_urbs
(
pegasus
);
up
(
&
pegasus
->
sem
);
return
0
;
...
...
@@ -986,38 +1066,14 @@ static void *pegasus_probe(struct usb_device *dev, unsigned int ifnum,
pegasus
->
dev_index
=
dev_index
;
init_waitqueue_head
(
&
pegasus
->
ctrl_wait
);
pegasus
->
ctrl_urb
=
usb_alloc_urb
(
0
,
GFP_KERNEL
);
if
(
!
pegasus
->
ctrl_urb
)
{
kfree
(
pegasus
);
return
NULL
;
}
pegasus
->
rx_urb
=
usb_alloc_urb
(
0
,
GFP_KERNEL
);
if
(
!
pegasus
->
rx_urb
)
{
usb_free_urb
(
pegasus
->
ctrl_urb
);
kfree
(
pegasus
);
return
NULL
;
}
pegasus
->
tx_urb
=
usb_alloc_urb
(
0
,
GFP_KERNEL
);
if
(
!
pegasus
->
tx_urb
)
{
usb_free_urb
(
pegasus
->
rx_urb
);
usb_free_urb
(
pegasus
->
ctrl_urb
);
kfree
(
pegasus
);
return
NULL
;
}
pegasus
->
intr_urb
=
usb_alloc_urb
(
0
,
GFP_KERNEL
);
if
(
!
pegasus
->
intr_urb
)
{
usb_free_urb
(
pegasus
->
tx_urb
);
usb_free_urb
(
pegasus
->
rx_urb
);
usb_free_urb
(
pegasus
->
ctrl_urb
);
if
(
!
alloc_urbs
(
pegasus
))
{
kfree
(
pegasus
);
return
NULL
;
}
net
=
init_etherdev
(
NULL
,
0
);
if
(
!
net
)
{
usb_free_urb
(
pegasus
->
tx_urb
);
usb_free_urb
(
pegasus
->
rx_urb
);
usb_free_urb
(
pegasus
->
ctrl_urb
);
free_all_urbs
(
pegasus
);
kfree
(
pegasus
);
return
NULL
;
}
...
...
@@ -1039,32 +1095,26 @@ static void *pegasus_probe(struct usb_device *dev, unsigned int ifnum,
net
->
set_multicast_list
=
pegasus_set_multicast
;
net
->
get_stats
=
pegasus_netdev_stats
;
net
->
mtu
=
PEGASUS_MTU
;
spin_lock_init
(
&
pegasus
->
rx_pool_lock
);
pegasus
->
features
=
usb_dev_id
[
dev_index
].
private
;
#ifdef PEGASUS_USE_INTR
get_interrupt_interval
(
pegasus
);
#endif
if
(
reset_mac
(
pegasus
))
{
err
(
"can't reset MAC"
);
unregister_netdev
(
pegasus
->
net
);
usb_free_urb
(
pegasus
->
tx_urb
);
usb_free_urb
(
pegasus
->
rx_urb
);
usb_free_urb
(
pegasus
->
ctrl_urb
);
free_all_urbs
(
pegasus
);
kfree
(
pegasus
->
net
);
kfree
(
pegasus
);
pegasus
=
NULL
;
goto
exit
;
}
info
(
"%s: %s"
,
net
->
name
,
usb_dev_id
[
dev_index
].
name
);
set_ethernet_addr
(
pegasus
);
fill_skb_pool
(
pegasus
);
printk
(
"%s: %s
\n
"
,
net
->
name
,
usb_dev_id
[
dev_index
].
name
);
if
(
pegasus
->
features
&
PEGASUS_II
)
{
info
(
"setup Pegasus II specific registers"
);
setup_pegasus_II
(
pegasus
);
}
pegasus
->
phy
=
mii_phy_probe
(
pegasus
);
if
(
pegasus
->
phy
==
0xff
)
{
warn
(
"can't locate MII phy, using default"
);
...
...
@@ -1087,14 +1137,9 @@ static void pegasus_disconnect(struct usb_device *dev, void *ptr)
pegasus
->
flags
|=
PEGASUS_UNPLUG
;
unregister_netdev
(
pegasus
->
net
);
usb_put_dev
(
dev
);
usb_unlink_urb
(
pegasus
->
intr_urb
);
usb_unlink_urb
(
pegasus
->
tx_urb
);
usb_unlink_urb
(
pegasus
->
rx_urb
);
usb_unlink_urb
(
pegasus
->
ctrl_urb
);
usb_free_urb
(
pegasus
->
intr_urb
);
usb_free_urb
(
pegasus
->
tx_urb
);
usb_free_urb
(
pegasus
->
rx_urb
);
usb_free_urb
(
pegasus
->
ctrl_urb
);
unlink_all_urbs
(
pegasus
);
free_all_urbs
(
pegasus
);
free_skb_pool
(
pegasus
);
if
(
pegasus
->
rx_skb
)
dev_kfree_skb
(
pegasus
->
rx_skb
);
kfree
(
pegasus
->
net
);
...
...
drivers/usb/net/pegasus.h
View file @
5bc21855
...
...
@@ -2,18 +2,8 @@
* Copyright (c) 1999-2002 Petko Manolov - Petkan (petkan@users.sourceforge.net)
*
* 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
* it under the terms of the GNU General Public License version 2 as published
* by the Free Software Foundation.
*/
...
...
@@ -23,6 +13,7 @@
#define HAS_HOME_PNA 0x40000000
#define PEGASUS_MTU 1536
#define RX_SKBS 4
#define EPROM_WRITE 0x01
#define EPROM_READ 0x02
...
...
@@ -100,10 +91,12 @@ typedef struct pegasus {
int
intr_interval
;
struct
tasklet_struct
rx_tl
;
struct
urb
*
ctrl_urb
,
*
rx_urb
,
*
tx_urb
,
*
intr_urb
;
struct
sk_buff
*
rx_pool
[
RX_SKBS
];
struct
sk_buff
*
rx_skb
;
struct
usb_ctrlrequest
dr
;
wait_queue_head_t
ctrl_wait
;
struct
semaphore
sem
;
spinlock_t
rx_pool_lock
;
unsigned
char
intr_buff
[
8
];
__u8
tx_buff
[
PEGASUS_MTU
];
__u8
eth_regs
[
4
];
...
...
drivers/usb/net/rtl8150.c
View file @
5bc21855
/*
* Copyright (c) 2002 Petko Manolov (petkan@users.sourceforge.net)
*
* 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.
* Copyright (c) 2002 Petko Manolov (petkan@users.sourceforge.net)
*
* 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.
*/
#include <linux/config.h>
#include <linux/sched.h>
#include <linux/init.h>
#include <linux/signal.h>
#include <linux/slab.h>
#include <linux/module.h>
...
...
@@ -19,7 +18,6 @@
#include <linux/ethtool.h>
#include <linux/devfs_fs_kernel.h>
#include <linux/usb.h>
#include <linux/init.h>
#include <asm/uaccess.h>
/* Version Information */
...
...
@@ -106,7 +104,7 @@ unsigned long multicast_filter_limit = 32;
static
void
fill_skb_pool
(
rtl8150_t
*
);
static
void
free_skb_pool
(
rtl8150_t
*
);
static
struct
sk_buff
*
pull_skb
(
rtl8150_t
*
);
static
inline
struct
sk_buff
*
pull_skb
(
rtl8150_t
*
);
static
void
rtl8150_disconnect
(
struct
usb_device
*
dev
,
void
*
ptr
);
static
void
*
rtl8150_probe
(
struct
usb_device
*
dev
,
unsigned
int
ifnum
,
const
struct
usb_device_id
*
id
);
...
...
@@ -312,7 +310,7 @@ static void read_bulk_callback(struct urb *urb)
case
-
ENOENT
:
return
;
/* the urb is in unlink state */
case
-
ETIMEDOUT
:
warn
(
"
reset needed may be
?.."
);
warn
(
"
may be reset is needed
?.."
);
goto
goon
;
default:
warn
(
"Rx status %d"
,
urb
->
status
);
...
...
@@ -331,13 +329,13 @@ static void read_bulk_callback(struct urb *urb)
netif_rx
(
dev
->
rx_skb
);
dev
->
stats
.
rx_packets
++
;
dev
->
stats
.
rx_bytes
+=
pkt_len
;
spin_lock
(
&
dev
->
rx_pool_lock
);
skb
=
pull_skb
(
dev
);
spin_unlock
(
&
dev
->
rx_pool_lock
);
if
(
!
skb
)
goto
resched
;
skb
->
dev
=
netdev
;
skb_reserve
(
skb
,
2
);
dev
->
rx_skb
=
skb
;
goon:
FILL_BULK_URB
(
dev
->
rx_urb
,
dev
->
udev
,
usb_rcvbulkpipe
(
dev
->
udev
,
1
),
...
...
@@ -361,11 +359,16 @@ static void rx_fixup(unsigned long data)
dev
=
(
rtl8150_t
*
)
data
;
spin_lock_irq
(
&
dev
->
rx_pool_lock
);
fill_skb_pool
(
dev
);
spin_unlock_irq
(
&
dev
->
rx_pool_lock
);
if
(
test_bit
(
RX_URB_FAIL
,
&
dev
->
flags
))
if
(
dev
->
rx_skb
)
goto
try_again
;
if
(
!
(
skb
=
pull_skb
(
dev
)))
spin_lock_irq
(
&
dev
->
rx_pool_lock
);
skb
=
pull_skb
(
dev
);
spin_unlock_irq
(
&
dev
->
rx_pool_lock
);
if
(
skb
==
NULL
)
goto
tlsched
;
dev
->
rx_skb
=
skb
;
FILL_BULK_URB
(
dev
->
rx_urb
,
dev
->
udev
,
usb_rcvbulkpipe
(
dev
->
udev
,
1
),
...
...
@@ -426,51 +429,41 @@ static void fill_skb_pool(rtl8150_t *dev)
{
struct
sk_buff
*
skb
;
int
i
;
unsigned
long
flags
;
spin_lock_irqsave
(
&
dev
->
rx_pool_lock
,
flags
);
for
(
i
=
0
;
i
<
RX_SKB_POOL_SIZE
;
i
++
)
{
if
(
dev
->
rx_skb_pool
[
i
])
continue
;
skb
=
dev_alloc_skb
(
RTL8150_MTU
+
2
);
if
(
!
skb
)
{
spin_unlock_irqrestore
(
&
dev
->
rx_pool_lock
,
flags
);
return
;
}
skb
->
dev
=
dev
->
netdev
;
skb_reserve
(
skb
,
2
);
dev
->
rx_skb_pool
[
i
]
=
skb
;
}
spin_unlock_irqrestore
(
&
dev
->
rx_pool_lock
,
flags
);
}
static
void
free_skb_pool
(
rtl8150_t
*
dev
)
{
int
i
;
spin_lock_irq
(
&
dev
->
rx_pool_lock
);
for
(
i
=
0
;
i
<
RX_SKB_POOL_SIZE
;
i
++
)
if
(
dev
->
rx_skb_pool
[
i
])
dev_kfree_skb
(
dev
->
rx_skb_pool
[
i
]);
spin_unlock_irq
(
&
dev
->
rx_pool_lock
);
}
static
struct
sk_buff
*
pull_skb
(
rtl8150_t
*
dev
)
static
inline
struct
sk_buff
*
pull_skb
(
rtl8150_t
*
dev
)
{
struct
sk_buff
*
skb
;
int
i
;
unsigned
long
flags
;
spin_lock_irqsave
(
&
dev
->
rx_pool_lock
,
flags
);
for
(
i
=
0
;
i
<
RX_SKB_POOL_SIZE
;
i
++
)
{
if
(
dev
->
rx_skb_pool
[
i
])
{
skb
=
dev
->
rx_skb_pool
[
i
];
dev
->
rx_skb_pool
[
i
]
=
NULL
;
spin_unlock_irqrestore
(
&
dev
->
rx_pool_lock
,
flags
);
return
skb
;
}
}
spin_unlock_irqrestore
(
&
dev
->
rx_pool_lock
,
flags
);
return
NULL
;
}
...
...
@@ -578,8 +571,8 @@ static int rtl8150_open(struct net_device *netdev)
if
(
dev
==
NULL
)
{
return
-
ENODEV
;
}
dev
->
rx_skb
=
pull_skb
(
dev
);
if
(
dev
->
rx_skb
==
NULL
)
dev
->
rx_skb
=
pull_skb
(
dev
);
if
(
!
dev
->
rx_skb
)
return
-
ENOMEM
;
...
...
@@ -816,13 +809,13 @@ static void rtl8150_disconnect(struct usb_device *udev, void *ptr)
dev
=
NULL
;
}
static
int
__init
usb_rtl8150_init
(
void
)
int
__init
usb_rtl8150_init
(
void
)
{
info
(
DRIVER_DESC
" "
DRIVER_VERSION
);
return
usb_register
(
&
rtl8150_driver
);
}
static
void
__exit
usb_rtl8150_exit
(
void
)
void
__exit
usb_rtl8150_exit
(
void
)
{
usb_deregister
(
&
rtl8150_driver
);
}
...
...
drivers/usb/storage/transport.c
View file @
5bc21855
...
...
@@ -428,18 +428,13 @@ int usb_stor_control_msg(struct us_data *us, unsigned int pipe,
void
*
data
,
u16
size
)
{
int
status
;
struct
usb_ctrlrequest
*
dr
;
dr
=
kmalloc
(
sizeof
(
struct
usb_ctrlrequest
),
GFP_NOIO
);
if
(
!
dr
)
return
-
ENOMEM
;
/* fill in the devrequest structure */
dr
->
bRequestType
=
requesttype
;
dr
->
bRequest
=
request
;
dr
->
wValue
=
cpu_to_le16
(
value
);
dr
->
wIndex
=
cpu_to_le16
(
index
);
dr
->
wLength
=
cpu_to_le16
(
size
);
us
->
dr
->
bRequestType
=
requesttype
;
us
->
dr
->
bRequest
=
request
;
us
->
dr
->
wValue
=
cpu_to_le16
(
value
);
us
->
dr
->
wIndex
=
cpu_to_le16
(
index
);
us
->
dr
->
wLength
=
cpu_to_le16
(
size
);
/* lock the URB */
down
(
&
(
us
->
current_urb_sem
));
...
...
@@ -452,7 +447,7 @@ int usb_stor_control_msg(struct us_data *us, unsigned int pipe,
/* fill the URB */
FILL_CONTROL_URB
(
us
->
current_urb
,
us
->
pusb_dev
,
pipe
,
(
unsigned
char
*
)
dr
,
data
,
size
,
(
unsigned
char
*
)
us
->
dr
,
data
,
size
,
usb_stor_blocking_completion
,
NULL
);
/* submit the URB */
...
...
@@ -1162,7 +1157,7 @@ int usb_stor_Bulk_max_lun(struct us_data *us)
int
pipe
;
/* issue the command -- use usb_control_msg() because
*
the state machine is not yet alive
*/
*
this is not a scsi queued-command
*/
pipe
=
usb_rcvctrlpipe
(
us
->
pusb_dev
,
0
);
result
=
usb_control_msg
(
us
->
pusb_dev
,
pipe
,
US_BULK_GET_MAX_LUN
,
...
...
@@ -1181,8 +1176,8 @@ int usb_stor_Bulk_max_lun(struct us_data *us)
if
(
result
==
-
EPIPE
)
{
US_DEBUGP
(
"clearing endpoint halt for pipe 0x%x
\n
"
,
pipe
);
/* Use usb_clear_halt() because th
e state machine
*
is not yet alive
*/
/* Use usb_clear_halt() because th
is is not a
*
scsi queued-command
*/
usb_clear_halt
(
us
->
pusb_dev
,
pipe
);
}
...
...
@@ -1356,27 +1351,6 @@ int usb_stor_Bulk_transport(Scsi_Cmnd *srb, struct us_data *us)
* Reset routines
***********************************************************************/
struct
us_timeout
{
struct
us_data
*
us
;
spinlock_t
timer_lock
;
};
/* The timeout event handler
*/
static
void
usb_stor_timeout_handler
(
unsigned
long
to__
)
{
struct
us_timeout
*
to
=
(
struct
us_timeout
*
)
to__
;
struct
us_data
*
us
=
to
->
us
;
US_DEBUGP
(
"Timeout occurred
\n
"
);
/* abort the current request */
usb_stor_abort_transport
(
us
);
/* let the reset routine know we have finished */
spin_unlock
(
&
to
->
timer_lock
);
}
/* This is the common part of the device reset code.
*
* It's handy that every transport mechanism uses the control endpoint for
...
...
@@ -1385,28 +1359,20 @@ static void usb_stor_timeout_handler(unsigned long to__)
* Basically, we send a reset with a 20-second timeout, so we don't get
* jammed attempting to do the reset.
*/
void
usb_stor_reset_common
(
struct
us_data
*
us
,
u8
request
,
u8
requesttype
,
static
int
usb_stor_reset_common
(
struct
us_data
*
us
,
u8
request
,
u8
requesttype
,
u16
value
,
u16
index
,
void
*
data
,
u16
size
)
{
int
result
;
struct
us_timeout
timeout_data
=
{
us
,
SPIN_LOCK_UNLOCKED
};
struct
timer_list
timeout_list
;
/* prepare the timeout handler */
spin_lock
(
&
timeout_data
.
timer_lock
);
init_timer
(
&
timeout_list
);
/* A 20-second timeout may seem rather long, but a LaCie
* StudioDrive USB2 device takes 16+ seconds to get going
* following a powerup or USB attach event. */
timeout_list
.
expires
=
jiffies
+
20
*
HZ
;
timeout_list
.
data
=
(
unsigned
long
)
&
timeout_data
;
timeout_list
.
function
=
usb_stor_timeout_handler
;
add_timer
(
&
timeout_list
);
result
=
usb_stor_control_msg
(
us
,
usb_sndctrlpipe
(
us
->
pusb_dev
,
0
),
request
,
requesttype
,
value
,
index
,
data
,
size
);
/* Use usb_control_msg() because this is not a queued-command */
result
=
usb_control_msg
(
us
->
pusb_dev
,
usb_sndctrlpipe
(
us
->
pusb_dev
,
0
),
request
,
requesttype
,
value
,
index
,
data
,
size
,
20
*
HZ
);
if
(
result
<
0
)
goto
Done
;
...
...
@@ -1415,41 +1381,30 @@ void usb_stor_reset_common(struct us_data *us, u8 request, u8 requesttype,
schedule_timeout
(
HZ
*
6
);
set_current_state
(
TASK_RUNNING
);
/* Use usb_clear_halt() because this is not a queued-command */
US_DEBUGP
(
"Soft reset: clearing bulk-in endpoint halt
\n
"
);
result
=
usb_
stor_clear_halt
(
us
,
result
=
usb_
clear_halt
(
us
->
pusb_dev
,
usb_rcvbulkpipe
(
us
->
pusb_dev
,
us
->
ep_in
));
if
(
result
<
0
)
goto
Done
;
US_DEBUGP
(
"Soft reset: clearing bulk-out endpoint halt
\n
"
);
result
=
usb_
stor_clear_halt
(
us
,
result
=
usb_
clear_halt
(
us
->
pusb_dev
,
usb_sndbulkpipe
(
us
->
pusb_dev
,
us
->
ep_out
));
Done:
/* prevent the timer from coming back to haunt us */
if
(
!
del_timer
(
&
timeout_list
))
{
/* the handler has already started; wait for it to finish */
spin_lock
(
&
timeout_data
.
timer_lock
);
/* change the abort into a timeout */
if
(
result
==
-
ENOENT
)
result
=
-
ETIMEDOUT
;
}
/* return a result code based on the result of the control message */
if
(
result
>=
0
)
US_DEBUGP
(
"Soft reset done
\n
"
);
else
if
(
result
<
0
)
{
US_DEBUGP
(
"Soft reset failed: %d
\n
"
,
result
);
if
(
result
==
-
ETIMEDOUT
)
us
->
srb
->
result
=
DID_TIME_OUT
<<
16
;
else
if
(
result
==
-
ENOENT
)
us
->
srb
->
result
=
DID_ABORT
<<
16
;
else
if
(
result
<
0
)
us
->
srb
->
result
=
DID_ERROR
<<
16
;
else
result
=
FAILED
;
}
else
{
US_DEBUGP
(
"Soft reset done
\n
"
);
us
->
srb
->
result
=
GOOD
<<
1
;
result
=
SUCCESS
;
}
return
result
;
}
/* This issues a CB[I] Reset to the device in question
...
...
@@ -1463,10 +1418,9 @@ int usb_stor_CB_reset(struct us_data *us)
memset
(
cmd
,
0xFF
,
sizeof
(
cmd
));
cmd
[
0
]
=
SEND_DIAGNOSTIC
;
cmd
[
1
]
=
4
;
usb_stor_reset_common
(
us
,
US_CBI_ADSC
,
return
usb_stor_reset_common
(
us
,
US_CBI_ADSC
,
USB_TYPE_CLASS
|
USB_RECIP_INTERFACE
,
0
,
us
->
ifnum
,
cmd
,
sizeof
(
cmd
));
return
(
us
->
srb
->
result
==
GOOD
<<
1
?
SUCCESS
:
FAILED
);
}
/* This issues a Bulk-only Reset to the device in question, including
...
...
@@ -1476,8 +1430,7 @@ int usb_stor_Bulk_reset(struct us_data *us)
{
US_DEBUGP
(
"Bulk reset requested
\n
"
);
usb_stor_reset_common
(
us
,
US_BULK_RESET_REQUEST
,
return
usb_stor_reset_common
(
us
,
US_BULK_RESET_REQUEST
,
USB_TYPE_CLASS
|
USB_RECIP_INTERFACE
,
0
,
us
->
ifnum
,
NULL
,
0
);
return
(
us
->
srb
->
result
==
GOOD
<<
1
?
SUCCESS
:
FAILED
);
}
drivers/usb/storage/usb.c
View file @
5bc21855
...
...
@@ -361,65 +361,42 @@ static int usb_stor_control_thread(void * __us)
BUG_ON
(
action
!=
US_ACT_COMMAND
);
/* lock the device pointers */
down
(
&
(
us
->
dev_semaphore
));
/* reject the command if the direction indicator
* is UNKNOWN
*/
if
(
us
->
srb
->
sc_data_direction
==
SCSI_DATA_UNKNOWN
)
{
US_DEBUGP
(
"UNKNOWN data direction
\n
"
);
us
->
srb
->
result
=
DID_ERROR
<<
16
;
scsi_lock
(
host
);
us
->
srb
->
scsi_done
(
us
->
srb
);
us
->
srb
=
NULL
;
scsi_unlock
(
host
);
continue
;
}
/* reject if target != 0 or if LUN is higher than
* the maximum known LUN
*/
if
(
us
->
srb
->
target
&&
else
if
(
us
->
srb
->
target
&&
!
(
us
->
flags
&
US_FL_SCM_MULT_TARG
))
{
US_DEBUGP
(
"Bad target number (%d/%d)
\n
"
,
us
->
srb
->
target
,
us
->
srb
->
lun
);
us
->
srb
->
result
=
DID_BAD_TARGET
<<
16
;
scsi_lock
(
host
);
us
->
srb
->
scsi_done
(
us
->
srb
);
us
->
srb
=
NULL
;
scsi_unlock
(
host
);
continue
;
}
if
(
us
->
srb
->
lun
>
us
->
max_lun
)
{
else
if
(
us
->
srb
->
lun
>
us
->
max_lun
)
{
US_DEBUGP
(
"Bad LUN (%d/%d)
\n
"
,
us
->
srb
->
target
,
us
->
srb
->
lun
);
us
->
srb
->
result
=
DID_BAD_TARGET
<<
16
;
scsi_lock
(
host
);
us
->
srb
->
scsi_done
(
us
->
srb
);
us
->
srb
=
NULL
;
scsi_unlock
(
host
);
continue
;
}
/* handle those devices which can't do a START_STOP */
if
((
us
->
srb
->
cmnd
[
0
]
==
START_STOP
)
&&
else
if
((
us
->
srb
->
cmnd
[
0
]
==
START_STOP
)
&&
(
us
->
flags
&
US_FL_START_STOP
))
{
US_DEBUGP
(
"Skipping START_STOP command
\n
"
);
us
->
srb
->
result
=
GOOD
<<
1
;
scsi_lock
(
host
);
us
->
srb
->
scsi_done
(
us
->
srb
);
us
->
srb
=
NULL
;
scsi_unlock
(
host
);
continue
;
}
/* lock the device pointers */
down
(
&
(
us
->
dev_semaphore
));
/* our device has gone - pretend not ready */
if
(
!
test_bit
(
DEV_ATTACHED
,
&
us
->
bitflags
))
{
else
if
(
!
test_bit
(
DEV_ATTACHED
,
&
us
->
bitflags
))
{
US_DEBUGP
(
"Request is for removed device
\n
"
);
/* For REQUEST_SENSE, it's the data. But
* for anything else, it should look like
...
...
@@ -443,24 +420,25 @@ static int usb_stor_control_thread(void * __us)
sizeof
(
usb_stor_sense_notready
));
us
->
srb
->
result
=
CHECK_CONDITION
<<
1
;
}
}
else
{
/* test_bit(DEV_ATTACHED, &us->bitflags) */
}
/* test_bit(DEV_ATTACHED, &us->bitflags) */
/* Handle those devices which need us to fake
* their inquiry data */
if
((
us
->
srb
->
cmnd
[
0
]
==
INQUIRY
)
&&
/* Handle those devices which need us to fake
* their inquiry data */
else
if
((
us
->
srb
->
cmnd
[
0
]
==
INQUIRY
)
&&
(
us
->
flags
&
US_FL_FIX_INQUIRY
))
{
unsigned
char
data_ptr
[
36
]
=
{
0x00
,
0x80
,
0x02
,
0x02
,
0x1F
,
0x00
,
0x00
,
0x00
};
unsigned
char
data_ptr
[
36
]
=
{
0x00
,
0x80
,
0x02
,
0x02
,
0x1F
,
0x00
,
0x00
,
0x00
};
US_DEBUGP
(
"Faking INQUIRY command
\n
"
);
fill_inquiry_response
(
us
,
data_ptr
,
36
);
us
->
srb
->
result
=
GOOD
<<
1
;
}
else
{
/* we've got a command, let's do it! */
US_DEBUG
(
usb_stor_show_command
(
us
->
srb
));
us
->
proto_handler
(
us
->
srb
,
us
);
}
US_DEBUGP
(
"Faking INQUIRY command
\n
"
);
fill_inquiry_response
(
us
,
data_ptr
,
36
);
us
->
srb
->
result
=
GOOD
<<
1
;
}
/* we've got a command, let's do it! */
else
{
US_DEBUG
(
usb_stor_show_command
(
us
->
srb
));
us
->
proto_handler
(
us
->
srb
,
us
);
}
/* unlock the device pointers */
...
...
@@ -487,54 +465,114 @@ static int usb_stor_control_thread(void * __us)
return
0
;
}
/* Set up the IRQ pipe and handler
/* Set up the URB, the usb_ctrlrequest, and the IRQ pipe and handler.
* ss->dev_semaphore should already be locked.
* Note that this function assumes that all the data in the us_data
* strucuture is current. This includes the ep_int field, which gives us
* the endpoint for the interrupt.
* Returns non-zero on failure, zero on success
*/
static
int
usb_stor_allocate_
irq
(
struct
us_data
*
ss
)
static
int
usb_stor_allocate_
urbs
(
struct
us_data
*
ss
)
{
unsigned
int
pipe
;
int
maxp
;
int
result
;
US_DEBUGP
(
"Allocating IRQ for CBI transport
\n
"
);
/* lock access to the data structure */
down
(
&
(
ss
->
irq_urb_sem
));
/* allocate the URB */
ss
->
irq_urb
=
usb_alloc_urb
(
0
,
GFP_KERNEL
);
if
(
!
ss
->
irq_urb
)
{
up
(
&
(
ss
->
irq_urb_sem
));
US_DEBUGP
(
"couldn't allocate interrupt URB"
);
/* allocate the URB we're going to use */
US_DEBUGP
(
"Allocating URB
\n
"
);
ss
->
current_urb
=
usb_alloc_urb
(
0
,
GFP_KERNEL
);
if
(
!
ss
->
current_urb
)
{
US_DEBUGP
(
"allocation failed
\n
"
);
return
1
;
}
/* calculate the pipe and max packet size */
pipe
=
usb_rcvintpipe
(
ss
->
pusb_dev
,
ss
->
ep_int
->
bEndpointAddress
&
USB_ENDPOINT_NUMBER_MASK
);
maxp
=
usb_maxpacket
(
ss
->
pusb_dev
,
pipe
,
usb_pipeout
(
pipe
));
if
(
maxp
>
sizeof
(
ss
->
irqbuf
))
maxp
=
sizeof
(
ss
->
irqbuf
);
/* fill in the URB with our data */
FILL_INT_URB
(
ss
->
irq_urb
,
ss
->
pusb_dev
,
pipe
,
ss
->
irqbuf
,
maxp
,
usb_stor_CBI_irq
,
ss
,
ss
->
ep_int
->
bInterval
);
/* submit the URB for processing */
result
=
usb_submit_urb
(
ss
->
irq_urb
,
GFP_KERNEL
);
US_DEBUGP
(
"usb_submit_urb() returns %d
\n
"
,
result
);
if
(
result
)
{
usb_free_urb
(
ss
->
irq_urb
);
up
(
&
(
ss
->
irq_urb_sem
));
/* allocate the usb_ctrlrequest for control packets */
US_DEBUGP
(
"Allocating usb_ctrlrequest
\n
"
);
ss
->
dr
=
kmalloc
(
sizeof
(
struct
usb_ctrlrequest
),
GFP_NOIO
);
if
(
!
ss
->
dr
)
{
US_DEBUGP
(
"allocation failed
\n
"
);
return
2
;
}
/* unlock the data structure and return success */
/* allocate the IRQ URB, if it is needed */
if
(
ss
->
protocol
==
US_PR_CBI
)
{
US_DEBUGP
(
"Allocating IRQ for CBI transport
\n
"
);
/* lock access to the data structure */
down
(
&
(
ss
->
irq_urb_sem
));
/* allocate the URB */
ss
->
irq_urb
=
usb_alloc_urb
(
0
,
GFP_KERNEL
);
if
(
!
ss
->
irq_urb
)
{
up
(
&
(
ss
->
irq_urb_sem
));
US_DEBUGP
(
"couldn't allocate interrupt URB"
);
return
3
;
}
/* calculate the pipe and max packet size */
pipe
=
usb_rcvintpipe
(
ss
->
pusb_dev
,
ss
->
ep_int
->
bEndpointAddress
&
USB_ENDPOINT_NUMBER_MASK
);
maxp
=
usb_maxpacket
(
ss
->
pusb_dev
,
pipe
,
usb_pipeout
(
pipe
));
if
(
maxp
>
sizeof
(
ss
->
irqbuf
))
maxp
=
sizeof
(
ss
->
irqbuf
);
/* fill in the URB with our data */
FILL_INT_URB
(
ss
->
irq_urb
,
ss
->
pusb_dev
,
pipe
,
ss
->
irqbuf
,
maxp
,
usb_stor_CBI_irq
,
ss
,
ss
->
ep_int
->
bInterval
);
/* submit the URB for processing */
result
=
usb_submit_urb
(
ss
->
irq_urb
,
GFP_KERNEL
);
US_DEBUGP
(
"usb_submit_urb() returns %d
\n
"
,
result
);
if
(
result
)
{
up
(
&
(
ss
->
irq_urb_sem
));
return
4
;
}
/* unlock the data structure */
up
(
&
(
ss
->
irq_urb_sem
));
}
/* ss->protocol == US_PR_CBI */
return
0
;
/* success */
}
/* Deallocate the URB, the usb_ctrlrequest, and the IRQ pipe.
* ss->dev_semaphore must already be locked.
*/
static
void
usb_stor_deallocate_urbs
(
struct
us_data
*
ss
)
{
int
result
;
/* release the IRQ, if we have one */
down
(
&
(
ss
->
irq_urb_sem
));
if
(
ss
->
irq_urb
)
{
US_DEBUGP
(
"-- releasing irq URB
\n
"
);
result
=
usb_unlink_urb
(
ss
->
irq_urb
);
US_DEBUGP
(
"-- usb_unlink_urb() returned %d
\n
"
,
result
);
usb_free_urb
(
ss
->
irq_urb
);
ss
->
irq_urb
=
NULL
;
}
up
(
&
(
ss
->
irq_urb_sem
));
return
0
;
/* free the usb_ctrlrequest buffer */
if
(
ss
->
dr
)
{
kfree
(
ss
->
dr
);
ss
->
dr
=
NULL
;
}
/* free up the main URB for this device */
if
(
ss
->
current_urb
)
{
US_DEBUGP
(
"-- releasing main URB
\n
"
);
result
=
usb_unlink_urb
(
ss
->
current_urb
);
US_DEBUGP
(
"-- usb_unlink_urb() returned %d
\n
"
,
result
);
usb_free_urb
(
ss
->
current_urb
);
ss
->
current_urb
=
NULL
;
}
/* mark the device as gone */
clear_bit
(
DEV_ATTACHED
,
&
ss
->
bitflags
);
usb_put_dev
(
ss
->
pusb_dev
);
ss
->
pusb_dev
=
NULL
;
}
/* Probe to see if a new device is actually a SCSI device */
...
...
@@ -712,13 +750,8 @@ static void * storage_probe(struct usb_device *dev, unsigned int ifnum,
USB_ENDPOINT_NUMBER_MASK
;
ss
->
ep_int
=
ep_int
;
/* allocate an IRQ callback if one is needed */
if
((
ss
->
protocol
==
US_PR_CBI
)
&&
usb_stor_allocate_irq
(
ss
))
goto
BadDevice
;
/* allocate the URB we're going to use */
ss
->
current_urb
=
usb_alloc_urb
(
0
,
GFP_KERNEL
);
if
(
!
ss
->
current_urb
)
/* allocate the URB, the usb_ctrlrequest, and the IRQ URB */
if
(
usb_stor_allocate_urbs
(
ss
))
goto
BadDevice
;
/* Re-Initialize the device if it needs it */
...
...
@@ -741,11 +774,6 @@ static void * storage_probe(struct usb_device *dev, unsigned int ifnum,
memset
(
ss
,
0
,
sizeof
(
struct
us_data
));
new_device
=
1
;
/* allocate the URB we're going to use */
ss
->
current_urb
=
usb_alloc_urb
(
0
,
GFP_KERNEL
);
if
(
!
ss
->
current_urb
)
goto
BadDevice
;
/* Initialize the mutexes only when the struct is new */
init_completion
(
&
(
ss
->
notify
));
init_MUTEX_LOCKED
(
&
(
ss
->
ip_waitq
));
...
...
@@ -943,8 +971,8 @@ static void * storage_probe(struct usb_device *dev, unsigned int ifnum,
}
US_DEBUGP
(
"Protocol: %s
\n
"
,
ss
->
protocol_name
);
/* allocate
an IRQ callback if one is needed
*/
if
(
(
ss
->
protocol
==
US_PR_CBI
)
&&
usb_stor_allocate_irq
(
ss
))
/* allocate
the URB, the usb_ctrlrequest, and the IRQ URB
*/
if
(
usb_stor_allocate_urbs
(
ss
))
goto
BadDevice
;
/*
...
...
@@ -1020,26 +1048,11 @@ static void * storage_probe(struct usb_device *dev, unsigned int ifnum,
/* we come here if there are any problems */
BadDevice:
US_DEBUGP
(
"storage_probe() failed
\n
"
);
down
(
&
ss
->
irq_urb_sem
);
if
(
ss
->
irq_urb
)
{
usb_unlink_urb
(
ss
->
irq_urb
);
usb_free_urb
(
ss
->
irq_urb
);
ss
->
irq_urb
=
NULL
;
}
up
(
&
ss
->
irq_urb_sem
);
if
(
ss
->
current_urb
)
{
usb_unlink_urb
(
ss
->
current_urb
);
usb_free_urb
(
ss
->
current_urb
);
ss
->
current_urb
=
NULL
;
}
clear_bit
(
DEV_ATTACHED
,
&
ss
->
bitflags
);
ss
->
pusb_dev
=
NULL
;
usb_stor_deallocate_urbs
(
ss
);
if
(
new_device
)
kfree
(
ss
);
else
up
(
&
ss
->
dev_semaphore
);
usb_put_dev
(
dev
);
return
NULL
;
}
...
...
@@ -1047,7 +1060,6 @@ static void * storage_probe(struct usb_device *dev, unsigned int ifnum,
static
void
storage_disconnect
(
struct
usb_device
*
dev
,
void
*
ptr
)
{
struct
us_data
*
ss
=
ptr
;
int
result
;
US_DEBUGP
(
"storage_disconnect() called
\n
"
);
...
...
@@ -1057,33 +1069,8 @@ static void storage_disconnect(struct usb_device *dev, void *ptr)
return
;
}
/* lock access to the device data structure */
down
(
&
(
ss
->
dev_semaphore
));
/* release the IRQ, if we have one */
down
(
&
(
ss
->
irq_urb_sem
));
if
(
ss
->
irq_urb
)
{
US_DEBUGP
(
"-- releasing irq URB
\n
"
);
result
=
usb_unlink_urb
(
ss
->
irq_urb
);
US_DEBUGP
(
"-- usb_unlink_urb() returned %d
\n
"
,
result
);
usb_free_urb
(
ss
->
irq_urb
);
ss
->
irq_urb
=
NULL
;
}
up
(
&
(
ss
->
irq_urb_sem
));
/* free up the main URB for this device */
US_DEBUGP
(
"-- releasing main URB
\n
"
);
result
=
usb_unlink_urb
(
ss
->
current_urb
);
US_DEBUGP
(
"-- usb_unlink_urb() returned %d
\n
"
,
result
);
usb_free_urb
(
ss
->
current_urb
);
ss
->
current_urb
=
NULL
;
/* mark the device as gone */
usb_put_dev
(
ss
->
pusb_dev
);
ss
->
pusb_dev
=
NULL
;
clear_bit
(
DEV_ATTACHED
,
&
ss
->
bitflags
);
/* unlock access to the device data structure */
usb_stor_deallocate_urbs
(
ss
);
up
(
&
(
ss
->
dev_semaphore
));
}
...
...
drivers/usb/storage/usb.h
View file @
5bc21855
...
...
@@ -185,6 +185,7 @@ struct us_data {
/* control and bulk communications data */
struct
semaphore
current_urb_sem
;
/* to protect irq_urb */
struct
urb
*
current_urb
;
/* non-int USB requests */
struct
usb_ctrlrequest
*
dr
;
/* control requests */
/* the semaphore for sleeping the control thread */
struct
semaphore
sema
;
/* to sleep thread on */
...
...
drivers/usb/usb-skeleton.c
View file @
5bc21855
...
...
@@ -189,9 +189,6 @@ static struct usb_driver skel_driver = {
name:
"skeleton"
,
probe:
skel_probe
,
disconnect:
skel_disconnect
,
fops:
&
skel_fops
,
minor:
USB_SKEL_MINOR_BASE
,
num_minors:
MAX_DEVICES
,
id_table:
skel_table
,
};
...
...
@@ -532,29 +529,18 @@ static void * skel_probe(struct usb_device *udev, unsigned int ifnum, const stru
}
down
(
&
minor_table_mutex
);
retval
=
usb_register_dev
(
&
skel_
driver
,
1
,
&
minor
);
retval
=
usb_register_dev
(
&
skel_
fops
,
USB_SKEL_MINOR_BASE
,
1
,
&
minor
);
if
(
retval
)
{
if
(
retval
!=
-
ENODEV
)
{
/* something prevented us from registering this driver */
err
(
"Not able to get a minor for this device."
);
goto
exit
;
}
/* we could not get a dynamic minor, so lets find one of our own */
for
(
minor
=
0
;
minor
<
MAX_DEVICES
;
++
minor
)
{
if
(
minor_table
[
minor
]
==
NULL
)
break
;
}
if
(
minor
>=
MAX_DEVICES
)
{
err
(
"Too many devices plugged in, can not handle this device."
);
goto
exit
;
}
/* something prevented us from registering this driver */
err
(
"Not able to get a minor for this device."
);
goto
exit
;
}
/* allocate memory for our device state and intialize it */
dev
=
kmalloc
(
sizeof
(
struct
usb_skel
),
GFP_KERNEL
);
if
(
dev
==
NULL
)
{
err
(
"Out of memory"
);
goto
exit
;
goto
exit
_minor
;
}
memset
(
dev
,
0x00
,
sizeof
(
*
dev
));
minor_table
[
minor
]
=
dev
;
...
...
@@ -628,6 +614,9 @@ static void * skel_probe(struct usb_device *udev, unsigned int ifnum, const stru
skel_delete
(
dev
);
dev
=
NULL
;
exit_minor:
usb_deregister_dev
(
1
,
minor
);
exit:
up
(
&
minor_table_mutex
);
return
dev
;
...
...
@@ -655,7 +644,7 @@ static void skel_disconnect(struct usb_device *udev, void *ptr)
devfs_unregister
(
dev
->
devfs
);
/* give back our dynamic minor */
usb_deregister_dev
(
&
skel_driver
,
1
,
minor
);
usb_deregister_dev
(
1
,
minor
);
/* if the device is not opened, then we clean up right now */
if
(
!
dev
->
open_count
)
{
...
...
fs/binfmt_elf.c
View file @
5bc21855
...
...
@@ -954,7 +954,7 @@ static int notesize(struct memelfnote *en)
int
sz
;
sz
=
sizeof
(
struct
elf_note
);
sz
+=
roundup
(
strlen
(
en
->
name
),
4
);
sz
+=
roundup
(
strlen
(
en
->
name
)
+
1
,
4
);
sz
+=
roundup
(
en
->
datasz
,
4
);
return
sz
;
...
...
@@ -989,7 +989,7 @@ static int writenote(struct memelfnote *men, struct file *file)
{
struct
elf_note
en
;
en
.
n_namesz
=
strlen
(
men
->
name
);
en
.
n_namesz
=
strlen
(
men
->
name
)
+
1
;
en
.
n_descsz
=
men
->
datasz
;
en
.
n_type
=
men
->
type
;
...
...
fs/reiserfs/buffer2.c
View file @
5bc21855
...
...
@@ -25,6 +25,13 @@ void wait_buffer_until_released (const struct buffer_head * bh)
{
int
repeat_counter
=
0
;
/*
* FIXME! Temporary cludge until ReiserFS people tell what they
* actually are trying to protect against!
*/
if
(
1
)
return
;
while
(
atomic_read
(
&
(
bh
->
b_count
))
>
1
)
{
if
(
!
(
++
repeat_counter
%
30000000
)
)
{
...
...
include/linux/usb.h
View file @
5bc21855
...
...
@@ -104,6 +104,7 @@
#include <linux/interrupt.h>
/* for in_interrupt() */
#include <linux/list.h>
/* for struct list_head */
#include <linux/device.h>
/* for struct device */
#include <linux/fs.h>
/* for struct file_operations */
static
__inline__
void
wait_ms
(
unsigned
int
ms
)
...
...
@@ -648,14 +649,6 @@ struct usb_device_id {
* because its device has been (or is being) disconnected. The
* handle passed is what was returned by probe(), or was provided
* to usb_driver_claim_interface().
* @fops: USB drivers can reuse some character device framework in
* the USB subsystem by providing a file operations vector and
* a minor number.
* @minor: Used with fops to simplify creating USB character devices.
* Such drivers have sixteen character devices, using the USB
* major number and starting with this minor number.
* @num_minors: Used with minor to specify how many minors are used by
* this driver.
* @ioctl: Used for drivers that want to talk to userspace through
* the "usbfs" filesystem. This lets devices provide ways to
* expose information to user space regardless of where they
...
...
@@ -694,11 +687,6 @@ struct usb_driver {
);
struct
list_head
driver_list
;
struct
file_operations
*
fops
;
int
minor
;
int
num_minors
;
struct
semaphore
serialize
;
/* ioctl -- userspace apps can talk to drivers through usbfs */
...
...
@@ -722,13 +710,8 @@ extern struct bus_type usb_bus_type;
extern
int
usb_register
(
struct
usb_driver
*
);
extern
void
usb_deregister
(
struct
usb_driver
*
);
#ifndef CONFIG_USB_DYNAMIC_MINORS
static
inline
int
usb_register_dev
(
struct
usb_driver
*
new_driver
,
int
num_minors
,
int
*
start_minor
)
{
return
-
ENODEV
;
}
static
inline
void
usb_deregister_dev
(
struct
usb_driver
*
driver
,
int
num_minors
,
int
start_minor
)
{}
#else
extern
int
usb_register_dev
(
struct
usb_driver
*
new_driver
,
int
num_minors
,
int
*
start_minor
);
extern
void
usb_deregister_dev
(
struct
usb_driver
*
driver
,
int
num_minors
,
int
start_minor
);
#endif
extern
int
usb_register_dev
(
struct
file_operations
*
fops
,
int
minor
,
int
num_minors
,
int
*
start_minor
);
extern
void
usb_deregister_dev
(
int
num_minors
,
int
start_minor
);
/* -------------------------------------------------------------------------- */
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment