diff options
Diffstat (limited to 'drivers/usb/gadget/fsl_usb2_udc.c')
-rw-r--r-- | drivers/usb/gadget/fsl_usb2_udc.c | 99 |
1 files changed, 36 insertions, 63 deletions
diff --git a/drivers/usb/gadget/fsl_usb2_udc.c b/drivers/usb/gadget/fsl_usb2_udc.c index 3ca2b3159f0..10b2b33b869 100644 --- a/drivers/usb/gadget/fsl_usb2_udc.c +++ b/drivers/usb/gadget/fsl_usb2_udc.c @@ -228,7 +228,7 @@ static int dr_controller_setup(struct fsl_udc *udc) /* Config PHY interface */ portctrl = fsl_readl(&dr_regs->portsc1); - portctrl &= ~(PORTSCX_PHY_TYPE_SEL & PORTSCX_PORT_WIDTH); + portctrl &= ~(PORTSCX_PHY_TYPE_SEL | PORTSCX_PORT_WIDTH); switch (udc->phy_mode) { case FSL_USB2_PHY_ULPI: portctrl |= PORTSCX_PTS_ULPI; @@ -601,39 +601,6 @@ static void fsl_free_request(struct usb_ep *_ep, struct usb_request *_req) kfree(req); } -/*------------------------------------------------------------------ - * Allocate an I/O buffer -*---------------------------------------------------------------------*/ -static void *fsl_alloc_buffer(struct usb_ep *_ep, unsigned bytes, - dma_addr_t *dma, gfp_t gfp_flags) -{ - struct fsl_ep *ep; - - if (!_ep) - return NULL; - - ep = container_of(_ep, struct fsl_ep, ep); - - return dma_alloc_coherent(ep->udc->gadget.dev.parent, - bytes, dma, gfp_flags); -} - -/*------------------------------------------------------------------ - * frees an i/o buffer -*---------------------------------------------------------------------*/ -static void fsl_free_buffer(struct usb_ep *_ep, void *buf, - dma_addr_t dma, unsigned bytes) -{ - struct fsl_ep *ep; - - if (!_ep) - return; - - ep = container_of(_ep, struct fsl_ep, ep); - - dma_free_coherent(ep->udc->gadget.dev.parent, bytes, buf, dma); -} - /*-------------------------------------------------------------------------*/ static int fsl_queue_td(struct fsl_ep *ep, struct fsl_req *req) { @@ -1047,9 +1014,6 @@ static struct usb_ep_ops fsl_ep_ops = { .alloc_request = fsl_alloc_request, .free_request = fsl_free_request, - .alloc_buffer = fsl_alloc_buffer, - .free_buffer = fsl_free_buffer, - .queue = fsl_ep_queue, .dequeue = fsl_ep_dequeue, @@ -2189,27 +2153,19 @@ static void fsl_udc_release(struct device *dev) * init resource for globle controller * Return the udc handle on success or NULL on failure ------------------------------------------------------------------*/ -static struct fsl_udc *__init struct_udc_setup(struct platform_device *pdev) +static int __init struct_udc_setup(struct fsl_udc *udc, + struct platform_device *pdev) { - struct fsl_udc *udc; struct fsl_usb2_platform_data *pdata; size_t size; - udc = kzalloc(sizeof(struct fsl_udc), GFP_KERNEL); - if (udc == NULL) { - ERR("malloc udc failed\n"); - return NULL; - } - pdata = pdev->dev.platform_data; udc->phy_mode = pdata->phy_mode; - /* max_ep_nr is bidirectional ep number, max_ep doubles the number */ - udc->max_ep = pdata->max_ep_nr * 2; udc->eps = kzalloc(sizeof(struct fsl_ep) * udc->max_ep, GFP_KERNEL); if (!udc->eps) { ERR("malloc fsl_ep failed\n"); - goto cleanup; + return -1; } /* initialized QHs, take care of alignment */ @@ -2225,7 +2181,7 @@ static struct fsl_udc *__init struct_udc_setup(struct platform_device *pdev) if (!udc->ep_qh) { ERR("malloc QHs for udc failed\n"); kfree(udc->eps); - goto cleanup; + return -1; } udc->ep_qh_size = size; @@ -2244,11 +2200,7 @@ static struct fsl_udc *__init struct_udc_setup(struct platform_device *pdev) udc->remote_wakeup = 0; /* default to 0 on reset */ spin_lock_init(&udc->lock); - return udc; - -cleanup: - kfree(udc); - return NULL; + return 0; } /*---------------------------------------------------------------- @@ -2287,35 +2239,37 @@ static int __init struct_ep_setup(struct fsl_udc *udc, unsigned char index, } /* Driver probe function - * all intialize operations implemented here except enabling usb_intr reg + * all intialization operations implemented here except enabling usb_intr reg + * board setup should have been done in the platform code */ static int __init fsl_udc_probe(struct platform_device *pdev) { struct resource *res; int ret = -ENODEV; unsigned int i; + u32 dccparams; if (strcmp(pdev->name, driver_name)) { VDBG("Wrong device\n"); return -ENODEV; } - /* board setup should have been done in the platform code */ - - /* Initialize the udc structure including QH member and other member */ - udc_controller = struct_udc_setup(pdev); - if (!udc_controller) { - VDBG("udc_controller is NULL \n"); + udc_controller = kzalloc(sizeof(struct fsl_udc), GFP_KERNEL); + if (udc_controller == NULL) { + ERR("malloc udc failed\n"); return -ENOMEM; } res = platform_get_resource(pdev, IORESOURCE_MEM, 0); - if (!res) + if (!res) { + kfree(udc_controller); return -ENXIO; + } if (!request_mem_region(res->start, res->end - res->start + 1, driver_name)) { ERR("request mem region for %s failed \n", pdev->name); + kfree(udc_controller); return -EBUSY; } @@ -2328,13 +2282,24 @@ static int __init fsl_udc_probe(struct platform_device *pdev) usb_sys_regs = (struct usb_sys_interface *) ((u32)dr_regs + USB_DR_SYS_OFFSET); + /* Read Device Controller Capability Parameters register */ + dccparams = fsl_readl(&dr_regs->dccparams); + if (!(dccparams & DCCPARAMS_DC)) { + ERR("This SOC doesn't support device role\n"); + ret = -ENODEV; + goto err2; + } + /* Get max device endpoints */ + /* DEN is bidirectional ep number, max_ep doubles the number */ + udc_controller->max_ep = (dccparams & DCCPARAMS_DEN_MASK) * 2; + udc_controller->irq = platform_get_irq(pdev, 0); if (!udc_controller->irq) { ret = -ENODEV; goto err2; } - ret = request_irq(udc_controller->irq, fsl_udc_irq, SA_SHIRQ, + ret = request_irq(udc_controller->irq, fsl_udc_irq, IRQF_SHARED, driver_name, udc_controller); if (ret != 0) { ERR("cannot request irq %d err %d \n", @@ -2342,6 +2307,13 @@ static int __init fsl_udc_probe(struct platform_device *pdev) goto err2; } + /* Initialize the udc structure including QH member and other member */ + if (struct_udc_setup(udc_controller, pdev)) { + ERR("Can't initialize udc data structure\n"); + ret = -ENOMEM; + goto err3; + } + /* initialize usb hw reg except for regs for EP, * leave usbintr reg untouched */ dr_controller_setup(udc_controller); @@ -2403,6 +2375,7 @@ err2: iounmap(dr_regs); err1: release_mem_region(res->start, res->end - res->start + 1); + kfree(udc_controller); return ret; } |