usb: dwc_otg_310: support vbus controlled by both gpio and pmic
[firefly-linux-kernel-4.4.55.git] / drivers / usb / dwc_otg_310 / dwc_otg_pcd_linux.c
1  /* ==========================================================================
2   * $File: //dwh/usb_iip/dev/software/otg/linux/drivers/dwc_otg_pcd_linux.c $
3   * $Revision: #26 $
4   * $Date: 2012/12/13 $
5   * $Change: 2125485 $
6   *
7   * Synopsys HS OTG Linux Software Driver and documentation (hereinafter,
8   * "Software") is an Unsupported proprietary work of Synopsys, Inc. unless
9   * otherwise expressly agreed to in writing between Synopsys and you.
10   *
11   * The Software IS NOT an item of Licensed Software or Licensed Product under
12   * any End User Software License Agreement or Agreement for Licensed Product
13   * with Synopsys or any supplement thereto. You are permitted to use and
14   * redistribute this Software in source and binary forms, with or without
15   * modification, provided that redistributions of source code must retain this
16   * notice. You may not view, use, disclose, copy or distribute this file or
17   * any information contained herein except pursuant to this license grant from
18   * Synopsys. If you do not agree with this notice, including the disclaimer
19   * below, then you are not authorized to use the Software.
20   *
21   * THIS SOFTWARE IS BEING DISTRIBUTED BY SYNOPSYS SOLELY ON AN "AS IS" BASIS
22   * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23   * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24   * ARE HEREBY DISCLAIMED. IN NO EVENT SHALL SYNOPSYS BE LIABLE FOR ANY DIRECT,
25   * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
26   * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
27   * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
28   * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
29   * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
30   * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH
31   * DAMAGE.
32   * ========================================================================== */
33 #ifndef DWC_HOST_ONLY
34
35 /** @file
36  * This file implements the Peripheral Controller Driver.
37  *
38  * The Peripheral Controller Driver (PCD) is responsible for
39  * translating requests from the Function Driver into the appropriate
40  * actions on the DWC_otg controller. It isolates the Function Driver
41  * from the specifics of the controller by providing an API to the
42  * Function Driver.
43  *
44  * The Peripheral Controller Driver for Linux will implement the
45  * Gadget API, so that the existing Gadget drivers can be used.
46  * (Gadget Driver is the Linux terminology for a Function Driver.)
47  *
48  * The Linux Gadget API is defined in the header file
49  * <code><linux/usb_gadget.h></code>.  The USB EP operations API is
50  * defined in the structure <code>usb_ep_ops</code> and the USB
51  * Controller API is defined in the structure
52  * <code>usb_gadget_ops</code>.
53  *
54  */
55
56 #include "dwc_otg_os_dep.h"
57 #include "dwc_otg_pcd_if.h"
58 #include "dwc_otg_pcd.h"
59 #include "dwc_otg_driver.h"
60 #include "dwc_otg_dbg.h"
61 #include "dwc_otg_attr.h"
62
63 #include "usbdev_rk.h"
64 static struct gadget_wrapper {
65         dwc_otg_pcd_t *pcd;
66
67         struct usb_gadget gadget;
68         struct usb_gadget_driver *driver;
69
70         struct usb_ep ep0;
71         struct usb_ep in_ep[16];
72         struct usb_ep out_ep[16];
73
74 } *gadget_wrapper;
75
76 /* Display the contents of the buffer */
77 extern void dump_msg(const u8 *buf, unsigned int length);
78
79 /**
80  * Get the dwc_otg_pcd_ep_t* from usb_ep* pointer - NULL in case
81  * if the endpoint is not found
82  */
83 static struct dwc_otg_pcd_ep *ep_from_handle(dwc_otg_pcd_t *pcd, void *handle)
84 {
85         int i;
86         if (pcd->ep0.priv == handle) {
87                 return &pcd->ep0;
88         }
89
90         for (i = 0; i < MAX_EPS_CHANNELS - 1; i++) {
91                 if (pcd->in_ep[i].priv == handle)
92                         return &pcd->in_ep[i];
93                 if (pcd->out_ep[i].priv == handle)
94                         return &pcd->out_ep[i];
95         }
96
97         return NULL;
98 }
99
100 /* USB Endpoint Operations */
101 /*
102  * The following sections briefly describe the behavior of the Gadget
103  * API endpoint operations implemented in the DWC_otg driver
104  * software. Detailed descriptions of the generic behavior of each of
105  * these functions can be found in the Linux header file
106  * include/linux/usb_gadget.h.
107  *
108  * The Gadget API provides wrapper functions for each of the function
109  * pointers defined in usb_ep_ops. The Gadget Driver calls the wrapper
110  * function, which then calls the underlying PCD function. The
111  * following sections are named according to the wrapper
112  * functions. Within each section, the corresponding DWC_otg PCD
113  * function name is specified.
114  *
115  */
116
117 /**
118  * This function is called by the Gadget Driver for each EP to be
119  * configured for the current configuration (SET_CONFIGURATION).
120  *
121  * This function initializes the dwc_otg_ep_t data structure, and then
122  * calls dwc_otg_ep_activate.
123  */
124 static int ep_enable(struct usb_ep *usb_ep,
125                      const struct usb_endpoint_descriptor *ep_desc)
126 {
127         int retval;
128
129         DWC_DEBUGPL(DBG_PCDV, "%s(%p,%p)\n", __func__, usb_ep, ep_desc);
130
131         if (!usb_ep || !ep_desc || ep_desc->bDescriptorType != USB_DT_ENDPOINT) {
132                 DWC_WARN("%s, bad ep or descriptor\n", __func__);
133                 return -EINVAL;
134         }
135         if (usb_ep == &gadget_wrapper->ep0) {
136                 DWC_WARN("%s, bad ep(0)\n", __func__);
137                 return -EINVAL;
138         }
139
140         /* Check FIFO size? */
141         if (!ep_desc->wMaxPacketSize) {
142                 DWC_WARN("%s, bad %s maxpacket\n", __func__, usb_ep->name);
143                 return -ERANGE;
144         }
145
146         if (!gadget_wrapper->driver ||
147             gadget_wrapper->gadget.speed == USB_SPEED_UNKNOWN) {
148                 DWC_WARN("%s, bogus device state\n", __func__);
149                 return -ESHUTDOWN;
150         }
151
152         /* Delete after check - MAS */
153 #if 0
154         nat = (uint32_t) ep_desc->wMaxPacketSize;
155         printk(KERN_ALERT "%s: nat (before) =%d\n", __func__, nat);
156         nat = (nat >> 11) & 0x03;
157         printk(KERN_ALERT "%s: nat (after) =%d\n", __func__, nat);
158 #endif
159         retval = dwc_otg_pcd_ep_enable(gadget_wrapper->pcd,
160                                        (const uint8_t *)ep_desc,
161                                        (void *)usb_ep);
162         if (retval) {
163                 DWC_WARN("dwc_otg_pcd_ep_enable failed\n");
164                 return -EINVAL;
165         }
166
167         usb_ep->maxpacket = le16_to_cpu(ep_desc->wMaxPacketSize);
168
169         return 0;
170 }
171
172 /**
173  * This function is called when an EP is disabled due to disconnect or
174  * change in configuration. Any pending requests will terminate with a
175  * status of -ESHUTDOWN.
176  *
177  * This function modifies the dwc_otg_ep_t data structure for this EP,
178  * and then calls dwc_otg_ep_deactivate.
179  */
180 static int ep_disable(struct usb_ep *usb_ep)
181 {
182         int retval;
183
184         DWC_DEBUGPL(DBG_PCDV, "%s(%p)\n", __func__, usb_ep);
185         if (!usb_ep) {
186                 DWC_DEBUGPL(DBG_PCD, "%s, %s not enabled\n", __func__,
187                             usb_ep ? usb_ep->name : NULL);
188                 return -EINVAL;
189         }
190
191         retval = dwc_otg_pcd_ep_disable(gadget_wrapper->pcd, usb_ep);
192         if (retval) {
193                 retval = -EINVAL;
194         }
195
196         return retval;
197 }
198
199 /**
200  * This function allocates a request object to use with the specified
201  * endpoint.
202  *
203  * @param ep The endpoint to be used with with the request
204  * @param gfp_flags the GFP_* flags to use.
205  */
206 static struct usb_request *dwc_otg_pcd_alloc_request(struct usb_ep *ep,
207                                                      gfp_t gfp_flags)
208 {
209         struct usb_request *usb_req;
210
211         DWC_DEBUGPL(DBG_PCDV, "%s(%p,%d)\n", __func__, ep, gfp_flags);
212         if (0 == ep) {
213                 DWC_WARN("%s() %s\n", __func__, "Invalid EP!\n");
214                 return 0;
215         }
216         usb_req = kmalloc(sizeof(*usb_req), gfp_flags);
217         if (0 == usb_req) {
218                 DWC_WARN("%s() %s\n", __func__, "request allocation failed!\n");
219                 return 0;
220         }
221         memset(usb_req, 0, sizeof(*usb_req));
222         usb_req->dma = DWC_DMA_ADDR_INVALID;
223
224         return usb_req;
225 }
226
227 /**
228  * This function frees a request object.
229  *
230  * @param ep The endpoint associated with the request
231  * @param req The request being freed
232  */
233 static void dwc_otg_pcd_free_request(struct usb_ep *ep, struct usb_request *req)
234 {
235         DWC_DEBUGPL(DBG_PCDV, "%s(%p,%p)\n", __func__, ep, req);
236
237         if (0 == ep || 0 == req) {
238                 DWC_WARN("%s() %s\n", __func__,
239                          "Invalid ep or req argument!\n");
240                 return;
241         }
242
243         kfree(req);
244 }
245
246 #if LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 28)
247 /**
248  * This function allocates an I/O buffer to be used for a transfer
249  * to/from the specified endpoint.
250  *
251  * @param usb_ep The endpoint to be used with with the request
252  * @param bytes The desired number of bytes for the buffer
253  * @param dma Pointer to the buffer's DMA address; must be valid
254  * @param gfp_flags the GFP_* flags to use.
255  * @return address of a new buffer or null is buffer could not be allocated.
256  */
257 static void *dwc_otg_pcd_alloc_buffer(struct usb_ep *usb_ep, unsigned bytes,
258                                       dma_addr_t *dma, gfp_t gfp_flags)
259 {
260         void *buf;
261         dwc_otg_pcd_t *pcd = 0;
262
263         pcd = gadget_wrapper->pcd;
264
265         DWC_DEBUGPL(DBG_PCDV, "%s(%p,%d,%p,%0x)\n", __func__, usb_ep, bytes,
266                     dma, gfp_flags);
267
268         /* Check dword alignment */
269         if ((bytes & 0x3UL) != 0) {
270                 DWC_WARN("%s() Buffer size is not a multiple of"
271                          "DWORD size (%d)", __func__, bytes);
272         }
273
274         buf = dma_alloc_coherent(NULL, bytes, dma, gfp_flags);
275
276         /* Check dword alignment */
277         if (((int)buf & 0x3UL) != 0) {
278                 DWC_WARN("%s() Buffer is not DWORD aligned (%p)",
279                          __func__, buf);
280         }
281
282         return buf;
283 }
284
285 /**
286  * This function frees an I/O buffer that was allocated by alloc_buffer.
287  *
288  * @param usb_ep the endpoint associated with the buffer
289  * @param buf address of the buffer
290  * @param dma The buffer's DMA address
291  * @param bytes The number of bytes of the buffer
292  */
293 static void dwc_otg_pcd_free_buffer(struct usb_ep *usb_ep, void *buf,
294                                     dma_addr_t dma, unsigned bytes)
295 {
296         dwc_otg_pcd_t *pcd = 0;
297
298         pcd = gadget_wrapper->pcd;
299
300         DWC_DEBUGPL(DBG_PCDV, "%s(%p,%0x,%d)\n", __func__, buf, dma, bytes);
301
302         dma_free_coherent(NULL, bytes, buf, dma);
303 }
304 #endif
305
306 /**
307  * This function is used to submit an I/O Request to an EP.
308  *
309  *      - When the request completes the request's completion callback
310  *        is called to return the request to the driver.
311  *      - An EP, except control EPs, may have multiple requests
312  *        pending.
313  *      - Once submitted the request cannot be examined or modified.
314  *      - Each request is turned into one or more packets.
315  *      - A BULK EP can queue any amount of data; the transfer is
316  *        packetized.
317  *      - Zero length Packets are specified with the request 'zero'
318  *        flag.
319  */
320 static int ep_queue(struct usb_ep *usb_ep, struct usb_request *usb_req,
321                     gfp_t gfp_flags)
322 {
323         dwc_otg_pcd_t *pcd;
324         struct dwc_otg_pcd_ep *ep = NULL;
325         int retval = 0, is_isoc_ep = 0;
326         dma_addr_t dma_addr = DWC_DMA_ADDR_INVALID;
327
328         DWC_DEBUGPL(DBG_PCDV, "%s(%p,%p,%d)\n",
329                     __func__, usb_ep, usb_req, gfp_flags);
330
331         if (!usb_req || !usb_req->complete || !usb_req->buf) {
332                 DWC_WARN("bad params\n");
333                 return -EINVAL;
334         }
335
336         if (!usb_ep) {
337                 DWC_WARN("bad ep\n");
338                 return -EINVAL;
339         }
340
341         pcd = gadget_wrapper->pcd;
342         if (!gadget_wrapper->driver ||
343             gadget_wrapper->gadget.speed == USB_SPEED_UNKNOWN) {
344                 DWC_DEBUGPL(DBG_PCDV, "gadget.speed=%d\n",
345                             gadget_wrapper->gadget.speed);
346                 DWC_WARN("bogus device state\n");
347                 return -ESHUTDOWN;
348         }
349
350         DWC_DEBUGPL(DBG_PCD, "%s queue req %p, len %d buf %p\n",
351                     usb_ep->name, usb_req, usb_req->length, usb_req->buf);
352
353         usb_req->status = -EINPROGRESS;
354         usb_req->actual = 0;
355
356         ep = ep_from_handle(pcd, usb_ep);
357         if (ep == NULL)
358                 is_isoc_ep = 0;
359         else
360                 is_isoc_ep = (ep->dwc_ep.type == DWC_OTG_EP_TYPE_ISOC) ? 1 : 0;
361 #if LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 28)
362         dma_addr = usb_req->dma;
363 #else
364         if (GET_CORE_IF(pcd)->dma_enable) {
365                 /* if (usb_req->length != 0) {*/
366                 /* In device DMA mode when gadget perform ep_queue request
367                  * with buffer length 0, Kernel stack dump occurred. For 0
368                  * length buffers perform dma_map_single() with length 4.*/
369                 if (usb_req->dma == DWC_DMA_ADDR_INVALID) {
370                         dma_addr =
371                             dma_map_single(gadget_wrapper->gadget.dev.parent,
372                                            usb_req->buf,
373                                            usb_req->length !=
374                                            0 ? usb_req->length : 4,
375                                            ep->dwc_ep.
376                                            is_in ? DMA_TO_DEVICE :
377                                            DMA_FROM_DEVICE);
378                         usb_req->dma = dma_addr;
379                 } else {
380                         dma_addr = usb_req->dma;
381                 }
382
383         }
384 #endif
385
386 #ifdef DWC_UTE_PER_IO
387         if (is_isoc_ep == 1) {
388                 retval =
389                     dwc_otg_pcd_xiso_ep_queue(pcd, usb_ep, usb_req->buf,
390                                               dma_addr, usb_req->length,
391                                               usb_req->zero, usb_req,
392                                               gfp_flags == GFP_ATOMIC ? 1 : 0,
393                                               &usb_req->ext_req);
394                 if (retval)
395                         return -EINVAL;
396
397                 return 0;
398         }
399 #endif
400         retval = dwc_otg_pcd_ep_queue(pcd, usb_ep, usb_req->buf, dma_addr,
401                                       usb_req->length, usb_req->zero, usb_req,
402                                       gfp_flags == GFP_ATOMIC ? 1 : 0);
403         if (retval) {
404                 return -EINVAL;
405         }
406
407         return 0;
408 }
409
410 /**
411  * This function cancels an I/O request from an EP.
412  */
413 static int ep_dequeue(struct usb_ep *usb_ep, struct usb_request *usb_req)
414 {
415         DWC_DEBUGPL(DBG_PCDV, "%s(%p,%p)\n", __func__, usb_ep, usb_req);
416
417         if (!usb_ep || !usb_req) {
418                 DWC_WARN("bad argument\n");
419                 return -EINVAL;
420         }
421         if (!gadget_wrapper->driver ||
422             gadget_wrapper->gadget.speed == USB_SPEED_UNKNOWN) {
423                 DWC_WARN("bogus device state\n");
424                 return -ESHUTDOWN;
425         }
426         if (dwc_otg_pcd_ep_dequeue(gadget_wrapper->pcd, usb_ep, usb_req)) {
427                 return -EINVAL;
428         }
429
430         return 0;
431 }
432
433 /**
434  * usb_ep_set_halt stalls an endpoint.
435  *
436  * usb_ep_clear_halt clears an endpoint halt and resets its data
437  * toggle.
438  *
439  * Both of these functions are implemented with the same underlying
440  * function. The behavior depends on the value argument.
441  *
442  * @param[in] usb_ep the Endpoint to halt or clear halt.
443  * @param[in] value
444  *      - 0 means clear_halt.
445  *      - 1 means set_halt,
446  *      - 2 means clear stall lock flag.
447  *      - 3 means set  stall lock flag.
448  */
449 static int ep_halt(struct usb_ep *usb_ep, int value)
450 {
451         int retval = 0;
452
453         DWC_DEBUGPL(DBG_PCD, "HALT %s %d\n", usb_ep->name, value);
454
455         if (!usb_ep) {
456                 DWC_WARN("bad ep\n");
457                 return -EINVAL;
458         }
459
460         retval = dwc_otg_pcd_ep_halt(gadget_wrapper->pcd, usb_ep, value);
461         if (retval == -DWC_E_AGAIN) {
462                 return -EAGAIN;
463         } else if (retval) {
464                 retval = -EINVAL;
465         }
466
467         return retval;
468 }
469
470 #if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 26)
471 static int ep_wedge(struct usb_ep *usb_ep)
472 {
473         DWC_DEBUGPL(DBG_PCD, "WEDGE %s\n", usb_ep->name);
474
475         return ep_halt(usb_ep, 3);
476 }
477 #endif
478
479 #ifdef DWC_EN_ISOC
480 /**
481  * This function is used to submit an ISOC Transfer Request to an EP.
482  *
483  *      - Every time a sync period completes the request's completion callback
484  *        is called to provide data to the gadget driver.
485  *      - Once submitted the request cannot be modified.
486  *      - Each request is turned into periodic data packets untill ISO
487  *        Transfer is stopped..
488  */
489 static int iso_ep_start(struct usb_ep *usb_ep, struct usb_iso_request *req,
490                         gfp_t gfp_flags)
491 {
492         int retval = 0;
493
494         if (!req || !req->process_buffer || !req->buf0 || !req->buf1) {
495                 DWC_WARN("bad params\n");
496                 return -EINVAL;
497         }
498
499         if (!usb_ep) {
500                 DWC_PRINTF("bad params\n");
501                 return -EINVAL;
502         }
503
504         req->status = -EINPROGRESS;
505
506         retval =
507             dwc_otg_pcd_iso_ep_start(gadget_wrapper->pcd, usb_ep, req->buf0,
508                                      req->buf1, req->dma0, req->dma1,
509                                      req->sync_frame, req->data_pattern_frame,
510                                      req->data_per_frame,
511                                      req->flags & USB_REQ_ISO_ASAP ? -1 :
512                                      req->start_frame, req->buf_proc_intrvl,
513                                      req, gfp_flags == GFP_ATOMIC ? 1 : 0);
514
515         if (retval) {
516                 return -EINVAL;
517         }
518
519         return retval;
520 }
521
522 /**
523  * This function stops ISO EP Periodic Data Transfer.
524  */
525 static int iso_ep_stop(struct usb_ep *usb_ep, struct usb_iso_request *req)
526 {
527         int retval = 0;
528         if (!usb_ep) {
529                 DWC_WARN("bad ep\n");
530         }
531
532         if (!gadget_wrapper->driver ||
533             gadget_wrapper->gadget.speed == USB_SPEED_UNKNOWN) {
534                 DWC_DEBUGPL(DBG_PCDV, "gadget.speed=%d\n",
535                             gadget_wrapper->gadget.speed);
536                 DWC_WARN("bogus device state\n");
537         }
538
539         dwc_otg_pcd_iso_ep_stop(gadget_wrapper->pcd, usb_ep, req);
540         if (retval) {
541                 retval = -EINVAL;
542         }
543
544         return retval;
545 }
546
547 static struct usb_iso_request *alloc_iso_request(struct usb_ep *ep,
548                                                  int packets, gfp_t gfp_flags)
549 {
550         struct usb_iso_request *pReq = NULL;
551         uint32_t req_size;
552
553         req_size = sizeof(struct usb_iso_request);
554         req_size +=
555             (2 * packets * (sizeof(struct usb_gadget_iso_packet_descriptor)));
556
557         pReq = kmalloc(req_size, gfp_flags);
558         if (!pReq) {
559                 DWC_WARN("Can't allocate Iso Request\n");
560                 return 0;
561         }
562         pReq->iso_packet_desc0 = (void *)(pReq + 1);
563
564         pReq->iso_packet_desc1 = pReq->iso_packet_desc0 + packets;
565
566         return pReq;
567 }
568
569 static void free_iso_request(struct usb_ep *ep, struct usb_iso_request *req)
570 {
571         kfree(req);
572 }
573
574 static struct usb_isoc_ep_ops dwc_otg_pcd_ep_ops = {
575         .ep_ops = {
576                    .enable = ep_enable,
577                    .disable = ep_disable,
578
579                    .alloc_request = dwc_otg_pcd_alloc_request,
580                    .free_request = dwc_otg_pcd_free_request,
581
582 #if LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 28)
583                    .alloc_buffer = dwc_otg_pcd_alloc_buffer,
584                    .free_buffer = dwc_otg_pcd_free_buffer,
585 #endif
586
587                    .queue = ep_queue,
588                    .dequeue = ep_dequeue,
589
590                    .set_halt = ep_halt,
591
592 #if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 26)
593                    .set_wedge = ep_wedge,
594 #endif
595                    .fifo_status = 0,
596                    .fifo_flush = 0,
597                    },
598
599         .iso_ep_start = iso_ep_start,
600         .iso_ep_stop = iso_ep_stop,
601         .alloc_iso_request = alloc_iso_request,
602         .free_iso_request = free_iso_request,
603 };
604
605 #else
606
607 static struct usb_ep_ops dwc_otg_pcd_ep_ops = {
608         .enable = ep_enable,
609         .disable = ep_disable,
610
611         .alloc_request = dwc_otg_pcd_alloc_request,
612         .free_request = dwc_otg_pcd_free_request,
613
614 #if LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 28)
615         .alloc_buffer = dwc_otg_pcd_alloc_buffer,
616         .free_buffer = dwc_otg_pcd_free_buffer,
617 #endif
618
619         .queue = ep_queue,
620         .dequeue = ep_dequeue,
621
622         .set_halt = ep_halt,
623
624 #if LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 26)
625         .set_wedge = ep_wedge,
626 #endif
627
628         .fifo_status = 0,
629         .fifo_flush = 0,
630
631 };
632
633 #endif /* _EN_ISOC_ */
634 /*      Gadget Operations */
635 /**
636  * The following gadget operations will be implemented in the DWC_otg
637  * PCD. Functions in the API that are not described below are not
638  * implemented.
639  *
640  * The Gadget API provides wrapper functions for each of the function
641  * pointers defined in usb_gadget_ops. The Gadget Driver calls the
642  * wrapper function, which then calls the underlying PCD function. The
643  * following sections are named according to the wrapper functions
644  * (except for ioctl, which doesn't have a wrapper function). Within
645  * each section, the corresponding DWC_otg PCD function name is
646  * specified.
647  *
648  */
649
650 /**
651  *Gets the USB Frame number of the last SOF.
652  */
653 static int get_frame_number(struct usb_gadget *gadget)
654 {
655         struct gadget_wrapper *d;
656
657         DWC_DEBUGPL(DBG_PCDV, "%s(%p)\n", __func__, gadget);
658
659         if (gadget == 0) {
660                 return -ENODEV;
661         }
662
663         d = container_of(gadget, struct gadget_wrapper, gadget);
664         return dwc_otg_pcd_get_frame_number(d->pcd);
665 }
666
667 #ifdef CONFIG_USB_DWC_OTG_LPM
668 static int test_lpm_enabled(struct usb_gadget *gadget)
669 {
670         struct gadget_wrapper *d;
671
672         d = container_of(gadget, struct gadget_wrapper, gadget);
673
674         return dwc_otg_pcd_is_lpm_enabled(d->pcd);
675 }
676
677 #if LINUX_VERSION_CODE >= KERNEL_VERSION(3, 6, 0)
678 static int test_besl_enabled(struct usb_gadget *gadget)
679 {
680         struct gadget_wrapper *d;
681
682         d = container_of(gadget, struct gadget_wrapper, gadget);
683
684         return dwc_otg_pcd_is_besl_enabled(d->pcd);
685 }
686
687 static int get_param_baseline_besl(struct usb_gadget *gadget)
688 {
689         struct gadget_wrapper *d;
690
691         d = container_of(gadget, struct gadget_wrapper, gadget);
692
693         return dwc_otg_pcd_get_param_baseline_besl(d->pcd);
694 }
695
696 static int get_param_deep_besl(struct usb_gadget *gadget)
697 {
698         struct gadget_wrapper *d;
699
700         d = container_of(gadget, struct gadget_wrapper, gadget);
701
702         return dwc_otg_pcd_get_param_deep_besl(d->pcd);
703 }
704 #endif
705 #endif
706
707 /**
708  * Initiates Session Request Protocol (SRP) to wakeup the host if no
709  * session is in progress. If a session is already in progress, but
710  * the device is suspended, remote wakeup signaling is started.
711  *
712  */
713 static int wakeup(struct usb_gadget *gadget)
714 {
715         struct gadget_wrapper *d;
716
717         DWC_DEBUGPL(DBG_PCDV, "%s(%p)\n", __func__, gadget);
718
719         if (gadget == 0) {
720                 return -ENODEV;
721         } else {
722                 d = container_of(gadget, struct gadget_wrapper, gadget);
723         }
724         dwc_otg_pcd_wakeup(d->pcd);
725         return 0;
726 }
727
728 static int dwc_otg_pcd_pullup(struct usb_gadget *_gadget, int is_on)
729 {
730         struct gadget_wrapper *d;
731         dwc_otg_pcd_t *pcd;
732         dwc_otg_core_if_t *core_if;
733
734         printk("pcd_pullup, is_on %d\n", is_on);
735         if (_gadget == NULL)
736                 return -ENODEV;
737         else {
738                 d = container_of(_gadget, struct gadget_wrapper, gadget);
739                 pcd = d->pcd;
740                 core_if = GET_CORE_IF(d->pcd);
741         }
742
743         if (is_on) {
744                 /* dwc_otg_pcd_pullup_enable(pcd); */
745                 pcd->conn_en = 1;
746                 pcd->conn_status = 0;
747         } else {
748                 dwc_otg_pcd_pullup_disable(pcd);
749                 pcd->conn_en = 0;
750         }
751
752         return 0;
753
754 }
755
756 static int dwc_otg_gadget_start(struct usb_gadget *g,
757                                 struct usb_gadget_driver *driver)
758 {
759         DWC_DEBUGPL(DBG_PCD, "registering gadget driver '%s'\n",
760                     driver->driver.name);
761         if (gadget_wrapper == 0) {
762                 DWC_ERROR("ENODEV\n");
763                 return -ENODEV;
764         }
765         if (gadget_wrapper->driver != 0) {
766                 DWC_ERROR("EBUSY (%p)\n", gadget_wrapper->driver);
767                 return -EBUSY;
768         }
769         /* hook up the driver */
770         gadget_wrapper->driver = driver;
771         gadget_wrapper->gadget.dev.driver = &driver->driver;
772
773         DWC_DEBUGPL(DBG_PCD, "bind to driver %s\n", driver->driver.name);
774
775         return 0;
776 }
777
778 static int dwc_otg_gadget_stop(struct usb_gadget *g)
779 {
780         struct gadget_wrapper *d;
781         struct usb_ep *ep;
782         s8 dev_endpoints;
783         int i;
784
785         if (!g)
786                 return -ENODEV;
787
788         d = container_of(g, struct gadget_wrapper, gadget);
789
790         /* all endpoints should be shutdown */
791         dev_endpoints = d->pcd->core_if->dev_if->num_in_eps;
792         for (i = 0; i < dev_endpoints; i++) {
793                 ep = &d->in_ep[i];
794                 ep_disable(ep);
795         }
796
797         dev_endpoints = d->pcd->core_if->dev_if->num_out_eps;
798         for (i = 0; i < dev_endpoints; i++) {
799                 ep = &d->out_ep[i];
800                 ep_disable(ep);
801         }
802
803         gadget_wrapper->driver = NULL;
804         gadget_wrapper->gadget.dev.driver = NULL;
805
806         return 0;
807 }
808
809 static const struct usb_gadget_ops dwc_otg_pcd_ops = {
810         .get_frame = get_frame_number,
811         .wakeup = wakeup,
812         .pullup = dwc_otg_pcd_pullup,
813 #ifdef CONFIG_USB_DWC_OTG_LPM
814         .lpm_support = test_lpm_enabled,
815 #if LINUX_VERSION_CODE >= KERNEL_VERSION(3, 6, 0)
816         .besl_support = test_besl_enabled,
817         .get_baseline_besl = get_param_baseline_besl,
818         .get_deep_besl = get_param_deep_besl,
819 #endif
820 #endif
821         .udc_start = dwc_otg_gadget_start,
822         .udc_stop = dwc_otg_gadget_stop,
823
824         /* current versions must always be self-powered */
825 };
826
827 static int _setup(dwc_otg_pcd_t *pcd, uint8_t *bytes)
828 {
829         int retval = -DWC_E_NOT_SUPPORTED;
830         if (gadget_wrapper->driver && gadget_wrapper->driver->setup) {
831                 retval = gadget_wrapper->driver->setup(&gadget_wrapper->gadget,
832                                                        (struct usb_ctrlrequest
833                                                         *)bytes);
834         }
835
836         if (retval == -ENOTSUPP) {
837                 retval = -DWC_E_NOT_SUPPORTED;
838         } else if (retval < 0) {
839                 retval = -DWC_E_INVALID;
840         }
841
842         return retval;
843 }
844
845 #ifdef DWC_EN_ISOC
846 static int _isoc_complete(dwc_otg_pcd_t *pcd, void *ep_handle,
847                           void *req_handle, int proc_buf_num)
848 {
849         int i, packet_count;
850         struct usb_gadget_iso_packet_descriptor *iso_packet = 0;
851         struct usb_iso_request *iso_req = req_handle;
852
853         if (proc_buf_num) {
854                 iso_packet = iso_req->iso_packet_desc1;
855         } else {
856                 iso_packet = iso_req->iso_packet_desc0;
857         }
858         packet_count =
859             dwc_otg_pcd_get_iso_packet_count(pcd, ep_handle, req_handle);
860         for (i = 0; i < packet_count; ++i) {
861                 int status;
862                 int actual;
863                 int offset;
864                 dwc_otg_pcd_get_iso_packet_params(pcd, ep_handle, req_handle,
865                                                   i, &status, &actual, &offset);
866                 switch (status) {
867                 case -DWC_E_NO_DATA:
868                         status = -ENODATA;
869                         break;
870                 default:
871                         if (status) {
872                                 DWC_PRINTF("unknown status in isoc packet\n");
873                         }
874
875                 }
876                 iso_packet[i].status = status;
877                 iso_packet[i].offset = offset;
878                 iso_packet[i].actual_length = actual;
879         }
880
881         iso_req->status = 0;
882         iso_req->process_buffer(ep_handle, iso_req);
883
884         return 0;
885 }
886 #endif /* DWC_EN_ISOC */
887
888 #ifdef DWC_UTE_PER_IO
889 /**
890  * Copy the contents of the extended request to the Linux usb_request's
891  * extended part and call the gadget's completion.
892  *
893  * @param pcd                   Pointer to the pcd structure
894  * @param ep_handle             Void pointer to the usb_ep structure
895  * @param req_handle    Void pointer to the usb_request structure
896  * @param status                Request status returned from the portable logic
897  * @param ereq_port             Void pointer to the extended request structure
898  *                                              created in the the portable part that contains the
899  *                                              results of the processed iso packets.
900  */
901 static int _xisoc_complete(dwc_otg_pcd_t *pcd, void *ep_handle,
902                            void *req_handle, int32_t status, void *ereq_port)
903 {
904         struct dwc_ute_iso_req_ext *ereqorg = NULL;
905         struct dwc_iso_xreq_port *ereqport = NULL;
906         struct dwc_ute_iso_packet_descriptor *desc_org = NULL;
907         int i;
908         struct usb_request *req;
909         /* struct dwc_ute_iso_packet_descriptor * */
910         /* int status = 0; */
911
912         req = (struct usb_request *)req_handle;
913         ereqorg = &req->ext_req;
914         ereqport = (struct dwc_iso_xreq_port *)ereq_port;
915         desc_org = ereqorg->per_io_frame_descs;
916
917         if (req && req->complete) {
918                 /* Copy the request data from the portable logic to our request */
919                 for (i = 0; i < ereqport->pio_pkt_count; i++) {
920                         desc_org[i].actual_length =
921                             ereqport->per_io_frame_descs[i].actual_length;
922                         desc_org[i].status =
923                             ereqport->per_io_frame_descs[i].status;
924                 }
925
926                 switch (status) {
927                 case -DWC_E_SHUTDOWN:
928                         req->status = -ESHUTDOWN;
929                         break;
930                 case -DWC_E_RESTART:
931                         req->status = -ECONNRESET;
932                         break;
933                 case -DWC_E_INVALID:
934                         req->status = -EINVAL;
935                         break;
936                 case -DWC_E_TIMEOUT:
937                         req->status = -ETIMEDOUT;
938                         break;
939                 default:
940                         req->status = status;
941                 }
942
943                 /* And call the gadget's completion */
944                 req->complete(ep_handle, req);
945         }
946
947         return 0;
948 }
949 #endif /* DWC_UTE_PER_IO */
950
951 static int _complete(dwc_otg_pcd_t *pcd, void *ep_handle,
952                      void *req_handle, int32_t status, uint32_t actual)
953 {
954         struct usb_request *req = (struct usb_request *)req_handle;
955         struct dwc_otg_pcd_ep *ep = NULL;
956
957         ep = ep_from_handle(pcd, ep_handle);
958
959         if (GET_CORE_IF(pcd)->dma_enable) {
960                 /* if (req->length != 0) */
961                 if (req->dma != DWC_DMA_ADDR_INVALID) {
962                         dma_unmap_single(gadget_wrapper->gadget.dev.parent,
963                                          req->dma,
964                                          req->length !=
965                                          0 ? req->length : 4,
966                                          ep->dwc_ep.is_in
967                                          ? DMA_TO_DEVICE : DMA_FROM_DEVICE);
968                         req->dma = DWC_DMA_ADDR_INVALID;
969                 }
970         }
971
972         if (req && req->complete) {
973                 switch (status) {
974                 case -DWC_E_SHUTDOWN:
975                         req->status = -ESHUTDOWN;
976                         break;
977                 case -DWC_E_RESTART:
978                         req->status = -ECONNRESET;
979                         break;
980                 case -DWC_E_INVALID:
981                         req->status = -EINVAL;
982                         break;
983                 case -DWC_E_TIMEOUT:
984                         req->status = -ETIMEDOUT;
985                         break;
986                 default:
987                         req->status = status;
988
989                 }
990
991                 req->actual = actual;
992                 DWC_SPINUNLOCK(pcd->lock);
993                 req->complete(ep_handle, req);
994                 DWC_SPINLOCK(pcd->lock);
995         }
996
997
998         return 0;
999 }
1000
1001 static int _connect(dwc_otg_pcd_t *pcd, int speed)
1002 {
1003         gadget_wrapper->gadget.speed = speed;
1004         return 0;
1005 }
1006
1007 static int _disconnect(dwc_otg_pcd_t *pcd)
1008 {
1009         if (gadget_wrapper->driver && gadget_wrapper->driver->disconnect) {
1010                 gadget_wrapper->driver->disconnect(&gadget_wrapper->gadget);
1011         }
1012         return 0;
1013 }
1014
1015 static int _resume(dwc_otg_pcd_t *pcd)
1016 {
1017         if (gadget_wrapper->driver && gadget_wrapper->driver->resume) {
1018                 gadget_wrapper->driver->resume(&gadget_wrapper->gadget);
1019         }
1020
1021         return 0;
1022 }
1023
1024 static int _suspend(dwc_otg_pcd_t *pcd)
1025 {
1026         if (gadget_wrapper->driver && gadget_wrapper->driver->suspend) {
1027                 gadget_wrapper->driver->suspend(&gadget_wrapper->gadget);
1028         }
1029         return 0;
1030 }
1031
1032 /**
1033  * This function updates the otg values in the gadget structure.
1034  */
1035 static int _hnp_changed(dwc_otg_pcd_t *pcd)
1036 {
1037
1038         if (!gadget_wrapper->gadget.is_otg)
1039                 return 0;
1040
1041         gadget_wrapper->gadget.b_hnp_enable = get_b_hnp_enable(pcd);
1042         gadget_wrapper->gadget.a_hnp_support = get_a_hnp_support(pcd);
1043         gadget_wrapper->gadget.a_alt_hnp_support = get_a_alt_hnp_support(pcd);
1044         return 0;
1045 }
1046
1047 static int _reset(dwc_otg_pcd_t *pcd)
1048 {
1049         return 0;
1050 }
1051
1052 #ifdef DWC_UTE_CFI
1053 static int _cfi_setup(dwc_otg_pcd_t *pcd, void *cfi_req)
1054 {
1055         int retval = -DWC_E_INVALID;
1056         if (gadget_wrapper->driver->cfi_feature_setup) {
1057                 retval =
1058                     gadget_wrapper->driver->cfi_feature_setup(&gadget_wrapper->
1059                                                               gadget,
1060                                                               (struct
1061                                                                cfi_usb_ctrlrequest
1062                                                                *)cfi_req);
1063         }
1064
1065         return retval;
1066 }
1067 #endif
1068
1069 static const struct dwc_otg_pcd_function_ops fops = {
1070         .complete = _complete,
1071 #ifdef DWC_EN_ISOC
1072         .isoc_complete = _isoc_complete,
1073 #endif
1074         .setup = _setup,
1075         .disconnect = _disconnect,
1076         .connect = _connect,
1077         .resume = _resume,
1078         .suspend = _suspend,
1079         .hnp_changed = _hnp_changed,
1080         .reset = _reset,
1081 #ifdef DWC_UTE_CFI
1082         .cfi_setup = _cfi_setup,
1083 #endif
1084 #ifdef DWC_UTE_PER_IO
1085         .xisoc_complete = _xisoc_complete,
1086 #endif
1087 };
1088
1089 /**
1090  * This function is the top level PCD interrupt handler.
1091  */
1092 static irqreturn_t dwc_otg_pcd_irq(int irq, void *dev)
1093 {
1094         dwc_otg_pcd_t *pcd = dev;
1095         int32_t retval = IRQ_NONE;
1096
1097         retval = dwc_otg_pcd_handle_intr(pcd);
1098         if (retval != 0) {
1099                 /* S3C2410X_CLEAR_EINTPEND();*/
1100         }
1101         return IRQ_RETVAL(retval);
1102 }
1103
1104 /**
1105  * This function initialized the usb_ep structures to there default
1106  * state.
1107  *
1108  * @param d Pointer on gadget_wrapper.
1109  */
1110 void gadget_add_eps(struct gadget_wrapper *d)
1111 {
1112         static const char *names[] = {
1113
1114                 "ep0",
1115                 "ep1in",
1116                 "ep2in",
1117                 "ep3in",
1118                 "ep4in",
1119                 "ep5in",
1120                 "ep6in",
1121                 "ep7in",
1122                 "ep8in",
1123                 "ep9in",
1124                 "ep10in",
1125                 "ep11in",
1126                 "ep12in",
1127                 "ep13in",
1128                 "ep14in",
1129                 "ep15in",
1130                 "ep1out",
1131                 "ep2out",
1132                 "ep3out",
1133                 "ep4out",
1134                 "ep5out",
1135                 "ep6out",
1136                 "ep7out",
1137                 "ep8out",
1138                 "ep9out",
1139                 "ep10out",
1140                 "ep11out",
1141                 "ep12out",
1142                 "ep13out",
1143                 "ep14out",
1144                 "ep15out"
1145         };
1146
1147         int i;
1148         struct usb_ep *ep;
1149         int8_t dev_endpoints;
1150
1151         DWC_DEBUGPL(DBG_PCDV, "%s\n", __func__);
1152
1153         INIT_LIST_HEAD(&d->gadget.ep_list);
1154         d->gadget.ep0 = &d->ep0;
1155         d->gadget.speed = USB_SPEED_UNKNOWN;
1156 #if LINUX_VERSION_CODE >= KERNEL_VERSION(3, 3, 0)
1157         d->gadget.max_speed = USB_SPEED_HIGH;
1158 #endif
1159
1160         INIT_LIST_HEAD(&d->gadget.ep0->ep_list);
1161
1162         /**
1163          * Initialize the EP0 structure.
1164          */
1165         ep = &d->ep0;
1166
1167         /* Init the usb_ep structure. */
1168         ep->caps.type_control = true;
1169         ep->name = names[0];
1170         ep->ops = (struct usb_ep_ops *)&dwc_otg_pcd_ep_ops;
1171
1172         /**
1173          * @todo NGS: What should the max packet size be set to
1174          * here?  Before EP type is set?
1175          */
1176         usb_ep_set_maxpacket_limit(ep, MAX_EP0_SIZE);
1177         dwc_otg_pcd_ep_enable(d->pcd, NULL, ep);
1178
1179         list_add_tail(&ep->ep_list, &d->gadget.ep_list);
1180
1181         /**
1182          * Initialize the EP structures.
1183          */
1184         dev_endpoints = d->pcd->core_if->dev_if->num_in_eps;
1185
1186         for (i = 0; i < dev_endpoints; i++) {
1187                 ep = &d->in_ep[i];
1188
1189                 /* Init the usb_ep structure. */
1190                 ep->caps.dir_in = true;
1191                 ep->caps.type_iso = true;
1192                 ep->caps.type_bulk = true;
1193                 ep->caps.type_int = true;
1194                 ep->name = names[d->pcd->in_ep[i].dwc_ep.num];
1195                 ep->ops = (struct usb_ep_ops *)&dwc_otg_pcd_ep_ops;
1196
1197                 /**
1198                  * @todo NGS: What should the max packet size be set to
1199                  * here?  Before EP type is set?
1200                  */
1201                 usb_ep_set_maxpacket_limit(ep, MAX_PACKET_SIZE);
1202                 list_add_tail(&ep->ep_list, &d->gadget.ep_list);
1203         }
1204
1205         dev_endpoints = d->pcd->core_if->dev_if->num_out_eps;
1206
1207         for (i = 0; i < dev_endpoints; i++) {
1208                 ep = &d->out_ep[i];
1209
1210                 /* Init the usb_ep structure. */
1211                 ep->caps.dir_out = true;
1212                 ep->caps.type_iso = true;
1213                 ep->caps.type_bulk = true;
1214                 ep->caps.type_int = true;
1215                 ep->name = names[15 + d->pcd->out_ep[i].dwc_ep.num];
1216                 ep->ops = (struct usb_ep_ops *)&dwc_otg_pcd_ep_ops;
1217
1218                 /**
1219                  * @todo NGS: What should the max packet size be set to
1220                  * here?  Before EP type is set?
1221                  */
1222                 usb_ep_set_maxpacket_limit(ep, MAX_PACKET_SIZE);
1223                 list_add_tail(&ep->ep_list, &d->gadget.ep_list);
1224         }
1225
1226         /* remove ep0 from the list.  There is a ep0 pointer. */
1227         list_del_init(&d->ep0.ep_list);
1228
1229         d->ep0.maxpacket = MAX_EP0_SIZE;
1230 }
1231
1232 /**
1233  * This function releases the Gadget device.
1234  * required by device_unregister().
1235  *
1236  * @todo Should this do something?      Should it free the PCD?
1237  */
1238 static void dwc_otg_pcd_gadget_release(struct device *dev)
1239 {
1240         DWC_DEBUGPL(DBG_PCDV, "%s(%p)\n", __func__, dev);
1241 }
1242
1243 static struct gadget_wrapper *alloc_wrapper(struct platform_device *_dev)
1244 {
1245         static char pcd_name[] = "dwc_otg_pcd";
1246
1247         dwc_otg_device_t *otg_dev = dwc_get_device_platform_data(_dev);
1248         struct gadget_wrapper *d;
1249         int retval;
1250
1251         d = DWC_ALLOC(sizeof(*d));
1252         if (d == NULL) {
1253                 return NULL;
1254         }
1255
1256         memset(d, 0, sizeof(*d));
1257
1258         d->gadget.name = pcd_name;
1259         d->pcd = otg_dev->pcd;
1260
1261 #if LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 30)
1262         strcpy(d->gadget.dev.bus_id, "gadget");
1263 #else
1264         dev_set_name(&d->gadget.dev, "%s", "gadget");
1265 #endif
1266
1267         d->gadget.dev.parent = &_dev->dev;
1268         d->gadget.dev.release = dwc_otg_pcd_gadget_release;
1269         d->gadget.ops = &dwc_otg_pcd_ops;
1270 #if LINUX_VERSION_CODE < KERNEL_VERSION(3, 0, 0)
1271         d->gadget.is_dualspeed = dwc_otg_pcd_is_dualspeed(otg_dev->pcd);
1272 #endif
1273         d->gadget.is_otg = dwc_otg_pcd_is_otg(otg_dev->pcd);
1274
1275         d->gadget.max_speed = USB_SPEED_HIGH;
1276         d->driver = 0;
1277         d->pcd->conn_en = 0;
1278         /* Register the gadget device */
1279         retval = usb_add_gadget_udc(&_dev->dev, &d->gadget);
1280         if (retval != 0) {
1281                 DWC_ERROR("device_register failed\n");
1282                 DWC_FREE(d);
1283                 return NULL;
1284         }
1285
1286         return d;
1287 }
1288
1289 static void free_wrapper(struct gadget_wrapper *d)
1290 {
1291         if (d->driver) {
1292                 /* should have been done already by driver model core */
1293                 DWC_WARN("driver '%s' is still registered\n",
1294                          d->driver->driver.name);
1295                 usb_gadget_unregister_driver(d->driver);
1296         }
1297
1298         usb_del_gadget_udc(&d->gadget);
1299         DWC_FREE(d);
1300 }
1301
1302 static void dwc_otg_pcd_work_init(dwc_otg_pcd_t *pcd,
1303                                   struct platform_device *dev);
1304
1305 /**
1306  * This function initialized the PCD portion of the driver.
1307  *
1308  */
1309 int pcd_init(struct platform_device *_dev)
1310 {
1311
1312         dwc_otg_device_t *otg_dev = dwc_get_device_platform_data(_dev);
1313
1314         int retval = 0;
1315         int irq;
1316         DWC_DEBUGPL(DBG_PCDV, "%s(%p)\n", __func__, _dev);
1317
1318         otg_dev->pcd = dwc_otg_pcd_init(otg_dev->core_if);
1319         printk("pcd_init otg_dev = %p\n", otg_dev);
1320
1321         if (!otg_dev->pcd) {
1322                 DWC_ERROR("dwc_otg_pcd_init failed\n");
1323                 return -ENOMEM;
1324         }
1325
1326         otg_dev->pcd->otg_dev = otg_dev;
1327         gadget_wrapper = alloc_wrapper(_dev);
1328
1329         /*
1330          * Initialize EP structures
1331          */
1332         gadget_add_eps(gadget_wrapper);
1333         /*
1334          * Setup interupt handler
1335          */
1336         irq = platform_get_irq(_dev, 0);
1337         DWC_DEBUGPL(DBG_ANY, "registering handler for irq%d\n", irq);
1338         retval = request_irq(irq, dwc_otg_pcd_irq,
1339                              IRQF_SHARED,
1340                              gadget_wrapper->gadget.name, otg_dev->pcd);
1341         if (retval != 0) {
1342                 DWC_ERROR("request of irq%d failed\n", irq);
1343                 free_wrapper(gadget_wrapper);
1344                 return -EBUSY;
1345         }
1346
1347         dwc_otg_pcd_start(gadget_wrapper->pcd, &fops);
1348
1349         dwc_otg_pcd_work_init(otg_dev->pcd, _dev);
1350
1351         return retval;
1352 }
1353
1354 /**
1355  * Cleanup the PCD.
1356  */
1357 void pcd_remove(struct platform_device *_dev)
1358 {
1359
1360         dwc_otg_device_t *otg_dev = dwc_get_device_platform_data(_dev);
1361         dwc_otg_pcd_t *pcd = otg_dev->pcd;
1362         int irq;
1363
1364         DWC_DEBUGPL(DBG_PCDV, "%s(%p)\n", __func__, _dev);
1365
1366         /*
1367          * Free the IRQ
1368          */
1369         irq = platform_get_irq(_dev, 0);
1370         free_irq(irq, pcd);
1371         free_wrapper(gadget_wrapper);
1372         dwc_otg_pcd_remove(otg_dev->pcd);
1373         otg_dev->pcd = 0;
1374 }
1375
1376 /**
1377  * This function registers a gadget driver with the PCD.
1378  *
1379  * When a driver is successfully registered, it will receive control
1380  * requests including set_configuration(), which enables non-control
1381  * requests.  then usb traffic follows until a disconnect is reported.
1382  * then a host may connect again, or the driver might get unbound.
1383  *
1384  * @param driver The driver being registered
1385  * @param bind The bind function of gadget driver
1386  */
1387 #if 0
1388 #if LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 37)
1389 int usb_gadget_register_driver(struct usb_gadget_driver *driver)
1390 #else
1391 int usb_gadget_probe_driver(struct usb_gadget_driver *driver,
1392                             int (*bind) (struct usb_gadget *))
1393 #endif
1394 {
1395         int retval;
1396
1397         DWC_DEBUGPL(DBG_PCD, "registering gadget driver '%s'\n",
1398                     driver->driver.name);
1399
1400         if (!driver ||
1401 #if LINUX_VERSION_CODE < KERNEL_VERSION(3, 3, 0)
1402             driver->speed == USB_SPEED_UNKNOWN ||
1403 #else
1404             driver->max_speed == USB_SPEED_UNKNOWN ||
1405 #endif
1406 #if LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 37)
1407             !driver->bind ||
1408 #else
1409             !bind ||
1410 #endif
1411             !driver->unbind || !driver->disconnect || !driver->setup) {
1412                 DWC_DEBUGPL(DBG_PCDV, "EINVAL\n");
1413                 return -EINVAL;
1414         }
1415         if (gadget_wrapper == 0) {
1416                 DWC_DEBUGPL(DBG_PCDV, "ENODEV\n");
1417                 return -ENODEV;
1418         }
1419         if (gadget_wrapper->driver != 0) {
1420                 DWC_DEBUGPL(DBG_PCDV, "EBUSY (%p)\n", gadget_wrapper->driver);
1421                 return -EBUSY;
1422         }
1423
1424         /* hook up the driver */
1425         gadget_wrapper->driver = driver;
1426         gadget_wrapper->gadget.dev.driver = &driver->driver;
1427
1428         DWC_DEBUGPL(DBG_PCD, "bind to driver %s\n", driver->driver.name);
1429 #if LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 37)
1430         retval = driver->bind(&gadget_wrapper->gadget);
1431 #else
1432         retval = bind(&gadget_wrapper->gadget);
1433 #endif
1434         if (retval) {
1435                 DWC_ERROR("bind to driver %s --> error %d\n",
1436                           driver->driver.name, retval);
1437                 gadget_wrapper->driver = 0;
1438                 gadget_wrapper->gadget.dev.driver = 0;
1439                 return retval;
1440         }
1441         DWC_DEBUGPL(DBG_ANY, "registered gadget driver '%s'\n",
1442                     driver->driver.name);
1443         return 0;
1444 }
1445
1446 #if LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 37)
1447 EXPORT_SYMBOL(usb_gadget_register_driver);
1448 #else
1449 EXPORT_SYMBOL(usb_gadget_probe_driver);
1450 #endif
1451
1452 /**
1453  * This function unregisters a gadget driver
1454  *
1455  * @param driver The driver being unregistered
1456  */
1457 int usb_gadget_unregister_driver(struct usb_gadget_driver *driver)
1458 {
1459         /* DWC_DEBUGPL(DBG_PCDV,"%s(%p)\n", __func__, _driver); */
1460
1461         if (gadget_wrapper == 0) {
1462                 DWC_DEBUGPL(DBG_ANY, "%s Return(%d): s_pcd==0\n", __func__,
1463                             -ENODEV);
1464                 return -ENODEV;
1465         }
1466         if (driver == 0 || driver != gadget_wrapper->driver) {
1467                 DWC_DEBUGPL(DBG_ANY, "%s Return(%d): driver?\n", __func__,
1468                             -EINVAL);
1469                 return -EINVAL;
1470         }
1471
1472         driver->unbind(&gadget_wrapper->gadget);
1473         gadget_wrapper->driver = 0;
1474
1475         DWC_DEBUGPL(DBG_ANY, "unregistered driver '%s'\n", driver->driver.name);
1476         return 0;
1477 }
1478
1479 EXPORT_SYMBOL(usb_gadget_unregister_driver);
1480
1481 #endif
1482
1483 /************************ for RK platform ************************/
1484
1485 void dwc_otg_msc_lock(dwc_otg_pcd_t *pcd)
1486 {
1487         unsigned long flags;
1488         local_irq_save(flags);
1489         wake_lock(&pcd->wake_lock);
1490         local_irq_restore(flags);
1491 }
1492
1493 void dwc_otg_msc_unlock(dwc_otg_pcd_t *pcd)
1494 {
1495         unsigned long flags;
1496         local_irq_save(flags);
1497         wake_unlock(&pcd->wake_lock);
1498         local_irq_restore(flags);
1499 }
1500
1501 unsigned int dwc_otg_battery_detect(bool det_type)
1502 {
1503         printk("%s\n", __func__);
1504         return 0;
1505 }
1506
1507 static void dwc_phy_reconnect(struct work_struct *work)
1508 {
1509         dwc_otg_pcd_t *pcd;
1510         dwc_otg_core_if_t *core_if;
1511         gotgctl_data_t gctrl;
1512         dctl_data_t dctl = {.d32 = 0 };
1513         struct dwc_otg_platform_data *pldata;
1514
1515         pcd = container_of(work, dwc_otg_pcd_t, reconnect.work);
1516         pldata = pcd->otg_dev->pldata;
1517         core_if = GET_CORE_IF(pcd);
1518         gctrl.d32 = DWC_READ_REG32(&core_if->core_global_regs->gotgctl);
1519
1520         if (gctrl.b.bsesvld) {
1521                 pcd->conn_status++;
1522                 pldata->soft_reset(pldata, RST_RECNT);
1523                 dwc_pcd_reset(pcd);
1524                 /*
1525                  * Enable the global interrupt after all the interrupt
1526                  * handlers are installed.
1527                  */
1528                 dctl.d32 =
1529                     DWC_READ_REG32(&core_if->dev_if->dev_global_regs->dctl);
1530                 dctl.b.sftdiscon = 0;
1531                 DWC_WRITE_REG32(&core_if->dev_if->dev_global_regs->dctl,
1532                                 dctl.d32);
1533                 printk
1534                     ("*******************soft connect!!!*******************\n");
1535         }
1536 }
1537
1538 static void id_status_change(dwc_otg_core_if_t *p, bool current_id)
1539 {
1540         dwc_otg_core_if_t *core_if = p;
1541         uint32_t count = 0;
1542         gotgctl_data_t gotgctl = {.d32 = 0 };
1543         dwc_otg_pcd_t *pcd = core_if->otg_dev->pcd;
1544
1545         gotgctl.d32 = DWC_READ_REG32(&core_if->core_global_regs->gotgctl);
1546         DWC_DEBUGPL(DBG_CIL, "gotgctl=%0x\n", gotgctl.d32);
1547         DWC_DEBUGPL(DBG_CIL, "gotgctl.b.conidsts=%d\n", gotgctl.b.conidsts);
1548
1549         if (core_if->usb_mode != USB_MODE_NORMAL)
1550                 return;
1551
1552         /* B-Device connector (Device Mode) */
1553         if (current_id) {
1554                 gotgctl_data_t gotgctl_local;
1555                 /* Wait for switch to device mode. */
1556                 while (!dwc_otg_is_device_mode(core_if)) {
1557                         gotgctl_local.d32 =
1558                             DWC_READ_REG32(&core_if->core_global_regs->gotgctl);
1559                         DWC_DEBUGPL(DBG_ANY,
1560                                     "Waiting for Peripheral Mode, Mode=%s count = %d gotgctl=%08x\n",
1561                                     (dwc_otg_is_host_mode(core_if) ? "Host" :
1562                                      "Peripheral"), count, gotgctl_local.d32);
1563                         dwc_mdelay(1);
1564                         if (++count > 200)
1565                                 break;
1566                 }
1567                 if (count >= 200) {
1568                         DWC_PRINTF("Connection id status change timed out");
1569                         return;
1570                 }
1571                 dwc_otg_set_force_mode(core_if, USB_MODE_FORCE_DEVICE);
1572                 core_if->op_state = B_PERIPHERAL;
1573                 cil_hcd_stop(core_if);
1574                 /* pcd->phy_suspend = 1; */
1575                 pcd->vbus_status = 0;
1576                 dwc_otg_core_init(core_if);
1577                 cil_pcd_start(core_if);
1578                 dwc_otg_pcd_start_check_vbus_work(pcd);
1579         } else {
1580                 /* A-Device connector (Host Mode) */
1581                 while (!dwc_otg_is_host_mode(core_if)) {
1582                         DWC_DEBUGPL(DBG_ANY, "Waiting for Host Mode, Mode=%s\n",
1583                                     (dwc_otg_is_host_mode(core_if) ? "Host" :
1584                                      "Peripheral"));
1585                         dwc_mdelay(1);  /* vahrama previously was 100 */
1586                         if (++count > 200)
1587                                 break;
1588                 }
1589                 if (count >= 200) {
1590                         DWC_PRINTF("Connection id status change timed out");
1591                         return;
1592                 }
1593
1594                 core_if->op_state = A_HOST;
1595                 dwc_otg_set_force_mode(core_if, USB_MODE_FORCE_HOST);
1596
1597                 cancel_delayed_work_sync(&pcd->check_vbus_work);
1598
1599                 /*
1600                  * Initialize the Core for Host mode.
1601                  */
1602                 dwc_otg_core_init(core_if);
1603                 cil_hcd_start(core_if);
1604                 dwc_otg_enable_global_interrupts(core_if);
1605         }
1606 }
1607
1608
1609 static void check_id(struct work_struct *work)
1610 {
1611         dwc_otg_pcd_t *_pcd =
1612             container_of(work, dwc_otg_pcd_t, check_id_work.work);
1613         struct dwc_otg_device *otg_dev = _pcd->otg_dev;
1614         struct dwc_otg_platform_data *pldata = otg_dev->pldata;
1615         static int last_id = -1;
1616         int id = pldata->get_status(USB_STATUS_ID);
1617
1618         if (last_id != id) {
1619                 pr_info("[otg id chg] last id %d current id %d\n", last_id, id);
1620
1621                 if (pldata->phy_status == USB_PHY_SUSPEND) {
1622                         pldata->clock_enable(pldata, 1);
1623                         pldata->phy_suspend(pldata, USB_PHY_ENABLED);
1624                 }
1625
1626                 /* Force Device or Host by id */
1627                 id_status_change(otg_dev->core_if, id);
1628         }
1629         last_id = id;
1630         schedule_delayed_work(&_pcd->check_id_work, (HZ));
1631 }
1632
1633 static void dwc_otg_pcd_check_vbus_work(struct work_struct *work)
1634 {
1635         dwc_otg_pcd_t *_pcd =
1636             container_of(work, dwc_otg_pcd_t, check_vbus_work.work);
1637         struct dwc_otg_device *otg_dev = _pcd->otg_dev;
1638         struct dwc_otg_platform_data *pldata = otg_dev->pldata;
1639
1640         if (pldata->get_status(USB_STATUS_BVABLID) &&
1641             pldata->get_status(USB_STATUS_ID)) {
1642                 /* if usb not connect before ,then start connect */
1643                 if (_pcd->vbus_status == USB_BC_TYPE_DISCNT) {
1644                         printk("***************vbus detect*****************\n");
1645                         if( pldata->bc_detect_cb != NULL )
1646                                 pldata->bc_detect_cb(_pcd->vbus_status =
1647                                         usb_battery_charger_detect(1));
1648                         else
1649                                 _pcd->vbus_status = USB_BC_TYPE_SDP;
1650                         if (_pcd->conn_en) {
1651                                 goto connect;
1652                         } else if (pldata->phy_status == USB_PHY_ENABLED) {
1653                                 /* do not allow to connect, suspend phy */
1654                                 pldata->phy_suspend(pldata, USB_PHY_SUSPEND);
1655                                 udelay(3);
1656                                 pldata->clock_enable(pldata, 0);
1657                         }
1658                 } else if ((_pcd->conn_en) && (_pcd->conn_status >= 0)
1659                            && (_pcd->conn_status < 2)) {
1660                         printk("**************soft reconnect**************\n");
1661                         goto connect;
1662                 } else if (_pcd->conn_status == 2) {
1663                         /* release pcd->wake_lock if fail to connect,
1664                          * allow system to enter second sleep.
1665                          */
1666                         dwc_otg_msc_unlock(_pcd);
1667                         _pcd->conn_status++;
1668                         if (pldata->bc_detect_cb != NULL) {
1669                                 pldata->bc_detect_cb(_pcd->vbus_status =
1670                                                      usb_battery_charger_detect(1));
1671                         } else {
1672                                 _pcd->vbus_status = USB_BC_TYPE_DCP;
1673                         }
1674                         /* fail to connect, suspend usb phy and disable clk */
1675                         if (pldata->phy_status == USB_PHY_ENABLED) {
1676                                 pldata->phy_suspend(pldata, USB_PHY_SUSPEND);
1677                                 udelay(3);
1678                                 pldata->clock_enable(pldata, 0);
1679                         }
1680                 }
1681         } else {
1682                 if (pldata->bc_detect_cb != NULL)
1683                         pldata->bc_detect_cb(_pcd->vbus_status =
1684                                              usb_battery_charger_detect(0));
1685                 else
1686                         _pcd->vbus_status = USB_BC_TYPE_DISCNT;
1687
1688                 if (_pcd->conn_status) {
1689                         _pcd->conn_status = 0;
1690                 }
1691
1692                 if (pldata->phy_status == USB_PHY_ENABLED) {
1693                         /* release wake lock */
1694                         dwc_otg_msc_unlock(_pcd);
1695                         if (pldata->get_status(USB_STATUS_ID)) {
1696                                 /* no vbus detect here , close usb phy  */
1697                                 pldata->phy_suspend(pldata, USB_PHY_SUSPEND);
1698                                 udelay(3);
1699                                 pldata->clock_enable(pldata, 0);
1700                         }
1701                 }
1702
1703                 /* usb phy bypass to uart mode  */
1704                 if (pldata->dwc_otg_uart_mode != NULL)
1705                         pldata->dwc_otg_uart_mode(pldata, PHY_UART_MODE);
1706         }
1707
1708         if (pldata->get_status(USB_STATUS_ID))
1709                 schedule_delayed_work(&_pcd->check_vbus_work, HZ);
1710         return;
1711
1712 connect:
1713         if (pldata->phy_status) {
1714                 pldata->clock_enable(pldata, 1);
1715                 pldata->phy_suspend(pldata, USB_PHY_ENABLED);
1716         }
1717
1718         if (_pcd->conn_status == 0)
1719                 dwc_otg_msc_lock(_pcd);
1720
1721         schedule_delayed_work(&_pcd->reconnect, 8);     /* delay 8 jiffies */
1722         schedule_delayed_work(&_pcd->check_vbus_work, (HZ));
1723         return;
1724 }
1725
1726 void dwc_otg_pcd_start_check_vbus_work(dwc_otg_pcd_t *pcd)
1727 {
1728         /*
1729          * when receive reset int,the vbus state may not be update,so
1730          * always start vbus work here.
1731          */
1732         schedule_delayed_work(&pcd->check_vbus_work, HZ/2);
1733
1734 }
1735
1736 /*
1737 * 20091228,HSL@RK,to get the current vbus status.
1738 */
1739 int dwc_vbus_status(void)
1740 {
1741 #ifdef CONFIG_USB20_OTG
1742         dwc_otg_pcd_t *pcd = 0;
1743         if (gadget_wrapper) {
1744                 pcd = gadget_wrapper->pcd;
1745         }
1746
1747         if (!pcd)
1748                 return 0;
1749         else
1750                 return pcd->vbus_status;
1751 #else
1752         return 0;
1753 #endif
1754 }
1755
1756 EXPORT_SYMBOL(dwc_vbus_status);
1757
1758 static void dwc_otg_pcd_work_init(dwc_otg_pcd_t *pcd,
1759                                   struct platform_device *dev)
1760 {
1761
1762         struct dwc_otg_device *otg_dev = pcd->otg_dev;
1763         struct dwc_otg_platform_data *pldata = otg_dev->pldata;
1764
1765         pcd->vbus_status = USB_BC_TYPE_DISCNT;
1766         pcd->phy_suspend = USB_PHY_ENABLED;
1767
1768         INIT_DELAYED_WORK(&pcd->reconnect, dwc_phy_reconnect);
1769         INIT_DELAYED_WORK(&pcd->check_vbus_work, dwc_otg_pcd_check_vbus_work);
1770         INIT_DELAYED_WORK(&pcd->check_id_work, check_id);
1771
1772         wake_lock_init(&pcd->wake_lock, WAKE_LOCK_SUSPEND, "usb_pcd");
1773
1774         if (dwc_otg_is_device_mode(pcd->core_if) &&
1775             (otg_dev->core_if->usb_mode != USB_MODE_FORCE_HOST)) {
1776                 if (pldata->get_status(USB_STATUS_BVABLID)) {
1777                         /* enter usb phy mode */
1778                         pldata->dwc_otg_uart_mode(pldata, PHY_USB_MODE);
1779                 } else {
1780                         /* usb phy bypass to uart mode */
1781                         pldata->dwc_otg_uart_mode(pldata, PHY_UART_MODE);
1782                 }
1783         } else if (pldata->dwc_otg_uart_mode != NULL) {
1784                 /* host mode,enter usb phy mode */
1785                 pldata->dwc_otg_uart_mode(pldata, PHY_USB_MODE);
1786         }
1787         schedule_delayed_work(&pcd->check_id_work, 8 * HZ);
1788         if (otg_dev->core_if->usb_mode == USB_MODE_FORCE_DEVICE) {
1789                 pcd->vbus_status = 0;
1790                 dwc_otg_core_init(otg_dev->core_if);
1791                 cil_pcd_start(otg_dev->core_if);
1792                 dwc_otg_pcd_start_check_vbus_work(pcd);
1793         }
1794 }
1795
1796 #endif /* DWC_HOST_ONLY */