diff --git a/drivers/usb/core/buffer.c b/drivers/usb/core/buffer.c index f4f4ef0f377a..840442a25b61 100644 --- a/drivers/usb/core/buffer.c +++ b/drivers/usb/core/buffer.c @@ -104,7 +104,7 @@ void *hcd_buffer_alloc ( dma_addr_t *dma ) { - struct usb_hcd *hcd = bus->hcpriv; + struct usb_hcd *hcd = bus_to_hcd(bus); int i; /* some USB hosts just use PIO */ @@ -127,7 +127,7 @@ void hcd_buffer_free ( dma_addr_t dma ) { - struct usb_hcd *hcd = bus->hcpriv; + struct usb_hcd *hcd = bus_to_hcd(bus); int i; if (!addr) diff --git a/drivers/usb/core/hcd.c b/drivers/usb/core/hcd.c index 0cc14206920a..9dfc812de034 100644 --- a/drivers/usb/core/hcd.c +++ b/drivers/usb/core/hcd.c @@ -664,31 +664,6 @@ static int usb_rh_urb_dequeue (struct usb_hcd *hcd, struct urb *urb) /*-------------------------------------------------------------------------*/ -/* exported only within usbcore */ -struct usb_bus *usb_bus_get(struct usb_bus *bus) -{ - if (bus) - kref_get(&bus->kref); - return bus; -} - -static void usb_host_release(struct kref *kref) -{ - struct usb_bus *bus = container_of(kref, struct usb_bus, kref); - - if (bus->release) - bus->release(bus); -} - -/* exported only within usbcore */ -void usb_bus_put(struct usb_bus *bus) -{ - if (bus) - kref_put(&bus->kref, usb_host_release); -} - -/*-------------------------------------------------------------------------*/ - static struct class *usb_host_class; int usb_host_init(void) @@ -720,15 +695,12 @@ static void usb_bus_init (struct usb_bus *bus) bus->devnum_next = 1; bus->root_hub = NULL; - bus->hcpriv = NULL; bus->busnum = -1; bus->bandwidth_allocated = 0; bus->bandwidth_int_reqs = 0; bus->bandwidth_isoc_reqs = 0; INIT_LIST_HEAD (&bus->bus_list); - - kref_init(&bus->kref); } /*-------------------------------------------------------------------------*/ @@ -1081,7 +1053,7 @@ static void urb_unlink (struct urb *urb) int usb_hcd_submit_urb (struct urb *urb, gfp_t mem_flags) { int status; - struct usb_hcd *hcd = urb->dev->bus->hcpriv; + struct usb_hcd *hcd = bus_to_hcd(urb->dev->bus); struct usb_host_endpoint *ep; unsigned long flags; @@ -1189,7 +1161,8 @@ int usb_hcd_submit_urb (struct urb *urb, gfp_t mem_flags) /* called in any context */ int usb_hcd_get_frame_number (struct usb_device *udev) { - struct usb_hcd *hcd = (struct usb_hcd *)udev->bus->hcpriv; + struct usb_hcd *hcd = bus_to_hcd(udev->bus); + if (!HC_IS_RUNNING (hcd->state)) return -ESHUTDOWN; return hcd->driver->get_frame_number (hcd); @@ -1262,7 +1235,7 @@ int usb_hcd_unlink_urb (struct urb *urb, int status) spin_lock (&hcd_data_lock); sys = &urb->dev->dev; - hcd = urb->dev->bus->hcpriv; + hcd = bus_to_hcd(urb->dev->bus); if (hcd == NULL) { retval = -ENODEV; goto done; @@ -1333,7 +1306,7 @@ void usb_hcd_endpoint_disable (struct usb_device *udev, struct usb_hcd *hcd; struct urb *urb; - hcd = udev->bus->hcpriv; + hcd = bus_to_hcd(udev->bus); WARN_ON (!HC_IS_RUNNING (hcd->state) && hcd->state != HC_STATE_HALT && udev->state != USB_STATE_NOTATTACHED); @@ -1673,14 +1646,6 @@ EXPORT_SYMBOL_GPL (usb_hc_died); /*-------------------------------------------------------------------------*/ -static void hcd_release (struct usb_bus *bus) -{ - struct usb_hcd *hcd; - - hcd = container_of(bus, struct usb_hcd, self); - kfree(hcd); -} - /** * usb_create_hcd - create and initialize an HCD structure * @driver: HC driver that will use this hcd @@ -1705,10 +1670,9 @@ struct usb_hcd *usb_create_hcd (const struct hc_driver *driver, return NULL; } dev_set_drvdata(dev, hcd); + kref_init(&hcd->kref); usb_bus_init(&hcd->self); - hcd->self.hcpriv = hcd; - hcd->self.release = &hcd_release; hcd->self.controller = dev; hcd->self.bus_name = bus_name; hcd->self.uses_dma = (dev->dma_mask != NULL); @@ -1725,10 +1689,25 @@ struct usb_hcd *usb_create_hcd (const struct hc_driver *driver, } EXPORT_SYMBOL (usb_create_hcd); +static void hcd_release (struct kref *kref) +{ + struct usb_hcd *hcd = container_of (kref, struct usb_hcd, kref); + + kfree(hcd); +} + +struct usb_hcd *usb_get_hcd (struct usb_hcd *hcd) +{ + if (hcd) + kref_get (&hcd->kref); + return hcd; +} +EXPORT_SYMBOL (usb_get_hcd); + void usb_put_hcd (struct usb_hcd *hcd) { - dev_set_drvdata(hcd->self.controller, NULL); - usb_bus_put(&hcd->self); + if (hcd) + kref_put (&hcd->kref, hcd_release); } EXPORT_SYMBOL (usb_put_hcd); diff --git a/drivers/usb/core/hcd.h b/drivers/usb/core/hcd.h index 83e229914797..7a2bcba2ae61 100644 --- a/drivers/usb/core/hcd.h +++ b/drivers/usb/core/hcd.h @@ -55,12 +55,13 @@ /*-------------------------------------------------------------------------*/ -struct usb_hcd { /* usb_bus.hcpriv points to this */ +struct usb_hcd { /* * housekeeping */ struct usb_bus self; /* hcd is-a bus */ + struct kref kref; /* reference counter */ const char *product_desc; /* product/vendor string */ char irq_descr[24]; /* driver + bus # */ @@ -129,8 +130,10 @@ static inline struct usb_bus *hcd_to_bus (struct usb_hcd *hcd) return &hcd->self; } - -// urb.hcpriv is really hardware-specific +static inline struct usb_hcd *bus_to_hcd (struct usb_bus *bus) +{ + return container_of(bus, struct usb_hcd, self); +} struct hcd_timeout { /* timeouts we allocate */ struct list_head timeout_list; @@ -210,6 +213,7 @@ extern int usb_hcd_get_frame_number (struct usb_device *udev); extern struct usb_hcd *usb_create_hcd (const struct hc_driver *driver, struct device *dev, char *bus_name); +extern struct usb_hcd *usb_get_hcd (struct usb_hcd *hcd); extern void usb_put_hcd (struct usb_hcd *hcd); extern int usb_add_hcd(struct usb_hcd *hcd, unsigned int irqnum, unsigned long irqflags); @@ -356,9 +360,6 @@ extern struct list_head usb_bus_list; extern struct mutex usb_bus_list_lock; extern wait_queue_head_t usb_kill_urb_queue; -extern struct usb_bus *usb_bus_get (struct usb_bus *bus); -extern void usb_bus_put (struct usb_bus *bus); - extern void usb_enable_root_hub_irq (struct usb_bus *bus); extern int usb_find_interface_driver (struct usb_device *dev, diff --git a/drivers/usb/core/usb.c b/drivers/usb/core/usb.c index 7ab9d29215f8..b0c0a993338f 100644 --- a/drivers/usb/core/usb.c +++ b/drivers/usb/core/usb.c @@ -169,7 +169,7 @@ static void usb_release_dev(struct device *dev) udev = to_usb_device(dev); usb_destroy_configuration(udev); - usb_bus_put(udev->bus); + usb_put_hcd(bus_to_hcd(udev->bus)); kfree(udev->product); kfree(udev->manufacturer); kfree(udev->serial); @@ -197,8 +197,7 @@ usb_alloc_dev(struct usb_device *parent, struct usb_bus *bus, unsigned port1) if (!dev) return NULL; - bus = usb_bus_get(bus); - if (!bus) { + if (!usb_get_hcd(bus_to_hcd(bus))) { kfree(dev); return NULL; } diff --git a/drivers/usb/gadget/dummy_hcd.c b/drivers/usb/gadget/dummy_hcd.c index 7d1c22c34957..fdab97a27c08 100644 --- a/drivers/usb/gadget/dummy_hcd.c +++ b/drivers/usb/gadget/dummy_hcd.c @@ -889,11 +889,9 @@ EXPORT_SYMBOL (net2280_set_fifo_mode); static void dummy_gadget_release (struct device *dev) { -#if 0 /* usb_bus_put isn't EXPORTed! */ struct dummy *dum = gadget_dev_to_dummy (dev); - usb_bus_put (&dummy_to_hcd (dum)->self); -#endif + usb_put_hcd (dummy_to_hcd (dum)); } static int dummy_udc_probe (struct platform_device *pdev) @@ -915,9 +913,7 @@ static int dummy_udc_probe (struct platform_device *pdev) if (rc < 0) return rc; -#if 0 /* usb_bus_get isn't EXPORTed! */ - usb_bus_get (&dummy_to_hcd (dum)->self); -#endif + usb_get_hcd (dummy_to_hcd (dum)); platform_set_drvdata (pdev, dum); device_create_file (&dum->gadget.dev, &dev_attr_function); diff --git a/drivers/usb/host/ehci-dbg.c b/drivers/usb/host/ehci-dbg.c index 65ac9fef3a7c..215ce6d06394 100644 --- a/drivers/usb/host/ehci-dbg.c +++ b/drivers/usb/host/ehci-dbg.c @@ -451,7 +451,7 @@ show_async (struct class_device *class_dev, char *buf) *buf = 0; bus = class_get_devdata(class_dev); - hcd = bus->hcpriv; + hcd = bus_to_hcd(bus); ehci = hcd_to_ehci (hcd); next = buf; size = PAGE_SIZE; @@ -497,7 +497,7 @@ show_periodic (struct class_device *class_dev, char *buf) seen_count = 0; bus = class_get_devdata(class_dev); - hcd = bus->hcpriv; + hcd = bus_to_hcd(bus); ehci = hcd_to_ehci (hcd); next = buf; size = PAGE_SIZE; @@ -634,7 +634,7 @@ show_registers (struct class_device *class_dev, char *buf) static char label [] = ""; bus = class_get_devdata(class_dev); - hcd = bus->hcpriv; + hcd = bus_to_hcd(bus); ehci = hcd_to_ehci (hcd); next = buf; size = PAGE_SIZE; diff --git a/drivers/usb/host/ohci-dbg.c b/drivers/usb/host/ohci-dbg.c index da52609a9290..534d07dcb824 100644 --- a/drivers/usb/host/ohci-dbg.c +++ b/drivers/usb/host/ohci-dbg.c @@ -477,7 +477,7 @@ show_async (struct class_device *class_dev, char *buf) unsigned long flags; bus = class_get_devdata(class_dev); - hcd = bus->hcpriv; + hcd = bus_to_hcd(bus); ohci = hcd_to_ohci(hcd); /* display control and bulk lists together, for simplicity */ @@ -510,7 +510,7 @@ show_periodic (struct class_device *class_dev, char *buf) seen_count = 0; bus = class_get_devdata(class_dev); - hcd = bus->hcpriv; + hcd = bus_to_hcd(bus); ohci = hcd_to_ohci(hcd); next = buf; size = PAGE_SIZE; @@ -607,7 +607,7 @@ show_registers (struct class_device *class_dev, char *buf) u32 rdata; bus = class_get_devdata(class_dev); - hcd = bus->hcpriv; + hcd = bus_to_hcd(bus); ohci = hcd_to_ohci(hcd); regs = ohci->regs; next = buf; diff --git a/drivers/usb/mon/mon_main.c b/drivers/usb/mon/mon_main.c index 275a66f83058..e0ed36cdfd8b 100644 --- a/drivers/usb/mon/mon_main.c +++ b/drivers/usb/mon/mon_main.c @@ -265,7 +265,6 @@ static void mon_dissolve(struct mon_bus *mbus, struct usb_bus *ubus) ubus->mon_bus = NULL; mbus->u_bus = NULL; mb(); - // usb_bus_put(ubus); } /* @@ -297,10 +296,9 @@ static void mon_bus_init(struct dentry *mondir, struct usb_bus *ubus) INIT_LIST_HEAD(&mbus->r_list); /* - * This usb_bus_get here is superfluous, because we receive - * a notification if usb_bus is about to be removed. + * We don't need to take a reference to ubus, because we receive + * a notification if the bus is about to be removed. */ - // usb_bus_get(ubus); mbus->u_bus = ubus; ubus->mon_bus = mbus; diff --git a/include/linux/usb.h b/include/linux/usb.h index 09661759621f..c66303285a45 100644 --- a/include/linux/usb.h +++ b/include/linux/usb.h @@ -280,7 +280,6 @@ struct usb_bus { struct usb_devmap devmap; /* device address allocation map */ struct usb_device *root_hub; /* Root hub */ struct list_head bus_list; /* list of busses */ - void *hcpriv; /* Host Controller private data */ int bandwidth_allocated; /* on this bus: how much of the time * reserved for periodic (intr/iso) @@ -295,8 +294,6 @@ struct usb_bus { struct dentry *usbfs_dentry; /* usbfs dentry entry for the bus */ struct class_device *class_dev; /* class device for this bus */ - struct kref kref; /* reference counting for this bus */ - void (*release)(struct usb_bus *bus); #if defined(CONFIG_USB_MON) struct mon_bus *mon_bus; /* non-null when associated */