Loading drivers/staging/ozwpan/ozhcd.c +12 −58 Original line number Original line Diff line number Diff line Loading @@ -45,10 +45,6 @@ */ */ #define OZ_PLAT_DEV_NAME "ozwpan" #define OZ_PLAT_DEV_NAME "ozwpan" /* Maximum number of free urb links that can be kept in the pool. */ #define OZ_MAX_LINK_POOL_SIZE 16 /* Get endpoint object from the containing link. /* Get endpoint object from the containing link. */ */ #define ep_from_link(__e) container_of((__e), struct oz_endpoint, link) #define ep_from_link(__e) container_of((__e), struct oz_endpoint, link) Loading @@ -75,6 +71,8 @@ struct oz_urb_link { unsigned submit_counter; unsigned submit_counter; }; }; static struct kmem_cache *oz_urb_link_cache; /* Holds state information about a USB endpoint. /* Holds state information about a USB endpoint. */ */ #define OZ_EP_BUFFER_SIZE_ISOC (1024 * 24) #define OZ_EP_BUFFER_SIZE_ISOC (1024 * 24) Loading Loading @@ -198,9 +196,6 @@ static struct platform_device *g_plat_dev; static struct oz_hcd *g_ozhcd; static struct oz_hcd *g_ozhcd; static DEFINE_SPINLOCK(g_hcdlock); /* Guards g_ozhcd. */ static DEFINE_SPINLOCK(g_hcdlock); /* Guards g_ozhcd. */ static const char g_hcd_name[] = "Ozmo WPAN"; static const char g_hcd_name[] = "Ozmo WPAN"; static struct list_head *g_link_pool; static int g_link_pool_size; static DEFINE_SPINLOCK(g_link_lock); static DEFINE_SPINLOCK(g_tasklet_lock); static DEFINE_SPINLOCK(g_tasklet_lock); static struct tasklet_struct g_urb_process_tasklet; static struct tasklet_struct g_urb_process_tasklet; static struct tasklet_struct g_urb_cancel_tasklet; static struct tasklet_struct g_urb_cancel_tasklet; Loading Loading @@ -265,68 +260,22 @@ static int oz_get_port_from_addr(struct oz_hcd *ozhcd, u8 bus_addr) } } /* /* * Allocates an urb link, first trying the pool but going to heap if empty. * Context: any * Context: any */ */ static struct oz_urb_link *oz_alloc_urb_link(void) static struct oz_urb_link *oz_alloc_urb_link(void) { { struct oz_urb_link *urbl = NULL; return kmem_cache_alloc(oz_urb_link_cache, GFP_ATOMIC); unsigned long irq_state; spin_lock_irqsave(&g_link_lock, irq_state); if (g_link_pool) { urbl = container_of(g_link_pool, struct oz_urb_link, link); g_link_pool = urbl->link.next; --g_link_pool_size; } spin_unlock_irqrestore(&g_link_lock, irq_state); if (urbl == NULL) urbl = kmalloc(sizeof(struct oz_urb_link), GFP_ATOMIC); return urbl; } } /* /* * Frees an urb link by putting it in the pool if there is enough space or * deallocating it to heap otherwise. * Context: any * Context: any */ */ static void oz_free_urb_link(struct oz_urb_link *urbl) static void oz_free_urb_link(struct oz_urb_link *urbl) { { if (urbl) { if (!urbl) unsigned long irq_state; return; spin_lock_irqsave(&g_link_lock, irq_state); if (g_link_pool_size < OZ_MAX_LINK_POOL_SIZE) { urbl->link.next = g_link_pool; g_link_pool = &urbl->link; urbl = NULL; g_link_pool_size++; } spin_unlock_irqrestore(&g_link_lock, irq_state); kfree(urbl); } } /* * Deallocates all the urb links in the pool. * Context: unknown */ static void oz_empty_link_pool(void) { struct list_head *e; unsigned long irq_state; spin_lock_irqsave(&g_link_lock, irq_state); kmem_cache_free(oz_urb_link_cache, urbl); e = g_link_pool; g_link_pool = NULL; g_link_pool_size = 0; spin_unlock_irqrestore(&g_link_lock, irq_state); while (e) { struct oz_urb_link *urbl = container_of(e, struct oz_urb_link, link); e = e->next; kfree(urbl); } } } /* /* Loading Loading @@ -2311,7 +2260,6 @@ static int oz_plat_remove(struct platform_device *dev) oz_dbg(ON, "Removing hcd\n"); oz_dbg(ON, "Removing hcd\n"); usb_remove_hcd(hcd); usb_remove_hcd(hcd); usb_put_hcd(hcd); usb_put_hcd(hcd); oz_empty_link_pool(); return 0; return 0; } } Loading Loading @@ -2341,6 +2289,11 @@ int oz_hcd_init(void) if (usb_disabled()) if (usb_disabled()) return -ENODEV; return -ENODEV; oz_urb_link_cache = KMEM_CACHE(oz_urb_link, 0); if (!oz_urb_link_cache) return -ENOMEM; tasklet_init(&g_urb_process_tasklet, oz_urb_process_tasklet, 0); tasklet_init(&g_urb_process_tasklet, oz_urb_process_tasklet, 0); tasklet_init(&g_urb_cancel_tasklet, oz_urb_cancel_tasklet, 0); tasklet_init(&g_urb_cancel_tasklet, oz_urb_cancel_tasklet, 0); err = platform_driver_register(&g_oz_plat_drv); err = platform_driver_register(&g_oz_plat_drv); Loading Loading @@ -2380,4 +2333,5 @@ void oz_hcd_term(void) platform_device_unregister(g_plat_dev); platform_device_unregister(g_plat_dev); platform_driver_unregister(&g_oz_plat_drv); platform_driver_unregister(&g_oz_plat_drv); oz_dbg(ON, "Pending urbs:%d\n", atomic_read(&g_pending_urbs)); oz_dbg(ON, "Pending urbs:%d\n", atomic_read(&g_pending_urbs)); kmem_cache_destroy(oz_urb_link_cache); } } Loading
drivers/staging/ozwpan/ozhcd.c +12 −58 Original line number Original line Diff line number Diff line Loading @@ -45,10 +45,6 @@ */ */ #define OZ_PLAT_DEV_NAME "ozwpan" #define OZ_PLAT_DEV_NAME "ozwpan" /* Maximum number of free urb links that can be kept in the pool. */ #define OZ_MAX_LINK_POOL_SIZE 16 /* Get endpoint object from the containing link. /* Get endpoint object from the containing link. */ */ #define ep_from_link(__e) container_of((__e), struct oz_endpoint, link) #define ep_from_link(__e) container_of((__e), struct oz_endpoint, link) Loading @@ -75,6 +71,8 @@ struct oz_urb_link { unsigned submit_counter; unsigned submit_counter; }; }; static struct kmem_cache *oz_urb_link_cache; /* Holds state information about a USB endpoint. /* Holds state information about a USB endpoint. */ */ #define OZ_EP_BUFFER_SIZE_ISOC (1024 * 24) #define OZ_EP_BUFFER_SIZE_ISOC (1024 * 24) Loading Loading @@ -198,9 +196,6 @@ static struct platform_device *g_plat_dev; static struct oz_hcd *g_ozhcd; static struct oz_hcd *g_ozhcd; static DEFINE_SPINLOCK(g_hcdlock); /* Guards g_ozhcd. */ static DEFINE_SPINLOCK(g_hcdlock); /* Guards g_ozhcd. */ static const char g_hcd_name[] = "Ozmo WPAN"; static const char g_hcd_name[] = "Ozmo WPAN"; static struct list_head *g_link_pool; static int g_link_pool_size; static DEFINE_SPINLOCK(g_link_lock); static DEFINE_SPINLOCK(g_tasklet_lock); static DEFINE_SPINLOCK(g_tasklet_lock); static struct tasklet_struct g_urb_process_tasklet; static struct tasklet_struct g_urb_process_tasklet; static struct tasklet_struct g_urb_cancel_tasklet; static struct tasklet_struct g_urb_cancel_tasklet; Loading Loading @@ -265,68 +260,22 @@ static int oz_get_port_from_addr(struct oz_hcd *ozhcd, u8 bus_addr) } } /* /* * Allocates an urb link, first trying the pool but going to heap if empty. * Context: any * Context: any */ */ static struct oz_urb_link *oz_alloc_urb_link(void) static struct oz_urb_link *oz_alloc_urb_link(void) { { struct oz_urb_link *urbl = NULL; return kmem_cache_alloc(oz_urb_link_cache, GFP_ATOMIC); unsigned long irq_state; spin_lock_irqsave(&g_link_lock, irq_state); if (g_link_pool) { urbl = container_of(g_link_pool, struct oz_urb_link, link); g_link_pool = urbl->link.next; --g_link_pool_size; } spin_unlock_irqrestore(&g_link_lock, irq_state); if (urbl == NULL) urbl = kmalloc(sizeof(struct oz_urb_link), GFP_ATOMIC); return urbl; } } /* /* * Frees an urb link by putting it in the pool if there is enough space or * deallocating it to heap otherwise. * Context: any * Context: any */ */ static void oz_free_urb_link(struct oz_urb_link *urbl) static void oz_free_urb_link(struct oz_urb_link *urbl) { { if (urbl) { if (!urbl) unsigned long irq_state; return; spin_lock_irqsave(&g_link_lock, irq_state); if (g_link_pool_size < OZ_MAX_LINK_POOL_SIZE) { urbl->link.next = g_link_pool; g_link_pool = &urbl->link; urbl = NULL; g_link_pool_size++; } spin_unlock_irqrestore(&g_link_lock, irq_state); kfree(urbl); } } /* * Deallocates all the urb links in the pool. * Context: unknown */ static void oz_empty_link_pool(void) { struct list_head *e; unsigned long irq_state; spin_lock_irqsave(&g_link_lock, irq_state); kmem_cache_free(oz_urb_link_cache, urbl); e = g_link_pool; g_link_pool = NULL; g_link_pool_size = 0; spin_unlock_irqrestore(&g_link_lock, irq_state); while (e) { struct oz_urb_link *urbl = container_of(e, struct oz_urb_link, link); e = e->next; kfree(urbl); } } } /* /* Loading Loading @@ -2311,7 +2260,6 @@ static int oz_plat_remove(struct platform_device *dev) oz_dbg(ON, "Removing hcd\n"); oz_dbg(ON, "Removing hcd\n"); usb_remove_hcd(hcd); usb_remove_hcd(hcd); usb_put_hcd(hcd); usb_put_hcd(hcd); oz_empty_link_pool(); return 0; return 0; } } Loading Loading @@ -2341,6 +2289,11 @@ int oz_hcd_init(void) if (usb_disabled()) if (usb_disabled()) return -ENODEV; return -ENODEV; oz_urb_link_cache = KMEM_CACHE(oz_urb_link, 0); if (!oz_urb_link_cache) return -ENOMEM; tasklet_init(&g_urb_process_tasklet, oz_urb_process_tasklet, 0); tasklet_init(&g_urb_process_tasklet, oz_urb_process_tasklet, 0); tasklet_init(&g_urb_cancel_tasklet, oz_urb_cancel_tasklet, 0); tasklet_init(&g_urb_cancel_tasklet, oz_urb_cancel_tasklet, 0); err = platform_driver_register(&g_oz_plat_drv); err = platform_driver_register(&g_oz_plat_drv); Loading Loading @@ -2380,4 +2333,5 @@ void oz_hcd_term(void) platform_device_unregister(g_plat_dev); platform_device_unregister(g_plat_dev); platform_driver_unregister(&g_oz_plat_drv); platform_driver_unregister(&g_oz_plat_drv); oz_dbg(ON, "Pending urbs:%d\n", atomic_read(&g_pending_urbs)); oz_dbg(ON, "Pending urbs:%d\n", atomic_read(&g_pending_urbs)); kmem_cache_destroy(oz_urb_link_cache); } }