]> code.ossystems Code Review - openembedded-core.git/blob
40eecf646bbb5b938b015f5cd9f1227b9487e8e2
[openembedded-core.git] /
1 From f12c49e8bf1ac056946bc3098c6c361d51891916 Mon Sep 17 00:00:00 2001
2 From: Henry Yuan <hang.yuan@intel.com>
3 Date: Thu, 6 May 2010 19:30:00 +0800
4 Subject: [PATCH] Moorestown USB-OTG drivers full patch 0.2 for MeeGo
5
6 This is a consolidated full patch against K2.6.33. It
7 includes USB-OTG client controller driver, transceiver
8 driver, still image gadget driver and fixing for sighting
9 3469616: OTG driver hangs in suspend function.
10
11 OTG host, client functions and role switch per cable
12 plugged are tested.
13 Known issue: HNP/SRP have problem.
14
15 Kernel config:
16 CONFIG_USB_LANGWELL_OTG = y
17 CONFIG_USB_OTG_WHITELIST = n
18 CONFIG_USB_GADGET = y
19 CONFIG_USB_GADGET_LANGWELL = y
20
21 CONFIG_USB_STILL_IMAGE = y
22 or select other gadget driver as needed.
23
24 Signed-off-by: Henry Yuan <hang.yuan@intel.com>
25 Patch-mainline: 2.6.34
26 ---
27  drivers/usb/gadget/Kconfig        |    8 +
28  drivers/usb/gadget/Makefile       |    2 +
29  drivers/usb/gadget/f_ecm.c        |   22 +
30  drivers/usb/gadget/f_subset.c     |   22 +
31  drivers/usb/gadget/langwell_udc.c |  582 ++++--
32  drivers/usb/gadget/langwell_udc.h |   13 +-
33  drivers/usb/gadget/still_image.c  | 4566 +++++++++++++++++++++++++++++++++++++
34  drivers/usb/otg/Kconfig           |   14 +
35  drivers/usb/otg/Makefile          |    1 +
36  drivers/usb/otg/langwell_otg.c    | 2260 ++++++++++++++++++
37  include/linux/usb/langwell_otg.h  |  201 ++
38  include/linux/usb/langwell_udc.h  |   13 +
39  12 files changed, 7516 insertions(+), 188 deletions(-)
40  create mode 100644 drivers/usb/gadget/still_image.c
41  create mode 100644 drivers/usb/otg/langwell_otg.c
42  create mode 100644 include/linux/usb/langwell_otg.h
43
44 diff --git a/drivers/usb/gadget/Kconfig b/drivers/usb/gadget/Kconfig
45 index ee41120..94cc94f 100644
46 --- a/drivers/usb/gadget/Kconfig
47 +++ b/drivers/usb/gadget/Kconfig
48 @@ -853,6 +853,14 @@ config USB_G_MULTI_CDC
49  
50           If unsure, say "y".
51  
52 +config USB_STILL_IMAGE
53 +       tristate "Lite Still Image Gadget"
54 +       help
55 +         The Lite Still Image Gadget implements object transfer based on
56 +         spec PIMA 15740:2000.
57 +
58 +         Say "y" to link the driver statically, or "m" to build a dynamically
59 +         linked module called "g_still_image".
60  
61  # put drivers that need isochronous transfer support (for audio
62  # or video class gadget drivers), or specific hardware, here.
63 diff --git a/drivers/usb/gadget/Makefile b/drivers/usb/gadget/Makefile
64 index 2e2c047..7ef974e 100644
65 --- a/drivers/usb/gadget/Makefile
66 +++ b/drivers/usb/gadget/Makefile
67 @@ -43,6 +43,7 @@ g_mass_storage-objs           := mass_storage.o
68  g_printer-objs                 := printer.o
69  g_cdc-objs                     := cdc2.o
70  g_multi-objs                   := multi.o
71 +g_still_image-objs             := still_image.o
72  
73  obj-$(CONFIG_USB_ZERO)         += g_zero.o
74  obj-$(CONFIG_USB_AUDIO)                += g_audio.o
75 @@ -55,4 +56,5 @@ obj-$(CONFIG_USB_G_PRINTER)   += g_printer.o
76  obj-$(CONFIG_USB_MIDI_GADGET)  += g_midi.o
77  obj-$(CONFIG_USB_CDC_COMPOSITE) += g_cdc.o
78  obj-$(CONFIG_USB_G_MULTI)      += g_multi.o
79 +obj-$(CONFIG_USB_STILL_IMAGE)  += g_still_image.o
80  
81 diff --git a/drivers/usb/gadget/f_ecm.c b/drivers/usb/gadget/f_ecm.c
82 index ecf5bdd..d004328 100644
83 --- a/drivers/usb/gadget/f_ecm.c
84 +++ b/drivers/usb/gadget/f_ecm.c
85 @@ -753,6 +753,26 @@ ecm_unbind(struct usb_configuration *c, struct usb_function *f)
86         kfree(ecm);
87  }
88  
89 +static void
90 +ecm_suspend(struct usb_function *f)
91 +{
92 +       struct f_ecm    *ecm = func_to_ecm(f);
93 +       struct eth_dev  *dev = ecm->port.ioport;
94 +
95 +       if (dev)
96 +               gether_disconnect(&ecm->port);
97 +}
98 +
99 +static void
100 +ecm_resume(struct usb_function *f)
101 +{
102 +       struct f_ecm    *ecm = func_to_ecm(f);
103 +       struct eth_dev  *dev = ecm->port.ioport;
104 +
105 +       if (!dev)
106 +               gether_connect(&ecm->port);
107 +}
108 +
109  /**
110   * ecm_bind_config - add CDC Ethernet network link to a configuration
111   * @c: the configuration to support the network link
112 @@ -821,6 +841,8 @@ int __init ecm_bind_config(struct usb_configuration *c, u8 ethaddr[ETH_ALEN])
113         ecm->port.func.get_alt = ecm_get_alt;
114         ecm->port.func.setup = ecm_setup;
115         ecm->port.func.disable = ecm_disable;
116 +       ecm->port.func.suspend = ecm_suspend;
117 +       ecm->port.func.resume = ecm_resume;
118  
119         status = usb_add_function(c, &ecm->port.func);
120         if (status) {
121 diff --git a/drivers/usb/gadget/f_subset.c b/drivers/usb/gadget/f_subset.c
122 index a9c98fd..893816d 100644
123 --- a/drivers/usb/gadget/f_subset.c
124 +++ b/drivers/usb/gadget/f_subset.c
125 @@ -353,6 +353,26 @@ geth_unbind(struct usb_configuration *c, struct usb_function *f)
126         kfree(func_to_geth(f));
127  }
128  
129 +static void
130 +geth_suspend(struct usb_function *f)
131 +{
132 +       struct f_gether *geth = func_to_geth(f);
133 +       struct eth_dev  *dev = geth->port.ioport;
134 +
135 +       if (dev)
136 +               gether_disconnect(&geth->port);
137 +}
138 +
139 +static void
140 +geth_resume(struct usb_function *f)
141 +{
142 +       struct f_gether *geth = func_to_geth(f);
143 +       struct eth_dev  *dev = geth->port.ioport;
144 +
145 +       if (!dev)
146 +               gether_connect(&geth->port);
147 +}
148 +
149  /**
150   * geth_bind_config - add CDC Subset network link to a configuration
151   * @c: the configuration to support the network link
152 @@ -411,6 +431,8 @@ int __init geth_bind_config(struct usb_configuration *c, u8 ethaddr[ETH_ALEN])
153         geth->port.func.unbind = geth_unbind;
154         geth->port.func.set_alt = geth_set_alt;
155         geth->port.func.disable = geth_disable;
156 +       geth->port.func.resume = geth_resume;
157 +       geth->port.func.suspend = geth_suspend;
158  
159         status = usb_add_function(c, &geth->port.func);
160         if (status) {
161 diff --git a/drivers/usb/gadget/langwell_udc.c b/drivers/usb/gadget/langwell_udc.c
162 index a391351..eb0e185 100644
163 --- a/drivers/usb/gadget/langwell_udc.c
164 +++ b/drivers/usb/gadget/langwell_udc.c
165 @@ -54,7 +54,7 @@
166  
167  
168  #define        DRIVER_DESC             "Intel Langwell USB Device Controller driver"
169 -#define        DRIVER_VERSION          "16 May 2009"
170 +#define        DRIVER_VERSION          "Apr 30, 2010"
171  
172  static const char driver_name[] = "langwell_udc";
173  static const char driver_desc[] = DRIVER_DESC;
174 @@ -73,7 +73,6 @@ langwell_ep0_desc = {
175         .wMaxPacketSize =       EP0_MAX_PKT_SIZE,
176  };
177  
178 -
179  /*-------------------------------------------------------------------------*/
180  /* debugging */
181  
182 @@ -114,104 +113,76 @@ static inline void print_all_registers(struct langwell_udc *dev)
183         int     i;
184  
185         /* Capability Registers */
186 -       printk(KERN_DEBUG "Capability Registers (offset: "
187 -                       "0x%04x, length: 0x%08x)\n",
188 -                       CAP_REG_OFFSET,
189 -                       (u32)sizeof(struct langwell_cap_regs));
190 -       printk(KERN_DEBUG "caplength=0x%02x\n",
191 -                       readb(&dev->cap_regs->caplength));
192 -       printk(KERN_DEBUG "hciversion=0x%04x\n",
193 -                       readw(&dev->cap_regs->hciversion));
194 -       printk(KERN_DEBUG "hcsparams=0x%08x\n",
195 -                       readl(&dev->cap_regs->hcsparams));
196 -       printk(KERN_DEBUG "hccparams=0x%08x\n",
197 -                       readl(&dev->cap_regs->hccparams));
198 -       printk(KERN_DEBUG "dciversion=0x%04x\n",
199 -                       readw(&dev->cap_regs->dciversion));
200 -       printk(KERN_DEBUG "dccparams=0x%08x\n",
201 -                       readl(&dev->cap_regs->dccparams));
202 +       DBG(dev, "Capability Registers (offset: 0x%04x, length: 0x%08x)\n",
203 +                       CAP_REG_OFFSET, (u32)sizeof(struct langwell_cap_regs));
204 +       DBG(dev, "caplength=0x%02x\n", readb(&dev->cap_regs->caplength));
205 +       DBG(dev, "hciversion=0x%04x\n", readw(&dev->cap_regs->hciversion));
206 +       DBG(dev, "hcsparams=0x%08x\n", readl(&dev->cap_regs->hcsparams));
207 +       DBG(dev, "hccparams=0x%08x\n", readl(&dev->cap_regs->hccparams));
208 +       DBG(dev, "dciversion=0x%04x\n", readw(&dev->cap_regs->dciversion));
209 +       DBG(dev, "dccparams=0x%08x\n", readl(&dev->cap_regs->dccparams));
210  
211         /* Operational Registers */
212 -       printk(KERN_DEBUG "Operational Registers (offset: "
213 -                       "0x%04x, length: 0x%08x)\n",
214 -                       OP_REG_OFFSET,
215 -                       (u32)sizeof(struct langwell_op_regs));
216 -       printk(KERN_DEBUG "extsts=0x%08x\n",
217 -                       readl(&dev->op_regs->extsts));
218 -       printk(KERN_DEBUG "extintr=0x%08x\n",
219 -                       readl(&dev->op_regs->extintr));
220 -       printk(KERN_DEBUG "usbcmd=0x%08x\n",
221 -                       readl(&dev->op_regs->usbcmd));
222 -       printk(KERN_DEBUG "usbsts=0x%08x\n",
223 -                       readl(&dev->op_regs->usbsts));
224 -       printk(KERN_DEBUG "usbintr=0x%08x\n",
225 -                       readl(&dev->op_regs->usbintr));
226 -       printk(KERN_DEBUG "frindex=0x%08x\n",
227 -                       readl(&dev->op_regs->frindex));
228 -       printk(KERN_DEBUG "ctrldssegment=0x%08x\n",
229 +       DBG(dev, "Operational Registers (offset: 0x%04x, length: 0x%08x)\n",
230 +                       OP_REG_OFFSET, (u32)sizeof(struct langwell_op_regs));
231 +       DBG(dev, "extsts=0x%08x\n", readl(&dev->op_regs->extsts));
232 +       DBG(dev, "extintr=0x%08x\n", readl(&dev->op_regs->extintr));
233 +       DBG(dev, "usbcmd=0x%08x\n", readl(&dev->op_regs->usbcmd));
234 +       DBG(dev, "usbsts=0x%08x\n", readl(&dev->op_regs->usbsts));
235 +       DBG(dev, "usbintr=0x%08x\n", readl(&dev->op_regs->usbintr));
236 +       DBG(dev, "frindex=0x%08x\n", readl(&dev->op_regs->frindex));
237 +       DBG(dev, "ctrldssegment=0x%08x\n",
238                         readl(&dev->op_regs->ctrldssegment));
239 -       printk(KERN_DEBUG "deviceaddr=0x%08x\n",
240 -                       readl(&dev->op_regs->deviceaddr));
241 -       printk(KERN_DEBUG "endpointlistaddr=0x%08x\n",
242 +       DBG(dev, "deviceaddr=0x%08x\n", readl(&dev->op_regs->deviceaddr));
243 +       DBG(dev, "endpointlistaddr=0x%08x\n",
244                         readl(&dev->op_regs->endpointlistaddr));
245 -       printk(KERN_DEBUG "ttctrl=0x%08x\n",
246 -                       readl(&dev->op_regs->ttctrl));
247 -       printk(KERN_DEBUG "burstsize=0x%08x\n",
248 -                       readl(&dev->op_regs->burstsize));
249 -       printk(KERN_DEBUG "txfilltuning=0x%08x\n",
250 -                       readl(&dev->op_regs->txfilltuning));
251 -       printk(KERN_DEBUG "txttfilltuning=0x%08x\n",
252 +       DBG(dev, "ttctrl=0x%08x\n", readl(&dev->op_regs->ttctrl));
253 +       DBG(dev, "burstsize=0x%08x\n", readl(&dev->op_regs->burstsize));
254 +       DBG(dev, "txfilltuning=0x%08x\n", readl(&dev->op_regs->txfilltuning));
255 +       DBG(dev, "txttfilltuning=0x%08x\n",
256                         readl(&dev->op_regs->txttfilltuning));
257 -       printk(KERN_DEBUG "ic_usb=0x%08x\n",
258 -                       readl(&dev->op_regs->ic_usb));
259 -       printk(KERN_DEBUG "ulpi_viewport=0x%08x\n",
260 +       DBG(dev, "ic_usb=0x%08x\n", readl(&dev->op_regs->ic_usb));
261 +       DBG(dev, "ulpi_viewport=0x%08x\n",
262                         readl(&dev->op_regs->ulpi_viewport));
263 -       printk(KERN_DEBUG "configflag=0x%08x\n",
264 -                       readl(&dev->op_regs->configflag));
265 -       printk(KERN_DEBUG "portsc1=0x%08x\n",
266 -                       readl(&dev->op_regs->portsc1));
267 -       printk(KERN_DEBUG "devlc=0x%08x\n",
268 -                       readl(&dev->op_regs->devlc));
269 -       printk(KERN_DEBUG "otgsc=0x%08x\n",
270 -                       readl(&dev->op_regs->otgsc));
271 -       printk(KERN_DEBUG "usbmode=0x%08x\n",
272 -                       readl(&dev->op_regs->usbmode));
273 -       printk(KERN_DEBUG "endptnak=0x%08x\n",
274 -                       readl(&dev->op_regs->endptnak));
275 -       printk(KERN_DEBUG "endptnaken=0x%08x\n",
276 -                       readl(&dev->op_regs->endptnaken));
277 -       printk(KERN_DEBUG "endptsetupstat=0x%08x\n",
278 +       DBG(dev, "configflag=0x%08x\n", readl(&dev->op_regs->configflag));
279 +       DBG(dev, "portsc1=0x%08x\n", readl(&dev->op_regs->portsc1));
280 +       DBG(dev, "devlc=0x%08x\n", readl(&dev->op_regs->devlc));
281 +       DBG(dev, "otgsc=0x%08x\n", readl(&dev->op_regs->otgsc));
282 +       DBG(dev, "usbmode=0x%08x\n", readl(&dev->op_regs->usbmode));
283 +       DBG(dev, "endptnak=0x%08x\n", readl(&dev->op_regs->endptnak));
284 +       DBG(dev, "endptnaken=0x%08x\n", readl(&dev->op_regs->endptnaken));
285 +       DBG(dev, "endptsetupstat=0x%08x\n",
286                         readl(&dev->op_regs->endptsetupstat));
287 -       printk(KERN_DEBUG "endptprime=0x%08x\n",
288 -                       readl(&dev->op_regs->endptprime));
289 -       printk(KERN_DEBUG "endptflush=0x%08x\n",
290 -                       readl(&dev->op_regs->endptflush));
291 -       printk(KERN_DEBUG "endptstat=0x%08x\n",
292 -                       readl(&dev->op_regs->endptstat));
293 -       printk(KERN_DEBUG "endptcomplete=0x%08x\n",
294 +       DBG(dev, "endptprime=0x%08x\n", readl(&dev->op_regs->endptprime));
295 +       DBG(dev, "endptflush=0x%08x\n", readl(&dev->op_regs->endptflush));
296 +       DBG(dev, "endptstat=0x%08x\n", readl(&dev->op_regs->endptstat));
297 +       DBG(dev, "endptcomplete=0x%08x\n",
298                         readl(&dev->op_regs->endptcomplete));
299  
300         for (i = 0; i < dev->ep_max / 2; i++) {
301 -               printk(KERN_DEBUG "endptctrl[%d]=0x%08x\n",
302 +               DBG(dev, "endptctrl[%d]=0x%08x\n",
303                                 i, readl(&dev->op_regs->endptctrl[i]));
304         }
305  }
306 +#else
307 +
308 +#define        print_all_registers(dev)        do { } while (0)
309 +
310  #endif /* VERBOSE */
311  
312  
313  /*-------------------------------------------------------------------------*/
314  
315 -#define        DIR_STRING(bAddress)    (((bAddress) & USB_DIR_IN) ? "in" : "out")
316 +#define        is_in(ep)       (((ep)->ep_num == 0) ? ((ep)->dev->ep0_dir ==   \
317 +                       USB_DIR_IN) : (usb_endpoint_dir_in((ep)->desc)))
318  
319 -#define is_in(ep)      (((ep)->ep_num == 0) ? ((ep)->dev->ep0_dir == \
320 -                       USB_DIR_IN) : ((ep)->desc->bEndpointAddress \
321 -                       & USB_DIR_IN) == USB_DIR_IN)
322 +#define        DIR_STRING(ep)  (is_in(ep) ? "in" : "out")
323  
324  
325  #ifdef DEBUG
326 -static char *type_string(u8 bmAttributes)
327 +static char *type_string(const struct usb_endpoint_descriptor *desc)
328  {
329 -       switch ((bmAttributes) & USB_ENDPOINT_XFERTYPE_MASK) {
330 +       switch (usb_endpoint_type(desc)) {
331         case USB_ENDPOINT_XFER_BULK:
332                 return "bulk";
333         case USB_ENDPOINT_XFER_ISOC:
334 @@ -274,11 +245,13 @@ static void ep0_reset(struct langwell_udc *dev)
335                 ep->dqh->dqh_ios = 1;
336                 ep->dqh->dqh_mpl = EP0_MAX_PKT_SIZE;
337  
338 -               /* FIXME: enable ep0-in HW zero length termination select */
339 +               /* enable ep0-in HW zero length termination select */
340                 if (is_in(ep))
341                         ep->dqh->dqh_zlt = 0;
342                 ep->dqh->dqh_mult = 0;
343  
344 +               ep->dqh->dtd_next = DTD_TERM;
345 +
346                 /* configure ep0 control registers */
347                 ep_reset(&dev->ep[0], 0, i, USB_ENDPOINT_XFER_CONTROL);
348         }
349 @@ -300,7 +273,7 @@ static int langwell_ep_enable(struct usb_ep *_ep,
350         struct langwell_ep      *ep;
351         u16                     max = 0;
352         unsigned long           flags;
353 -       int                     retval = 0;
354 +       int                     i, retval = 0;
355         unsigned char           zlt, ios = 0, mult = 0;
356  
357         ep = container_of(_ep, struct langwell_ep, ep);
358 @@ -326,7 +299,7 @@ static int langwell_ep_enable(struct usb_ep *_ep,
359          * sanity check type, direction, address, and then
360          * initialize the endpoint capabilities fields in dQH
361          */
362 -       switch (desc->bmAttributes & USB_ENDPOINT_XFERTYPE_MASK) {
363 +       switch (usb_endpoint_type(desc)) {
364         case USB_ENDPOINT_XFER_CONTROL:
365                 ios = 1;
366                 break;
367 @@ -386,28 +359,31 @@ static int langwell_ep_enable(struct usb_ep *_ep,
368  
369         spin_lock_irqsave(&dev->lock, flags);
370  
371 -       /* configure endpoint capabilities in dQH */
372 -       ep->dqh->dqh_ios = ios;
373 -       ep->dqh->dqh_mpl = cpu_to_le16(max);
374 -       ep->dqh->dqh_zlt = zlt;
375 -       ep->dqh->dqh_mult = mult;
376 -
377         ep->ep.maxpacket = max;
378         ep->desc = desc;
379         ep->stopped = 0;
380 -       ep->ep_num = desc->bEndpointAddress & USB_ENDPOINT_NUMBER_MASK;
381 +       ep->ep_num = usb_endpoint_num(desc);
382  
383         /* ep_type */
384 -       ep->ep_type = desc->bmAttributes & USB_ENDPOINT_XFERTYPE_MASK;
385 +       ep->ep_type = usb_endpoint_type(desc);
386  
387         /* configure endpoint control registers */
388         ep_reset(ep, ep->ep_num, is_in(ep), ep->ep_type);
389  
390 +       /* configure endpoint capabilities in dQH */
391 +       i = ep->ep_num * 2 + is_in(ep);
392 +       ep->dqh = &dev->ep_dqh[i];
393 +       ep->dqh->dqh_ios = ios;
394 +       ep->dqh->dqh_mpl = cpu_to_le16(max);
395 +       ep->dqh->dqh_zlt = zlt;
396 +       ep->dqh->dqh_mult = mult;
397 +       ep->dqh->dtd_next = DTD_TERM;
398 +
399         DBG(dev, "enabled %s (ep%d%s-%s), max %04x\n",
400                         _ep->name,
401                         ep->ep_num,
402 -                       DIR_STRING(desc->bEndpointAddress),
403 -                       type_string(desc->bmAttributes),
404 +                       DIR_STRING(ep),
405 +                       type_string(desc),
406                         max);
407  
408         spin_unlock_irqrestore(&dev->lock, flags);
409 @@ -617,7 +593,7 @@ static int queue_dtd(struct langwell_ep *ep, struct langwell_request *req)
410                 VDBG(dev, "%s\n", ep->name);
411         else
412                 /* ep0 */
413 -               VDBG(dev, "%s-%s\n", ep->name, is_in(ep) ? "in" : "out");
414 +               VDBG(dev, "%s-%s\n", ep->name, DIR_STRING(ep));
415  
416         VDBG(dev, "ep_dqh[%d] addr: 0x%08x\n", i, (u32)&(dev->ep_dqh[i]));
417  
418 @@ -667,6 +643,9 @@ static int queue_dtd(struct langwell_ep *ep, struct langwell_request *req)
419         dqh->dtd_status &= dtd_status;
420         VDBG(dev, "dqh->dtd_status = 0x%x\n", dqh->dtd_status);
421  
422 +       /* ensure that updates to the dQH will occure before priming */
423 +       wmb();
424 +
425         /* write 1 to endptprime register to PRIME endpoint */
426         bit_mask = is_in(ep) ? (1 << (ep->ep_num + 16)) : (1 << ep->ep_num);
427         VDBG(dev, "endprime bit_mask = 0x%08x\n", bit_mask);
428 @@ -805,7 +784,7 @@ static int langwell_ep_queue(struct usb_ep *_ep, struct usb_request *_req,
429         req->ep = ep;
430         VDBG(dev, "---> %s()\n", __func__);
431  
432 -       if (ep->desc->bmAttributes == USB_ENDPOINT_XFER_ISOC) {
433 +       if (usb_endpoint_xfer_isoc(ep->desc)) {
434                 if (req->req.length > ep->ep.maxpacket)
435                         return -EMSGSIZE;
436                 is_iso = 1;
437 @@ -844,7 +823,7 @@ static int langwell_ep_queue(struct usb_ep *_ep, struct usb_request *_req,
438  
439         DBG(dev, "%s queue req %p, len %u, buf %p, dma 0x%08x\n",
440                         _ep->name,
441 -                       _req, _req->length, _req->buf, _req->dma);
442 +                       _req, _req->length, _req->buf, (int)_req->dma);
443  
444         _req->status = -EINPROGRESS;
445         _req->actual = 0;
446 @@ -1024,8 +1003,7 @@ static int langwell_ep_set_halt(struct usb_ep *_ep, int value)
447         if (!dev->driver || dev->gadget.speed == USB_SPEED_UNKNOWN)
448                 return -ESHUTDOWN;
449  
450 -       if (ep->desc && (ep->desc->bmAttributes & USB_ENDPOINT_XFERTYPE_MASK)
451 -                       == USB_ENDPOINT_XFER_ISOC)
452 +       if (usb_endpoint_xfer_isoc(ep->desc))
453                 return  -EOPNOTSUPP;
454  
455         spin_lock_irqsave(&dev->lock, flags);
456 @@ -1094,7 +1072,7 @@ static void langwell_ep_fifo_flush(struct usb_ep *_ep)
457                 return;
458         }
459  
460 -       VDBG(dev, "%s-%s fifo flush\n", _ep->name, is_in(ep) ? "in" : "out");
461 +       VDBG(dev, "%s-%s fifo flush\n", _ep->name, DIR_STRING(ep));
462  
463         /* flush endpoint buffer */
464         if (ep->ep_num == 0)
465 @@ -1181,6 +1159,7 @@ static int langwell_wakeup(struct usb_gadget *_gadget)
466  {
467         struct langwell_udc     *dev;
468         u32                     portsc1, devlc;
469 +       u8                      devlc_byte2;
470         unsigned long           flags;
471  
472         if (!_gadget)
473 @@ -1189,9 +1168,11 @@ static int langwell_wakeup(struct usb_gadget *_gadget)
474         dev = container_of(_gadget, struct langwell_udc, gadget);
475         VDBG(dev, "---> %s()\n", __func__);
476  
477 -       /* Remote Wakeup feature not enabled by host */
478 -       if (!dev->remote_wakeup)
479 +       /* remote wakeup feature not enabled by host */
480 +       if (!dev->remote_wakeup) {
481 +               INFO(dev, "remote wakeup is disabled\n");
482                 return -ENOTSUPP;
483 +       }
484  
485         spin_lock_irqsave(&dev->lock, flags);
486  
487 @@ -1201,23 +1182,25 @@ static int langwell_wakeup(struct usb_gadget *_gadget)
488                 return 0;
489         }
490  
491 -       /* LPM L1 to L0, remote wakeup */
492 -       if (dev->lpm && dev->lpm_state == LPM_L1) {
493 -               portsc1 |= PORTS_SLP;
494 -               writel(portsc1, &dev->op_regs->portsc1);
495 -       }
496 -
497 -       /* force port resume */
498 -       if (dev->usb_state == USB_STATE_SUSPENDED) {
499 -               portsc1 |= PORTS_FPR;
500 -               writel(portsc1, &dev->op_regs->portsc1);
501 -       }
502 +       /* LPM L1 to L0 or legacy remote wakeup */
503 +       if (dev->lpm && dev->lpm_state == LPM_L1)
504 +               INFO(dev, "LPM L1 to L0 remote wakeup\n");
505 +       else
506 +               INFO(dev, "device remote wakeup\n");
507  
508         /* exit PHY low power suspend */
509         devlc = readl(&dev->op_regs->devlc);
510         VDBG(dev, "devlc = 0x%08x\n", devlc);
511         devlc &= ~LPM_PHCD;
512 -       writel(devlc, &dev->op_regs->devlc);
513 +       /* FIXME: workaround for Langwell A1/A2/A3 sighting */
514 +       devlc_byte2 = (devlc >> 16) & 0xff;
515 +       writeb(devlc_byte2, (u8 *)&dev->op_regs->devlc + 2);
516 +       devlc = readl(&dev->op_regs->devlc);
517 +       VDBG(dev, "exit PHY low power suspend, devlc = 0x%08x\n", devlc);
518 +
519 +       /* force port resume */
520 +       portsc1 |= PORTS_FPR;
521 +       writel(portsc1, &dev->op_regs->portsc1);
522  
523         spin_unlock_irqrestore(&dev->lock, flags);
524  
525 @@ -1346,6 +1329,7 @@ static const struct usb_gadget_ops langwell_ops = {
526  static int langwell_udc_reset(struct langwell_udc *dev)
527  {
528         u32             usbcmd, usbmode, devlc, endpointlistaddr;
529 +       u8              devlc_byte0, devlc_byte2;
530         unsigned long   timeout;
531  
532         if (!dev)
533 @@ -1390,9 +1374,16 @@ static int langwell_udc_reset(struct langwell_udc *dev)
534         /* if support USB LPM, ACK all LPM token */
535         if (dev->lpm) {
536                 devlc = readl(&dev->op_regs->devlc);
537 +               VDBG(dev, "devlc = 0x%08x\n", devlc);
538 +               /* FIXME: workaround for Langwell A1/A2/A3 sighting */
539                 devlc &= ~LPM_STL;      /* don't STALL LPM token */
540                 devlc &= ~LPM_NYT_ACK;  /* ACK LPM token */
541 -               writel(devlc, &dev->op_regs->devlc);
542 +               devlc_byte0 = devlc & 0xff;
543 +               devlc_byte2 = (devlc >> 16) & 0xff;
544 +               writeb(devlc_byte0, (u8 *)&dev->op_regs->devlc);
545 +               writeb(devlc_byte2, (u8 *)&dev->op_regs->devlc + 2);
546 +               devlc = readl(&dev->op_regs->devlc);
547 +               VDBG(dev, "ACK LPM token, devlc = 0x%08x\n", devlc);
548         }
549  
550         /* fill endpointlistaddr register */
551 @@ -1449,8 +1440,6 @@ static int eps_reinit(struct langwell_udc *dev)
552  
553                 INIT_LIST_HEAD(&ep->queue);
554                 list_add_tail(&ep->ep.ep_list, &dev->gadget.ep_list);
555 -
556 -               ep->dqh = &dev->ep_dqh[i];
557         }
558  
559         VDBG(dev, "<--- %s()\n", __func__);
560 @@ -1539,21 +1528,6 @@ static void stop_activity(struct langwell_udc *dev,
561  
562  /*-------------------------------------------------------------------------*/
563  
564 -/* device "function" sysfs attribute file */
565 -static ssize_t show_function(struct device *_dev,
566 -               struct device_attribute *attr, char *buf)
567 -{
568 -       struct langwell_udc     *dev = the_controller;
569 -
570 -       if (!dev->driver || !dev->driver->function
571 -                       || strlen(dev->driver->function) > PAGE_SIZE)
572 -               return 0;
573 -
574 -       return scnprintf(buf, PAGE_SIZE, "%s\n", dev->driver->function);
575 -}
576 -static DEVICE_ATTR(function, S_IRUGO, show_function, NULL);
577 -
578 -
579  /* device "langwell_udc" sysfs attribute file */
580  static ssize_t show_langwell_udc(struct device *_dev,
581                 struct device_attribute *attr, char *buf)
582 @@ -1659,13 +1633,15 @@ static ssize_t show_langwell_udc(struct device *_dev,
583                 "Over-current Change: %s\n"
584                 "Port Enable/Disable Change: %s\n"
585                 "Port Enabled/Disabled: %s\n"
586 -               "Current Connect Status: %s\n\n",
587 +               "Current Connect Status: %s\n"
588 +               "LPM Suspend Status: %s\n\n",
589                 (tmp_reg & PORTS_PR) ? "Reset" : "Not Reset",
590                 (tmp_reg & PORTS_SUSP) ? "Suspend " : "Not Suspend",
591                 (tmp_reg & PORTS_OCC) ? "Detected" : "No",
592                 (tmp_reg & PORTS_PEC) ? "Changed" : "Not Changed",
593                 (tmp_reg & PORTS_PE) ? "Enable" : "Not Correct",
594 -               (tmp_reg & PORTS_CCS) ?  "Attached" : "Not Attached");
595 +               (tmp_reg & PORTS_CCS) ?  "Attached" : "Not Attached",
596 +               (tmp_reg & PORTS_SLP) ? "LPM L1" : "LPM L0");
597         size -= t;
598         next += t;
599  
600 @@ -1676,7 +1652,7 @@ static ssize_t show_langwell_udc(struct device *_dev,
601                 "Serial Transceiver : %d\n"
602                 "Port Speed: %s\n"
603                 "Port Force Full Speed Connenct: %s\n"
604 -               "PHY Low Power Suspend Clock Disable: %s\n"
605 +               "PHY Low Power Suspend Clock: %s\n"
606                 "BmAttributes: %d\n\n",
607                 LPM_PTS(tmp_reg),
608                 (tmp_reg & LPM_STS) ? 1 : 0,
609 @@ -1797,6 +1773,40 @@ static ssize_t show_langwell_udc(struct device *_dev,
610  static DEVICE_ATTR(langwell_udc, S_IRUGO, show_langwell_udc, NULL);
611  
612  
613 +/* device "remote_wakeup" sysfs attribute file */
614 +static ssize_t store_remote_wakeup(struct device *_dev,
615 +               struct device_attribute *attr, const char *buf, size_t count)
616 +{
617 +       struct langwell_udc     *dev = the_controller;
618 +#if defined(CONFIG_USB_DEBUG)
619 +       unsigned long           flags;
620 +#endif
621 +       ssize_t                 rc = count;
622 +
623 +       if (count > 2)
624 +               return -EINVAL;
625 +
626 +       if (count > 0 && buf[count-1] == '\n')
627 +               ((char *) buf)[count-1] = 0;
628 +
629 +       if (buf[0] != '1')
630 +               return -EINVAL;
631 +
632 +#if defined(CONFIG_USB_DEBUG)
633 +       /* force remote wakeup enabled in case gadget driver doesn't support */
634 +       spin_lock_irqsave(&dev->lock, flags);
635 +       dev->remote_wakeup = 1;
636 +       dev->dev_status |= (1 << USB_DEVICE_REMOTE_WAKEUP);
637 +       spin_unlock_irqrestore(&dev->lock, flags);
638 +#endif
639 +
640 +       langwell_wakeup(&dev->gadget);
641 +
642 +       return rc;
643 +}
644 +static DEVICE_ATTR(remote_wakeup, S_IWUSR, NULL, store_remote_wakeup);
645 +
646 +
647  /*-------------------------------------------------------------------------*/
648  
649  /*
650 @@ -1818,6 +1828,9 @@ int usb_gadget_register_driver(struct usb_gadget_driver *driver)
651  
652         DBG(dev, "---> %s()\n", __func__);
653  
654 +       if (unlikely(!driver || !driver->bind))
655 +               return -EINVAL;
656 +
657         if (dev->driver)
658                 return -EBUSY;
659  
660 @@ -1839,34 +1852,24 @@ int usb_gadget_register_driver(struct usb_gadget_driver *driver)
661                 return retval;
662         }
663  
664 -       retval = device_create_file(&dev->pdev->dev, &dev_attr_function);
665 -       if (retval)
666 -               goto err_unbind;
667 -
668         dev->usb_state = USB_STATE_ATTACHED;
669         dev->ep0_state = WAIT_FOR_SETUP;
670         dev->ep0_dir = USB_DIR_OUT;
671  
672 +       /* bind OTG transceiver */
673 +       if (dev->transceiver)
674 +               (void)otg_set_peripheral(dev->transceiver, &dev->gadget);
675 +
676         /* enable interrupt and set controller to run state */
677         if (dev->got_irq)
678                 langwell_udc_start(dev);
679  
680         VDBG(dev, "After langwell_udc_start(), print all registers:\n");
681 -#ifdef VERBOSE
682         print_all_registers(dev);
683 -#endif
684  
685         INFO(dev, "register driver: %s\n", driver->driver.name);
686 -       VDBG(dev, "<--- %s()\n", __func__);
687 -       return 0;
688 -
689 -err_unbind:
690 -       driver->unbind(&dev->gadget);
691 -       dev->gadget.dev.driver = NULL;
692 -       dev->driver = NULL;
693 -
694         DBG(dev, "<--- %s()\n", __func__);
695 -       return retval;
696 +       return 0;
697  }
698  EXPORT_SYMBOL(usb_gadget_register_driver);
699  
700 @@ -1876,15 +1879,27 @@ int usb_gadget_unregister_driver(struct usb_gadget_driver *driver)
701  {
702         struct langwell_udc     *dev = the_controller;
703         unsigned long           flags;
704 +       u32                     devlc;
705 +       u8                      devlc_byte2;
706  
707         if (!dev)
708                 return -ENODEV;
709  
710         DBG(dev, "---> %s()\n", __func__);
711  
712 -       if (unlikely(!driver || !driver->bind || !driver->unbind))
713 +       if (unlikely(!driver || !driver->unbind || !driver->disconnect))
714                 return -EINVAL;
715  
716 +       /* exit PHY low power suspend */
717 +       devlc = readl(&dev->op_regs->devlc);
718 +       VDBG(dev, "devlc = 0x%08x\n", devlc);
719 +       devlc &= ~LPM_PHCD;
720 +       /* FIXME: workaround for Langwell A1/A2/A3 sighting */
721 +       devlc_byte2 = (devlc >> 16) & 0xff;
722 +       writeb(devlc_byte2, (u8 *)&dev->op_regs->devlc + 2);
723 +       devlc = readl(&dev->op_regs->devlc);
724 +       VDBG(dev, "exit PHY low power suspend, devlc = 0x%08x\n", devlc);
725 +
726         /* unbind OTG transceiver */
727         if (dev->transceiver)
728                 (void)otg_set_peripheral(dev->transceiver, 0);
729 @@ -1908,8 +1923,6 @@ int usb_gadget_unregister_driver(struct usb_gadget_driver *driver)
730         dev->gadget.dev.driver = NULL;
731         dev->driver = NULL;
732  
733 -       device_remove_file(&dev->pdev->dev, &dev_attr_function);
734 -
735         INFO(dev, "unregistered driver '%s'\n", driver->driver.name);
736         DBG(dev, "<--- %s()\n", __func__);
737         return 0;
738 @@ -1917,6 +1930,55 @@ int usb_gadget_unregister_driver(struct usb_gadget_driver *driver)
739  EXPORT_SYMBOL(usb_gadget_unregister_driver);
740  
741  
742 +/* gets the maximum power consumption */
743 +int langwell_udc_maxpower(int *mA)
744 +{
745 +       struct langwell_udc     *dev = the_controller;
746 +       u32                     usbmode, portsc1, usbcmd;
747 +
748 +       /* fatal error */
749 +       if (!dev) {
750 +               *mA = 0;
751 +               return -EOTGFAIL;
752 +       }
753 +
754 +       DBG(dev, "---> %s()\n", __func__);
755 +
756 +       /* contrller is not in device mode */
757 +       usbmode = readl(&dev->op_regs->usbmode);
758 +       if (MODE_CM(usbmode) != MODE_DEVICE) {
759 +               *mA = 0;
760 +               return -EOTGNODEVICE;
761 +       }
762 +
763 +       /* can't get maximum power */
764 +       usbcmd = readl(&dev->op_regs->usbcmd);
765 +       if (!(usbcmd & CMD_RUNSTOP)) {
766 +               *mA = 0;
767 +               return -EOTGCHARGER;
768 +       }
769 +
770 +       /* disconnect to USB host */
771 +       portsc1 = readl(&dev->op_regs->portsc1);
772 +       if (!(portsc1 & PORTS_CCS)) {
773 +               *mA = 0;
774 +               return -EOTGDISCONN;
775 +       }
776 +
777 +       /* set max power capability */
778 +       *mA = CONFIG_USB_GADGET_VBUS_DRAW;
779 +
780 +       if ((*mA < 8) || (*mA > 500)) {
781 +               *mA = 0;
782 +               return -EOTGINVAL;
783 +       }
784 +
785 +       DBG(dev, "<--- %s()\n", __func__);
786 +       return 0;
787 +}
788 +EXPORT_SYMBOL(langwell_udc_maxpower);
789 +
790 +
791  /*-------------------------------------------------------------------------*/
792  
793  /*
794 @@ -2113,8 +2175,7 @@ static void get_status(struct langwell_udc *dev, u8 request_type, u16 value,
795  
796         if ((request_type & USB_RECIP_MASK) == USB_RECIP_DEVICE) {
797                 /* get device status */
798 -               status_data = 1 << USB_DEVICE_SELF_POWERED;
799 -               status_data |= dev->remote_wakeup << USB_DEVICE_REMOTE_WAKEUP;
800 +               status_data = dev->dev_status;
801         } else if ((request_type & USB_RECIP_MASK) == USB_RECIP_INTERFACE) {
802                 /* get interface status */
803                 status_data = 0;
804 @@ -2129,6 +2190,8 @@ static void get_status(struct langwell_udc *dev, u8 request_type, u16 value,
805                 status_data = ep_is_stall(epn) << USB_ENDPOINT_HALT;
806         }
807  
808 +       DBG(dev, "get status data: 0x%04x\n", status_data);
809 +
810         dev->ep0_dir = USB_DIR_IN;
811  
812         /* borrow the per device status_req */
813 @@ -2247,22 +2310,37 @@ static void handle_setup_packet(struct langwell_udc *dev,
814                 } else if ((setup->bRequestType & (USB_RECIP_MASK
815                                 | USB_TYPE_MASK)) == (USB_RECIP_DEVICE
816                                 | USB_TYPE_STANDARD)) {
817 -                       if (!gadget_is_otg(&dev->gadget))
818 +                       rc = 0;
819 +                       switch (wValue) {
820 +                       case USB_DEVICE_REMOTE_WAKEUP:
821 +                               if (setup->bRequest == USB_REQ_SET_FEATURE) {
822 +                                       dev->remote_wakeup = 1;
823 +                                       dev->dev_status |= (1 << wValue);
824 +                               } else {
825 +                                       dev->remote_wakeup = 0;
826 +                                       dev->dev_status &= ~(1 << wValue);
827 +                               }
828                                 break;
829 -                       else if (setup->bRequest == USB_DEVICE_B_HNP_ENABLE) {
830 +                       case USB_DEVICE_B_HNP_ENABLE:
831                                 dev->gadget.b_hnp_enable = 1;
832  #ifdef OTG_TRANSCEIVER
833                                 if (!dev->lotg->otg.default_a)
834                                         dev->lotg->hsm.b_hnp_enable = 1;
835  #endif
836 -                       } else if (setup->bRequest == USB_DEVICE_A_HNP_SUPPORT)
837 +                               dev->dev_status |= (1 << wValue);
838 +                               break;
839 +                       case USB_DEVICE_A_HNP_SUPPORT:
840                                 dev->gadget.a_hnp_support = 1;
841 -                       else if (setup->bRequest ==
842 -                                       USB_DEVICE_A_ALT_HNP_SUPPORT)
843 +                               dev->dev_status |= (1 << wValue);
844 +                               break;
845 +                       case USB_DEVICE_A_ALT_HNP_SUPPORT:
846                                 dev->gadget.a_alt_hnp_support = 1;
847 -                       else
848 +                               dev->dev_status |= (1 << wValue);
849                                 break;
850 -                       rc = 0;
851 +                       default:
852 +                               rc = -EOPNOTSUPP;
853 +                               break;
854 +                       }
855                 } else
856                         break;
857  
858 @@ -2387,7 +2465,7 @@ static int process_ep_req(struct langwell_udc *dev, int index,
859                 } else {
860                         /* transfers completed with errors */
861                         if (dtd_status & DTD_STS_ACTIVE) {
862 -                               DBG(dev, "request not completed\n");
863 +                               DBG(dev, "dTD status ACTIVE dQH[%d]\n", index);
864                                 retval = 1;
865                                 return retval;
866                         } else if (dtd_status & DTD_STS_HALTED) {
867 @@ -2586,18 +2664,14 @@ static void handle_port_change(struct langwell_udc *dev)
868         /* LPM L0 to L1 */
869         if (dev->lpm && dev->lpm_state == LPM_L0)
870                 if (portsc1 & PORTS_SUSP && portsc1 & PORTS_SLP) {
871 -                               INFO(dev, "LPM L0 to L1\n");
872 -                               dev->lpm_state = LPM_L1;
873 +                       INFO(dev, "LPM L0 to L1\n");
874 +                       dev->lpm_state = LPM_L1;
875                 }
876  
877         /* LPM L1 to L0, force resume or remote wakeup finished */
878         if (dev->lpm && dev->lpm_state == LPM_L1)
879                 if (!(portsc1 & PORTS_SUSP)) {
880 -                       if (portsc1 & PORTS_SLP)
881 -                               INFO(dev, "LPM L1 to L0, force resume\n");
882 -                       else
883 -                               INFO(dev, "LPM L1 to L0, remote wakeup\n");
884 -
885 +                       INFO(dev, "LPM L1 to L0\n");
886                         dev->lpm_state = LPM_L0;
887                 }
888  
889 @@ -2634,7 +2708,10 @@ static void handle_usb_reset(struct langwell_udc *dev)
890  
891         dev->ep0_dir = USB_DIR_OUT;
892         dev->ep0_state = WAIT_FOR_SETUP;
893 -       dev->remote_wakeup = 0;         /* default to 0 on reset */
894 +
895 +       /* remote wakeup reset to 0 when the device is reset */
896 +       dev->remote_wakeup = 0;
897 +       dev->dev_status = 1 << USB_DEVICE_SELF_POWERED;
898         dev->gadget.b_hnp_enable = 0;
899         dev->gadget.a_hnp_support = 0;
900         dev->gadget.a_alt_hnp_support = 0;
901 @@ -2699,6 +2776,7 @@ static void handle_usb_reset(struct langwell_udc *dev)
902  static void handle_bus_suspend(struct langwell_udc *dev)
903  {
904         u32             devlc;
905 +       u8              devlc_byte2;
906         DBG(dev, "---> %s()\n", __func__);
907  
908         dev->resume_state = dev->usb_state;
909 @@ -2706,7 +2784,8 @@ static void handle_bus_suspend(struct langwell_udc *dev)
910  
911  #ifdef OTG_TRANSCEIVER
912         if (dev->lotg->otg.default_a) {
913 -               if (dev->lotg->hsm.b_bus_suspend_vld == 1) {
914 +               /* ignore host LPM capability checking during enumeration */
915 +               if (dev->lotg->hsm.b_bus_suspend_vld == 2) {
916                         dev->lotg->hsm.b_bus_suspend = 1;
917                         /* notify transceiver the state changes */
918                         if (spin_trylock(&dev->lotg->wq_lock)) {
919 @@ -2741,7 +2820,11 @@ static void handle_bus_suspend(struct langwell_udc *dev)
920         devlc = readl(&dev->op_regs->devlc);
921         VDBG(dev, "devlc = 0x%08x\n", devlc);
922         devlc |= LPM_PHCD;
923 -       writel(devlc, &dev->op_regs->devlc);
924 +       /* FIXME: workaround for Langwell A1/A2/A3 sighting */
925 +       devlc_byte2 = (devlc >> 16) & 0xff;
926 +       writeb(devlc_byte2, (u8 *)&dev->op_regs->devlc + 2);
927 +       devlc = readl(&dev->op_regs->devlc);
928 +       VDBG(dev, "enter PHY low power suspend, devlc = 0x%08x\n", devlc);
929  
930         DBG(dev, "<--- %s()\n", __func__);
931  }
932 @@ -2750,6 +2833,7 @@ static void handle_bus_suspend(struct langwell_udc *dev)
933  static void handle_bus_resume(struct langwell_udc *dev)
934  {
935         u32             devlc;
936 +       u8              devlc_byte2;
937         DBG(dev, "---> %s()\n", __func__);
938  
939         dev->usb_state = dev->resume_state;
940 @@ -2759,7 +2843,11 @@ static void handle_bus_resume(struct langwell_udc *dev)
941         devlc = readl(&dev->op_regs->devlc);
942         VDBG(dev, "devlc = 0x%08x\n", devlc);
943         devlc &= ~LPM_PHCD;
944 -       writel(devlc, &dev->op_regs->devlc);
945 +       /* FIXME: workaround for Langwell A1/A2/A3 sighting */
946 +       devlc_byte2 = (devlc >> 16) & 0xff;
947 +       writeb(devlc_byte2, (u8 *)&dev->op_regs->devlc + 2);
948 +       devlc = readl(&dev->op_regs->devlc);
949 +       VDBG(dev, "exit PHY low power suspend, devlc = 0x%08x\n", devlc);
950  
951  #ifdef OTG_TRANSCEIVER
952         if (dev->lotg->otg.default_a == 0)
953 @@ -2898,6 +2986,50 @@ static void gadget_release(struct device *_dev)
954  }
955  
956  
957 +/* enable SRAM caching if SRAM detected */
958 +static void sram_init(struct langwell_udc *dev)
959 +{
960 +       struct pci_dev          *pdev = dev->pdev;
961 +
962 +       DBG(dev, "---> %s()\n", __func__);
963 +
964 +       dev->sram_addr = pci_resource_start(pdev, 1);
965 +       dev->sram_size = pci_resource_len(pdev, 1);
966 +       INFO(dev, "Found private SRAM at %x size:%x\n",
967 +                       dev->sram_addr, dev->sram_size);
968 +       dev->got_sram = 1;
969 +
970 +       if (pci_request_region(pdev, 1, kobject_name(&pdev->dev.kobj))) {
971 +               WARNING(dev, "SRAM request failed\n");
972 +               dev->got_sram = 0;
973 +       } else if (!dma_declare_coherent_memory(&pdev->dev, dev->sram_addr,
974 +                       dev->sram_addr, dev->sram_size, DMA_MEMORY_MAP)) {
975 +               WARNING(dev, "SRAM DMA declare failed\n");
976 +               pci_release_region(pdev, 1);
977 +               dev->got_sram = 0;
978 +       }
979 +
980 +       DBG(dev, "<--- %s()\n", __func__);
981 +}
982 +
983 +
984 +/* release SRAM caching */
985 +static void sram_deinit(struct langwell_udc *dev)
986 +{
987 +       struct pci_dev *pdev = dev->pdev;
988 +
989 +       DBG(dev, "---> %s()\n", __func__);
990 +
991 +       dma_release_declared_memory(&pdev->dev);
992 +       pci_release_region(pdev, 1);
993 +
994 +       dev->got_sram = 0;
995 +
996 +       INFO(dev, "release SRAM caching\n");
997 +       DBG(dev, "<--- %s()\n", __func__);
998 +}
999 +
1000 +
1001  /* tear down the binding between this driver and the pci device */
1002  static void langwell_udc_remove(struct pci_dev *pdev)
1003  {
1004 @@ -2910,19 +3042,25 @@ static void langwell_udc_remove(struct pci_dev *pdev)
1005  
1006         dev->done = &done;
1007  
1008 -       /* free memory allocated in probe */
1009 +#ifndef        OTG_TRANSCEIVER
1010 +       /* free dTD dma_pool and dQH */
1011         if (dev->dtd_pool)
1012                 dma_pool_destroy(dev->dtd_pool);
1013  
1014 +       if (dev->ep_dqh)
1015 +               dma_free_coherent(&pdev->dev, dev->ep_dqh_size,
1016 +                       dev->ep_dqh, dev->ep_dqh_dma);
1017 +
1018 +       /* release SRAM caching */
1019 +       if (dev->has_sram && dev->got_sram)
1020 +               sram_deinit(dev);
1021 +#endif
1022 +
1023         if (dev->status_req) {
1024                 kfree(dev->status_req->req.buf);
1025                 kfree(dev->status_req);
1026         }
1027  
1028 -       if (dev->ep_dqh)
1029 -               dma_free_coherent(&pdev->dev, dev->ep_dqh_size,
1030 -                       dev->ep_dqh, dev->ep_dqh_dma);
1031 -
1032         kfree(dev->ep);
1033  
1034         /* diable IRQ handler */
1035 @@ -2954,6 +3092,7 @@ static void langwell_udc_remove(struct pci_dev *pdev)
1036  
1037         device_unregister(&dev->gadget.dev);
1038         device_remove_file(&pdev->dev, &dev_attr_langwell_udc);
1039 +       device_remove_file(&pdev->dev, &dev_attr_remote_wakeup);
1040  
1041  #ifndef        OTG_TRANSCEIVER
1042         pci_set_drvdata(pdev, NULL);
1043 @@ -2976,9 +3115,9 @@ static int langwell_udc_probe(struct pci_dev *pdev,
1044         struct langwell_udc     *dev;
1045  #ifndef        OTG_TRANSCEIVER
1046         unsigned long           resource, len;
1047 +       size_t                  size;
1048  #endif
1049         void                    __iomem *base = NULL;
1050 -       size_t                  size;
1051         int                     retval;
1052  
1053         if (the_controller) {
1054 @@ -3049,7 +3188,15 @@ static int langwell_udc_probe(struct pci_dev *pdev,
1055                 goto error;
1056         }
1057  
1058 +       dev->has_sram = 1;
1059 +       dev->got_sram = 0;
1060 +       VDBG(dev, "dev->has_sram: %d\n", dev->has_sram);
1061 +
1062  #ifndef        OTG_TRANSCEIVER
1063 +       /* enable SRAM caching if detected */
1064 +       if (dev->has_sram && !dev->got_sram)
1065 +               sram_init(dev);
1066 +
1067         INFO(dev, "irq %d, io mem: 0x%08lx, len: 0x%08lx, pci mem 0x%p\n",
1068                         pdev->irq, resource, len, base);
1069         /* enables bus-mastering for device dev */
1070 @@ -3094,6 +3241,7 @@ static int langwell_udc_probe(struct pci_dev *pdev,
1071                 goto error;
1072         }
1073  
1074 +#ifndef        OTG_TRANSCEIVER
1075         /* allocate device dQH memory */
1076         size = dev->ep_max * sizeof(struct langwell_dqh);
1077         VDBG(dev, "orig size = %d\n", size);
1078 @@ -3112,6 +3260,7 @@ static int langwell_udc_probe(struct pci_dev *pdev,
1079         }
1080         dev->ep_dqh_size = size;
1081         VDBG(dev, "ep_dqh_size = %d\n", dev->ep_dqh_size);
1082 +#endif
1083  
1084         /* initialize ep0 status request structure */
1085         dev->status_req = kzalloc(sizeof(struct langwell_request), GFP_KERNEL);
1086 @@ -3129,7 +3278,10 @@ static int langwell_udc_probe(struct pci_dev *pdev,
1087         dev->resume_state = USB_STATE_NOTATTACHED;
1088         dev->usb_state = USB_STATE_POWERED;
1089         dev->ep0_dir = USB_DIR_OUT;
1090 -       dev->remote_wakeup = 0; /* default to 0 on reset */
1091 +
1092 +       /* remote wakeup reset to 0 when the device is reset */
1093 +       dev->remote_wakeup = 0;
1094 +       dev->dev_status = 1 << USB_DEVICE_SELF_POWERED;
1095  
1096  #ifndef        OTG_TRANSCEIVER
1097         /* reset device controller */
1098 @@ -3159,7 +3311,6 @@ static int langwell_udc_probe(struct pci_dev *pdev,
1099  #ifndef        OTG_TRANSCEIVER
1100         /* reset ep0 dQH and endptctrl */
1101         ep0_reset(dev);
1102 -#endif
1103  
1104         /* create dTD dma_pool resource */
1105         dev->dtd_pool = dma_pool_create("langwell_dtd",
1106 @@ -3172,6 +3323,7 @@ static int langwell_udc_probe(struct pci_dev *pdev,
1107                 retval = -ENOMEM;
1108                 goto error;
1109         }
1110 +#endif
1111  
1112         /* done */
1113         INFO(dev, "%s\n", driver_desc);
1114 @@ -3183,9 +3335,7 @@ static int langwell_udc_probe(struct pci_dev *pdev,
1115         INFO(dev, "Support USB LPM: %s\n", dev->lpm ? "Yes" : "No");
1116  
1117         VDBG(dev, "After langwell_udc_probe(), print all registers:\n");
1118 -#ifdef VERBOSE
1119         print_all_registers(dev);
1120 -#endif
1121  
1122         the_controller = dev;
1123  
1124 @@ -3197,9 +3347,15 @@ static int langwell_udc_probe(struct pci_dev *pdev,
1125         if (retval)
1126                 goto error;
1127  
1128 +       retval = device_create_file(&pdev->dev, &dev_attr_remote_wakeup);
1129 +       if (retval)
1130 +               goto error_attr1;
1131 +
1132         VDBG(dev, "<--- %s()\n", __func__);
1133         return 0;
1134  
1135 +error_attr1:
1136 +       device_remove_file(&pdev->dev, &dev_attr_langwell_udc);
1137  error:
1138         if (dev) {
1139                 DBG(dev, "<--- %s()\n", __func__);
1140 @@ -3215,6 +3371,7 @@ static int langwell_udc_suspend(struct pci_dev *pdev, pm_message_t state)
1141  {
1142         struct langwell_udc     *dev = the_controller;
1143         u32                     devlc;
1144 +       u8                      devlc_byte2;
1145  
1146         DBG(dev, "---> %s()\n", __func__);
1147  
1148 @@ -3226,10 +3383,21 @@ static int langwell_udc_suspend(struct pci_dev *pdev, pm_message_t state)
1149                 free_irq(pdev->irq, dev);
1150         dev->got_irq = 0;
1151  
1152 -
1153         /* save PCI state */
1154         pci_save_state(pdev);
1155  
1156 +       /* free dTD dma_pool and dQH */
1157 +       if (dev->dtd_pool)
1158 +               dma_pool_destroy(dev->dtd_pool);
1159 +
1160 +       if (dev->ep_dqh)
1161 +               dma_free_coherent(&pdev->dev, dev->ep_dqh_size,
1162 +                       dev->ep_dqh, dev->ep_dqh_dma);
1163 +
1164 +       /* release SRAM caching */
1165 +       if (dev->has_sram && dev->got_sram)
1166 +               sram_deinit(dev);
1167 +
1168         /* set device power state */
1169         pci_set_power_state(pdev, PCI_D3hot);
1170  
1171 @@ -3237,7 +3405,11 @@ static int langwell_udc_suspend(struct pci_dev *pdev, pm_message_t state)
1172         devlc = readl(&dev->op_regs->devlc);
1173         VDBG(dev, "devlc = 0x%08x\n", devlc);
1174         devlc |= LPM_PHCD;
1175 -       writel(devlc, &dev->op_regs->devlc);
1176 +       /* FIXME: workaround for Langwell A1/A2/A3 sighting */
1177 +       devlc_byte2 = (devlc >> 16) & 0xff;
1178 +       writeb(devlc_byte2, (u8 *)&dev->op_regs->devlc + 2);
1179 +       devlc = readl(&dev->op_regs->devlc);
1180 +       VDBG(dev, "enter PHY low power suspend, devlc = 0x%08x\n", devlc);
1181  
1182         DBG(dev, "<--- %s()\n", __func__);
1183         return 0;
1184 @@ -3249,6 +3421,8 @@ static int langwell_udc_resume(struct pci_dev *pdev)
1185  {
1186         struct langwell_udc     *dev = the_controller;
1187         u32                     devlc;
1188 +       u8                      devlc_byte2;
1189 +       size_t                  size;
1190  
1191         DBG(dev, "---> %s()\n", __func__);
1192  
1193 @@ -3256,19 +3430,55 @@ static int langwell_udc_resume(struct pci_dev *pdev)
1194         devlc = readl(&dev->op_regs->devlc);
1195         VDBG(dev, "devlc = 0x%08x\n", devlc);
1196         devlc &= ~LPM_PHCD;
1197 -       writel(devlc, &dev->op_regs->devlc);
1198 +       /* FIXME: workaround for Langwell A1/A2/A3 sighting */
1199 +       devlc_byte2 = (devlc >> 16) & 0xff;
1200 +       writeb(devlc_byte2, (u8 *)&dev->op_regs->devlc + 2);
1201 +       devlc = readl(&dev->op_regs->devlc);
1202 +       VDBG(dev, "exit PHY low power suspend, devlc = 0x%08x\n", devlc);
1203  
1204         /* set device D0 power state */
1205         pci_set_power_state(pdev, PCI_D0);
1206  
1207 +       /* enable SRAM caching if detected */
1208 +       if (dev->has_sram && !dev->got_sram)
1209 +               sram_init(dev);
1210 +
1211 +       /* allocate device dQH memory */
1212 +       size = dev->ep_max * sizeof(struct langwell_dqh);
1213 +       VDBG(dev, "orig size = %d\n", size);
1214 +       if (size < DQH_ALIGNMENT)
1215 +               size = DQH_ALIGNMENT;
1216 +       else if ((size % DQH_ALIGNMENT) != 0) {
1217 +               size += DQH_ALIGNMENT + 1;
1218 +               size &= ~(DQH_ALIGNMENT - 1);
1219 +       }
1220 +       dev->ep_dqh = dma_alloc_coherent(&pdev->dev, size,
1221 +                                       &dev->ep_dqh_dma, GFP_KERNEL);
1222 +       if (!dev->ep_dqh) {
1223 +               ERROR(dev, "allocate dQH memory failed\n");
1224 +               return -ENOMEM;
1225 +       }
1226 +       dev->ep_dqh_size = size;
1227 +       VDBG(dev, "ep_dqh_size = %d\n", dev->ep_dqh_size);
1228 +
1229 +       /* create dTD dma_pool resource */
1230 +       dev->dtd_pool = dma_pool_create("langwell_dtd",
1231 +                       &dev->pdev->dev,
1232 +                       sizeof(struct langwell_dtd),
1233 +                       DTD_ALIGNMENT,
1234 +                       DMA_BOUNDARY);
1235 +
1236 +       if (!dev->dtd_pool)
1237 +               return -ENOMEM;
1238 +
1239         /* restore PCI state */
1240         pci_restore_state(pdev);
1241  
1242         /* enable IRQ handler */
1243 -       if (request_irq(pdev->irq, langwell_irq, IRQF_SHARED, driver_name, dev)
1244 -                       != 0) {
1245 +       if (request_irq(pdev->irq, langwell_irq, IRQF_SHARED,
1246 +                               driver_name, dev) != 0) {
1247                 ERROR(dev, "request interrupt %d failed\n", pdev->irq);
1248 -               return -1;
1249 +               return -EBUSY;
1250         }
1251         dev->got_irq = 1;
1252  
1253 diff --git a/drivers/usb/gadget/langwell_udc.h b/drivers/usb/gadget/langwell_udc.h
1254 index 9719934..323c574 100644
1255 --- a/drivers/usb/gadget/langwell_udc.h
1256 +++ b/drivers/usb/gadget/langwell_udc.h
1257 @@ -174,7 +174,7 @@ enum lpm_state {
1258  struct langwell_udc {
1259         /* each pci device provides one gadget, several endpoints */
1260         struct usb_gadget       gadget;
1261 -       spinlock_t              lock;   /* device lock */
1262 +       spinlock_t              lock;           /* device lock */
1263         struct langwell_ep      *ep;
1264         struct usb_gadget_driver        *driver;
1265         struct otg_transceiver  *transceiver;
1266 @@ -199,7 +199,9 @@ struct langwell_udc {
1267                                 vbus_active:1,
1268                                 suspended:1,
1269                                 stopped:1,
1270 -                               lpm:1;  /* LPM capability */
1271 +                               lpm:1,          /* LPM capability */
1272 +                               has_sram:1,     /* SRAM caching */
1273 +                               got_sram:1;
1274  
1275         /* pci state used to access those endpoints */
1276         struct pci_dev          *pdev;
1277 @@ -224,5 +226,12 @@ struct langwell_udc {
1278  
1279         /* make sure release() is done */
1280         struct completion       *done;
1281 +
1282 +       /* for private SRAM caching */
1283 +       unsigned int            sram_addr;
1284 +       unsigned int            sram_size;
1285 +
1286 +       /* device status data for get_status request */
1287 +       u16                     dev_status;
1288  };
1289  
1290 diff --git a/drivers/usb/gadget/still_image.c b/drivers/usb/gadget/still_image.c
1291 new file mode 100644
1292 index 0000000..94c17ce
1293 --- /dev/null
1294 +++ b/drivers/usb/gadget/still_image.c
1295 @@ -0,0 +1,4566 @@
1296 +/*
1297 + * still_image.c -- Lite USB Still Image Capture Gadget, for USB development
1298 + * Copyright (C) 2009, Intel Corporation.
1299 + *
1300 + * This program is free software; you can redistribute it and/or modify it
1301 + * under the terms and conditions of the GNU General Public License,
1302 + * version 2, as published by the Free Software Foundation.
1303 + *
1304 + * This program is distributed in the hope it will be useful, but WITHOUT
1305 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
1306 + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
1307 + * more details.
1308 + *
1309 + * You should have received a copy of the GNU General Public License along with
1310 + * this program; if not, write to the Free Software Foundation, Inc.,
1311 + * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
1312 + *
1313 + */
1314 +
1315 +
1316 +/*
1317 + * This code is partly based on:
1318 + * File-backed USB Storage Gadget driver, Copyright (C) 2003-2008 Alan Stern
1319 + *
1320 + *
1321 + * Refer to the USB Device Class Definition for Still Image Capture Device:
1322 + * http://www.usb.org/developers/devclass_docs/usb_still_img10.zip
1323 + *
1324 + *
1325 + * Supported PIMA 15740/PTP operations:
1326 + *     - GetDeviceInfo
1327 + *     - OpenSession
1328 + *     - CloseSession
1329 + *     - GetStorageIDs
1330 + *     - GetStorageInfo
1331 + *     - GetNumObjects
1332 + *     - GetObjectHandles
1333 + *     - GetObjectInfo
1334 + *     - GetObject
1335 + *     - DeleteObject
1336 + *     - SendObjectInfo
1337 + *     - SendObject
1338 + *     - CopyObject
1339 + *     - MoveObject
1340 + *
1341 + * Supported object formats:
1342 + *     - EXIF/JPEG, JFIF
1343 + *     - PNG
1344 + *     - TIFF, TIFF/IT, TIFF/EP
1345 + *     - BMP
1346 + *     - GIF
1347 + *     - Unknown image object
1348 + *     - Undefined non-image object
1349 + *
1350 + * Supported PIMA 15740/PTP events:
1351 + *     - N/A
1352 + *
1353 + * Storage filesystem type:
1354 + *     - Generic hierarchical
1355 + *
1356 + *
1357 + * Module options:
1358 + *     folder=foldername       Default NULL, name of the backing folder
1359 + *     vendor=0xVVVV           Default 0x8087 (Intel), USB Vendor ID
1360 + *     product=0xPPPP          Default 0x811e, USB Product ID
1361 + *     release=0xRRRR          Override the USB release number (bcdDevice)
1362 + *     buflen=N                Default N=16384, buffer size used (will be
1363 + *                                     rounded down to a multiple of
1364 + *                                     PAGE_CACHE_SIZE)
1365 + *
1366 + * Sysfs attribute file:
1367 + *     folder                  read/write the name of the backing folder
1368 + *
1369 + */
1370 +
1371 +
1372 +#define        VERBOSE_DEBUG
1373 +
1374 +#include <linux/blkdev.h>
1375 +#include <linux/completion.h>
1376 +#include <linux/dcache.h>
1377 +#include <linux/delay.h>
1378 +#include <linux/device.h>
1379 +#include <linux/fcntl.h>
1380 +#include <linux/file.h>
1381 +#include <linux/fs.h>
1382 +#include <linux/vfs.h>
1383 +#include <linux/namei.h>
1384 +#include <linux/kref.h>
1385 +#include <linux/kthread.h>
1386 +#include <linux/limits.h>
1387 +#include <linux/rwsem.h>
1388 +#include <linux/slab.h>
1389 +#include <linux/spinlock.h>
1390 +#include <linux/string.h>
1391 +#include <linux/freezer.h>
1392 +#include <linux/utsname.h>
1393 +#include <linux/sort.h>
1394 +
1395 +#include <linux/usb/ch9.h>
1396 +#include <linux/usb/gadget.h>
1397 +
1398 +#include "gadget_chips.h"
1399 +
1400 +#include "usbstring.c"
1401 +#include "config.c"
1402 +#include "epautoconf.c"
1403 +
1404 +
1405 +/*-------------------------------------------------------------------------*/
1406 +
1407 +#define        DRIVER_DESC             "Still Image Gadget"
1408 +#define        DRIVER_NAME             "g_still_image"
1409 +#define        DRIVER_VERSION          "Apr 30, 2010"
1410 +
1411 +
1412 +static const char longname[] = DRIVER_DESC;
1413 +static const char shortname[] = DRIVER_NAME;
1414 +
1415 +
1416 +MODULE_DESCRIPTION(DRIVER_DESC);
1417 +MODULE_AUTHOR("Xiaochen Shen <xiaochen.shen@intel.com>; "
1418 +               "Hang Yuan <hang.yuan@intel.com>");
1419 +MODULE_VERSION(DRIVER_VERSION);
1420 +MODULE_LICENSE("GPL");
1421 +
1422 +
1423 +/*
1424 + * Intel Corporation donates this product ID.
1425 + *
1426 + * DO NOT REUSE THESE IDs with any other driver
1427 + * instead:  allocate your own, using normal USB-IF procedures.
1428 + */
1429 +#define        DRIVER_VENDOR_ID        0x8087
1430 +#define        DRIVER_PRODUCT_ID       0x811e
1431 +
1432 +
1433 +/*-------------------------------------------------------------------------*/
1434 +
1435 +#define        MDBG(fmt, args...) \
1436 +       pr_debug(DRIVER_NAME ": " fmt, ## args)
1437 +#define        MINFO(fmt, args...) \
1438 +       pr_info(DRIVER_NAME ": " fmt, ## args)
1439 +
1440 +#ifdef DEBUG
1441 +#define        DBG(d, fmt, args...) \
1442 +       dev_dbg(&(d)->gadget->dev, fmt, ## args)
1443 +#else
1444 +#define        DBG(dev, fmt, args...) \
1445 +       do { } while (0)
1446 +#endif /* DEBUG */
1447 +
1448 +
1449 +#ifndef        DEBUG
1450 +#undef VERBOSE_DEBUG
1451 +#endif /* !DEBUG */
1452 +
1453 +#ifdef VERBOSE_DEBUG
1454 +#define        VDBG    DBG
1455 +#else
1456 +#define        VDBG(sti, fmt, args...) \
1457 +       do { } while (0)
1458 +#endif /* VERBOSE_DEBUG */
1459 +
1460 +#define        ERROR(d, fmt, args...) \
1461 +       dev_err(&(d)->gadget->dev, fmt, ## args)
1462 +#define        WARNING(d, fmt, args...) \
1463 +       dev_warn(&(d)->gadget->dev, fmt, ## args)
1464 +#define        INFO(d, fmt, args...) \
1465 +       dev_info(&(d)->gadget->dev, fmt, ## args)
1466 +
1467 +
1468 +/*-------------------------------------------------------------------------*/
1469 +
1470 +/* encapsulate the module parameter settings */
1471 +
1472 +static struct {
1473 +       char            *folder;
1474 +       unsigned short  vendor;
1475 +       unsigned short  product;
1476 +       unsigned short  release;
1477 +       unsigned int    buflen;
1478 +} mod_data = {                         /* default values */
1479 +       .vendor         = DRIVER_VENDOR_ID,
1480 +       .product        = DRIVER_PRODUCT_ID,
1481 +       .release        = 0xffff,       /* use controller chip type */
1482 +       .buflen         = 16384,
1483 +};
1484 +
1485 +
1486 +module_param_named(folder, mod_data.folder, charp, S_IRUGO);
1487 +MODULE_PARM_DESC(folder, "name of the backing folder");
1488 +
1489 +module_param_named(vendor, mod_data.vendor, ushort, S_IRUGO);
1490 +MODULE_PARM_DESC(vendor, "USB Vendor ID");
1491 +
1492 +module_param_named(product, mod_data.product, ushort, S_IRUGO);
1493 +MODULE_PARM_DESC(product, "USB Product ID");
1494 +
1495 +module_param_named(release, mod_data.release, ushort, S_IRUGO);
1496 +MODULE_PARM_DESC(release, "USB release number");
1497 +
1498 +module_param_named(buflen, mod_data.buflen, uint, S_IRUGO);
1499 +MODULE_PARM_DESC(buflen, "I/O buffer size");
1500 +
1501 +
1502 +/*-------------------------------------------------------------------------*/
1503 +
1504 +/*
1505 + * DESCRIPTORS ... most are static, but strings and (full) configuration
1506 + * descriptors are built on demand.  Also the (static) config and interface
1507 + * descriptors are adjusted during sti_bind().
1508 + */
1509 +#define        STRING_MANUFACTURER     1
1510 +#define        STRING_PRODUCT          2
1511 +#define        STRING_SERIAL           3
1512 +#define        STRING_CONFIG           4
1513 +#define        STRING_INTERFACE        5
1514 +
1515 +
1516 +/* only one configuration */
1517 +#define        CONFIG_VALUE            1
1518 +
1519 +static struct usb_device_descriptor
1520 +device_desc = {
1521 +       .bLength =              sizeof device_desc,
1522 +       .bDescriptorType =      USB_DT_DEVICE,
1523 +
1524 +       .bcdUSB =               cpu_to_le16(0x0200),
1525 +       .bDeviceClass =         USB_CLASS_PER_INTERFACE,
1526 +
1527 +       /* the next three values can be overridden by module parameters */
1528 +       .idVendor =             cpu_to_le16(DRIVER_VENDOR_ID),
1529 +       .idProduct =            cpu_to_le16(DRIVER_PRODUCT_ID),
1530 +       .bcdDevice =            cpu_to_le16(0xffff),
1531 +
1532 +       .iManufacturer =        STRING_MANUFACTURER,
1533 +       .iProduct =             STRING_PRODUCT,
1534 +       .iSerialNumber =        STRING_SERIAL,
1535 +       .bNumConfigurations =   1,
1536 +};
1537 +
1538 +static struct usb_config_descriptor
1539 +config_desc = {
1540 +       .bLength =              sizeof config_desc,
1541 +       .bDescriptorType =      USB_DT_CONFIG,
1542 +
1543 +       /* wTotalLength computed by usb_gadget_config_buf() */
1544 +       .bNumInterfaces =       1,
1545 +       .bConfigurationValue =  CONFIG_VALUE,
1546 +       .iConfiguration =       STRING_CONFIG,
1547 +       .bmAttributes =         USB_CONFIG_ATT_ONE | USB_CONFIG_ATT_SELFPOWER,
1548 +       .bMaxPower =            CONFIG_USB_GADGET_VBUS_DRAW / 2,
1549 +};
1550 +
1551 +static struct usb_otg_descriptor
1552 +otg_desc = {
1553 +       .bLength =              sizeof(otg_desc),
1554 +       .bDescriptorType =      USB_DT_OTG,
1555 +
1556 +       .bmAttributes =         USB_OTG_SRP,
1557 +};
1558 +
1559 +
1560 +/* one interface */
1561 +static struct usb_interface_descriptor
1562 +intf_desc = {
1563 +       .bLength =              sizeof intf_desc,
1564 +       .bDescriptorType =      USB_DT_INTERFACE,
1565 +
1566 +       .bNumEndpoints =        3,      /* adjusted during sti_bind() */
1567 +       .bInterfaceClass =      USB_CLASS_STILL_IMAGE,
1568 +       .bInterfaceSubClass =   0x01,   /* Still Image Capture device */
1569 +       .bInterfaceProtocol =   0x01,   /* Bulk-only protocol */
1570 +       .iInterface =           STRING_INTERFACE,
1571 +};
1572 +
1573 +
1574 +/* two full-speed endpoint descriptors: bulk-in, bulk-out */
1575 +
1576 +static struct usb_endpoint_descriptor
1577 +fs_bulk_in_desc = {
1578 +       .bLength =              USB_DT_ENDPOINT_SIZE,
1579 +       .bDescriptorType =      USB_DT_ENDPOINT,
1580 +
1581 +       .bEndpointAddress =     USB_DIR_IN,
1582 +       .bmAttributes =         USB_ENDPOINT_XFER_BULK,
1583 +       /* wMaxPacketSize set by autoconfiguration */
1584 +};
1585 +
1586 +static struct usb_endpoint_descriptor
1587 +fs_bulk_out_desc = {
1588 +       .bLength =              USB_DT_ENDPOINT_SIZE,
1589 +       .bDescriptorType =      USB_DT_ENDPOINT,
1590 +
1591 +       .bEndpointAddress =     USB_DIR_OUT,
1592 +       .bmAttributes =         USB_ENDPOINT_XFER_BULK,
1593 +       /* wMaxPacketSize set by autoconfiguration */
1594 +};
1595 +
1596 +static struct usb_endpoint_descriptor
1597 +fs_intr_in_desc = {
1598 +       .bLength =              USB_DT_ENDPOINT_SIZE,
1599 +       .bDescriptorType =      USB_DT_ENDPOINT,
1600 +
1601 +       .bEndpointAddress =     USB_DIR_IN,
1602 +       .bmAttributes =         USB_ENDPOINT_XFER_INT,
1603 +       .wMaxPacketSize =       cpu_to_le16(2),
1604 +       .bInterval =            32,     /* frames -> 32 ms */
1605 +};
1606 +
1607 +static const struct usb_descriptor_header *fs_function[] = {
1608 +       (struct usb_descriptor_header *) &otg_desc,
1609 +       (struct usb_descriptor_header *) &intf_desc,
1610 +       (struct usb_descriptor_header *) &fs_bulk_in_desc,
1611 +       (struct usb_descriptor_header *) &fs_bulk_out_desc,
1612 +       (struct usb_descriptor_header *) &fs_intr_in_desc,
1613 +       NULL,
1614 +};
1615 +
1616 +#define        FS_FUNCTION_PRE_EP_ENTRIES      2
1617 +
1618 +
1619 +/*
1620 + * USB 2.0 devices need to expose both high speed and full speed
1621 + * descriptors, unless they only run at full speed.
1622 + *
1623 + * That means alternate endpoint descriptors (bigger packets)
1624 + * and a "device qualifier" ... plus more construction options
1625 + * for the config descriptor.
1626 + */
1627 +static struct usb_qualifier_descriptor
1628 +dev_qualifier = {
1629 +       .bLength =              sizeof dev_qualifier,
1630 +       .bDescriptorType =      USB_DT_DEVICE_QUALIFIER,
1631 +
1632 +       .bcdUSB =               cpu_to_le16(0x0200),
1633 +       .bDeviceClass =         USB_CLASS_PER_INTERFACE,
1634 +
1635 +       .bNumConfigurations =   1,
1636 +};
1637 +
1638 +static struct usb_endpoint_descriptor
1639 +hs_bulk_in_desc = {
1640 +       .bLength =              USB_DT_ENDPOINT_SIZE,
1641 +       .bDescriptorType =      USB_DT_ENDPOINT,
1642 +
1643 +       /* bEndpointAddress copied from fs_bulk_in_desc during sti_bind() */
1644 +       .bmAttributes =         USB_ENDPOINT_XFER_BULK,
1645 +       .wMaxPacketSize =       cpu_to_le16(512),
1646 +};
1647 +
1648 +static struct usb_endpoint_descriptor
1649 +hs_bulk_out_desc = {
1650 +       .bLength =              USB_DT_ENDPOINT_SIZE,
1651 +       .bDescriptorType =      USB_DT_ENDPOINT,
1652 +
1653 +       /* bEndpointAddress copied from fs_bulk_out_desc during sti_bind() */
1654 +       .bmAttributes =         USB_ENDPOINT_XFER_BULK,
1655 +       .wMaxPacketSize =       cpu_to_le16(512),
1656 +       .bInterval =            1,      /* NAK every 1 uframe */
1657 +};
1658 +
1659 +static struct usb_endpoint_descriptor
1660 +hs_intr_in_desc = {
1661 +       .bLength =              USB_DT_ENDPOINT_SIZE,
1662 +       .bDescriptorType =      USB_DT_ENDPOINT,
1663 +
1664 +       /* bEndpointAddress copied from fs_intr_in_desc during sti_bind() */
1665 +       .bmAttributes =         USB_ENDPOINT_XFER_INT,
1666 +       .wMaxPacketSize =       cpu_to_le16(2),
1667 +       .bInterval =            9,      /* 2**(9-1) = 256 uframes -> 32 ms */
1668 +};
1669 +
1670 +static const struct usb_descriptor_header *hs_function[] = {
1671 +       (struct usb_descriptor_header *) &otg_desc,
1672 +       (struct usb_descriptor_header *) &intf_desc,
1673 +       (struct usb_descriptor_header *) &hs_bulk_in_desc,
1674 +       (struct usb_descriptor_header *) &hs_bulk_out_desc,
1675 +       (struct usb_descriptor_header *) &hs_intr_in_desc,
1676 +       NULL,
1677 +};
1678 +
1679 +#define        HS_FUNCTION_PRE_EP_ENTRIES      2
1680 +
1681 +
1682 +/* maxpacket and other transfer characteristics vary by speed. */
1683 +static struct usb_endpoint_descriptor *
1684 +ep_desc(struct usb_gadget *g, struct usb_endpoint_descriptor *fs,
1685 +               struct usb_endpoint_descriptor *hs)
1686 +{
1687 +       if (gadget_is_dualspeed(g) && g->speed == USB_SPEED_HIGH)
1688 +               return hs;
1689 +
1690 +       return fs;
1691 +}
1692 +
1693 +static char            manufacturer[64];
1694 +static char            serial[13];
1695 +
1696 +/* static strings, in UTF-8 (for simplicity we use only ASCII characters) */
1697 +static struct usb_string               strings[] = {
1698 +       {STRING_MANUFACTURER,   manufacturer},
1699 +       {STRING_PRODUCT,        longname},
1700 +       {STRING_SERIAL,         serial},
1701 +       {STRING_CONFIG,         "Self-powered"},
1702 +       {STRING_INTERFACE,      "Still Image"},
1703 +       {}
1704 +};
1705 +
1706 +static struct usb_gadget_strings       stringtab = {
1707 +       .language       = 0x0409,               /* en-us */
1708 +       .strings        = strings,
1709 +};
1710 +
1711 +
1712 +/*-------------------------------------------------------------------------*/
1713 +
1714 +/* protocol, driver and device data structures */
1715 +
1716 +/* big enough to hold the biggest descriptor */
1717 +#define        EP0_BUFSIZE             256
1718 +
1719 +#define        DELAYED_STATUS          (EP0_BUFSIZE + 999)
1720 +
1721 +/* number of buffers we will use.  2 is enough for double-buffering */
1722 +#define        NUM_BUFFERS             2
1723 +
1724 +/* PIMA 15740, operation and response datasets have at most 5 parameters */
1725 +#define        PARAM_NUM_MAX           5
1726 +
1727 +/* PIMA 15740 generic container head length */
1728 +#define        PIMA15740_CONTAINER_LEN 12
1729 +
1730 +/* storage id, description */
1731 +#define        STORAGE_ID              0x00010001
1732 +#define        STORAGE_DESCRIPTION     "Built-in Storage"
1733 +
1734 +/* Still Image class-specific requests */
1735 +#define        STI_CANCEL_REQUEST                      0x64
1736 +#define        STI_GET_EXTENDED_EVENT_DATA             0x65
1737 +#define        STI_DEVICE_RESET_REQUEST                0x66
1738 +#define        STI_GET_DEVICE_STATUS                   0x67
1739 +
1740 +#define        STI_CANCEL_REQUEST_LENGTH               0x0006
1741 +#define        STI_CANCEL_REQUEST_CODE                 0x4001
1742 +
1743 +/* supported PIMA 15740 operations */
1744 +#define        PIMA15740_OP_GET_DEVICE_INFO            0x1001
1745 +#define        PIMA15740_OP_OPEN_SESSION               0x1002
1746 +#define        PIMA15740_OP_CLOSE_SESSION              0x1003
1747 +#define        PIMA15740_OP_GET_STORAGE_IDS            0x1004
1748 +#define        PIMA15740_OP_GET_STORAGE_INFO           0x1005
1749 +#define        PIMA15740_OP_GET_NUM_OBJECTS            0x1006
1750 +#define        PIMA15740_OP_GET_OBJECT_HANDLES         0x1007
1751 +#define        PIMA15740_OP_GET_OBJECT_INFO            0x1008
1752 +#define        PIMA15740_OP_GET_OBJECT                 0x1009
1753 +#define        PIMA15740_OP_DELETE_OBJECT              0x100b
1754 +#define        PIMA15740_OP_SEND_OBJECT_INFO           0x100c
1755 +#define        PIMA15740_OP_SEND_OBJECT                0x100d
1756 +#define        PIMA15740_OP_MOVE_OBJECT                0x1019
1757 +#define        PIMA15740_OP_COPY_OBJECT                0x101a
1758 +
1759 +/* PIMA 15740 responses definition */
1760 +#define        PIMA15740_RES_UNDEFINED                 0x2000
1761 +#define        PIMA15740_RES_OK                        0x2001
1762 +#define        PIMA15740_RES_GENERAL_ERROR             0x2002
1763 +#define        PIMA15740_RES_SESSION_NOT_OPEN          0x2003
1764 +#define        PIMA15740_RES_INVALID_TRANS_ID          0x2004
1765 +#define        PIMA15740_RES_OPERATION_NOT_SUPPORTED   0x2005
1766 +#define        PIMA15740_RES_PARAMETER_NOT_SUPPORTED   0x2006
1767 +#define        PIMA15740_RES_INCOMPLETE_TRANSFER       0x2007
1768 +#define        PIMA15740_RES_INVALID_STORAGE_ID        0x2008
1769 +#define        PIMA15740_RES_INVALID_OBJECT_HANDLE     0x2009
1770 +#define        PIMA15740_RES_DEVICE_PROP_NOT_SUPPORTED 0x200a
1771 +#define        PIMA15740_RES_INVALID_OBJECT_FORMAT     0x200b
1772 +#define        PIMA15740_RES_STORE_FULL                0x200c
1773 +#define        PIMA15740_RES_OBJECT_WRITE_PROTECTED    0x200d
1774 +#define        PIMA15740_RES_STORE_READ_ONLY           0x200e
1775 +#define        PIMA15740_RES_ACCESS_DENIED             0x200f
1776 +#define        PIMA15740_RES_NO_THUMBNAIL_PRESENT      0x2010
1777 +#define        PIMA15740_RES_SELF_TEST_FAILED          0x2011
1778 +#define        PIMA15740_RES_PARTIAL_DELETION          0x2012
1779 +#define        PIMA15740_RES_STORE_NOT_AVAILABLE       0x2013
1780 +#define        PIMA15740_RES_SPEC_BY_FORMAT_UNSUP      0x2014
1781 +#define        PIMA15740_RES_NO_VALID_OBJECT_INFO      0x2015
1782 +#define        PIMA15740_RES_INVALID_CODE_FORMAT       0x2016
1783 +#define        PIMA15740_RES_UNKNOWN_VENDOR_CODE       0x2017
1784 +#define        PIMA15740_RES_CAPTURE_ALREADY_TERM      0x2018
1785 +#define        PIMA15740_RES_DEVICE_BUSY               0x2019
1786 +#define        PIMA15740_RES_INVALID_PARENT_OBJECT     0x201a
1787 +#define        PIMA15740_RES_INVALID_DEV_PROP_FORMAT   0x201b
1788 +#define        PIMA15740_RES_INVALID_DEV_PROP_VALUE    0x201c
1789 +#define        PIMA15740_RES_INVALID_PARAMETER         0x201d
1790 +#define        PIMA15740_RES_SESSION_ALREADY_OPEN      0x201e
1791 +#define        PIMA15740_RES_TRANSACTION_CANCELLED     0x201f
1792 +#define        PIMA15740_RES_SPEC_OF_DESTINATION_UNSUP 0x2020
1793 +
1794 +/* PIMA 15740 functional mode */
1795 +#define        PIMA15740_STANDARD_MODE                 0x0000
1796 +#define        PIMA15740_SLEEP_STATE_MODE              0x0001
1797 +
1798 +/* PIMA 15740 storage type */
1799 +#define        PIMA15740_STOR_UNDEFINED                0x0000
1800 +#define        PIMA15740_STOR_FIXED_ROM                0x0001
1801 +#define        PIMA15740_STOR_REMOVABLE_ROM            0x0002
1802 +#define        PIMA15740_STOR_FIXED_RAM                0x0003
1803 +#define        PIMA15740_STOR_REMOVABLE_RAM            0x0004
1804 +
1805 +/* PIMA 15740 filesystem type */
1806 +#define        PIMA15740_FS_UNDEFINED                  0x0000
1807 +#define        PIMA15740_FS_GENERIC_FLAT               0x0001
1808 +#define        PIMA15740_FS_HIERARCHICAL               0x0002
1809 +#define        PIMA15740_FS_DCF                        0x0003
1810 +
1811 +/* PIMA 15740 access capability */
1812 +#define        PIMA15740_ACCESS_CAP_RW                 0x0000
1813 +#define        PIMA15740_ACCESS_CAP_RO_WO_DELITION     0x0001
1814 +#define        PIMA15740_ACCESS_CAP_RO_W_DELITION      0x0002
1815 +
1816 +/* PIMA 15740 object format codes */
1817 +#define        PIMA15740_FMT_A_UNDEFINED               0x3000
1818 +#define        PIMA15740_FMT_A_ASSOCIATION             0x3001
1819 +#define        PIMA15740_FMT_I_UNDEFINED               0x3800
1820 +#define        PIMA15740_FMT_I_EXIF_JPEG               0x3801
1821 +#define        PIMA15740_FMT_I_TIFF_EP                 0x3802
1822 +#define        PIMA15740_FMT_I_FLASHPIX                0x3803
1823 +#define        PIMA15740_FMT_I_BMP                     0x3804
1824 +#define        PIMA15740_FMT_I_CIFF                    0x3805
1825 +#define        PIMA15740_FMT_I_GIF                     0x3807
1826 +#define        PIMA15740_FMT_I_JFIF                    0x3808
1827 +#define        PIMA15740_FMT_I_PCD                     0x3809
1828 +#define        PIMA15740_FMT_I_PICT                    0x380a
1829 +#define        PIMA15740_FMT_I_PNG                     0x380b
1830 +#define        PIMA15740_FMT_I_TIFF                    0x380d
1831 +#define        PIMA15740_FMT_I_TIFF_IT                 0x380e
1832 +#define        PIMA15740_FMT_I_JP2                     0x380f
1833 +#define        PIMA15740_FMT_I_JPX                     0x3810
1834 +
1835 +/* PIMA 15740 object protection status */
1836 +#define        PIMA15740_OBJECT_NO_PROTECTION          0x0000
1837 +#define        PIMA15740_OBJECT_READ_ONLY              0x0001
1838 +
1839 +/* PIMA 15740 object association type */
1840 +#define        PIMA15740_AS_UNDEFINED                  0x0000
1841 +#define        PIMA15740_AS_GENERIC_FOLDER             0x0001
1842 +
1843 +
1844 +static const char storage_desc[] = STORAGE_DESCRIPTION;
1845 +static const char device_version[] = DRIVER_VERSION;
1846 +
1847 +
1848 +/*-------------------------------------------------------------------------*/
1849 +
1850 +/* PIMA 15740 data structure */
1851 +
1852 +enum pima15740_container_type {
1853 +       TYPE_UNDEFINED          = 0,
1854 +       TYPE_COMMAND_BLOCK      = 1,
1855 +       TYPE_DATA_BLOCK         = 2,
1856 +       TYPE_RESPONSE_BLOCK     = 3,
1857 +       TYPE_EVENT_BLOCK        = 4,
1858 +};
1859 +
1860 +/* PIMA15740 generic container structure, little endian */
1861 +struct pima15740_container {
1862 +       __le32                  container_len;
1863 +       __le16                  container_type;
1864 +       __le16                  code;
1865 +       __le32                  transaction_id;
1866 +} __attribute__ ((packed));
1867 +
1868 +/* data stage of Get Extended Event Data */
1869 +struct sti_ext_event {
1870 +       u16                     event_code;
1871 +       u32                     transaction_id;
1872 +       u16                     param_num;
1873 +} __attribute__ ((packed));
1874 +
1875 +/* data stage of Get Device Status Data */
1876 +struct sti_dev_status {
1877 +       u16                     wlength;
1878 +       u16                     code;
1879 +} __attribute__ ((packed));
1880 +
1881 +
1882 +/* DeviceInfo Dataset */
1883 +struct pima15740_device_info {
1884 +       u16     standard_version;
1885 +       u32     vendor_extension_id;
1886 +       u16     vendor_extension_version;
1887 +       u8      vendor_extension_desc_len;
1888 +       u8      vendor_extension_desc[0];
1889 +       u16     functional_mode;
1890 +       u32     operations_supported_count;
1891 +       u16     operations_supported[14];
1892 +       u32     events_supported_count;
1893 +       u16     events_supported[0];
1894 +       u32     device_properties_count;
1895 +       u16     device_properties_supported[0];
1896 +       u32     capture_formats_count;
1897 +       u16     capture_formats[0];
1898 +       u32     image_formats_count;
1899 +       u16     image_formats[10];
1900 +       u8      manufacturer_len;
1901 +       u8      manufacturer[sizeof(manufacturer) * 2];
1902 +       u8      model_len;
1903 +       u8      model[sizeof(longname) * 2];
1904 +       u8      device_version_len;
1905 +       u8      device_version[sizeof(device_version) * 2];
1906 +       u8      serial_number_len;
1907 +       u8      serial_number[sizeof(serial) * 2];
1908 +} __attribute__ ((packed));
1909 +
1910 +static struct pima15740_device_info sti_device_info = {
1911 +       .standard_version               = 100,
1912 +       .vendor_extension_id            = 0,
1913 +       .vendor_extension_version       = 0,
1914 +       .vendor_extension_desc_len      = 0,
1915 +       .functional_mode                = PIMA15740_STANDARD_MODE,
1916 +       .operations_supported_count     = 14,
1917 +       .operations_supported           = {
1918 +               cpu_to_le16(PIMA15740_OP_GET_DEVICE_INFO),
1919 +               cpu_to_le16(PIMA15740_OP_OPEN_SESSION),
1920 +               cpu_to_le16(PIMA15740_OP_CLOSE_SESSION),
1921 +               cpu_to_le16(PIMA15740_OP_GET_STORAGE_IDS),
1922 +               cpu_to_le16(PIMA15740_OP_GET_STORAGE_INFO),
1923 +               cpu_to_le16(PIMA15740_OP_GET_NUM_OBJECTS),
1924 +               cpu_to_le16(PIMA15740_OP_GET_OBJECT_HANDLES),
1925 +               cpu_to_le16(PIMA15740_OP_GET_OBJECT_INFO),
1926 +               cpu_to_le16(PIMA15740_OP_GET_OBJECT),
1927 +               cpu_to_le16(PIMA15740_OP_DELETE_OBJECT),
1928 +               cpu_to_le16(PIMA15740_OP_SEND_OBJECT_INFO),
1929 +               cpu_to_le16(PIMA15740_OP_SEND_OBJECT),
1930 +               cpu_to_le16(PIMA15740_OP_COPY_OBJECT),
1931 +               cpu_to_le16(PIMA15740_OP_MOVE_OBJECT)
1932 +       },
1933 +       .events_supported_count         = 0,
1934 +       .device_properties_count        = 0,
1935 +       .capture_formats_count          = 0,
1936 +       .image_formats_count            = 10,
1937 +       .image_formats                  = {
1938 +               cpu_to_le16(PIMA15740_FMT_I_EXIF_JPEG),
1939 +               cpu_to_le16(PIMA15740_FMT_I_JFIF),
1940 +               cpu_to_le16(PIMA15740_FMT_I_PNG),
1941 +               cpu_to_le16(PIMA15740_FMT_I_TIFF),
1942 +               cpu_to_le16(PIMA15740_FMT_I_TIFF_EP),
1943 +               cpu_to_le16(PIMA15740_FMT_I_TIFF_IT),
1944 +               cpu_to_le16(PIMA15740_FMT_I_BMP),
1945 +               cpu_to_le16(PIMA15740_FMT_I_GIF),
1946 +               cpu_to_le16(PIMA15740_FMT_I_UNDEFINED),
1947 +               cpu_to_le16(PIMA15740_FMT_A_UNDEFINED)
1948 +       },
1949 +       /* others will be filled in sti_bind() */
1950 +};
1951 +
1952 +
1953 +/* StorageInfo Dataset */
1954 +struct pima15740_storage_info {
1955 +       u16     storage_type;
1956 +       u16     filesystem_type;
1957 +       u16     access_capability;
1958 +       u64     max_capacity;
1959 +       u64     free_space_in_bytes;
1960 +       u32     free_space_in_images;
1961 +       u8      storage_desc_len;
1962 +       u8      storage_desc[sizeof(storage_desc) * 2];
1963 +       u8      volume_label_len;
1964 +       u8      volume_label[0];
1965 +} __attribute__ ((packed));
1966 +
1967 +static struct pima15740_storage_info sti_storage_info = {
1968 +       .storage_type           = cpu_to_le16(PIMA15740_STOR_FIXED_RAM),
1969 +       .filesystem_type        = cpu_to_le16(PIMA15740_FS_HIERARCHICAL),
1970 +       .access_capability      = cpu_to_le16(PIMA15740_ACCESS_CAP_RW),
1971 +       .storage_desc_len       = sizeof(storage_desc),
1972 +       .volume_label_len       = 0,
1973 +       /* others will be filled later */
1974 +};
1975 +
1976 +
1977 +/* ObjectInfo Dataset */
1978 +struct pima15740_object_info {
1979 +       u32     storage_id;
1980 +       u16     object_format;
1981 +       u16     protection_status;
1982 +       u32     object_compressed_size;
1983 +       u16     thumb_format;
1984 +       u32     thumb_compressed_size;
1985 +       u32     thumb_pix_width;
1986 +       u32     thumb_pix_height;
1987 +       u32     image_pix_width;
1988 +       u32     image_pix_height;
1989 +       u32     image_bit_depth;
1990 +       u32     parent_object;
1991 +       u16     association_type;
1992 +       u32     association_desc;
1993 +       u32     sequence_number;
1994 +       /* filename, capture date, modification date, keywords */
1995 +       u8      obj_strings[];  /* size will be fixed later */
1996 +} __attribute__ ((packed));
1997 +
1998 +/* object list element with object info data */
1999 +struct sti_object {
2000 +       struct list_head                list;
2001 +       u32                             obj_handle;
2002 +       u32                             parent_object;
2003 +       u32                             storage_id;
2004 +       int                             is_dir;
2005 +       int                             send_valid;
2006 +       size_t                          obj_info_size;
2007 +       char                            filename[NAME_MAX];
2008 +       char                            full_path[PATH_MAX];
2009 +       struct pima15740_object_info    obj_info;
2010 +};
2011 +
2012 +
2013 +/*-------------------------------------------------------------------------*/
2014 +
2015 +/* device data structure */
2016 +
2017 +enum sti_buffer_state {
2018 +       BUF_STATE_EMPTY = 0,
2019 +       BUF_STATE_FULL,
2020 +       BUF_STATE_BUSY
2021 +};
2022 +
2023 +struct sti_buffhd {
2024 +       void                    *buf;
2025 +       enum sti_buffer_state   state;
2026 +       struct sti_buffhd       *next;
2027 +       unsigned int            bulk_out_intended_length;
2028 +       struct usb_request      *inreq;
2029 +       int                     inreq_busy;
2030 +       struct usb_request      *outreq;
2031 +       int                     outreq_busy;
2032 +};
2033 +
2034 +enum sti_state {
2035 +       STI_STATE_COMMAND_PHASE = -10,  /* this one isn't used anywhere */
2036 +       STI_STATE_DATA_PHASE,
2037 +       STI_STATE_STATUS_PHASE,
2038 +
2039 +       STI_STATE_IDLE = 0,
2040 +       STI_STATE_ABORT_BULK_OUT,
2041 +       STI_STATE_CANCEL,
2042 +       STI_STATE_RESET,
2043 +       STI_STATE_INTERFACE_CHANGE,
2044 +       STI_STATE_CONFIG_CHANGE,
2045 +       STI_STATE_DISCONNECT,
2046 +       STI_STATE_EXIT,
2047 +       STI_STATE_TERMINATED
2048 +};
2049 +
2050 +enum data_direction {
2051 +       DATA_DIR_UNKNOWN = 0,
2052 +       DATA_DIR_FROM_HOST,
2053 +       DATA_DIR_TO_HOST,
2054 +       DATA_DIR_NONE
2055 +};
2056 +
2057 +struct sti_dev {
2058 +       /* lock protects: device, req, endpoints states */
2059 +       spinlock_t              lock;
2060 +
2061 +       /* filesem protects: backing folder in use */
2062 +       struct rw_semaphore     filesem;
2063 +
2064 +       struct usb_gadget       *gadget;
2065 +
2066 +       /* reference counting: wait until released */
2067 +       struct kref             ref;
2068 +
2069 +       /* handy copy of gadget->ep0 */
2070 +       struct usb_ep           *ep0;
2071 +
2072 +       /* for control responses */
2073 +       struct usb_request      *ep0req;
2074 +       unsigned int            ep0_req_tag;
2075 +       const char              *ep0req_name;
2076 +
2077 +       /* for interrupt responses */
2078 +       struct usb_request      *intreq;
2079 +       int                     intreq_busy;
2080 +       struct sti_buffhd       *intr_buffhd;
2081 +
2082 +       /* for exception handling */
2083 +       enum sti_state          state;
2084 +       unsigned int            exception_req_tag;
2085 +
2086 +       unsigned int            bulk_out_maxpacket;
2087 +       u8                      config, new_config;
2088 +
2089 +       unsigned int            running:1;
2090 +       unsigned int            bulk_in_enabled:1;
2091 +       unsigned int            bulk_out_enabled:1;
2092 +       unsigned int            intr_in_enabled:1;
2093 +       unsigned int            registered:1;
2094 +       unsigned int            session_open:1;
2095 +
2096 +       unsigned long           atomic_bitflags;
2097 +#define        REGISTERED              0
2098 +#define        CLEAR_BULK_HALTS        1
2099 +#define        SUSPENDED               2
2100 +
2101 +       struct usb_ep           *bulk_in;
2102 +       struct usb_ep           *bulk_out;
2103 +       struct usb_ep           *intr_in;
2104 +
2105 +       struct sti_buffhd       *next_buffhd_to_fill;
2106 +       struct sti_buffhd       *next_buffhd_to_drain;
2107 +       struct sti_buffhd       buffhds[NUM_BUFFERS];
2108 +
2109 +       int                     thread_wakeup_needed;
2110 +       struct completion       thread_notifier;
2111 +       struct task_struct      *thread_task;
2112 +
2113 +       __le32                  container_len;
2114 +       __le16                  container_type;
2115 +       __le16                  code;
2116 +       __le32                  transaction_id;
2117 +
2118 +       __le16                  response_code;
2119 +
2120 +       u32                     ops_params[PARAM_NUM_MAX];
2121 +       u32                     session_id;
2122 +       u32                     storage_id;
2123 +       u32                     object_num;
2124 +       u32                     sub_object_num;
2125 +
2126 +       char                    root_path[PATH_MAX];
2127 +       struct file             *root_filp;
2128 +       struct list_head        obj_list;
2129 +       struct list_head        tmp_obj_list;
2130 +
2131 +       struct sti_ext_event    ext_event_data;
2132 +       struct sti_dev_status   status_data;
2133 +
2134 +       struct device           dev;
2135 +};
2136 +
2137 +
2138 +/*-------------------------------------------------------------------------*/
2139 +
2140 +#define        backing_folder_is_open(sti)     ((sti)->root_filp != NULL)
2141 +
2142 +
2143 +typedef void (*sti_routine_t)(struct sti_dev *);
2144 +
2145 +static int exception_in_progress(struct sti_dev *sti)
2146 +{
2147 +       return (sti->state > STI_STATE_IDLE);
2148 +}
2149 +
2150 +/* make bulk-out requests be divisible by the maxpacket size */
2151 +static void set_bulk_out_req_length(struct sti_dev *sti,
2152 +               struct sti_buffhd *bh, unsigned int length)
2153 +{
2154 +       unsigned int    rem;
2155 +       VDBG(sti, "---> %s()\n", __func__);
2156 +
2157 +       bh->bulk_out_intended_length = length;
2158 +       rem = length % sti->bulk_out_maxpacket;
2159 +       if (rem > 0)
2160 +               length += sti->bulk_out_maxpacket - rem;
2161 +       bh->outreq->length = length;
2162 +
2163 +       VDBG(sti, "<--- %s()\n", __func__);
2164 +}
2165 +
2166 +
2167 +/* global variables */
2168 +static struct sti_dev                  *the_sti;
2169 +static struct usb_gadget_driver                sti_driver;
2170 +
2171 +static void close_backing_folder(struct sti_dev *sti);
2172 +
2173 +
2174 +/*-------------------------------------------------------------------------*/
2175 +
2176 +#ifdef VERBOSE_DEBUG
2177 +
2178 +static void dump_msg(struct sti_dev *sti, const char *label,
2179 +               const u8 *buf, unsigned int length)
2180 +{
2181 +       if (length < 512) {
2182 +               DBG(sti, "%s, length %u:\n", label, length);
2183 +               print_hex_dump(KERN_DEBUG, "", DUMP_PREFIX_OFFSET,
2184 +                               16, 1, buf, length, 0);
2185 +       }
2186 +}
2187 +
2188 +static void dump_cb(struct sti_dev *sti)
2189 +{
2190 +       print_hex_dump(KERN_DEBUG, "PIMA15740 Command Block: ",
2191 +                       DUMP_PREFIX_NONE, 16, 1, &sti->container_len,
2192 +                       PIMA15740_CONTAINER_LEN, 0);
2193 +}
2194 +
2195 +static void dump_device_info(struct sti_dev *sti)
2196 +{
2197 +       int     i;
2198 +
2199 +       VDBG(sti, "DeviceInfo Dataset:\n");
2200 +       VDBG(sti, "\tstandard_version: %u\n",
2201 +                       sti_device_info.standard_version);
2202 +       VDBG(sti, "\tvendor_extension_id: %u\n",
2203 +                       sti_device_info.vendor_extension_id);
2204 +       VDBG(sti, "\tvendor_extension_version: %u\n",
2205 +                       sti_device_info.vendor_extension_version);
2206 +       VDBG(sti, "\tvendor_extension_desc_len: %u\n",
2207 +                       sti_device_info.vendor_extension_desc_len);
2208 +       VDBG(sti, "\tfunctional_mode: 0x%04x\n",
2209 +                       sti_device_info.functional_mode);
2210 +       VDBG(sti, "\toperations_supported_count: %u\n",
2211 +                       sti_device_info.operations_supported_count);
2212 +       VDBG(sti, "\toperations_supported:\n");
2213 +       for (i = 0; i < sti_device_info.operations_supported_count; i++)
2214 +               VDBG(sti, "\t\t0x%04x\n",
2215 +                               sti_device_info.operations_supported[i]);
2216 +       VDBG(sti, "\tevents_supported_count: %u\n",
2217 +                       sti_device_info.events_supported_count);
2218 +       VDBG(sti, "\tdevice_properties_count: %u\n",
2219 +                       sti_device_info.device_properties_count);
2220 +       VDBG(sti, "\tcapture_formats_count: %u\n",
2221 +                       sti_device_info.capture_formats_count);
2222 +       VDBG(sti, "\timage_formats_count: %u\n",
2223 +                       sti_device_info.image_formats_count);
2224 +       VDBG(sti, "\tmanufacturer_len: %u\n",
2225 +                       sti_device_info.manufacturer_len);
2226 +       VDBG(sti, "\tmanufacturer: %s\n", manufacturer);
2227 +       VDBG(sti, "\tmodel_len: %u\n",
2228 +                       sti_device_info.model_len);
2229 +       VDBG(sti, "\tmodel: %s\n", longname);
2230 +       VDBG(sti, "\tdevice_version_len: %u\n",
2231 +                       sti_device_info.device_version_len);
2232 +       VDBG(sti, "\tdevice_version: %s\n", device_version);
2233 +       VDBG(sti, "\tserial_number_len: %u\n",
2234 +                       sti_device_info.serial_number_len);
2235 +       VDBG(sti, "\tserial_number: %s\n", serial);
2236 +}
2237 +
2238 +static void dump_storage_info(struct sti_dev *sti)
2239 +{
2240 +       VDBG(sti, "StorageInfo Dataset:\n");
2241 +       VDBG(sti, "\tstorage_type: 0x%04x\n", sti_storage_info.storage_type);
2242 +       VDBG(sti, "\tfilesystem_type: 0x%04x\n",
2243 +                       sti_storage_info.filesystem_type);
2244 +       VDBG(sti, "\taccess_capability: 0x%04x\n",
2245 +                       sti_storage_info.access_capability);
2246 +       VDBG(sti, "\tmax_capacity: %llu\n", sti_storage_info.max_capacity);
2247 +       VDBG(sti, "\tfree_space_in_bytes: %llu\n",
2248 +                       sti_storage_info.free_space_in_bytes);
2249 +       VDBG(sti, "\tfree_space_in_images: %u\n",
2250 +                       sti_storage_info.free_space_in_images);
2251 +       VDBG(sti, "\tstorage_desc_len: %u\n",
2252 +                       sti_storage_info.storage_desc_len);
2253 +       VDBG(sti, "\tstorage_desc: %s\n", storage_desc);
2254 +       VDBG(sti, "\tvolume_label_len: %u\n",
2255 +                       sti_storage_info.volume_label_len);
2256 +}
2257 +
2258 +static void dump_object_info(struct sti_dev *sti, struct sti_object *obj)
2259 +{
2260 +       u8      filename_len;
2261 +
2262 +       VDBG(sti, "ObjectInfo Dataset:\n");
2263 +       VDBG(sti, "\tstorage_id: 0x%08x\n", obj->obj_info.storage_id);
2264 +       VDBG(sti, "\tobject_format: 0x%04x\n", obj->obj_info.object_format);
2265 +       VDBG(sti, "\tprotection_status: 0x%04x\n",
2266 +                       obj->obj_info.protection_status);
2267 +       VDBG(sti, "\tobject_compressed_size: %u\n",
2268 +                       obj->obj_info.object_compressed_size);
2269 +       VDBG(sti, "\tthumb_format: %u\n", obj->obj_info.thumb_format);
2270 +       VDBG(sti, "\tthumb_compressed_size: %u\n",
2271 +                       obj->obj_info.thumb_compressed_size);
2272 +       VDBG(sti, "\tthumb_pix_width: %u\n",
2273 +                       obj->obj_info.thumb_pix_width);
2274 +       VDBG(sti, "\tthumb_pix_height: %u\n",
2275 +                       obj->obj_info.thumb_pix_height);
2276 +       VDBG(sti, "\timage_pix_width: %u\n",
2277 +                       obj->obj_info.image_pix_width);
2278 +       VDBG(sti, "\timage_pix_height: %u\n",
2279 +                       obj->obj_info.image_pix_height);
2280 +       VDBG(sti, "\timage_bit_depth: %u\n",
2281 +                       obj->obj_info.image_bit_depth);
2282 +       VDBG(sti, "\tparent_object: 0x%08x\n",
2283 +                       obj->obj_info.parent_object);
2284 +       VDBG(sti, "\tassociation_type: 0x%04x\n",
2285 +                       obj->obj_info.association_type);
2286 +       VDBG(sti, "\tassociation_desc: 0x%08x\n",
2287 +                       obj->obj_info.association_desc);
2288 +       VDBG(sti, "\tsequence_number: 0x%08x\n",
2289 +                       obj->obj_info.sequence_number);
2290 +       VDBG(sti, "\tfilename_len: %u\n", obj->obj_info.obj_strings[0]);
2291 +       filename_len = obj->obj_info.obj_strings[0];
2292 +       VDBG(sti, "\tfilename: %s\n", obj->filename);
2293 +       VDBG(sti, "\tcapture_date_len: %u\n",
2294 +                       obj->obj_info.obj_strings[filename_len * 2 + 1]);
2295 +       VDBG(sti, "\tmodification_date_len: %u\n",
2296 +                       obj->obj_info.obj_strings[filename_len * 2 + 2]);
2297 +       VDBG(sti, "\tkeywords_len: %u\n",
2298 +                       obj->obj_info.obj_strings[filename_len * 2 + 3]);
2299 +}
2300 +
2301 +#else
2302 +
2303 +static void dump_msg(struct sti_dev *sti, const char *label,
2304 +               const u8 *buf, unsigned int length)
2305 +{}
2306 +
2307 +static void dump_cb(struct sti_dev *sti)
2308 +{}
2309 +
2310 +static void dump_device_info(struct sti_dev *sti)
2311 +{}
2312 +
2313 +static void dump_storage_info(struct sti_dev *sti)
2314 +{}
2315 +
2316 +static void dump_object_info(struct sti_dev *sti, struct sti_object *obj)
2317 +{}
2318 +
2319 +#endif /* VERBOSE_DEBUG */
2320 +
2321 +
2322 +/*-------------------------------------------------------------------------*/
2323 +
2324 +
2325 +
2326 +/*
2327 + * Config descriptors must agree with the code that sets configurations
2328 + * and with code managing interfaces and their altsettings. They must
2329 + * also handle different speeds and other-speed requests.
2330 + */
2331 +static int populate_config_buf(struct usb_gadget *gadget,
2332 +               u8 *buf, u8 type, unsigned index)
2333 +{
2334 +       enum usb_device_speed                   speed = gadget->speed;
2335 +       int                                     len;
2336 +       const struct usb_descriptor_header      **function;
2337 +
2338 +       if (index > 0)
2339 +               return -EINVAL;
2340 +
2341 +       if (gadget_is_dualspeed(gadget) && type == USB_DT_OTHER_SPEED_CONFIG)
2342 +               speed = (USB_SPEED_FULL + USB_SPEED_HIGH) - speed;
2343 +       if (gadget_is_dualspeed(gadget) && speed == USB_SPEED_HIGH)
2344 +               function = hs_function;
2345 +       else
2346 +               function = fs_function;
2347 +
2348 +       /* for now, don't advertise srp-only devices */
2349 +       if (!gadget_is_otg(gadget))
2350 +               function++;
2351 +
2352 +       len = usb_gadget_config_buf(&config_desc, buf, EP0_BUFSIZE, function);
2353 +       ((struct usb_config_descriptor *) buf)->bDescriptorType = type;
2354 +
2355 +       return len;
2356 +}
2357 +
2358 +
2359 +/*-------------------------------------------------------------------------*/
2360 +
2361 +/* these routines may be called in process context or in_irq */
2362 +
2363 +/* caller must hold sti->lock */
2364 +static void wakeup_thread(struct sti_dev *sti)
2365 +{
2366 +       VDBG(sti, "---> %s()\n", __func__);
2367 +
2368 +       /* tell the main thread that something has happened */
2369 +       sti->thread_wakeup_needed = 1;
2370 +       if (sti->thread_task)
2371 +               wake_up_process(sti->thread_task);
2372 +
2373 +       VDBG(sti, "<--- %s()\n", __func__);
2374 +}
2375 +
2376 +
2377 +static void raise_exception(struct sti_dev *sti, enum sti_state new_state)
2378 +{
2379 +       unsigned long           flags;
2380 +       VDBG(sti, "---> %s()\n", __func__);
2381 +
2382 +       /*
2383 +        * Do nothing if a higher-priority exception is already in progress.
2384 +        * If a lower-or-equal priority exception is in progress, preempt it
2385 +        * and notify the main thread by sending it a signal.
2386 +        */
2387 +       spin_lock_irqsave(&sti->lock, flags);
2388 +       if (sti->state <= new_state) {
2389 +               sti->exception_req_tag = sti->ep0_req_tag;
2390 +               sti->state = new_state;
2391 +               if (sti->thread_task)
2392 +                       send_sig_info(SIGUSR1, SEND_SIG_FORCED,
2393 +                                       sti->thread_task);
2394 +       }
2395 +       spin_unlock_irqrestore(&sti->lock, flags);
2396 +
2397 +       VDBG(sti, "<--- %s()\n", __func__);
2398 +}
2399 +
2400 +
2401 +/*-------------------------------------------------------------------------*/
2402 +
2403 +/*
2404 + * The disconnect callback and ep0 routines. These always run in_irq,
2405 + * except that ep0_queue() is called in the main thread to acknowledge
2406 + * completion of various requests: set config, set interface, and
2407 + * Bulk-only device reset.
2408 + */
2409 +
2410 +static void sti_disconnect(struct usb_gadget *gadget)
2411 +{
2412 +       struct sti_dev          *sti = get_gadget_data(gadget);
2413 +       VDBG(sti, "---> %s()\n", __func__);
2414 +
2415 +       DBG(sti, "disconnect or port reset\n");
2416 +       raise_exception(sti, STI_STATE_DISCONNECT);
2417 +
2418 +       VDBG(sti, "<--- %s()\n", __func__);
2419 +}
2420 +
2421 +static int ep0_queue(struct sti_dev *sti)
2422 +{
2423 +       int     rc;
2424 +       VDBG(sti, "---> %s()\n", __func__);
2425 +
2426 +       rc = usb_ep_queue(sti->ep0, sti->ep0req, GFP_ATOMIC);
2427 +       if (rc != 0 && rc != -ESHUTDOWN) {
2428 +               /* we can't do much more than wait for a reset */
2429 +               WARNING(sti, "error in submission: %s --> %d\n",
2430 +                               sti->ep0->name, rc);
2431 +       }
2432 +
2433 +       VDBG(sti, "<--- %s()\n", __func__);
2434 +       return rc;
2435 +}
2436 +
2437 +static void ep0_complete(struct usb_ep *ep, struct usb_request *req)
2438 +{
2439 +       struct sti_dev          *sti = ep->driver_data;
2440 +       VDBG(sti, "---> %s()\n", __func__);
2441 +
2442 +       if (req->actual > 0)
2443 +               dump_msg(sti, sti->ep0req_name, req->buf, req->actual);
2444 +
2445 +       if (req->status || req->actual != req->length)
2446 +               VDBG(sti, "%s --> %d, %u/%u\n", __func__,
2447 +                               req->status, req->actual, req->length);
2448 +
2449 +       /* request was cancelled */
2450 +       if (req->status == -ECONNRESET)
2451 +               usb_ep_fifo_flush(ep);
2452 +
2453 +       if (req->status == 0 && req->context)
2454 +               ((sti_routine_t) (req->context))(sti);
2455 +
2456 +       VDBG(sti, "<--- %s()\n", __func__);
2457 +}
2458 +
2459 +
2460 +/*-------------------------------------------------------------------------*/
2461 +
2462 +/* endpoint completion handlers, always run in_irq */
2463 +
2464 +static void bulk_in_complete(struct usb_ep *ep, struct usb_request *req)
2465 +{
2466 +       struct sti_dev          *sti = ep->driver_data;
2467 +       struct sti_buffhd       *bh = req->context;
2468 +       VDBG(sti, "---> %s()\n", __func__);
2469 +
2470 +       if (req->status || req->actual != req->length)
2471 +               VDBG(sti, "%s --> %d, %u/%u\n", __func__,
2472 +                               req->status, req->actual, req->length);
2473 +       /* request was cancelled */
2474 +       if (req->status == -ECONNRESET)
2475 +               usb_ep_fifo_flush(ep);
2476 +
2477 +       /* hold the lock while we update the request and buffer states */
2478 +       smp_wmb();
2479 +       spin_lock(&sti->lock);
2480 +       bh->inreq_busy = 0;
2481 +       bh->state = BUF_STATE_EMPTY;
2482 +       wakeup_thread(sti);
2483 +       spin_unlock(&sti->lock);
2484 +
2485 +       VDBG(sti, "<--- %s()\n", __func__);
2486 +}
2487 +
2488 +static void bulk_out_complete(struct usb_ep *ep, struct usb_request *req)
2489 +{
2490 +       struct sti_dev          *sti = ep->driver_data;
2491 +       struct sti_buffhd       *bh = req->context;
2492 +       VDBG(sti, "---> %s()\n", __func__);
2493 +
2494 +       dump_msg(sti, "bulk-out", req->buf, req->actual);
2495 +       if (req->status || req->actual != bh->bulk_out_intended_length)
2496 +               VDBG(sti, "%s --> %d, %u/%u\n", __func__,
2497 +                               req->status, req->actual,
2498 +                               bh->bulk_out_intended_length);
2499 +
2500 +       /* request was cancelled */
2501 +       if (req->status == -ECONNRESET)
2502 +               usb_ep_fifo_flush(ep);
2503 +
2504 +       /* hold the lock while we update the request and buffer states */
2505 +       smp_wmb();
2506 +       spin_lock(&sti->lock);
2507 +       bh->outreq_busy = 0;
2508 +       bh->state = BUF_STATE_FULL;
2509 +       wakeup_thread(sti);
2510 +       spin_unlock(&sti->lock);
2511 +
2512 +       VDBG(sti, "<--- %s()\n", __func__);
2513 +}
2514 +
2515 +
2516 +/*-------------------------------------------------------------------------*/
2517 +
2518 +static int sti_set_halt(struct sti_dev *sti, struct usb_ep *ep)
2519 +{
2520 +       const char      *name;
2521 +       VDBG(sti, "---> %s()\n", __func__);
2522 +
2523 +       if (ep == sti->bulk_in)
2524 +               name = "bulk-in";
2525 +       else if (ep == sti->bulk_out)
2526 +               name = "bulk-out";
2527 +       else
2528 +               name = ep->name;
2529 +
2530 +       DBG(sti, "%s set halt\n", name);
2531 +       VDBG(sti, "<--- %s()\n", __func__);
2532 +
2533 +       return usb_ep_set_halt(ep);
2534 +}
2535 +
2536 +
2537 +static void received_cancel_request(struct sti_dev *sti)
2538 +{
2539 +       struct usb_request      *req = sti->ep0req;
2540 +       u16                     cancel_code;
2541 +       u32                     trans_id;
2542 +       int                     rc;
2543 +       VDBG(sti, "---> %s()\n", __func__);
2544 +
2545 +       /* error in command transfer */
2546 +       if (req->status || req->length != req->actual) {
2547 +               /* wait for reset */
2548 +               sti_set_halt(sti, sti->ep0);
2549 +               return;
2550 +       }
2551 +
2552 +       VDBG(sti, "receive cancel request\n");
2553 +
2554 +       if (!req->buf)
2555 +               return;
2556 +
2557 +       cancel_code = get_unaligned_le16(req->buf);
2558 +       if (cancel_code != cpu_to_le16(STI_CANCEL_REQUEST_CODE)) {
2559 +               VDBG(sti, "invalid cancel_code: 0x%04x\n", cancel_code);
2560 +               goto out;
2561 +       }
2562 +
2563 +       trans_id = get_unaligned_le32(req->buf + 2);
2564 +       if (trans_id != sti->transaction_id) {
2565 +               VDBG(sti, "invalid trans_id:0x%04x\n", trans_id);
2566 +               goto out;
2567 +       }
2568 +
2569 +       /* stall bulk endpoints */
2570 +       sti_set_halt(sti, sti->bulk_out);
2571 +
2572 +       rc = sti_set_halt(sti, sti->bulk_in);
2573 +       if (rc == -EAGAIN)
2574 +               VDBG(sti, "delayed bulk-in endpoint halt\n");
2575 +
2576 +       sti->response_code = PIMA15740_RES_DEVICE_BUSY;
2577 +out:
2578 +       raise_exception(sti, STI_STATE_CANCEL);
2579 +
2580 +       VDBG(sti, "<--- %s()\n", __func__);
2581 +}
2582 +
2583 +
2584 +/* ep0 class-specific request handlers, always run in_irq */
2585 +static int class_setup_req(struct sti_dev *sti,
2586 +               const struct usb_ctrlrequest *ctrl)
2587 +{
2588 +       struct usb_request      *req = sti->ep0req;
2589 +       int                     value = -EOPNOTSUPP;
2590 +       u16                     w_index = le16_to_cpu(ctrl->wIndex);
2591 +       u16                     w_value = le16_to_cpu(ctrl->wValue);
2592 +       u16                     w_length = le16_to_cpu(ctrl->wLength);
2593 +       VDBG(sti, "---> %s()\n", __func__);
2594 +
2595 +       if (!sti->config)
2596 +               return value;
2597 +
2598 +       /* handle class-specific requests */
2599 +       switch (ctrl->bRequest) {
2600 +
2601 +       case STI_CANCEL_REQUEST:
2602 +               if (ctrl->bRequestType != (USB_DIR_OUT |
2603 +                               USB_TYPE_CLASS | USB_RECIP_INTERFACE))
2604 +                       break;
2605 +               if (w_index != 0 || w_value != 0 || w_length != 6) {
2606 +                       value = -EDOM;
2607 +                       break;
2608 +               }
2609 +
2610 +               DBG(sti, "cancel request\n");
2611 +
2612 +               value = w_length;
2613 +               sti->ep0req->context = received_cancel_request;
2614 +               break;
2615 +
2616 +       case STI_GET_EXTENDED_EVENT_DATA:
2617 +               /* asynchronous events by interrupt endpoint */
2618 +               if (ctrl->bRequestType != (USB_DIR_IN |
2619 +                               USB_TYPE_CLASS | USB_RECIP_INTERFACE))
2620 +                       break;
2621 +               if (w_index != 0 || w_value != 0) {
2622 +                       value = -EDOM;
2623 +                       break;
2624 +               }
2625 +
2626 +               DBG(sti, "get extended event data\n");
2627 +
2628 +               sti->ext_event_data.event_code = PIMA15740_RES_OK;
2629 +               sti->ext_event_data.transaction_id = sti->transaction_id;
2630 +               sti->ext_event_data.param_num = 0;
2631 +
2632 +               value = min_t(unsigned, w_length,
2633 +                               sizeof(struct sti_ext_event));
2634 +               memcpy(req->buf, &sti->ext_event_data, value);
2635 +               break;
2636 +
2637 +       case STI_DEVICE_RESET_REQUEST:
2638 +               if (ctrl->bRequestType != (USB_DIR_OUT |
2639 +                               USB_TYPE_CLASS | USB_RECIP_INTERFACE))
2640 +                       break;
2641 +               if (w_index != 0 || w_value != 0 || w_length != 0) {
2642 +                       value = -EDOM;
2643 +                       break;
2644 +               }
2645 +
2646 +               /* Raise an exception to stop the current operation
2647 +                * and reinitialize our state. */
2648 +               DBG(sti, "device reset request\n");
2649 +
2650 +               sti->response_code = PIMA15740_RES_OK;
2651 +               sti->session_open = 1;
2652 +
2653 +               raise_exception(sti, STI_STATE_RESET);
2654 +               value = DELAYED_STATUS;
2655 +               break;
2656 +
2657 +       case STI_GET_DEVICE_STATUS:
2658 +               if (ctrl->bRequestType != (USB_DIR_IN |
2659 +                               USB_TYPE_CLASS | USB_RECIP_INTERFACE))
2660 +                       break;
2661 +               if (w_index != 0 || w_value != 0) {
2662 +                       value = -EDOM;
2663 +                       break;
2664 +               }
2665 +
2666 +               DBG(sti, "get device status\n");
2667 +               sti->status_data.wlength = 4;
2668 +               sti->status_data.code = sti->response_code;
2669 +
2670 +               value = min_t(unsigned, w_length,
2671 +                               sizeof(struct sti_dev_status));
2672 +               memcpy(req->buf, &sti->status_data, value);
2673 +               break;
2674 +
2675 +       default:
2676 +               DBG(sti, "unknown class-specific control req "
2677 +                       "%02x.%02x v%04x i%04x l%u\n",
2678 +                       ctrl->bRequestType, ctrl->bRequest,
2679 +                       le16_to_cpu(ctrl->wValue), w_index, w_length);
2680 +               break;
2681 +       }
2682 +
2683 +       VDBG(sti, "<--- %s()\n", __func__);
2684 +       return value;
2685 +}
2686 +
2687 +
2688 +/*-------------------------------------------------------------------------*/
2689 +
2690 +/* ep0 standard request handlers, always run in_irq */
2691 +
2692 +static int standard_setup_req(struct sti_dev *sti,
2693 +               const struct usb_ctrlrequest *ctrl)
2694 +{
2695 +       struct usb_request      *req = sti->ep0req;
2696 +       int                     value = -EOPNOTSUPP;
2697 +       u16                     w_index = le16_to_cpu(ctrl->wIndex);
2698 +       u16                     w_value = le16_to_cpu(ctrl->wValue);
2699 +       VDBG(sti, "---> %s()\n", __func__);
2700 +
2701 +       /* usually this just stores reply data in the pre-allocated ep0 buffer,
2702 +        * but config change events will also reconfigure hardware */
2703 +       switch (ctrl->bRequest) {
2704 +
2705 +       case USB_REQ_GET_DESCRIPTOR:
2706 +               if (ctrl->bRequestType != (USB_DIR_IN | USB_TYPE_STANDARD |
2707 +                               USB_RECIP_DEVICE))
2708 +                       break;
2709 +               switch (w_value >> 8) {
2710 +
2711 +               case USB_DT_DEVICE:
2712 +                       VDBG(sti, "get device descriptor\n");
2713 +                       value = sizeof device_desc;
2714 +                       memcpy(req->buf, &device_desc, value);
2715 +                       break;
2716 +               case USB_DT_DEVICE_QUALIFIER:
2717 +                       VDBG(sti, "get device qualifier\n");
2718 +                       if (!gadget_is_dualspeed(sti->gadget))
2719 +                               break;
2720 +                       value = sizeof dev_qualifier;
2721 +                       memcpy(req->buf, &dev_qualifier, value);
2722 +                       break;
2723 +
2724 +               case USB_DT_OTHER_SPEED_CONFIG:
2725 +                       VDBG(sti, "get other-speed config descriptor\n");
2726 +                       if (!gadget_is_dualspeed(sti->gadget))
2727 +                               break;
2728 +                       goto get_config;
2729 +               case USB_DT_CONFIG:
2730 +                       VDBG(sti, "get configuration descriptor\n");
2731 +get_config:
2732 +                       value = populate_config_buf(sti->gadget,
2733 +                                       req->buf,
2734 +                                       w_value >> 8,
2735 +                                       w_value & 0xff);
2736 +                       break;
2737 +
2738 +               case USB_DT_STRING:
2739 +                       VDBG(sti, "get string descriptor\n");
2740 +
2741 +                       /* wIndex == language code */
2742 +                       value = usb_gadget_get_string(&stringtab,
2743 +                                       w_value & 0xff, req->buf);
2744 +                       break;
2745 +               }
2746 +               break;
2747 +
2748 +       /* one config, two speeds */
2749 +       case USB_REQ_SET_CONFIGURATION:
2750 +               if (ctrl->bRequestType != (USB_DIR_OUT | USB_TYPE_STANDARD |
2751 +                               USB_RECIP_DEVICE))
2752 +                       break;
2753 +               VDBG(sti, "set configuration\n");
2754 +               if (w_value == CONFIG_VALUE || w_value == 0) {
2755 +                       sti->new_config = w_value;
2756 +
2757 +                       /* Raise an exception to wipe out previous transaction
2758 +                        * state (queued bufs, etc) and set the new config. */
2759 +                       raise_exception(sti, STI_STATE_CONFIG_CHANGE);
2760 +                       value = DELAYED_STATUS;
2761 +               }
2762 +               break;
2763 +
2764 +       case USB_REQ_GET_CONFIGURATION:
2765 +               if (ctrl->bRequestType != (USB_DIR_IN | USB_TYPE_STANDARD |
2766 +                               USB_RECIP_DEVICE))
2767 +                       break;
2768 +               VDBG(sti, "get configuration\n");
2769 +               *(u8 *) req->buf = sti->config;
2770 +               value = 1;
2771 +               break;
2772 +
2773 +       case USB_REQ_SET_INTERFACE:
2774 +               if (ctrl->bRequestType != (USB_DIR_OUT | USB_TYPE_STANDARD |
2775 +                               USB_RECIP_INTERFACE))
2776 +                       break;
2777 +               if (sti->config && w_index == 0) {
2778 +
2779 +                       /* Raise an exception to wipe out previous transaction
2780 +                        * state (queued bufs, etc) and install the new
2781 +                        * interface altsetting. */
2782 +                       raise_exception(sti, STI_STATE_INTERFACE_CHANGE);
2783 +                       value = DELAYED_STATUS;
2784 +               }
2785 +               break;
2786 +
2787 +       case USB_REQ_GET_INTERFACE:
2788 +               if (ctrl->bRequestType != (USB_DIR_IN | USB_TYPE_STANDARD |
2789 +                               USB_RECIP_INTERFACE))
2790 +                       break;
2791 +               if (!sti->config)
2792 +                       break;
2793 +               if (w_index != 0) {
2794 +                       value = -EDOM;
2795 +                       break;
2796 +               }
2797 +               VDBG(sti, "get interface\n");
2798 +               *(u8 *) req->buf = 0;
2799 +               value = 1;
2800 +               break;
2801 +
2802 +       default:
2803 +               VDBG(sti, "unknown control req %02x.%02x v%04x i%04x l%u\n",
2804 +                       ctrl->bRequestType, ctrl->bRequest,
2805 +                       w_value, w_index, le16_to_cpu(ctrl->wLength));
2806 +       }
2807 +
2808 +       VDBG(sti, "<--- %s()\n", __func__);
2809 +       return value;
2810 +}
2811 +
2812 +static int sti_setup(struct usb_gadget *gadget,
2813 +               const struct usb_ctrlrequest *ctrl)
2814 +{
2815 +       struct sti_dev          *sti = get_gadget_data(gadget);
2816 +       int                     rc;
2817 +       int                     w_length = le16_to_cpu(ctrl->wLength);
2818 +       VDBG(sti, "---> %s()\n", __func__);
2819 +
2820 +       /* record arrival of a new request */
2821 +       ++sti->ep0_req_tag;
2822 +       sti->ep0req->context = NULL;
2823 +       sti->ep0req->length = 0;
2824 +       dump_msg(sti, "ep0-setup", (u8 *) ctrl, sizeof(*ctrl));
2825 +
2826 +       if ((ctrl->bRequestType & USB_TYPE_MASK) == USB_TYPE_CLASS)
2827 +               rc = class_setup_req(sti, ctrl);
2828 +       else
2829 +               rc = standard_setup_req(sti, ctrl);
2830 +
2831 +       /* respond with data/status or defer until later */
2832 +       if (rc >= 0 && rc != DELAYED_STATUS) {
2833 +               rc = min(rc, w_length);
2834 +               sti->ep0req->length = rc;
2835 +               sti->ep0req->zero = rc < w_length;
2836 +               sti->ep0req_name = (ctrl->bRequestType & USB_DIR_IN ?
2837 +                               "ep0-in" : "ep0-out");
2838 +               rc = ep0_queue(sti);
2839 +       }
2840 +
2841 +       VDBG(sti, "<--- %s()\n", __func__);
2842 +       /* device either stalls (rc < 0) or reports success */
2843 +       return rc;
2844 +}
2845 +
2846 +
2847 +/*-------------------------------------------------------------------------*/
2848 +
2849 +/* all the following routines run in process context */
2850 +
2851 +/* use this for bulk or interrupt transfers, not ep0 */
2852 +static void start_transfer(struct sti_dev *sti, struct usb_ep *ep,
2853 +               struct usb_request *req, int *pbusy,
2854 +               enum sti_buffer_state *state)
2855 +{
2856 +       int     rc;
2857 +       VDBG(sti, "---> %s()\n", __func__);
2858 +
2859 +       if (ep == sti->bulk_in)
2860 +               dump_msg(sti, "bulk-in", req->buf, req->length);
2861 +       else if (ep == sti->intr_in)
2862 +               dump_msg(sti, "intr-in", req->buf, req->length);
2863 +
2864 +       spin_lock_irq(&sti->lock);
2865 +       *pbusy = 1;
2866 +       *state = BUF_STATE_BUSY;
2867 +       spin_unlock_irq(&sti->lock);
2868 +
2869 +       rc = usb_ep_queue(ep, req, GFP_KERNEL);
2870 +       VDBG(sti, "start_transfer, rc: %d\n", rc);
2871 +       if (rc != 0) {
2872 +               *pbusy = 0;
2873 +               *state = BUF_STATE_EMPTY;
2874 +               if (rc != -ESHUTDOWN && !(rc == -EOPNOTSUPP &&
2875 +                                               req->length == 0))
2876 +                       WARNING(sti, "error in submission: %s --> %d\n",
2877 +                                       ep->name, rc);
2878 +       }
2879 +
2880 +       VDBG(sti, "<--- %s()\n", __func__);
2881 +}
2882 +
2883 +
2884 +static int sleep_thread(struct sti_dev *sti)
2885 +{
2886 +       int     rc = 0;
2887 +       VDBG(sti, "---> %s()\n", __func__);
2888 +
2889 +       /* wait until a signal arrives or we are woken up */
2890 +       for (;;) {
2891 +               try_to_freeze();
2892 +               set_current_state(TASK_INTERRUPTIBLE);
2893 +               if (signal_pending(current)) {
2894 +                       rc = -EINTR;
2895 +                       break;
2896 +               }
2897 +               if (sti->thread_wakeup_needed)
2898 +                       break;
2899 +
2900 +               schedule();
2901 +       }
2902 +
2903 +       __set_current_state(TASK_RUNNING);
2904 +       sti->thread_wakeup_needed = 0;
2905 +
2906 +       VDBG(sti, "<--- %s()\n", __func__);
2907 +       return rc;
2908 +}
2909 +
2910 +
2911 +/*-------------------------------------------------------------------------*/
2912 +
2913 +static int fill_data_container(struct sti_buffhd *bh,
2914 +               struct sti_dev *sti, unsigned int size)
2915 +{
2916 +       struct pima15740_container      *rb;
2917 +       VDBG(sti, "---> %s()\n", __func__);
2918 +
2919 +       rb = bh->buf;
2920 +
2921 +       rb->container_len = size;
2922 +       rb->container_type = TYPE_DATA_BLOCK;
2923 +       rb->code = sti->code;
2924 +       rb->transaction_id = sti->transaction_id;
2925 +
2926 +       bh->inreq->zero = 0;
2927 +
2928 +       VDBG(sti, "<--- %s()\n", __func__);
2929 +       return 0;
2930 +}
2931 +
2932 +
2933 +static int send_response(struct sti_dev *sti, unsigned int code)
2934 +{
2935 +       struct sti_buffhd               *bh;
2936 +       struct pima15740_container      *rb;
2937 +       int                             rc = 0;
2938 +       VDBG(sti, "---> %s()\n", __func__);
2939 +
2940 +       /* wait for the next buffer to become available */
2941 +       bh = sti->next_buffhd_to_fill;
2942 +       while (bh->state != BUF_STATE_EMPTY) {
2943 +               rc = sleep_thread(sti);
2944 +               if (rc)
2945 +                       return rc;
2946 +       }
2947 +
2948 +       rb = bh->buf;
2949 +
2950 +       rb->container_len = PIMA15740_CONTAINER_LEN;
2951 +       rb->container_type = TYPE_RESPONSE_BLOCK;
2952 +       rb->code = code;
2953 +       rb->transaction_id = sti->transaction_id;
2954 +
2955 +       bh->inreq->length = PIMA15740_CONTAINER_LEN;
2956 +       bh->state = BUF_STATE_FULL;
2957 +       bh->inreq->zero = 0;
2958 +
2959 +       start_transfer(sti, sti->bulk_in, bh->inreq,
2960 +                       &bh->inreq_busy, &bh->state);
2961 +
2962 +       sti->next_buffhd_to_fill = bh->next;
2963 +
2964 +       VDBG(sti, "<--- %s()\n", __func__);
2965 +       return rc;
2966 +}
2967 +
2968 +
2969 +static int send_params_response(struct sti_dev *sti, unsigned int code,
2970 +               u32 p1, u32 p2, u32 p3, unsigned p_num)
2971 +{
2972 +       struct sti_buffhd               *bh;
2973 +       struct pima15740_container      *rb;
2974 +       int                             rc = 0;
2975 +       VDBG(sti, "---> %s()\n", __func__);
2976 +
2977 +       /* wait for the next buffer to become available */
2978 +       bh = sti->next_buffhd_to_fill;
2979 +       while (bh->state != BUF_STATE_EMPTY) {
2980 +               rc = sleep_thread(sti);
2981 +               if (rc)
2982 +                       return rc;
2983 +       }
2984 +
2985 +       rb = bh->buf;
2986 +
2987 +       rb->container_len = PIMA15740_CONTAINER_LEN + p_num * 4;
2988 +       rb->container_type = TYPE_RESPONSE_BLOCK;
2989 +       rb->code = code;
2990 +       rb->transaction_id = sti->transaction_id;
2991 +
2992 +       switch (p_num) {
2993 +       case 3:
2994 +               memcpy((u8 *)rb + PIMA15740_CONTAINER_LEN, &p1, 4);
2995 +               memcpy((u8 *)rb + PIMA15740_CONTAINER_LEN + 4, &p2, 4);
2996 +               memcpy((u8 *)rb + PIMA15740_CONTAINER_LEN + 8, &p3, 4);
2997 +               break;
2998 +       case 2:
2999 +               memcpy((u8 *)rb + PIMA15740_CONTAINER_LEN, &p1, 4);
3000 +               memcpy((u8 *)rb + PIMA15740_CONTAINER_LEN + 4, &p2, 4);
3001 +               break;
3002 +       case 1:
3003 +               memcpy((u8 *)rb + PIMA15740_CONTAINER_LEN, &p1, 4);
3004 +               break;
3005 +       default:
3006 +               break;
3007 +       }
3008 +
3009 +       bh->inreq->length = PIMA15740_CONTAINER_LEN + p_num * 4;
3010 +       bh->state = BUF_STATE_FULL;
3011 +       bh->inreq->zero = 0;
3012 +
3013 +       start_transfer(sti, sti->bulk_in, bh->inreq,
3014 +                       &bh->inreq_busy, &bh->state);
3015 +
3016 +       sti->next_buffhd_to_fill = bh->next;
3017 +
3018 +       VDBG(sti, "<--- %s()\n", __func__);
3019 +       return rc;
3020 +}
3021 +
3022 +/* ISO-8859-1 to UTF-16LE */
3023 +static unsigned short str_to_uni16(const char *src, char *dest)
3024 +{
3025 +       unsigned int    i;
3026 +
3027 +       for (i = 0; i < strlen(src); i++) {
3028 +               dest[i * 2] = src[i];
3029 +               dest[i * 2 + 1] = '\0';
3030 +       }
3031 +
3032 +       /* null-terminated string */
3033 +       dest[i * 2] = dest[i * 2 + 1] = '\0';
3034 +
3035 +       return (i + 1) * 2;
3036 +}
3037 +
3038 +/* UTF-16LE to ISO-8859-1 */
3039 +static void uni16_to_str(const char *src, char *dest, unsigned short len)
3040 +{
3041 +       unsigned int    i;
3042 +
3043 +       for (i = 0; i < len; i++)
3044 +               dest[i] = src[i * 2];
3045 +}
3046 +
3047 +
3048 +static int do_get_device_info(struct sti_dev *sti, struct sti_buffhd *bh)
3049 +{
3050 +       size_t          size;
3051 +       int             rc = 0;
3052 +       VDBG(sti, "---> %s()\n", __func__);
3053 +
3054 +       /* dump DeviceInfo Dataset */
3055 +       dump_device_info(sti);
3056 +
3057 +       size = sizeof sti_device_info;
3058 +       fill_data_container(bh, sti, PIMA15740_CONTAINER_LEN + size);
3059 +
3060 +       memcpy(bh->buf + PIMA15740_CONTAINER_LEN, &sti_device_info, size);
3061 +
3062 +       bh->inreq->length = PIMA15740_CONTAINER_LEN + size;
3063 +       bh->state = BUF_STATE_FULL;
3064 +       start_transfer(sti, sti->bulk_in, bh->inreq,
3065 +                       &bh->inreq_busy, &bh->state);
3066 +       sti->next_buffhd_to_fill = bh->next;
3067 +
3068 +       /* send response */
3069 +       rc = send_response(sti, PIMA15740_RES_OK);
3070 +
3071 +       VDBG(sti, "<--- %s()\n", __func__);
3072 +       return rc;
3073 +}
3074 +
3075 +
3076 +static int filldir_all(void *__buf, const char *name, int len,
3077 +               loff_t pos, u64 ino, unsigned int d_type)
3078 +{
3079 +       struct sti_dev          *sti = __buf;
3080 +       struct sti_object       *obj;
3081 +       char                    *ext;
3082 +       u8                      filename_len;
3083 +       char                    filename_utf16le[NAME_MAX * 2];
3084 +       size_t                  obj_size;
3085 +       u16                     object_format = PIMA15740_FMT_A_UNDEFINED;
3086 +       int                     rc = 0;
3087 +       VDBG(sti, "---> %s()\n", __func__);
3088 +       VDBG(sti, "name: %s, len: %d, pos: %lu, ino: %llu, d_type: %u\n",
3089 +                       name, len, (unsigned long)pos, ino, d_type);
3090 +
3091 +       /* ignore "." and ".." directories */
3092 +       if (!strcmp(name, ".") || !strcmp(name, ".."))
3093 +               goto out;
3094 +
3095 +       if (d_type != DT_DIR && d_type != DT_REG)
3096 +               goto out;
3097 +
3098 +       /* filename strings length */
3099 +       filename_len = len + 1;
3100 +       VDBG(sti, "filename_len: %u\n", filename_len);
3101 +
3102 +       /* sti_object size */
3103 +       obj_size = sizeof(struct sti_object) + 2 * filename_len + 4;
3104 +       VDBG(sti, "obj_size: %u\n", obj_size);
3105 +       /* obj_size > sizeof(struct sti_object) */
3106 +       obj = kzalloc(obj_size, GFP_KERNEL);
3107 +       if (!obj) {
3108 +               rc = -ENOMEM;
3109 +               goto out;
3110 +       }
3111 +
3112 +       /* fill part of sti_object info */
3113 +       obj->storage_id = STORAGE_ID;
3114 +       obj->send_valid = 0;
3115 +
3116 +       /* ObjectInfo Dataset size */
3117 +       obj->obj_info_size = sizeof(struct pima15740_object_info)
3118 +               + 2 * filename_len + 4;
3119 +       VDBG(sti, "obj_info_size: %u\n", obj->obj_info_size);
3120 +
3121 +       /* filename */
3122 +       memset(obj->filename, 0, sizeof(obj->filename));
3123 +       strncpy(obj->filename, name, len);
3124 +
3125 +       /* fill ObjectInfo Dataset */
3126 +       obj->obj_info.storage_id = cpu_to_le32(STORAGE_ID);
3127 +
3128 +       if (d_type == DT_DIR) {         /* association */
3129 +               object_format = PIMA15740_FMT_A_ASSOCIATION;
3130 +               obj->obj_info.association_type =
3131 +                       cpu_to_le16(PIMA15740_AS_GENERIC_FOLDER);
3132 +               obj->is_dir = 1;
3133 +       } else if (d_type == DT_REG) {  /* regular file */
3134 +               ext = strrchr(obj->filename, '.');
3135 +               if (ext) {
3136 +                       /* image object */
3137 +                       if (!strcasecmp(ext, ".jpg") ||
3138 +                                       !strcasecmp(ext, ".jpeg") ||
3139 +                                       !strcasecmp(ext, ".jpe"))
3140 +                               object_format = PIMA15740_FMT_I_EXIF_JPEG;
3141 +                       else if (!strcasecmp(ext, ".jfif"))
3142 +                               object_format = PIMA15740_FMT_I_JFIF;
3143 +                       else if (!strcasecmp(ext, ".tif") ||
3144 +                                       !strcasecmp(ext, ".tiff"))
3145 +                               object_format = PIMA15740_FMT_I_TIFF;
3146 +                       else if (!strcasecmp(ext, ".png"))
3147 +                               object_format = PIMA15740_FMT_I_PNG;
3148 +                       else if (!strcasecmp(ext, ".bmp"))
3149 +                               object_format = PIMA15740_FMT_I_BMP;
3150 +                       else if (!strcasecmp(ext, ".gif"))
3151 +                               object_format = PIMA15740_FMT_I_GIF;
3152 +                       else    /* undefined non-image object */
3153 +                               object_format = PIMA15740_FMT_A_UNDEFINED;
3154 +               } else  /* file without extension */
3155 +                       object_format = PIMA15740_FMT_A_UNDEFINED;
3156 +               obj->obj_info.association_type =
3157 +                       cpu_to_le16(PIMA15740_AS_UNDEFINED);
3158 +               obj->is_dir = 0;
3159 +       }
3160 +       obj->obj_info.object_format = cpu_to_le16(object_format);
3161 +
3162 +       /* protection_status, object_compressed_size will be filled later */
3163 +       obj->obj_info.thumb_format = cpu_to_le16(0);
3164 +       obj->obj_info.thumb_compressed_size = cpu_to_le32(0);
3165 +       obj->obj_info.thumb_pix_width = cpu_to_le32(0);
3166 +       obj->obj_info.thumb_pix_height = cpu_to_le32(0);
3167 +       obj->obj_info.image_pix_width = cpu_to_le32(0);
3168 +       obj->obj_info.image_pix_height = cpu_to_le32(0);
3169 +       obj->obj_info.image_bit_depth = cpu_to_le32(0);
3170 +
3171 +       obj->obj_info.association_desc = cpu_to_le32(0);
3172 +       obj->obj_info.sequence_number = cpu_to_le32(0);
3173 +
3174 +       /* filename_utf16le: UTF-16LE unicode string */
3175 +       obj->obj_info.obj_strings[0] = filename_len;
3176 +       memset(filename_utf16le, 0, sizeof(filename_utf16le));
3177 +       str_to_uni16(obj->filename, filename_utf16le);
3178 +       memcpy(obj->obj_info.obj_strings + 1, filename_utf16le,
3179 +                       filename_len * 2);
3180 +
3181 +       /* capture date */
3182 +       obj->obj_info.obj_strings[filename_len * 2 + 1] = 0;
3183 +
3184 +       /* modification date */
3185 +       obj->obj_info.obj_strings[filename_len * 2 + 2] = 0;
3186 +
3187 +       /* keywords */
3188 +       obj->obj_info.obj_strings[filename_len * 2 + 3] = 0;
3189 +
3190 +       /* increase object number */
3191 +       sti->sub_object_num++;
3192 +
3193 +       /* add to temp object list */
3194 +       list_add_tail(&obj->list, &sti->tmp_obj_list);
3195 +out:
3196 +       VDBG(sti, "<--- %s()\n", __func__);
3197 +       return rc;
3198 +}
3199 +
3200 +
3201 +/* alphabetic sort function */
3202 +static int alnumsort(const void *a, const void *b)
3203 +{
3204 +       const struct sti_object *oa = *(const struct sti_object **)a;
3205 +       const struct sti_object *ob = *(const struct sti_object **)b;
3206 +       return strcmp(oa->filename, ob->filename);
3207 +}
3208 +
3209 +
3210 +/* descend through the hierarchical folder recursively */
3211 +static int list_objects(struct sti_dev *sti, const char *folder_name,
3212 +               struct sti_object *folder_obj, bool recursive)
3213 +{
3214 +       struct file             *filp;
3215 +       struct dentry           *dentry;
3216 +       struct sti_object       *obj = NULL;
3217 +       struct sti_object       *tmp_obj;
3218 +       struct sti_object       **pobj, **temp_pobj = NULL;
3219 +       struct kstat            stat;
3220 +       u32                     parent_object;
3221 +       int                     i, rc = 0;
3222 +       VDBG(sti, "---> %s()\n", __func__);
3223 +
3224 +       /* root directory */
3225 +       if (!strcmp(folder_name, sti->root_path)) {
3226 +               filp = sti->root_filp;
3227 +               parent_object = 0;
3228 +               VDBG(sti, "root directory\n");
3229 +       } else {        /* subdirectory */
3230 +               filp = filp_open(folder_name, O_RDONLY | O_DIRECTORY, 0);
3231 +               if (IS_ERR(filp)) {
3232 +                       ERROR(sti, "unable to open folder: %s\n",
3233 +                                       folder_name);
3234 +                       return PTR_ERR(filp);
3235 +               }
3236 +               VDBG(sti, "folder_name: %s\n", folder_name);
3237 +               parent_object = folder_obj->obj_handle;
3238 +       }
3239 +       dentry = filp->f_dentry;
3240 +
3241 +       sti->sub_object_num = 0;
3242 +       filp->f_pos = 0;
3243 +       rc = vfs_readdir(filp, filldir_all, sti);
3244 +       if (rc)
3245 +               ERROR(sti, "vfs_readdir %s error: %d\n",
3246 +                               folder_name, rc);
3247 +       VDBG(sti, "%d objects in folder %s\n",
3248 +                       sti->sub_object_num, folder_name);
3249 +
3250 +       /* no file in the directory */
3251 +       if  (!sti->sub_object_num)
3252 +               goto out;
3253 +
3254 +       /* pre-allocated objects array */
3255 +       pobj = kzalloc((sti->sub_object_num + 1) * sizeof(struct sti_object *),
3256 +                       GFP_KERNEL);
3257 +       if (!pobj) {
3258 +               rc = -ENOMEM;
3259 +               goto out;
3260 +       }
3261 +
3262 +       temp_pobj = pobj;
3263 +
3264 +       i = 0;
3265 +       list_for_each_entry_safe(obj, tmp_obj, &sti->tmp_obj_list, list) {
3266 +               pobj[i] = obj;
3267 +               /* remove from temp object list */
3268 +               list_del_init(&obj->list);
3269 +               i++;
3270 +       }
3271 +       VDBG(sti, "i = %d\n", i);
3272 +       pobj[i] = NULL;
3273 +
3274 +       /* sort the objects array */
3275 +       sort(pobj, sti->sub_object_num, sizeof(struct sti_object *),
3276 +                       alnumsort, NULL);
3277 +
3278 +       while (*pobj) {
3279 +               /* increase total object number */
3280 +               sti->object_num++;
3281 +
3282 +               /* fill object handle */
3283 +               (*pobj)->obj_handle = sti->object_num;
3284 +
3285 +               /* fill parent object */
3286 +               (*pobj)->parent_object = cpu_to_le32(parent_object);
3287 +               (*pobj)->obj_info.parent_object = cpu_to_le32(parent_object);
3288 +
3289 +               /* object full path */
3290 +               memset((*pobj)->full_path, 0, sizeof((*pobj)->full_path));
3291 +               snprintf((*pobj)->full_path, sizeof((*pobj)->full_path),
3292 +                               "%s/%s", folder_name, (*pobj)->filename);
3293 +
3294 +               VDBG(sti, "full_path: %s, obj_handle: 0x%08x, "
3295 +                               "parent_object: 0x%08x\n",
3296 +                               (*pobj)->full_path, (*pobj)->obj_handle,
3297 +                               parent_object);
3298 +
3299 +               /* get file statistics info */
3300 +               rc = vfs_stat((char __user *)(*pobj)->full_path, &stat);
3301 +               if (rc) {
3302 +                       ERROR(sti, "vfs_stat error: %d\n", rc);
3303 +                       goto out;
3304 +               }
3305 +
3306 +               /* fill remained ObjectInfo Dataset */
3307 +               if (stat.mode & S_IWUSR)
3308 +                       (*pobj)->obj_info.protection_status =
3309 +                               cpu_to_le16(PIMA15740_OBJECT_NO_PROTECTION);
3310 +               else
3311 +                       (*pobj)->obj_info.protection_status =
3312 +                               cpu_to_le16(PIMA15740_OBJECT_READ_ONLY);
3313 +
3314 +               (*pobj)->obj_info.object_compressed_size =
3315 +                       cpu_to_le32((u32)stat.size);
3316 +
3317 +               /* add to object list */
3318 +               list_add_tail(&(*pobj)->list, &sti->obj_list);
3319 +
3320 +               if ((*pobj)->is_dir && recursive)
3321 +                       list_objects(sti, (*pobj)->full_path, *pobj, true);
3322 +
3323 +               pobj++;
3324 +       }
3325 +
3326 +out:
3327 +       /* free pre-allocated objects array */
3328 +       kfree(temp_pobj);
3329 +
3330 +       if (strcmp(folder_name, sti->root_path))
3331 +               filp_close(filp, current->files);
3332 +
3333 +       VDBG(sti, "<--- %s()\n", __func__);
3334 +       return rc;
3335 +}
3336 +
3337 +
3338 +static int do_open_session(struct sti_dev *sti)
3339 +{
3340 +       struct sti_object       *obj;
3341 +       u8                      filename_len;
3342 +       int                     rc = 0;
3343 +       VDBG(sti, "---> %s()\n", __func__);
3344 +
3345 +       if (sti->session_open) {
3346 +               sti->response_code = PIMA15740_RES_SESSION_ALREADY_OPEN;
3347 +               goto out;
3348 +       }
3349 +
3350 +       sti->session_id = sti->ops_params[0];
3351 +       VDBG(sti, "session_id: 0x%08x\n", sti->session_id);
3352 +       if (sti->session_id) {
3353 +               sti->response_code = PIMA15740_RES_OK;
3354 +               sti->session_open = 1;
3355 +       } else {
3356 +               sti->response_code = PIMA15740_RES_INVALID_PARAMETER;
3357 +               sti->session_open = 0;
3358 +               goto out;
3359 +       }
3360 +
3361 +       /* reset total object number */
3362 +       sti->object_num = 0;
3363 +
3364 +       /* root object init */
3365 +       filename_len = strlen(sti->root_filp->f_dentry->d_name.name) + 1;
3366 +       VDBG(sti, "root object: %s\n", sti->root_path);
3367 +       VDBG(sti, "filename_len: %u\n", filename_len);
3368 +       obj = kzalloc(sizeof(*obj), GFP_KERNEL);
3369 +       if (!obj) {
3370 +               sti->response_code = PIMA15740_RES_DEVICE_BUSY;
3371 +               goto out;
3372 +       }
3373 +
3374 +       spin_lock_irq(&sti->lock);
3375 +
3376 +       obj->obj_handle = 0;
3377 +       obj->parent_object = 0;
3378 +       obj->storage_id = STORAGE_ID;
3379 +       obj->is_dir = 1;
3380 +       obj->send_valid = 0;
3381 +       obj->obj_info_size = sizeof(struct pima15740_object_info);
3382 +
3383 +       /* root object filename */
3384 +       memset(obj->filename, 0, sizeof(obj->filename));
3385 +       strncpy(obj->filename, sti->root_filp->f_dentry->d_name.name,
3386 +                       sizeof(obj->filename));
3387 +       VDBG(sti, "root object filename: %s\n", obj->filename);
3388 +
3389 +       /* root object full path */
3390 +       memset(obj->full_path, 0, sizeof(obj->full_path));
3391 +       strncpy(obj->full_path, sti->root_path, sizeof(obj->full_path));
3392 +       VDBG(sti, "root object full path: %s\n", obj->full_path);
3393 +
3394 +       /* add to object list */
3395 +       list_add_tail(&obj->list, &sti->obj_list);
3396 +
3397 +       spin_unlock_irq(&sti->lock);
3398 +out:
3399 +       /* send response */
3400 +       rc = send_response(sti, sti->response_code);
3401 +
3402 +       VDBG(sti, "<--- %s()\n", __func__);
3403 +       return rc;
3404 +}
3405 +
3406 +
3407 +static int do_close_session(struct sti_dev *sti)
3408 +{
3409 +       struct sti_object       *obj, *tmp_obj;
3410 +       int                     rc = 0;
3411 +       VDBG(sti, "---> %s()\n", __func__);
3412 +
3413 +       if (sti->session_open) {
3414 +               sti->response_code = PIMA15740_RES_OK;
3415 +               sti->session_open = 0;
3416 +       } else {
3417 +               sti->response_code = PIMA15740_RES_SESSION_NOT_OPEN;
3418 +               goto out;
3419 +       }
3420 +
3421 +       spin_lock_irq(&sti->lock);
3422 +
3423 +       /* release object list */
3424 +       list_for_each_entry_safe(obj, tmp_obj, &sti->obj_list, list) {
3425 +               list_del_init(&obj->list);
3426 +               kfree(obj);
3427 +       }
3428 +
3429 +       spin_unlock_irq(&sti->lock);
3430 +
3431 +       DBG(sti, "release object list\n");
3432 +out:
3433 +       /* send response */
3434 +       rc = send_response(sti, sti->response_code);
3435 +
3436 +       VDBG(sti, "<--- %s()\n", __func__);
3437 +       return rc;
3438 +}
3439 +
3440 +
3441 +static int do_get_storage_ids(struct sti_dev *sti, struct sti_buffhd *bh)
3442 +{
3443 +       size_t          size;
3444 +       u32             i;
3445 +       int             rc = 0;
3446 +       VDBG(sti, "---> %s()\n", __func__);
3447 +
3448 +       if (!sti->session_open) {
3449 +               sti->response_code = PIMA15740_RES_SESSION_NOT_OPEN;
3450 +               goto out;
3451 +       }
3452 +
3453 +       sti->storage_id = cpu_to_le32(STORAGE_ID);
3454 +       DBG(sti, "storage_id: 0x%08x\n", sti->storage_id);
3455 +
3456 +       /* 4 bytes array number and 4 bytes storage id */
3457 +       size = 8;
3458 +       fill_data_container(bh, sti, PIMA15740_CONTAINER_LEN + size);
3459 +
3460 +       /* support one storage id */
3461 +       i = 1;
3462 +       memcpy(bh->buf + PIMA15740_CONTAINER_LEN, &i, 4);
3463 +       memcpy(bh->buf + PIMA15740_CONTAINER_LEN + 4, &sti->storage_id, 4);
3464 +
3465 +       bh->inreq->length = PIMA15740_CONTAINER_LEN + size;
3466 +       bh->state = BUF_STATE_FULL;
3467 +       start_transfer(sti, sti->bulk_in, bh->inreq,
3468 +                       &bh->inreq_busy, &bh->state);
3469 +       sti->next_buffhd_to_fill = bh->next;
3470 +
3471 +       sti->response_code = PIMA15740_RES_OK;
3472 +out:
3473 +       /* send response */
3474 +       rc = send_response(sti, sti->response_code);
3475 +
3476 +       VDBG(sti, "<--- %s()\n", __func__);
3477 +       return rc;
3478 +}
3479 +
3480 +
3481 +static int do_get_storage_info(struct sti_dev *sti, struct sti_buffhd *bh)
3482 +{
3483 +       size_t          size;
3484 +       u32             storage_id;
3485 +       u64             sbytes_max, sbytes_free;
3486 +       struct kstatfs  sbuf;
3487 +       int             rc = 0;
3488 +       VDBG(sti, "---> %s()\n", __func__);
3489 +
3490 +       if (!sti->session_open) {
3491 +               sti->response_code = PIMA15740_RES_SESSION_NOT_OPEN;
3492 +               goto out;
3493 +       }
3494 +
3495 +       /* storage id */
3496 +       storage_id = sti->ops_params[0];
3497 +       if (storage_id != sti->storage_id) {
3498 +               WARNING(sti, "invalid storage id: 0x%08x\n", storage_id);
3499 +               sti->response_code = PIMA15740_RES_INVALID_STORAGE_ID;
3500 +               goto out;
3501 +       }
3502 +
3503 +       /* get filesystem statistics info */
3504 +       rc = vfs_statfs(sti->root_filp->f_dentry, &sbuf);
3505 +       if (rc) {
3506 +               sti->response_code = PIMA15740_RES_ACCESS_DENIED;
3507 +               goto out;
3508 +       }
3509 +
3510 +       /* fill remained items in StorageInfo Dataset */
3511 +       sbytes_max = (u64) sbuf.f_bsize * sbuf.f_blocks;
3512 +       sbytes_free = (u64) sbuf.f_bsize * sbuf.f_bfree;
3513 +       sti_storage_info.max_capacity = cpu_to_le64(sbytes_max);
3514 +       sti_storage_info.free_space_in_bytes = cpu_to_le64(sbytes_free);
3515 +       sti_storage_info.free_space_in_images = cpu_to_le32((u32)~0);
3516 +       str_to_uni16(storage_desc, sti_storage_info.storage_desc);
3517 +
3518 +       /* dump StorageInfo Dataset */
3519 +       dump_storage_info(sti);
3520 +
3521 +       memcpy(bh->buf + PIMA15740_CONTAINER_LEN, &sti_storage_info,
3522 +                       sizeof(sti_storage_info));
3523 +
3524 +       size = PIMA15740_CONTAINER_LEN + sizeof(sti_storage_info);
3525 +       fill_data_container(bh, sti, size);
3526 +
3527 +       bh->inreq->length = size;
3528 +       bh->state = BUF_STATE_FULL;
3529 +       start_transfer(sti, sti->bulk_in, bh->inreq,
3530 +                       &bh->inreq_busy, &bh->state);
3531 +       sti->next_buffhd_to_fill = bh->next;
3532 +
3533 +       sti->response_code = PIMA15740_RES_OK;
3534 +out:
3535 +       /* send response */
3536 +       rc = send_response(sti, sti->response_code);
3537 +
3538 +       VDBG(sti, "<--- %s()\n", __func__);
3539 +       return rc;
3540 +}
3541 +
3542 +
3543 +static int do_get_num_objects(struct sti_dev *sti, struct sti_buffhd *bh)
3544 +{
3545 +       int             i;
3546 +       int             rc = 0;
3547 +       VDBG(sti, "---> %s()\n", __func__);
3548 +
3549 +       if (!sti->session_open) {
3550 +               sti->response_code = PIMA15740_RES_SESSION_NOT_OPEN;
3551 +               goto out;
3552 +       }
3553 +
3554 +       for (i = 0; i < PARAM_NUM_MAX; i++)
3555 +               VDBG(sti, "parameter[%u]: 0x%08x\n",
3556 +                               i + 1, sti->ops_params[i]);
3557 +
3558 +       if (!backing_folder_is_open(sti)) {
3559 +               ERROR(sti, "backing folder is not open\n");
3560 +               sti->response_code = PIMA15740_RES_STORE_NOT_AVAILABLE;
3561 +               goto out;
3562 +       }
3563 +
3564 +       DBG(sti, "total object number: %u\n", sti->object_num);
3565 +
3566 +       sti->response_code = PIMA15740_RES_OK;
3567 +out:
3568 +       /* send response */
3569 +       rc = send_params_response(sti, sti->response_code,
3570 +                       sti->object_num, 0, 0,
3571 +                       1);
3572 +
3573 +       VDBG(sti, "<--- %s()\n", __func__);
3574 +       return rc;
3575 +}
3576 +
3577 +
3578 +static int do_get_object_handles(struct sti_dev *sti, struct sti_buffhd *bh)
3579 +{
3580 +       size_t                  size;
3581 +       u32                     storage_id, obj_handle;
3582 +       u32                     new_obj_num, old_obj_num, tmp_obj_num;
3583 +       char                    *cur_path = NULL;
3584 +       struct sti_object       *obj;
3585 +       int                     i, rc = 0;
3586 +
3587 +       VDBG(sti, "---> %s()\n", __func__);
3588 +
3589 +       if (!sti->session_open) {
3590 +               sti->response_code = PIMA15740_RES_SESSION_NOT_OPEN;
3591 +               goto out;
3592 +       }
3593 +
3594 +       for (i = 0; i < PARAM_NUM_MAX; i++)
3595 +               VDBG(sti, "parameter[%u]: 0x%08x\n",
3596 +                               i + 1, sti->ops_params[i]);
3597 +
3598 +       if (!backing_folder_is_open(sti)) {
3599 +               ERROR(sti, "backing folder is not open\n");
3600 +               sti->response_code = PIMA15740_RES_STORE_NOT_AVAILABLE;
3601 +               goto out;
3602 +       }
3603 +
3604 +       storage_id = sti->ops_params[0];
3605 +       obj_handle = sti->ops_params[2];
3606 +       old_obj_num = sti->object_num;
3607 +
3608 +       if (storage_id == 0xffffffff) {
3609 +               /* list all objects recursive */
3610 +               rc = list_objects(sti, sti->root_path, NULL, true);
3611 +               new_obj_num = sti->object_num;
3612 +       } else {
3613 +               /* list objects of current folder */
3614 +               list_for_each_entry(obj, &sti->obj_list, list) {
3615 +                       if (obj->obj_handle == obj_handle)
3616 +                               break;
3617 +               }
3618 +
3619 +               if (obj_handle == 0xffffffff)
3620 +                       cur_path = sti->root_path;
3621 +               else
3622 +                       cur_path = obj->full_path;
3623 +               VDBG(sti, "current path: %s\n", cur_path);
3624 +
3625 +               if (cur_path)
3626 +                       rc = list_objects(sti, cur_path, obj, false);
3627 +               else {
3628 +                       sti->response_code = PIMA15740_RES_DEVICE_BUSY;
3629 +                       goto out;
3630 +               }
3631 +
3632 +               new_obj_num = sti->sub_object_num;
3633 +       }
3634 +
3635 +       if (rc) {
3636 +               sti->response_code = PIMA15740_RES_DEVICE_BUSY;
3637 +               goto out;
3638 +       }
3639 +
3640 +       /* 4 bytes array number plus object handles size */
3641 +       size = 4 + new_obj_num * 4;
3642 +       VDBG(sti, "object number: %u, payload size: %u\n",
3643 +                       new_obj_num, size);
3644 +       fill_data_container(bh, sti, PIMA15740_CONTAINER_LEN + size);
3645 +
3646 +       /* fill object handles array */
3647 +       memcpy(bh->buf + PIMA15740_CONTAINER_LEN, &new_obj_num, 4);
3648 +       for (i = 1; i <= new_obj_num; i++) {
3649 +               tmp_obj_num = old_obj_num + i;
3650 +               memcpy(bh->buf + PIMA15740_CONTAINER_LEN + i * 4,
3651 +                               &tmp_obj_num, 4);
3652 +       }
3653 +
3654 +       bh->inreq->length = PIMA15740_CONTAINER_LEN + size;
3655 +       bh->state = BUF_STATE_FULL;
3656 +       start_transfer(sti, sti->bulk_in, bh->inreq,
3657 +                       &bh->inreq_busy, &bh->state);
3658 +       sti->next_buffhd_to_fill = bh->next;
3659 +
3660 +       sti->response_code = PIMA15740_RES_OK;
3661 +out:
3662 +       /* send response */
3663 +       rc = send_response(sti, sti->response_code);
3664 +
3665 +       VDBG(sti, "<--- %s()\n", __func__);
3666 +       return rc;
3667 +}
3668 +
3669 +
3670 +static int do_get_object_info(struct sti_dev *sti, struct sti_buffhd *bh)
3671 +{
3672 +       size_t                  size = 0;
3673 +       u32                     obj_handle;
3674 +       struct sti_object       *obj;
3675 +       int                     rc = 0;
3676 +       VDBG(sti, "---> %s()\n", __func__);
3677 +
3678 +       if (!sti->session_open) {
3679 +               sti->response_code = PIMA15740_RES_SESSION_NOT_OPEN;
3680 +               goto out;
3681 +       }
3682 +
3683 +       obj_handle = sti->ops_params[0];
3684 +       if (obj_handle == 0 || obj_handle > sti->object_num) {
3685 +               WARNING(sti, "invalid object handle: 0x%08x\n", obj_handle);
3686 +               sti->response_code = PIMA15740_RES_INVALID_OBJECT_HANDLE;
3687 +               goto out;
3688 +       }
3689 +
3690 +       spin_lock_irq(&sti->lock);
3691 +
3692 +       /* find the object */
3693 +       list_for_each_entry(obj, &sti->obj_list, list) {
3694 +               if (obj->obj_handle == obj_handle)
3695 +                       break;
3696 +       }
3697 +
3698 +       memcpy(bh->buf + PIMA15740_CONTAINER_LEN, &obj->obj_info,
3699 +                       obj->obj_info_size);
3700 +       size = PIMA15740_CONTAINER_LEN + obj->obj_info_size;
3701 +       fill_data_container(bh, sti, size);
3702 +
3703 +       bh->inreq->length = size;
3704 +       bh->state = BUF_STATE_FULL;
3705 +
3706 +       spin_unlock_irq(&sti->lock);
3707 +
3708 +       start_transfer(sti, sti->bulk_in, bh->inreq,
3709 +                       &bh->inreq_busy, &bh->state);
3710 +       sti->next_buffhd_to_fill = bh->next;
3711 +
3712 +       DBG(sti, "get object info: %s\n", obj->full_path);
3713 +       VDBG(sti, "obj_handle: 0x%08x\n", obj->obj_handle);
3714 +
3715 +       /* dump ObjectInfo Dataset */
3716 +       dump_object_info(sti, obj);
3717 +
3718 +       sti->response_code = PIMA15740_RES_OK;
3719 +out:
3720 +       /* send response */
3721 +       rc = send_response(sti, sti->response_code);
3722 +
3723 +       VDBG(sti, "<--- %s()\n", __func__);
3724 +       return rc;
3725 +}
3726 +
3727 +
3728 +static int do_get_object(struct sti_dev *sti, struct sti_buffhd *bh)
3729 +{
3730 +       u32                     obj_handle;
3731 +       loff_t                  file_size, file_offset, file_offset_tmp;
3732 +       unsigned int            amount_left, amount;
3733 +       ssize_t                 nread;
3734 +       struct sti_object       *obj;
3735 +       struct file             *filp = NULL;
3736 +       struct inode            *inode = NULL;
3737 +       char __user             *buf;
3738 +       int                     rc = 0;
3739 +       VDBG(sti, "---> %s()\n", __func__);
3740 +
3741 +       if (!sti->session_open) {
3742 +               sti->response_code = PIMA15740_RES_SESSION_NOT_OPEN;
3743 +               goto out1;
3744 +       }
3745 +
3746 +       obj_handle = sti->ops_params[0];
3747 +       if (obj_handle == 0 || obj_handle > sti->object_num) {
3748 +               WARNING(sti, "invalid object handle: 0x%08x\n", obj_handle);
3749 +               sti->response_code = PIMA15740_RES_INVALID_OBJECT_HANDLE;
3750 +               goto out1;
3751 +       }
3752 +
3753 +       spin_lock_irq(&sti->lock);
3754 +
3755 +       /* find the object */
3756 +       list_for_each_entry(obj, &sti->obj_list, list) {
3757 +               if (obj->obj_handle == obj_handle)
3758 +                       break;
3759 +       }
3760 +
3761 +       spin_unlock_irq(&sti->lock);
3762 +
3763 +       /* open object file */
3764 +       filp = filp_open(obj->full_path, O_RDONLY | O_LARGEFILE, 0);
3765 +       if (IS_ERR(filp)) {
3766 +               ERROR(sti, "unable to open file: %s. Err = %d\n",
3767 +                               obj->full_path, (int) PTR_ERR(filp));
3768 +               sti->response_code = PIMA15740_RES_STORE_NOT_AVAILABLE;
3769 +               goto out1;
3770 +       }
3771 +
3772 +       /* figure out the size and read the remaining amount */
3773 +       inode = filp->f_dentry->d_inode;
3774 +       file_size = i_size_read(inode->i_mapping->host);
3775 +       VDBG(sti, "object file size: %llu\n", (unsigned long long) file_size);
3776 +       if (unlikely(file_size == 0)) {
3777 +               sti->response_code = PIMA15740_RES_STORE_NOT_AVAILABLE;
3778 +               goto out2;
3779 +       }
3780 +
3781 +       DBG(sti, "get object: %s\n", obj->full_path);
3782 +
3783 +       file_offset = 0;
3784 +       amount_left = file_size;
3785 +
3786 +       while (amount_left > 0) {
3787 +               bh = sti->next_buffhd_to_fill;
3788 +               while (bh->state != BUF_STATE_EMPTY) {
3789 +                       rc = sleep_thread(sti);
3790 +                       if (rc) {
3791 +                               filp_close(filp, current->files);
3792 +                               return rc;
3793 +                       }
3794 +               }
3795 +
3796 +               /* don't read more than the buffer size  */
3797 +               if (file_offset == 0) {
3798 +                       fill_data_container(bh, sti,
3799 +                                       file_size + PIMA15740_CONTAINER_LEN);
3800 +                       buf = (char __user *) bh->buf +
3801 +                               PIMA15740_CONTAINER_LEN;
3802 +                       amount = min((unsigned int) amount_left,
3803 +                               mod_data.buflen - PIMA15740_CONTAINER_LEN);
3804 +               } else {
3805 +                       buf = (char __user *) bh->buf;
3806 +                       amount = min((unsigned int) amount_left,
3807 +                                       mod_data.buflen);
3808 +               }
3809 +
3810 +               /* no more left to read */
3811 +               if (amount == 0)
3812 +                       break;
3813 +
3814 +               /* perform the read */
3815 +               file_offset_tmp = file_offset;
3816 +               nread = vfs_read(filp, buf, amount, &file_offset_tmp);
3817 +               VDBG(sti, "file read %u @ %llu -> %d\n", amount,
3818 +                               (unsigned long long) file_offset,
3819 +                               (int) nread);
3820 +
3821 +               if (signal_pending(current)) {
3822 +                       filp_close(filp, current->files);
3823 +                       return -EINTR;
3824 +               }
3825 +
3826 +               if (nread < 0) {
3827 +                       WARNING(sti, "error in file read: %d\n",
3828 +                                       (int) nread);
3829 +                       nread = 0;
3830 +               } else if (nread < amount) {
3831 +                       WARNING(sti, "partial file read: %d/%u\n",
3832 +                                       (int) nread, amount);
3833 +                       /* round down to a block */
3834 +                       nread -= (nread & 511);
3835 +               }
3836 +
3837 +               /*
3838 +                * PIMA 15740 generic container head resides in
3839 +                * first data block payload
3840 +                */
3841 +               if (file_offset == 0)
3842 +                       bh->inreq->length = nread + PIMA15740_CONTAINER_LEN;
3843 +               else
3844 +                       bh->inreq->length = nread;
3845 +               bh->state = BUF_STATE_FULL;
3846 +               bh->inreq->zero = 0;
3847 +
3848 +               file_offset += nread;
3849 +               amount_left -= nread;
3850 +
3851 +               /* send this buffer and go read some more */
3852 +               start_transfer(sti, sti->bulk_in, bh->inreq,
3853 +                               &bh->inreq_busy, &bh->state);
3854 +               sti->next_buffhd_to_fill = bh->next;
3855 +       }
3856 +
3857 +       sti->response_code = PIMA15740_RES_OK;
3858 +out2:
3859 +       filp_close(filp, current->files);
3860 +out1:
3861 +       /* send response */
3862 +       rc = send_response(sti, sti->response_code);
3863 +
3864 +       VDBG(sti, "<--- %s()\n", __func__);
3865 +       return rc;
3866 +}
3867 +
3868 +
3869 +static int do_delete_object(struct sti_dev *sti, struct sti_buffhd *bh)
3870 +{
3871 +       u32                     obj_handle;
3872 +       struct sti_object       *obj, *tmp_obj;
3873 +       struct nameidata        nd;
3874 +       int                     i;
3875 +       int                     rc = 0;
3876 +       VDBG(sti, "---> %s()\n", __func__);
3877 +
3878 +       if (!sti->session_open) {
3879 +               sti->response_code = PIMA15740_RES_SESSION_NOT_OPEN;
3880 +               goto out;
3881 +       }
3882 +
3883 +       for (i = 0; i < PARAM_NUM_MAX; i++)
3884 +               VDBG(sti, "parameter[%u]: 0x%08x\n",
3885 +                               i + 1, sti->ops_params[i]);
3886 +
3887 +       obj_handle = sti->ops_params[0];
3888 +       if (obj_handle == 0 || obj_handle > sti->object_num) {
3889 +               WARNING(sti, "invalid object handle: 0x%08x\n", obj_handle);
3890 +               sti->response_code = PIMA15740_RES_INVALID_OBJECT_HANDLE;
3891 +               goto out;
3892 +       }
3893 +
3894 +       spin_lock_irq(&sti->lock);
3895 +
3896 +       /* find the object */
3897 +       list_for_each_entry_safe(obj, tmp_obj, &sti->obj_list, list) {
3898 +               if (obj->obj_handle == obj_handle) {
3899 +                       list_del_init(&obj->list);
3900 +                       kfree(obj);
3901 +                       break;
3902 +               }
3903 +       }
3904 +
3905 +       spin_unlock_irq(&sti->lock);
3906 +
3907 +       /* lookup the object file */
3908 +       rc = path_lookup(obj->full_path, 0, &nd);
3909 +       if (rc) {
3910 +               ERROR(sti, "invalid object file path: %s\n", obj->full_path);
3911 +               sti->response_code = PIMA15740_RES_STORE_NOT_AVAILABLE;
3912 +               goto out;
3913 +       }
3914 +
3915 +       /* unlink the file */
3916 +       rc = vfs_unlink(nd.path.dentry->d_parent->d_inode, nd.path.dentry);
3917 +       if (rc) {
3918 +               ERROR(sti, "can't delete object\n");
3919 +               sti->response_code = PIMA15740_RES_DEVICE_BUSY;
3920 +               goto out;
3921 +       }
3922 +
3923 +       DBG(sti, "delete object: %s\n", obj->full_path);
3924 +
3925 +       sti->response_code = PIMA15740_RES_OK;
3926 +out:
3927 +       /* send response */
3928 +       rc = send_response(sti, sti->response_code);
3929 +
3930 +       VDBG(sti, "<--- %s()\n", __func__);
3931 +       return rc;
3932 +}
3933 +
3934 +
3935 +static int do_send_object_info(struct sti_dev *sti, struct sti_buffhd *bh)
3936 +{
3937 +       u8                      filename_len;
3938 +       u32                     storage_id;
3939 +       u32                     parent_object = 0xffffffff;
3940 +       unsigned int            offset;
3941 +       struct sti_object       *obj, *parent_obj;
3942 +       size_t                  obj_size;
3943 +       int                     i;
3944 +       int                     rc = 0;
3945 +       VDBG(sti, "---> %s()\n", __func__);
3946 +
3947 +       if (!sti->session_open) {
3948 +               sti->response_code = PIMA15740_RES_SESSION_NOT_OPEN;
3949 +               goto out2;
3950 +       }
3951 +
3952 +       for (i = 0; i < PARAM_NUM_MAX; i++)
3953 +               VDBG(sti, "parameter[%u]: 0x%08x\n",
3954 +                               i + 1, sti->ops_params[i]);
3955 +
3956 +       /* destination storage id */
3957 +       storage_id = sti->ops_params[0];
3958 +       if (storage_id != STORAGE_ID) {
3959 +               WARNING(sti, "invalid storage id: 0x%08x\n", storage_id);
3960 +               sti->response_code = PIMA15740_RES_INVALID_STORAGE_ID;
3961 +               goto out2;
3962 +       }
3963 +
3964 +       /* parent object handle where object should be placed */
3965 +       parent_object = sti->ops_params[1];
3966 +
3967 +       /* if root directory, parent object is 0xffffffff  */
3968 +       if (parent_object == 0 || (parent_object > sti->object_num
3969 +                               && parent_object != 0xffffffff)) {
3970 +               WARNING(sti, "invalid parent handle: 0x%08x\n",
3971 +                               parent_object);
3972 +               sti->response_code = PIMA15740_RES_INVALID_PARENT_OBJECT;
3973 +               goto out2;
3974 +       }
3975 +
3976 +       /* queue a request to read ObjectInfo Dataset */
3977 +       set_bulk_out_req_length(sti, bh, 512);
3978 +       bh->outreq->short_not_ok = 1;
3979 +       start_transfer(sti, sti->bulk_out, bh->outreq,
3980 +                       &bh->outreq_busy, &bh->state);
3981 +
3982 +       /* wait for the ObjectInfo Dataset to arrive */
3983 +       while (bh->state != BUF_STATE_FULL) {
3984 +               rc = sleep_thread(sti);
3985 +               if (rc)
3986 +                       goto out1;
3987 +       }
3988 +
3989 +       /* filename strings length */
3990 +       offset = offsetof(struct pima15740_object_info, obj_strings[0]);
3991 +       filename_len = *(u8 *)(bh->outreq->buf + PIMA15740_CONTAINER_LEN
3992 +                       + offset);
3993 +       VDBG(sti, "filename_len: %u\n", filename_len);
3994 +
3995 +       /* sti_object size */
3996 +       obj_size = sizeof(*obj) + 2 * filename_len + 4;
3997 +       VDBG(sti, "obj_size: %u\n", obj_size);
3998 +       obj = kzalloc(obj_size, GFP_KERNEL);
3999 +       if (!obj) {
4000 +               sti->response_code = PIMA15740_RES_STORE_NOT_AVAILABLE;
4001 +               goto out2;
4002 +       }
4003 +
4004 +       spin_lock_irq(&sti->lock);
4005 +
4006 +       /* increase total object number */
4007 +       sti->object_num++;
4008 +
4009 +       /* fill sti_object info */
4010 +       obj->obj_handle = sti->object_num;
4011 +       VDBG(sti, "obj_handle: 0x%08x\n", obj->obj_handle);
4012 +
4013 +       if (parent_object == 0xffffffff)
4014 +               obj->parent_object = 0;
4015 +       else
4016 +               obj->parent_object = parent_object;
4017 +       VDBG(sti, "parent_object: 0x%08x\n", obj->parent_object);
4018 +
4019 +       obj->storage_id = storage_id;
4020 +
4021 +       /* mark object ready to send */
4022 +       obj->send_valid = 1;
4023 +
4024 +       /* ObjectInfo Dataset size */
4025 +       obj->obj_info_size = sizeof(struct pima15740_object_info)
4026 +               + 2 * filename_len + 4;
4027 +       VDBG(sti, "obj_info_size: %u\n", obj->obj_info_size);
4028 +
4029 +       /* filename */
4030 +       offset = offsetof(struct pima15740_object_info, obj_strings[1]);
4031 +       uni16_to_str(bh->outreq->buf + PIMA15740_CONTAINER_LEN + offset,
4032 +                       obj->filename, filename_len);
4033 +
4034 +       /* object full path */
4035 +       memset(obj->full_path, 0, sizeof(obj->full_path));
4036 +       if (parent_object == 0xffffffff) {
4037 +               snprintf(obj->full_path, sizeof(obj->full_path),  "%s/%s",
4038 +                               sti->root_path, obj->filename);
4039 +       } else {
4040 +               /* find the parent object */
4041 +               list_for_each_entry(parent_obj, &sti->obj_list, list) {
4042 +                       if (parent_obj->obj_handle == parent_object)
4043 +                               break;
4044 +               }
4045 +               snprintf(obj->full_path, sizeof(obj->full_path), "%s/%s",
4046 +                               parent_obj->full_path, obj->filename);
4047 +       }
4048 +       VDBG(sti, "full_path: %s\n", obj->full_path);
4049 +
4050 +       /* fetch ObjectInfo Dataset from buffer */
4051 +       memcpy(&obj->obj_info, bh->outreq->buf + PIMA15740_CONTAINER_LEN,
4052 +                       obj->obj_info_size);
4053 +
4054 +       /* root directory, modify parent object */
4055 +       if (parent_object == 0xffffffff)
4056 +               obj->obj_info.parent_object = cpu_to_le32(0);
4057 +       else
4058 +               obj->obj_info.parent_object = parent_object;
4059 +
4060 +       obj->obj_info.storage_id = storage_id;
4061 +
4062 +       /* capture date */
4063 +       obj->obj_info.obj_strings[filename_len * 2 + 1] = 0;
4064 +
4065 +       /* modification date */
4066 +       obj->obj_info.obj_strings[filename_len * 2 + 2] = 0;
4067 +
4068 +       /* keywords */
4069 +       obj->obj_info.obj_strings[filename_len * 2 + 3] = 0;
4070 +
4071 +       bh->state = BUF_STATE_EMPTY;
4072 +
4073 +       /* add to object list */
4074 +       list_add_tail(&obj->list, &sti->obj_list);
4075 +
4076 +       spin_unlock_irq(&sti->lock);
4077 +
4078 +       DBG(sti, "send object info: %s\n", obj->filename);
4079 +
4080 +       /* dump ObjectInfo Dataset */
4081 +       dump_object_info(sti, obj);
4082 +out2:
4083 +       /* send response */
4084 +       rc = send_params_response(sti, PIMA15740_RES_OK,
4085 +                       sti->storage_id, parent_object, sti->object_num,
4086 +                       3);
4087 +out1:
4088 +       VDBG(sti, "<--- %s()\n", __func__);
4089 +       return rc;
4090 +}
4091 +
4092 +
4093 +static int do_send_object(struct sti_dev *sti, struct sti_buffhd *bh)
4094 +{
4095 +       int                     rc = -EINVAL;
4096 +       int                     get_some_more;
4097 +       u32                     amount_left_to_req, amount_left_to_write;
4098 +       loff_t                  file_size, file_offset, file_offset_tmp,
4099 +                               usb_offset;
4100 +       unsigned int            amount;
4101 +       ssize_t                 nwritten;
4102 +       struct sti_object       *obj;
4103 +       struct file             *filp = NULL;
4104 +       char __user             *buf;
4105 +       VDBG(sti, "---> %s()\n", __func__);
4106 +
4107 +       spin_lock_irq(&sti->lock);
4108 +
4109 +       /* find the object */
4110 +       list_for_each_entry(obj, &sti->obj_list, list) {
4111 +               if (obj->send_valid)
4112 +                       break;
4113 +       }
4114 +
4115 +       /* mark object already sent */
4116 +       obj->send_valid = 0;
4117 +
4118 +       spin_unlock_irq(&sti->lock);
4119 +
4120 +       /* open object file */
4121 +       filp = filp_open(obj->full_path, O_CREAT | O_RDWR | O_LARGEFILE, 0666);
4122 +       if (IS_ERR(filp)) {
4123 +               ERROR(sti, "unable to open file: %s. Err = %d\n",
4124 +                               obj->full_path, (int) PTR_ERR(filp));
4125 +               sti->response_code = PIMA15740_RES_STORE_NOT_AVAILABLE;
4126 +               goto out1;
4127 +       }
4128 +
4129 +       file_size = obj->obj_info.object_compressed_size;
4130 +       VDBG(sti, "object file size: %llu\n",
4131 +                       (unsigned long long) file_size);
4132 +       if (unlikely(file_size == 0)) {
4133 +               sti->response_code = PIMA15740_RES_STORE_NOT_AVAILABLE;
4134 +               goto out2;
4135 +       }
4136 +
4137 +       DBG(sti, "send object: %s\n", obj->full_path);
4138 +
4139 +       /* carry out the file writes */
4140 +       get_some_more = 1;
4141 +       file_offset = usb_offset = 0;
4142 +
4143 +       amount_left_to_req = file_size + PIMA15740_CONTAINER_LEN;
4144 +       amount_left_to_write = file_size;
4145 +       VDBG(sti, "in total: amount_left_to_req: %u\n",
4146 +                       amount_left_to_req);
4147 +       VDBG(sti, "in total: amount_left_to_write: %u\n",
4148 +                       amount_left_to_write);
4149 +
4150 +       while (amount_left_to_write > 0) {
4151 +               bh = sti->next_buffhd_to_fill;
4152 +               if (bh->state == BUF_STATE_EMPTY && get_some_more) {
4153 +                       amount = min(amount_left_to_req, mod_data.buflen);
4154 +                       amount = min((loff_t) amount, file_size
4155 +                               + PIMA15740_CONTAINER_LEN - usb_offset);
4156 +                       VDBG(sti, "usb amount: %u\n", amount);
4157 +
4158 +                       /* no left data request to transfer */
4159 +                       if (amount == 0) {
4160 +                               get_some_more = 0;
4161 +                               continue;
4162 +                       }
4163 +
4164 +                       /* get the next buffer */
4165 +                       usb_offset += amount;
4166 +                       amount_left_to_req -= amount;
4167 +
4168 +                       if (amount_left_to_req == 0)
4169 +                               get_some_more = 0;
4170 +
4171 +                       /* amount is always divisible by bulk-out
4172 +                          maxpacket size */
4173 +                       bh->outreq->length = bh->bulk_out_intended_length =
4174 +                                       amount;
4175 +                       bh->outreq->short_not_ok = 1;
4176 +                       start_transfer(sti, sti->bulk_out, bh->outreq,
4177 +                                       &bh->outreq_busy, &bh->state);
4178 +                       sti->next_buffhd_to_fill = bh->next;
4179 +                       continue;
4180 +               }
4181 +
4182 +               /* write the received data to the backing folder */
4183 +               bh = sti->next_buffhd_to_drain;
4184 +
4185 +               /* host stopped early */
4186 +               if (bh->state == BUF_STATE_EMPTY && !get_some_more) {
4187 +                       WARNING(sti, "host stops early, bh->state: %d\n",
4188 +                                       bh->state);
4189 +                       sti->response_code = PIMA15740_RES_INCOMPLETE_TRANSFER;
4190 +                       goto out2;
4191 +               }
4192 +
4193 +               if (bh->state == BUF_STATE_FULL) {
4194 +                       smp_rmb();
4195 +                       sti->next_buffhd_to_drain = bh->next;
4196 +                       bh->state = BUF_STATE_EMPTY;
4197 +
4198 +                       /* something go wrong with the transfer */
4199 +                       if (bh->outreq->status != 0) {
4200 +                               sti->response_code =
4201 +                                       PIMA15740_RES_INCOMPLETE_TRANSFER;
4202 +                               goto out2;
4203 +                       }
4204 +
4205 +                       /*
4206 +                        * PIMA 15740 generic container head resides in
4207 +                        * first data block payload
4208 +                        */
4209 +                       if (file_offset == 0) {
4210 +                               buf = (char __user *) bh->buf +
4211 +                                       PIMA15740_CONTAINER_LEN;
4212 +                               amount = bh->outreq->actual -
4213 +                                       PIMA15740_CONTAINER_LEN;
4214 +                       } else {
4215 +                               buf = (char __user *) bh->buf;
4216 +                               amount = bh->outreq->actual;
4217 +                       }
4218 +                       amount = min((loff_t) amount,
4219 +                                       file_size - file_offset);
4220 +
4221 +                       /* across page boundary, recalculate the length */
4222 +                       if (amount == 0) {
4223 +                               INFO(sti, "extra bulk out zlp packets\n");
4224 +                               usb_offset -= bh->outreq->length;
4225 +                               amount_left_to_req += bh->outreq->length;
4226 +                               continue;
4227 +                       }
4228 +
4229 +                       /* perform the write */
4230 +                       file_offset_tmp = file_offset;
4231 +                       nwritten = vfs_write(filp, (char __user *) buf,
4232 +                                       amount, &file_offset_tmp);
4233 +                       VDBG(sti, "file write %u @ %llu -> %d\n", amount,
4234 +                                       (unsigned long long) file_offset,
4235 +                                       (int) nwritten);
4236 +
4237 +                       if (signal_pending(current)) {
4238 +                               filp_close(filp, current->files);
4239 +                               return -EINTR;
4240 +                       }
4241 +
4242 +                       if (nwritten < 0) {
4243 +                               VDBG(sti, "error in file write: %d\n",
4244 +                                               (int) nwritten);
4245 +                               nwritten = 0;
4246 +                       } else if (nwritten < amount) {
4247 +                               VDBG(sti, "partial file write: %d/%u\n",
4248 +                                               (int) nwritten, amount);
4249 +                               /* round down to a block */
4250 +                               nwritten -= (nwritten & 511);
4251 +                       }
4252 +
4253 +                       file_offset += nwritten;
4254 +                       amount_left_to_write -= nwritten;
4255 +
4256 +                       VDBG(sti, "file_offset: %llu, "
4257 +                                       "amount_left_to_write: %u\n",
4258 +                                       (unsigned long long) file_offset,
4259 +                                       amount_left_to_write);
4260 +
4261 +                       /* error occurred */
4262 +                       if (nwritten < amount) {
4263 +                               sti->response_code =
4264 +                                       PIMA15740_RES_INCOMPLETE_TRANSFER;
4265 +                               goto out2;
4266 +                       }
4267 +                       continue;
4268 +               }
4269 +
4270 +               /* wait for something to happen */
4271 +               rc = sleep_thread(sti);
4272 +               if (rc) {
4273 +                       filp_close(filp, current->files);
4274 +                       return rc;
4275 +               }
4276 +       }
4277 +
4278 +       /* fsync object file */
4279 +       vfs_fsync(filp, filp->f_path.dentry, 1);
4280 +
4281 +       sti->response_code = PIMA15740_RES_OK;
4282 +out2:
4283 +       filp_close(filp, current->files);
4284 +out1:
4285 +       /* send response */
4286 +       rc = send_response(sti, sti->response_code);
4287 +
4288 +       VDBG(sti, "<--- %s()\n", __func__);
4289 +       return rc;
4290 +}
4291 +
4292 +
4293 +static int do_copy_object(struct sti_dev *sti, struct sti_buffhd *bh)
4294 +{
4295 +       int                     rc = 0, i;
4296 +       size_t                  size = 0;
4297 +       unsigned int            old_obj_handle, new_obj_parent_handle;
4298 +       unsigned int            new_storage_id, amount, amount_left;
4299 +       struct sti_object       *old_obj = NULL,  *new_obj_parent = NULL;
4300 +       struct sti_object       *new_obj, *tmp_obj;
4301 +       char                    *new_obj_fname;
4302 +       struct file             *old_fp, *new_fp;
4303 +       struct inode            *inode = NULL;
4304 +       char __user             *buf;
4305 +       loff_t                  file_size, file_offset, file_offset_tmp;
4306 +       ssize_t                 nread, nwritten;
4307 +       VDBG(sti, "---> %s()\n", __func__);
4308 +
4309 +       if (!sti->session_open) {
4310 +               sti->response_code = PIMA15740_RES_SESSION_NOT_OPEN;
4311 +               goto out1;
4312 +       }
4313 +
4314 +       old_obj_handle = sti->ops_params[0];
4315 +       new_storage_id = sti->ops_params[1];
4316 +       new_obj_parent_handle = sti->ops_params[2];
4317 +
4318 +       if ((old_obj_handle == 0) || (old_obj_handle > sti->object_num)) {
4319 +               WARNING(sti, "invalid object handle: %u\n", old_obj_handle);
4320 +               sti->response_code = PIMA15740_RES_INVALID_OBJECT_HANDLE;
4321 +               goto out1;
4322 +       }
4323 +
4324 +       if (new_storage_id != sti->storage_id) {
4325 +               WARNING(sti, "invalid storage id: %u\n", new_storage_id);
4326 +               sti->response_code = PIMA15740_RES_INVALID_STORAGE_ID;
4327 +               goto out1;
4328 +       }
4329 +
4330 +       if (new_obj_parent_handle > sti->object_num
4331 +                       && new_obj_parent_handle != 0xffffffff) {
4332 +               WARNING(sti, "invalid parent object handle: %u\n",
4333 +                               new_obj_parent_handle);
4334 +               sti->response_code = PIMA15740_RES_INVALID_PARENT_OBJECT;
4335 +               goto out1;
4336 +       }
4337 +
4338 +       spin_lock_irq(&sti->lock);
4339 +
4340 +       /* find the old object to be copied */
4341 +       i = 0;
4342 +       list_for_each_entry(tmp_obj, &sti->obj_list, list) {
4343 +               if (tmp_obj->obj_handle == old_obj_handle) {
4344 +                       i++;
4345 +                       old_obj = tmp_obj;
4346 +               }
4347 +
4348 +               if (tmp_obj->obj_handle == new_obj_parent_handle) {
4349 +                       i++;
4350 +                       new_obj_parent = tmp_obj;
4351 +               }
4352 +
4353 +               if (i == 2)
4354 +                       break;
4355 +       }
4356 +
4357 +       spin_unlock_irq(&sti->lock);
4358 +
4359 +       if (i != 2 || !old_obj || !new_obj_parent) {
4360 +               WARNING(sti, "invalid objects %u or %u\n",
4361 +                       old_obj_handle, new_obj_parent_handle);
4362 +               sti->response_code = PIMA15740_RES_INVALID_PARENT_OBJECT;
4363 +               goto out1;
4364 +       }
4365 +
4366 +       size = strlen(new_obj_parent->full_path) +
4367 +               strlen(old_obj->filename) + 2;
4368 +       new_obj_fname = kzalloc(size, GFP_KERNEL);
4369 +       if (!new_obj_fname) {
4370 +               sti->response_code = PIMA15740_RES_DEVICE_BUSY;
4371 +               rc = -EINVAL;
4372 +               goto out1;
4373 +       }
4374 +       strncpy(new_obj_fname, new_obj_parent->full_path, size);
4375 +       strncat(new_obj_fname, "/", size);
4376 +       strncat(new_obj_fname, old_obj->filename, size);
4377 +
4378 +       VDBG(sti, "copy object: from [%s] to [%s]\n",
4379 +                       old_obj->full_path, new_obj_fname);
4380 +
4381 +       old_fp = filp_open(old_obj->full_path, O_RDONLY | O_LARGEFILE, 0);
4382 +       if (IS_ERR(old_fp)) {
4383 +               ERROR(sti, "unable to open file: %s. Err = %d\n",
4384 +                       old_obj->full_path, (int) PTR_ERR(old_fp));
4385 +               sti->response_code = PIMA15740_RES_DEVICE_BUSY;
4386 +               rc = -EINVAL;
4387 +               goto out2;
4388 +       }
4389 +
4390 +       new_fp = filp_open(new_obj_fname, O_CREAT | O_RDWR | O_LARGEFILE, 0666);
4391 +       if (IS_ERR(new_fp)) {
4392 +               ERROR(sti, "unable to create file: %s. Err = %d\n",
4393 +                       new_obj_fname, (int) PTR_ERR(new_fp));
4394 +               sti->response_code = PIMA15740_RES_DEVICE_BUSY;
4395 +               rc = -EINVAL;
4396 +               goto out3;
4397 +       }
4398 +
4399 +       buf = kzalloc(PAGE_SIZE, GFP_KERNEL);
4400 +       if (!buf) {
4401 +               sti->response_code = PIMA15740_RES_OPERATION_NOT_SUPPORTED;
4402 +               rc = -EINVAL;
4403 +               goto out4;
4404 +       }
4405 +
4406 +       inode = old_fp->f_dentry->d_inode;
4407 +       file_size = i_size_read(inode->i_mapping->host);
4408 +       VDBG(sti, "object file size: %llu\n", (unsigned long long) file_size);
4409 +
4410 +       if (unlikely(file_size == 0)) {
4411 +               sti->response_code = PIMA15740_RES_STORE_NOT_AVAILABLE;
4412 +               rc = -EIO;
4413 +               goto out5;
4414 +       }
4415 +
4416 +       file_offset = 0;
4417 +       amount_left = file_size;
4418 +
4419 +       while (amount_left > 0) {
4420 +               amount = min(amount_left, (unsigned int) PAGE_SIZE);
4421 +               if (amount == 0)
4422 +                       break;
4423 +
4424 +               file_offset_tmp = file_offset;
4425 +               nread = vfs_read(old_fp, buf, amount, &file_offset_tmp);
4426 +
4427 +               if (signal_pending(current)) {
4428 +                       rc = -EINTR;
4429 +                       goto out5;
4430 +               }
4431 +
4432 +               if (nread < 0) {
4433 +                       DBG(sti, "error in file read: %d\n",
4434 +                                       (int) nread);
4435 +                       nread = 0;
4436 +               } else if (nread < amount) {
4437 +                       DBG(sti, "partial file read: %d/%u\n",
4438 +                                       (int) nread, amount);
4439 +                       /* round down to a block */
4440 +                       nread -= (nread & 511);
4441 +               }
4442 +
4443 +               amount = min(amount, (unsigned int) nread);
4444 +               file_offset_tmp = file_offset;
4445 +               nwritten = vfs_write(new_fp, buf, amount, &file_offset_tmp);
4446 +
4447 +               if (signal_pending(current)) {
4448 +                       rc = -EINTR;
4449 +                       goto out5;
4450 +               }
4451 +
4452 +               if (nwritten < 0) {
4453 +                       VDBG(sti, "error in file write: %d\n",
4454 +                                       (int) nwritten);
4455 +                       nwritten = 0;
4456 +               } else if (nwritten < amount) {
4457 +                       VDBG(sti, "partial file write: %d/%u\n",
4458 +                                       (int) nwritten, amount);
4459 +                       /* round down to a block */
4460 +                       nwritten -= (nwritten & 511);
4461 +               }
4462 +
4463 +               amount = min(amount, (unsigned int) nwritten);
4464 +               file_offset += amount;
4465 +               amount_left -= amount;
4466 +       }
4467 +
4468 +       size = sizeof(*old_obj);
4469 +       new_obj = kzalloc(size, GFP_KERNEL);
4470 +       if (!new_obj) {
4471 +               rc = -ENOMEM;
4472 +               goto out5;
4473 +       }
4474 +
4475 +       spin_lock_irq(&sti->lock);
4476 +
4477 +       sti->object_num++;
4478 +
4479 +       /* change obj_handle */
4480 +       new_obj->obj_handle = sti->object_num;
4481 +
4482 +       /* change parent object */
4483 +       if (new_obj_parent_handle == 0xffffffff)
4484 +               new_obj->parent_object = 0;
4485 +       else
4486 +               new_obj->parent_object = new_obj_parent_handle;
4487 +
4488 +       new_obj->storage_id = old_obj->storage_id;
4489 +       new_obj->is_dir = old_obj->is_dir;
4490 +       new_obj->send_valid = old_obj->send_valid;
4491 +       new_obj->obj_info_size = old_obj->obj_info_size;
4492 +       strncpy(new_obj->filename, old_obj->filename,
4493 +                       sizeof(new_obj->filename));
4494 +
4495 +       /* change full path name */
4496 +       strncpy(new_obj->full_path, new_obj_fname, sizeof(new_obj->full_path));
4497 +
4498 +       /* copy object_info */
4499 +       memcpy(&new_obj->obj_info, &old_obj->obj_info, old_obj->obj_info_size);
4500 +
4501 +       /* fill parent_object in object_info */
4502 +       new_obj->obj_info.parent_object = new_obj->parent_object;
4503 +
4504 +       /* add to object list */
4505 +       list_add_tail(&new_obj->list, &sti->obj_list);
4506 +
4507 +       spin_unlock_irq(&sti->lock);
4508 +
4509 +       sti->response_code = PIMA15740_RES_OK;
4510 +out5:
4511 +       kfree(buf);
4512 +out4:
4513 +       filp_close(new_fp, current->files);
4514 +out3:
4515 +       filp_close(old_fp, current->files);
4516 +out2:
4517 +       kfree(new_obj_fname);
4518 +out1:
4519 +       /* send response */
4520 +       rc = send_params_response(sti, sti->response_code,
4521 +                       sti->object_num, 0, 0,
4522 +                       1);
4523 +
4524 +       VDBG(sti, "<--- %s()\n", __func__);
4525 +       return rc;
4526 +}
4527 +
4528 +
4529 +static int do_move_object(struct sti_dev *sti, struct sti_buffhd *bh)
4530 +{
4531 +       int                     i, rc = 0;
4532 +       size_t                  size = 0;
4533 +       unsigned int            old_obj_handle, new_obj_parent_handle;
4534 +       unsigned int            new_storage_id;
4535 +       char                    *new_obj_fname;
4536 +       struct file             *old_fp, *new_fp;
4537 +       struct inode            *old_dir, *new_dir;
4538 +       struct dentry           *old_dentry, *new_dentry;
4539 +       struct sti_object       *old_obj = NULL;
4540 +       struct sti_object       *new_obj = NULL;
4541 +       struct sti_object       *new_obj_parent = NULL;
4542 +       struct sti_object        *tmp_obj = NULL;
4543 +       VDBG(sti, "---> %s()\n", __func__);
4544 +
4545 +       if (!sti->session_open) {
4546 +               sti->response_code = PIMA15740_RES_SESSION_NOT_OPEN;
4547 +               goto out1;
4548 +       }
4549 +
4550 +       old_obj_handle = sti->ops_params[0];
4551 +       new_storage_id = sti->ops_params[1];
4552 +       new_obj_parent_handle = sti->ops_params[2];
4553 +
4554 +       if ((old_obj_handle == 0) || (old_obj_handle > sti->object_num)) {
4555 +               WARNING(sti, "invalid object handle: %u\n", old_obj_handle);
4556 +               sti->response_code = PIMA15740_RES_INVALID_OBJECT_HANDLE;
4557 +               goto out1;
4558 +       }
4559 +
4560 +       if (new_storage_id != sti->storage_id) {
4561 +               WARNING(sti, "invalid storage id: %u\n", new_storage_id);
4562 +               sti->response_code = PIMA15740_RES_INVALID_STORAGE_ID;
4563 +               goto out1;
4564 +       }
4565 +
4566 +       if (new_obj_parent_handle > sti->object_num
4567 +                       && new_obj_parent_handle != 0xffffffff) {
4568 +               WARNING(sti, "invalid parent object handle: %u\n",
4569 +                               new_obj_parent_handle);
4570 +               sti->response_code = PIMA15740_RES_INVALID_PARENT_OBJECT;
4571 +               goto out1;
4572 +       }
4573 +
4574 +       spin_lock_irq(&sti->lock);
4575 +
4576 +       /* find the old object to be moved */
4577 +       i = 0;
4578 +       list_for_each_entry(tmp_obj, &sti->obj_list, list) {
4579 +               if (tmp_obj->obj_handle == old_obj_handle) {
4580 +                       i++;
4581 +                       old_obj = tmp_obj;
4582 +               }
4583 +
4584 +               if (tmp_obj->obj_handle == new_obj_parent_handle) {
4585 +                       i++;
4586 +                       new_obj_parent = tmp_obj;
4587 +               }
4588 +
4589 +               if (i == 2)
4590 +                       break;
4591 +       }
4592 +
4593 +       spin_unlock_irq(&sti->lock);
4594 +
4595 +       if (i != 2 || !old_obj || !new_obj_parent) {
4596 +               WARNING(sti, "invalid objects %u or %u\n",
4597 +                       old_obj_handle, new_obj_parent_handle);
4598 +               sti->response_code = PIMA15740_RES_INVALID_PARENT_OBJECT;
4599 +               goto out1;
4600 +       }
4601 +
4602 +       size = strlen(new_obj_parent->full_path) +
4603 +               strlen(old_obj->filename) + 2;
4604 +       new_obj_fname = kzalloc(size, GFP_KERNEL);
4605 +       if (!new_obj_fname) {
4606 +               sti->response_code = PIMA15740_RES_DEVICE_BUSY;
4607 +               rc = -EINVAL;
4608 +               goto out1;
4609 +       }
4610 +       strncpy(new_obj_fname, new_obj_parent->full_path, size);
4611 +       strncat(new_obj_fname, "/", size);
4612 +       strncat(new_obj_fname, old_obj->filename, size);
4613 +
4614 +       VDBG(sti, "move object: from [%s] to [%s]\n",
4615 +                       old_obj->full_path, new_obj_fname);
4616 +
4617 +       old_fp = filp_open(old_obj->full_path, O_RDONLY | O_LARGEFILE, 0);
4618 +       if (IS_ERR(old_fp)) {
4619 +               ERROR(sti, "unable to open file: %s. Err = %d\n",
4620 +                       old_obj->full_path, (int) PTR_ERR(old_fp));
4621 +               sti->response_code = PIMA15740_RES_DEVICE_BUSY;
4622 +               rc = -EINVAL;
4623 +               goto out2;
4624 +       }
4625 +
4626 +       new_fp = filp_open(new_obj_fname, O_CREAT | O_RDWR | O_LARGEFILE, 0666);
4627 +       if (IS_ERR(new_fp)) {
4628 +               ERROR(sti, "unable to create file: %s. Err = %d\n",
4629 +                       new_obj_fname, (int) PTR_ERR(new_fp));
4630 +               sti->response_code = PIMA15740_RES_DEVICE_BUSY;
4631 +               rc = -EINVAL;
4632 +               goto out3;
4633 +       }
4634 +
4635 +       old_dir = old_fp->f_dentry->d_parent->d_inode;
4636 +       new_dir = new_fp->f_dentry->d_parent->d_inode;
4637 +       old_dentry = old_fp->f_dentry;
4638 +       new_dentry = new_fp->f_dentry;
4639 +
4640 +       rc = vfs_rename(old_dir, old_dentry, new_dir, new_dentry);
4641 +
4642 +       if (rc) {
4643 +               sti->response_code = PIMA15740_RES_OPERATION_NOT_SUPPORTED;
4644 +               goto out4;
4645 +       } else
4646 +               sti->response_code = PIMA15740_RES_OK;
4647 +
4648 +       size = sizeof(*old_obj);
4649 +       new_obj = kzalloc(size, GFP_KERNEL);
4650 +       if (!new_obj) {
4651 +               rc = -ENOMEM;
4652 +               goto out4;
4653 +       }
4654 +
4655 +       spin_lock_irq(&sti->lock);
4656 +
4657 +       /* change parent object */
4658 +       if (new_obj_parent_handle == 0xffffffff)
4659 +               new_obj->parent_object = 0;
4660 +       else
4661 +               new_obj->parent_object = new_obj_parent_handle;
4662 +
4663 +       new_obj->obj_handle = old_obj->obj_handle;
4664 +       new_obj->storage_id = old_obj->storage_id;
4665 +       new_obj->is_dir = old_obj->is_dir;
4666 +       new_obj->send_valid = old_obj->send_valid;
4667 +       new_obj->obj_info_size = old_obj->obj_info_size;
4668 +       strncpy(new_obj->filename, old_obj->filename,
4669 +                       sizeof(new_obj->filename));
4670 +
4671 +       /* change full path name */
4672 +       strncpy(new_obj->full_path, new_obj_fname, sizeof(new_obj->full_path));
4673 +
4674 +       /* copy object_info */
4675 +       memcpy(&new_obj->obj_info, &old_obj->obj_info, old_obj->obj_info_size);
4676 +
4677 +       /* fill parent_object in object_info */
4678 +       new_obj->obj_info.parent_object = new_obj->parent_object;
4679 +
4680 +       /* add to object list */
4681 +       list_add_tail(&new_obj->list, &sti->obj_list);
4682 +
4683 +       /* remove from object list */
4684 +       list_del_init(&old_obj->list);
4685 +
4686 +       spin_unlock_irq(&sti->lock);
4687 +
4688 +       kfree(old_obj);
4689 +out4:
4690 +       filp_close(new_fp, current->files);
4691 +out3:
4692 +       filp_close(old_fp, current->files);
4693 +out2:
4694 +       kfree(new_obj_fname);
4695 +out1:
4696 +       /* send response */
4697 +       rc = send_response(sti, sti->response_code);
4698 +
4699 +       VDBG(sti, "<--- %s()\n", __func__);
4700 +       return rc;
4701 +}
4702 +
4703 +
4704 +/* TODO: PIMA 15740 Event handling via interrupt endpoint */
4705 +static int send_status(struct sti_dev *sti)
4706 +{
4707 +       VDBG(sti, "---> %s()\n", __func__);
4708 +       VDBG(sti, "<--- %s()\n", __func__);
4709 +       return 0;
4710 +}
4711 +
4712 +
4713 +/*-------------------------------------------------------------------------*/
4714 +
4715 +/* handle supported PIMA 15740 operations */
4716 +static int do_still_image_command(struct sti_dev *sti)
4717 +{
4718 +       struct sti_buffhd       *bh;
4719 +       int                     rc = -EINVAL;
4720 +       int                     reply = -EINVAL;
4721 +       VDBG(sti, "---> %s()\n", __func__);
4722 +
4723 +       dump_cb(sti);
4724 +
4725 +       if (!backing_folder_is_open(sti)) {
4726 +               ERROR(sti, "backing folder is not open\n");
4727 +               return rc;
4728 +       }
4729 +
4730 +       /* wait for the next buffer to become available for data or status */
4731 +       bh = sti->next_buffhd_to_drain = sti->next_buffhd_to_fill;
4732 +       while (bh->state != BUF_STATE_EMPTY) {
4733 +               rc = sleep_thread(sti);
4734 +               if (rc)
4735 +                       return rc;
4736 +       }
4737 +
4738 +       down_read(&sti->filesem);
4739 +       switch (sti->code) {
4740 +
4741 +       case PIMA15740_OP_GET_DEVICE_INFO:
4742 +               DBG(sti, "PIMA15740 OPS: get device info\n");
4743 +               reply = do_get_device_info(sti, bh);
4744 +               break;
4745 +
4746 +       case PIMA15740_OP_OPEN_SESSION:
4747 +               DBG(sti, "PIMA15740 OPS: open session\n");
4748 +               reply = do_open_session(sti);
4749 +               break;
4750 +
4751 +       case PIMA15740_OP_CLOSE_SESSION:
4752 +               DBG(sti, "PIMA15740 OPS: close session\n");
4753 +               reply = do_close_session(sti);
4754 +               break;
4755 +
4756 +       case PIMA15740_OP_GET_STORAGE_IDS:
4757 +               DBG(sti, "PIMA15740 OPS: get storage ids\n");
4758 +               reply = do_get_storage_ids(sti, bh);
4759 +               break;
4760 +
4761 +       case PIMA15740_OP_GET_STORAGE_INFO:
4762 +               DBG(sti, "PIMA15740 OPS: get storage info\n");
4763 +               reply = do_get_storage_info(sti, bh);
4764 +               break;
4765 +
4766 +       case PIMA15740_OP_GET_NUM_OBJECTS:
4767 +               DBG(sti, "PIMA15740 OPS: get num objects\n");
4768 +               reply = do_get_num_objects(sti, bh);
4769 +               break;
4770 +
4771 +       case PIMA15740_OP_GET_OBJECT_HANDLES:
4772 +               DBG(sti, "PIMA15740 OPS: get object handles\n");
4773 +               reply = do_get_object_handles(sti, bh);
4774 +               break;
4775 +
4776 +       case PIMA15740_OP_GET_OBJECT_INFO:
4777 +               DBG(sti, "PIMA15740 OPS: get object info\n");
4778 +               reply = do_get_object_info(sti, bh);
4779 +               break;
4780 +
4781 +       case PIMA15740_OP_GET_OBJECT:
4782 +               DBG(sti, "PIMA15740 OPS: get object\n");
4783 +               reply = do_get_object(sti, bh);
4784 +               break;
4785 +
4786 +       case PIMA15740_OP_DELETE_OBJECT:
4787 +               DBG(sti, "PIMA15740 OPS: delete object\n");
4788 +               reply = do_delete_object(sti, bh);
4789 +               break;
4790 +
4791 +       case PIMA15740_OP_SEND_OBJECT_INFO:
4792 +               DBG(sti, "PIMA15740 OPS: send object info\n");
4793 +               reply = do_send_object_info(sti, bh);
4794 +               break;
4795 +
4796 +       case PIMA15740_OP_SEND_OBJECT:
4797 +               DBG(sti, "PIMA15740 OPS: send object\n");
4798 +               reply = do_send_object(sti, bh);
4799 +               break;
4800 +
4801 +       case PIMA15740_OP_COPY_OBJECT:
4802 +               DBG(sti, "PIMA15740 OPS: copy object\n");
4803 +               reply = do_copy_object(sti, bh);
4804 +               break;
4805 +
4806 +       case PIMA15740_OP_MOVE_OBJECT:
4807 +               DBG(sti, "PIMA15740 OPS: move object\n");
4808 +               reply = do_move_object(sti, bh);
4809 +               break;
4810 +
4811 +       default:
4812 +               WARNING(sti, "unknown PIMA15740 OPS 0x%04x\n", sti->code);
4813 +               break;
4814 +       }
4815 +       up_read(&sti->filesem);
4816 +
4817 +       if (reply == -EINTR || signal_pending(current))
4818 +               rc = -EINTR;
4819 +
4820 +       if (reply == -EINVAL)
4821 +               rc = 0;
4822 +
4823 +       VDBG(sti, "<--- %s()\n", __func__);
4824 +       return rc;
4825 +}
4826 +
4827 +
4828 +/*-------------------------------------------------------------------------*/
4829 +
4830 +/* received PIMA 15740 Command Blocks */
4831 +static int received_cb(struct sti_dev *sti, struct sti_buffhd *bh)
4832 +{
4833 +       struct usb_request              *req = bh->outreq;
4834 +       struct pima15740_container      *cb = req->buf;
4835 +       unsigned short          n;
4836 +       VDBG(sti, "---> %s()\n", __func__);
4837 +
4838 +       /* this is not a real packet */
4839 +       if (req->status)
4840 +               return -EINVAL;
4841 +
4842 +       /* save the command for later */
4843 +       sti->container_len = cb->container_len;
4844 +       sti->container_type = cb->container_type;
4845 +       sti->code = cb->code;
4846 +       sti->transaction_id = cb->transaction_id;
4847 +
4848 +       /* get Command Block Parameters 1..N */
4849 +       n = sti->container_len - PIMA15740_CONTAINER_LEN;
4850 +       if (n != 0)
4851 +               memcpy(sti->ops_params, cb + 1, n);
4852 +
4853 +       VDBG(sti, "Command Block: len=%u, type=0x%04x, "
4854 +                       "code=0x%04x, trans_id=0x%08x\n",
4855 +                       sti->container_len, sti->container_type,
4856 +                       sti->code, sti->transaction_id);
4857 +
4858 +       VDBG(sti, "<--- %s()\n", __func__);
4859 +       return 0;
4860 +}
4861 +
4862 +
4863 +static int get_next_command(struct sti_dev *sti)
4864 +{
4865 +       struct sti_buffhd       *bh;
4866 +       int                     rc = 0;
4867 +       VDBG(sti, "---> %s()\n", __func__);
4868 +
4869 +       /* wait for the next buffer to become available */
4870 +       bh = sti->next_buffhd_to_fill;
4871 +       while (bh->state != BUF_STATE_EMPTY) {
4872 +               rc = sleep_thread(sti);
4873 +               if (rc)
4874 +                       return rc;
4875 +       }
4876 +
4877 +       /* queue a request to read a Bulk-only Command Block */
4878 +       set_bulk_out_req_length(sti, bh, 512);
4879 +       bh->outreq->short_not_ok = 1;
4880 +       start_transfer(sti, sti->bulk_out, bh->outreq,
4881 +                       &bh->outreq_busy, &bh->state);
4882 +
4883 +       /* we will drain the buffer in software, which means we
4884 +        * can reuse it for the next filling. No need to advance
4885 +        * next_buffhd_to_fill. */
4886 +
4887 +       /* wait for the Command Block to arrive */
4888 +       while (bh->state != BUF_STATE_FULL) {
4889 +               rc = sleep_thread(sti);
4890 +               if (rc)
4891 +                       return rc;
4892 +       }
4893 +       smp_rmb();
4894 +       rc = received_cb(sti, bh);
4895 +       bh->state = BUF_STATE_EMPTY;
4896 +
4897 +       VDBG(sti, "<--- %s()\n", __func__);
4898 +       return rc;
4899 +}
4900 +
4901 +
4902 +/*-------------------------------------------------------------------------*/
4903 +
4904 +static int enable_endpoint(struct sti_dev *sti, struct usb_ep *ep,
4905 +               const struct usb_endpoint_descriptor *d)
4906 +{
4907 +       int     rc;
4908 +       VDBG(sti, "---> %s()\n", __func__);
4909 +
4910 +       ep->driver_data = sti;
4911 +       rc = usb_ep_enable(ep, d);
4912 +       if (rc)
4913 +               ERROR(sti, "can't enable %s, result %d\n", ep->name, rc);
4914 +
4915 +       VDBG(sti, "<--- %s()\n", __func__);
4916 +       return rc;
4917 +}
4918 +
4919 +static int alloc_request(struct sti_dev *sti, struct usb_ep *ep,
4920 +               struct usb_request **preq)
4921 +{
4922 +       VDBG(sti, "---> %s()\n", __func__);
4923 +
4924 +       *preq = usb_ep_alloc_request(ep, GFP_ATOMIC);
4925 +       if (*preq)
4926 +               return 0;
4927 +
4928 +       ERROR(sti, "can't allocate request for %s\n", ep->name);
4929 +
4930 +       VDBG(sti, "<--- %s()\n", __func__);
4931 +       return -ENOMEM;
4932 +}
4933 +
4934 +/*
4935 + * Reset interface setting and re-init endpoint state (toggle etc).
4936 + * Call with altsetting < 0 to disable the interface.  The only other
4937 + * available altsetting is 0, which enables the interface.
4938 + */
4939 +static int do_set_interface(struct sti_dev *sti, int altsetting)
4940 +{
4941 +       int     rc = 0;
4942 +       int     i;
4943 +       const struct usb_endpoint_descriptor    *d;
4944 +       VDBG(sti, "---> %s()\n", __func__);
4945 +
4946 +       if (sti->running)
4947 +               DBG(sti, "reset interface\n");
4948 +
4949 +reset:
4950 +       /* deallocate the requests */
4951 +       for (i = 0; i < NUM_BUFFERS; ++i) {
4952 +               struct sti_buffhd *bh = &sti->buffhds[i];
4953 +
4954 +               if (bh->inreq) {
4955 +                       usb_ep_free_request(sti->bulk_in, bh->inreq);
4956 +                       bh->inreq = NULL;
4957 +               }
4958 +               if (bh->outreq) {
4959 +                       usb_ep_free_request(sti->bulk_out, bh->outreq);
4960 +                       bh->outreq = NULL;
4961 +               }
4962 +       }
4963 +       if (sti->intreq) {
4964 +               usb_ep_free_request(sti->intr_in, sti->intreq);
4965 +               sti->intreq = NULL;
4966 +       }
4967 +
4968 +       /* disable the endpoints */
4969 +       if (sti->bulk_in_enabled) {
4970 +               usb_ep_disable(sti->bulk_in);
4971 +               sti->bulk_in_enabled = 0;
4972 +       }
4973 +       if (sti->bulk_out_enabled) {
4974 +               usb_ep_disable(sti->bulk_out);
4975 +               sti->bulk_out_enabled = 0;
4976 +       }
4977 +       if (sti->intr_in_enabled) {
4978 +               usb_ep_disable(sti->intr_in);
4979 +               sti->intr_in_enabled = 0;
4980 +       }
4981 +
4982 +       sti->running = 0;
4983 +       if (altsetting < 0 || rc != 0)
4984 +               return rc;
4985 +
4986 +       DBG(sti, "set interface %d\n", altsetting);
4987 +
4988 +       /* enable the endpoints */
4989 +       d = ep_desc(sti->gadget, &fs_bulk_in_desc, &hs_bulk_in_desc);
4990 +       rc = enable_endpoint(sti, sti->bulk_in, d);
4991 +       if (rc)
4992 +               goto reset;
4993 +       sti->bulk_in_enabled = 1;
4994 +
4995 +       d = ep_desc(sti->gadget, &fs_bulk_out_desc, &hs_bulk_out_desc);
4996 +       rc = enable_endpoint(sti, sti->bulk_out, d);
4997 +       if (rc)
4998 +               goto reset;
4999 +       sti->bulk_out_enabled = 1;
5000 +       sti->bulk_out_maxpacket = le16_to_cpu(d->wMaxPacketSize);
5001 +       clear_bit(CLEAR_BULK_HALTS, &sti->atomic_bitflags);
5002 +
5003 +       d = ep_desc(sti->gadget, &fs_intr_in_desc, &hs_intr_in_desc);
5004 +       rc = enable_endpoint(sti, sti->intr_in, d);
5005 +       if (rc)
5006 +               goto reset;
5007 +       sti->intr_in_enabled = 1;
5008 +
5009 +       /* allocate the requests */
5010 +       for (i = 0; i < NUM_BUFFERS; ++i) {
5011 +               struct sti_buffhd       *bh = &sti->buffhds[i];
5012 +
5013 +               rc = alloc_request(sti, sti->bulk_in, &bh->inreq);
5014 +               if (rc)
5015 +                       goto reset;
5016 +
5017 +               rc = alloc_request(sti, sti->bulk_out, &bh->outreq);
5018 +               if (rc)
5019 +                       goto reset;
5020 +
5021 +               bh->inreq->buf = bh->outreq->buf = bh->buf;
5022 +               bh->inreq->context = bh->outreq->context = bh;
5023 +               bh->inreq->complete = bulk_in_complete;
5024 +               bh->outreq->complete = bulk_out_complete;
5025 +       }
5026 +
5027 +       rc = alloc_request(sti, sti->intr_in, &sti->intreq);
5028 +       if (rc)
5029 +               goto reset;
5030 +
5031 +       sti->running = 1;
5032 +
5033 +       VDBG(sti, "<--- %s()\n", __func__);
5034 +       return rc;
5035 +}
5036 +
5037 +
5038 +/*
5039 + * Change our operational configuration.  This code must agree with the code
5040 + * that returns config descriptors, and with interface altsetting code.
5041 + *
5042 + * It's also responsible for power management interactions.  Some
5043 + * configurations might not work with our current power sources.
5044 + * For now we just assume the gadget is always self-powered.
5045 + */
5046 +static int do_set_config(struct sti_dev *sti, u8 new_config)
5047 +{
5048 +       int     rc = 0;
5049 +       VDBG(sti, "---> %s()\n", __func__);
5050 +
5051 +       /* disable the single interface */
5052 +       if (sti->config != 0) {
5053 +               DBG(sti, "reset config\n");
5054 +               sti->config = 0;
5055 +               rc = do_set_interface(sti, -1);
5056 +       }
5057 +
5058 +       /* enable the interface */
5059 +       if (new_config != 0) {
5060 +               sti->config = new_config;
5061 +               rc = do_set_interface(sti, 0);
5062 +               if (rc)
5063 +                       sti->config = 0;        /* reset on errors */
5064 +               else {
5065 +                       char *speed;
5066 +
5067 +                       switch (sti->gadget->speed) {
5068 +                       case USB_SPEED_LOW:
5069 +                               speed = "low";
5070 +                               break;
5071 +                       case USB_SPEED_FULL:
5072 +                               speed = "full";
5073 +                               break;
5074 +                       case USB_SPEED_HIGH:
5075 +                               speed = "high";
5076 +                               break;
5077 +                       default:
5078 +                               speed = "?";
5079 +                               break;
5080 +                       }
5081 +                       INFO(sti, "%s speed config #%d\n",
5082 +                                       speed, sti->config);
5083 +               }
5084 +       }
5085 +
5086 +       VDBG(sti, "<--- %s()\n", __func__);
5087 +       return rc;
5088 +}
5089 +
5090 +
5091 +/*-------------------------------------------------------------------------*/
5092 +
5093 +static void handle_exception(struct sti_dev *sti)
5094 +{
5095 +       siginfo_t               info;
5096 +       int                     sig;
5097 +       int                     i;
5098 +       int                     num_active;
5099 +       struct sti_buffhd       *bh;
5100 +       enum sti_state          old_state;
5101 +       u8                      new_config;
5102 +       unsigned int            exception_req_tag;
5103 +       int                     rc;
5104 +
5105 +       VDBG(sti, "---> %s()\n", __func__);
5106 +
5107 +       /* Clear the existing signals. Anything but SIGUSR1 is converted
5108 +        * into a high-priority EXIT exception. */
5109 +       for (;;) {
5110 +               sig = dequeue_signal_lock(current, &current->blocked, &info);
5111 +               if (!sig)
5112 +                       break;
5113 +
5114 +               if (sig != SIGUSR1) {
5115 +                       if (sti->state < STI_STATE_EXIT)
5116 +                               DBG(sti, "main thread exiting on signal\n");
5117 +                       raise_exception(sti, STI_STATE_EXIT);
5118 +               }
5119 +       }
5120 +
5121 +       /* cancel all the pending transfers */
5122 +       if (sti->intreq_busy)
5123 +               usb_ep_dequeue(sti->intr_in, sti->intreq);
5124 +
5125 +       for (i = 0; i < NUM_BUFFERS; ++i) {
5126 +               bh = &sti->buffhds[i];
5127 +               if (bh->inreq_busy)
5128 +                       usb_ep_dequeue(sti->bulk_in, bh->inreq);
5129 +               if (bh->outreq_busy)
5130 +                       usb_ep_dequeue(sti->bulk_out, bh->outreq);
5131 +       }
5132 +
5133 +       /* wait until everything is idle */
5134 +       for (;;) {
5135 +               num_active = sti->intreq_busy;
5136 +               for (i = 0; i < NUM_BUFFERS; ++i) {
5137 +                       bh = &sti->buffhds[i];
5138 +                       num_active += bh->inreq_busy + bh->outreq_busy;
5139 +               }
5140 +
5141 +               if (num_active == 0)
5142 +                       break;
5143 +
5144 +               if (sleep_thread(sti))
5145 +                       return;
5146 +       }
5147 +
5148 +       /* clear out the controller's fifos */
5149 +       if (sti->bulk_in_enabled)
5150 +               usb_ep_fifo_flush(sti->bulk_in);
5151 +       if (sti->bulk_out_enabled)
5152 +               usb_ep_fifo_flush(sti->bulk_out);
5153 +       if (sti->intr_in_enabled)
5154 +               usb_ep_fifo_flush(sti->intr_in);
5155 +
5156 +       /*
5157 +        * Reset the I/O buffer states and pointers, the device
5158 +        * state, and the exception. Then invoke the handler.
5159 +        */
5160 +       spin_lock_irq(&sti->lock);
5161 +
5162 +       for (i = 0; i < NUM_BUFFERS; ++i) {
5163 +               bh = &sti->buffhds[i];
5164 +               bh->state = BUF_STATE_EMPTY;
5165 +       }
5166 +       sti->next_buffhd_to_fill = sti->next_buffhd_to_drain =
5167 +                       &sti->buffhds[0];
5168 +
5169 +       exception_req_tag = sti->exception_req_tag;
5170 +       new_config = sti->new_config;
5171 +       old_state = sti->state;
5172 +
5173 +       if (old_state == STI_STATE_ABORT_BULK_OUT)
5174 +               sti->state = STI_STATE_STATUS_PHASE;
5175 +       else
5176 +               sti->state = STI_STATE_IDLE;
5177 +       spin_unlock_irq(&sti->lock);
5178 +
5179 +       /* carry out any extra actions required for the exception */
5180 +       switch (old_state) {
5181 +       default:
5182 +               break;
5183 +
5184 +       case STI_STATE_CANCEL:
5185 +               if (usb_ep_clear_halt(sti->bulk_out) ||
5186 +                               usb_ep_clear_halt(sti->bulk_in))
5187 +                       sti->response_code = PIMA15740_RES_DEVICE_BUSY;
5188 +               else
5189 +                       sti->response_code = PIMA15740_RES_OK;
5190 +               break;
5191 +
5192 +       case STI_STATE_ABORT_BULK_OUT:
5193 +               send_status(sti);
5194 +               spin_lock_irq(&sti->lock);
5195 +               if (sti->state == STI_STATE_STATUS_PHASE)
5196 +                       sti->state = STI_STATE_IDLE;
5197 +               spin_unlock_irq(&sti->lock);
5198 +               break;
5199 +
5200 +       case STI_STATE_RESET:
5201 +               /* in case we were forced against our will to halt a
5202 +                * bulk endpoint, clear the halt now */
5203 +               if (test_and_clear_bit(CLEAR_BULK_HALTS,
5204 +                               &sti->atomic_bitflags)) {
5205 +                       usb_ep_clear_halt(sti->bulk_in);
5206 +                       usb_ep_clear_halt(sti->bulk_out);
5207 +               }
5208 +
5209 +               if (sti->ep0_req_tag == exception_req_tag)
5210 +                       /* complete the status stage */
5211 +                       ep0_queue(sti);
5212 +               break;
5213 +
5214 +       case STI_STATE_INTERFACE_CHANGE:
5215 +               rc = do_set_interface(sti, 0);
5216 +               if (sti->ep0_req_tag != exception_req_tag)
5217 +                       break;
5218 +               if (rc != 0)            /* STALL on errors */
5219 +                       sti_set_halt(sti, sti->ep0);
5220 +               else                    /* complete the status stage */
5221 +                       ep0_queue(sti);
5222 +               break;
5223 +
5224 +       case STI_STATE_CONFIG_CHANGE:
5225 +               rc = do_set_config(sti, new_config);
5226 +               if (sti->ep0_req_tag != exception_req_tag)
5227 +                       break;
5228 +               if (rc != 0)            /* STALL on errors */
5229 +                       sti_set_halt(sti, sti->ep0);
5230 +               else                    /* complete the status stage */
5231 +                       ep0_queue(sti);
5232 +               break;
5233 +
5234 +       case STI_STATE_DISCONNECT:
5235 +               do_set_config(sti, 0);  /* unconfigured state */
5236 +               break;
5237 +
5238 +       case STI_STATE_EXIT:
5239 +       case STI_STATE_TERMINATED:
5240 +               do_set_config(sti, 0);  /* free resources */
5241 +               spin_lock_irq(&sti->lock);
5242 +               sti->state = STI_STATE_TERMINATED;      /* stop the thread */
5243 +               spin_unlock_irq(&sti->lock);
5244 +               break;
5245 +       }
5246 +
5247 +       VDBG(sti, "<--- %s()\n", __func__);
5248 +}
5249 +
5250 +
5251 +/*-------------------------------------------------------------------------*/
5252 +
5253 +static int sti_main_thread(void *sti_)
5254 +{
5255 +       struct sti_dev          *sti = sti_;
5256 +       VDBG(sti, "---> %s()\n", __func__);
5257 +
5258 +       /*
5259 +        * allow the thread to be killed by a signal, but set the signal mask
5260 +        * to block everything but INT, TERM, KILL, and USR1
5261 +        */
5262 +       allow_signal(SIGINT);
5263 +       allow_signal(SIGTERM);
5264 +       allow_signal(SIGKILL);
5265 +       allow_signal(SIGUSR1);
5266 +
5267 +       /* allow the thread to be frozen */
5268 +       set_freezable();
5269 +
5270 +       /*
5271 +        * arrange for userspace references to be interpreted as kernel
5272 +        * pointers. That way we can pass a kernel pointer to a routine
5273 +        * that expects a __user pointer and it will work okay.
5274 +        */
5275 +       set_fs(get_ds());
5276 +
5277 +       /* the main loop */
5278 +       while (sti->state != STI_STATE_TERMINATED) {
5279 +               if (exception_in_progress(sti) || signal_pending(current)) {
5280 +                       handle_exception(sti);
5281 +                       continue;
5282 +               }
5283 +
5284 +               if (!sti->running) {
5285 +                       sleep_thread(sti);
5286 +                       continue;
5287 +               }
5288 +
5289 +               if (get_next_command(sti))
5290 +                       continue;
5291 +
5292 +               spin_lock_irq(&sti->lock);
5293 +               if (!exception_in_progress(sti))
5294 +                       sti->state = STI_STATE_DATA_PHASE;
5295 +               spin_unlock_irq(&sti->lock);
5296 +
5297 +               if (do_still_image_command(sti))
5298 +                       continue;
5299 +
5300 +               spin_lock_irq(&sti->lock);
5301 +               if (!exception_in_progress(sti))
5302 +                       sti->state = STI_STATE_STATUS_PHASE;
5303 +               spin_unlock_irq(&sti->lock);
5304 +
5305 +               if (send_status(sti))
5306 +                       continue;
5307 +
5308 +               spin_lock_irq(&sti->lock);
5309 +               if (!exception_in_progress(sti))
5310 +                       sti->state = STI_STATE_IDLE;
5311 +               spin_unlock_irq(&sti->lock);
5312 +       }
5313 +
5314 +       spin_lock_irq(&sti->lock);
5315 +       sti->thread_task = NULL;
5316 +       spin_unlock_irq(&sti->lock);
5317 +
5318 +       /* in case we are exiting because of a signal, unregister the
5319 +        * gadget driver */
5320 +       if (test_and_clear_bit(REGISTERED, &sti->atomic_bitflags))
5321 +               usb_gadget_unregister_driver(&sti_driver);
5322 +
5323 +       /* let the unbind and cleanup routines know the thread has exited */
5324 +       complete_and_exit(&sti->thread_notifier, 0);
5325 +
5326 +       VDBG(sti, "<--- %s()\n", __func__);
5327 +}
5328 +
5329 +
5330 +/*-------------------------------------------------------------------------*/
5331 +
5332 +static int open_backing_folder(struct sti_dev *sti, const char *folder_name)
5333 +{
5334 +       struct file             *filp = NULL;
5335 +       int                     rc = -EINVAL;
5336 +       struct inode            *inode = NULL;
5337 +       size_t                  len;
5338 +       VDBG(sti, "---> %s()\n", __func__);
5339 +
5340 +       /* remove the trailing path sign */
5341 +       len = strlen(folder_name);
5342 +       if (len > 1 && folder_name[len-1] == '/')
5343 +               ((char *) folder_name)[len-1] = 0;
5344 +
5345 +       memset(sti->root_path, 0, sizeof(sti->root_path));
5346 +       strncpy(sti->root_path, folder_name, sizeof(sti->root_path));
5347 +
5348 +       filp = filp_open(sti->root_path, O_RDONLY | O_DIRECTORY, 0);
5349 +       if (IS_ERR(filp)) {
5350 +               ERROR(sti, "unable to open backing folder: %s\n",
5351 +                               sti->root_path);
5352 +               return PTR_ERR(filp);
5353 +       }
5354 +
5355 +       if (filp->f_path.dentry)
5356 +               inode = filp->f_dentry->d_inode;
5357 +
5358 +       if (!inode || !S_ISDIR(inode->i_mode)) {
5359 +               ERROR(sti, "%s is not a directory\n", sti->root_path);
5360 +               goto out;
5361 +       }
5362 +
5363 +       get_file(filp);
5364 +
5365 +       sti->root_filp = filp;
5366 +
5367 +       INFO(sti, "open backing folder: %s\n", folder_name);
5368 +       rc = 0;
5369 +out:
5370 +       filp_close(filp, current->files);
5371 +
5372 +       VDBG(sti, "<--- %s()\n", __func__);
5373 +       return rc;
5374 +}
5375 +
5376 +static void close_backing_folder(struct sti_dev *sti)
5377 +{
5378 +       VDBG(sti, "---> %s()\n", __func__);
5379 +
5380 +       if (sti->root_filp) {
5381 +               INFO(sti, "close backing folder\n");
5382 +               fput(sti->root_filp);
5383 +               sti->root_filp = NULL;
5384 +       }
5385 +
5386 +       VDBG(sti, "<--- %s()\n", __func__);
5387 +}
5388 +
5389 +
5390 +/*-------------------------------------------------------------------------*/
5391 +
5392 +/* sysfs attribute files */
5393 +static ssize_t show_folder(struct device *dev, struct device_attribute *attr,
5394 +               char *buf)
5395 +{
5396 +       struct sti_dev  *sti = dev_get_drvdata(dev);
5397 +       char            *p;
5398 +       ssize_t         rc;
5399 +
5400 +       down_read(&sti->filesem);
5401 +       if (backing_folder_is_open(sti)) {
5402 +               /* get the complete pathname */
5403 +               p = d_path(&sti->root_filp->f_path, buf, PAGE_SIZE - 1);
5404 +               if (IS_ERR(p))
5405 +                       rc = PTR_ERR(p);
5406 +               else {
5407 +                       rc = strlen(p);
5408 +                       memmove(buf, p, rc);
5409 +
5410 +                       /* add a newline */
5411 +                       buf[rc] = '\n';
5412 +                       buf[++rc] = 0;
5413 +               }
5414 +       } else {        /* no file */
5415 +               *buf = 0;
5416 +               rc = 0;
5417 +       }
5418 +       up_read(&sti->filesem);
5419 +
5420 +       return rc;
5421 +}
5422 +
5423 +
5424 +static ssize_t store_folder(struct device *dev, struct device_attribute *attr,
5425 +               const char *buf, size_t count)
5426 +{
5427 +       struct sti_dev  *sti = dev_get_drvdata(dev);
5428 +       int             rc = 0;
5429 +
5430 +       /* remove a trailing newline */
5431 +       if (count > 0 && buf[count-1] == '\n')
5432 +               ((char *) buf)[count-1] = 0;
5433 +
5434 +       /* eject current medium */
5435 +       down_write(&sti->filesem);
5436 +       if (backing_folder_is_open(sti))
5437 +               close_backing_folder(sti);
5438 +
5439 +       /* load new medium */
5440 +       if (count > 0 && buf[0])
5441 +               rc = open_backing_folder(sti, buf);
5442 +
5443 +       up_write(&sti->filesem);
5444 +
5445 +       return (rc < 0 ? rc : count);
5446 +}
5447 +
5448 +/* the write permissions and store_xxx pointers are set in sti_bind() */
5449 +static DEVICE_ATTR(folder, 0444, show_folder, NULL);
5450 +
5451 +
5452 +/*-------------------------------------------------------------------------*/
5453 +
5454 +static void sti_release(struct kref *ref)
5455 +{
5456 +       struct sti_dev  *sti = container_of(ref, struct sti_dev, ref);
5457 +
5458 +       while (!list_empty(&sti->obj_list)) {
5459 +               struct sti_object *obj = NULL;
5460 +               obj = list_entry(sti->obj_list.next, struct sti_object, list);
5461 +               list_del_init(&obj->list);
5462 +               kfree(obj);
5463 +       }
5464 +
5465 +       while (!list_empty(&sti->tmp_obj_list)) {
5466 +               struct sti_object *obj = NULL;
5467 +               obj = list_entry(sti->tmp_obj_list.next, struct sti_object,
5468 +                               list);
5469 +               list_del_init(&obj->list);
5470 +               kfree(obj);
5471 +       }
5472 +
5473 +       kfree(sti);
5474 +}
5475 +
5476 +static void gadget_release(struct device *dev)
5477 +{
5478 +       struct sti_dev  *sti = dev_get_drvdata(dev);
5479 +       VDBG(sti, "---> %s()\n", __func__);
5480 +       VDBG(sti, "<--- %s()\n", __func__);
5481 +
5482 +       kref_put(&sti->ref, sti_release);
5483 +}
5484 +
5485 +
5486 +static void /* __init_or_exit */ sti_unbind(struct usb_gadget *gadget)
5487 +{
5488 +       struct sti_dev          *sti = get_gadget_data(gadget);
5489 +       int                     i;
5490 +       struct usb_request      *req = sti->ep0req;
5491 +       VDBG(sti, "---> %s()\n", __func__);
5492 +
5493 +       DBG(sti, "unbind\n");
5494 +       clear_bit(REGISTERED, &sti->atomic_bitflags);
5495 +
5496 +       /* unregister the sysfs attribute files */
5497 +       if (sti->registered) {
5498 +               device_remove_file(&sti->dev, &dev_attr_folder);
5499 +               close_backing_folder(sti);
5500 +               device_unregister(&sti->dev);
5501 +               sti->registered = 0;
5502 +       }
5503 +
5504 +       /* if the thread isn't already dead, tell it to exit now */
5505 +       if (sti->state != STI_STATE_TERMINATED) {
5506 +               raise_exception(sti, STI_STATE_EXIT);
5507 +               wait_for_completion(&sti->thread_notifier);
5508 +
5509 +               /* the cleanup routine waits for this completion also */
5510 +               complete(&sti->thread_notifier);
5511 +       }
5512 +
5513 +       /* free the data buffers */
5514 +       for (i = 0; i < NUM_BUFFERS; ++i)
5515 +               kfree(sti->buffhds[i].buf);
5516 +
5517 +       /* free the request and buffer for endpoint 0 */
5518 +       if (req) {
5519 +               kfree(req->buf);
5520 +               usb_ep_free_request(sti->ep0, req);
5521 +       }
5522 +
5523 +       set_gadget_data(gadget, NULL);
5524 +
5525 +       VDBG(sti, "<--- %s()\n", __func__);
5526 +}
5527 +
5528 +
5529 +static int __init check_parameters(struct sti_dev *sti)
5530 +{
5531 +       int     gcnum;
5532 +       VDBG(sti, "---> %s()\n", __func__);
5533 +
5534 +       /* parameter wasn't set */
5535 +       if (mod_data.release == 0xffff) {
5536 +               gcnum = usb_gadget_controller_number(sti->gadget);
5537 +               if (gcnum >= 0)
5538 +                       mod_data.release = 0x0300 + gcnum;
5539 +               else {
5540 +                       WARNING(sti, "controller '%s' not recognized\n",
5541 +                               sti->gadget->name);
5542 +                       mod_data.release = 0x0399;
5543 +               }
5544 +       }
5545 +
5546 +       mod_data.buflen &= PAGE_CACHE_MASK;
5547 +       if (mod_data.buflen <= 0) {
5548 +               ERROR(sti, "invalid buflen\n");
5549 +               return -ETOOSMALL;
5550 +       }
5551 +
5552 +       VDBG(sti, "<--- %s()\n", __func__);
5553 +       return 0;
5554 +}
5555 +
5556 +
5557 +static int __init sti_bind(struct usb_gadget *gadget)
5558 +{
5559 +       struct sti_dev          *sti = the_sti;
5560 +       int                     rc;
5561 +       int                     i;
5562 +       struct usb_ep           *ep;
5563 +       struct usb_request      *req;
5564 +
5565 +       sti->gadget = gadget;
5566 +       set_gadget_data(gadget, sti);
5567 +       sti->ep0 = gadget->ep0;
5568 +       sti->ep0->driver_data = sti;
5569 +
5570 +       rc = check_parameters(sti);
5571 +       if (rc)
5572 +               goto out;
5573 +
5574 +       /* enable store_xxx attributes */
5575 +       dev_attr_folder.attr.mode = 0644;
5576 +       dev_attr_folder.store = store_folder;
5577 +
5578 +       sti->dev.release = gadget_release;
5579 +       sti->dev.parent = &gadget->dev;
5580 +       sti->dev.driver = &sti_driver.driver;
5581 +       dev_set_drvdata(&sti->dev, sti);
5582 +       dev_set_name(&sti->dev, "%s", sti_driver.driver.name);
5583 +
5584 +       rc = device_register(&sti->dev);
5585 +       if (rc) {
5586 +               INFO(sti, "failed to register sti: %d\n", rc);
5587 +               goto out;
5588 +       }
5589 +
5590 +       rc = device_create_file(&sti->dev, &dev_attr_folder);
5591 +       if (rc) {
5592 +               device_unregister(&sti->dev);
5593 +               goto out;
5594 +       }
5595 +
5596 +       sti->registered = 1;
5597 +       kref_get(&sti->ref);
5598 +
5599 +       /* initialize object list */
5600 +       INIT_LIST_HEAD(&sti->obj_list);
5601 +       INIT_LIST_HEAD(&sti->tmp_obj_list);
5602 +
5603 +       if (mod_data.folder && *mod_data.folder)
5604 +               rc = open_backing_folder(sti, mod_data.folder);
5605 +               if (rc)
5606 +                       goto out;
5607 +
5608 +       /* find all the endpoints we will use */
5609 +       usb_ep_autoconfig_reset(gadget);
5610 +       ep = usb_ep_autoconfig(gadget, &fs_bulk_in_desc);
5611 +       if (!ep)
5612 +               goto autoconf_fail;
5613 +
5614 +       /* claim bulk-in endpoint */
5615 +       ep->driver_data = sti;
5616 +       sti->bulk_in = ep;
5617 +
5618 +       ep = usb_ep_autoconfig(gadget, &fs_bulk_out_desc);
5619 +       if (!ep)
5620 +               goto autoconf_fail;
5621 +
5622 +       /* claim bulk-out endpoint */
5623 +       ep->driver_data = sti;
5624 +       sti->bulk_out = ep;
5625 +
5626 +       ep = usb_ep_autoconfig(gadget, &fs_intr_in_desc);
5627 +       if (!ep)
5628 +               goto autoconf_fail;
5629 +
5630 +       /* claim intr-in endpoint */
5631 +       ep->driver_data = sti;
5632 +       sti->intr_in = ep;
5633 +
5634 +       /* fix up the descriptors */
5635 +       device_desc.bMaxPacketSize0 = sti->ep0->maxpacket;
5636 +       device_desc.idVendor = cpu_to_le16(mod_data.vendor);
5637 +       device_desc.idProduct = cpu_to_le16(mod_data.product);
5638 +       device_desc.bcdDevice = cpu_to_le16(mod_data.release);
5639 +
5640 +       fs_function[3 + FS_FUNCTION_PRE_EP_ENTRIES] = NULL;
5641 +
5642 +       if (gadget_is_dualspeed(gadget)) {
5643 +               hs_function[3 + HS_FUNCTION_PRE_EP_ENTRIES] = NULL;
5644 +
5645 +               /* assume ep0 uses the same maxpacket value for both speeds */
5646 +               dev_qualifier.bMaxPacketSize0 = sti->ep0->maxpacket;
5647 +
5648 +               /* assume endpoint addresses are the same for both speeds */
5649 +               hs_bulk_in_desc.bEndpointAddress =
5650 +                               fs_bulk_in_desc.bEndpointAddress;
5651 +               hs_bulk_out_desc.bEndpointAddress =
5652 +                               fs_bulk_out_desc.bEndpointAddress;
5653 +               hs_intr_in_desc.bEndpointAddress =
5654 +                               fs_intr_in_desc.bEndpointAddress;
5655 +       }
5656 +
5657 +       if (gadget_is_otg(gadget))
5658 +               otg_desc.bmAttributes |= USB_OTG_HNP;
5659 +
5660 +       rc = -ENOMEM;
5661 +
5662 +       /* allocate the request and buffer for endpoint 0 */
5663 +       sti->ep0req = req = usb_ep_alloc_request(sti->ep0, GFP_KERNEL);
5664 +       if (!req)
5665 +               goto autoconf_fail;
5666 +
5667 +       req->buf = kmalloc(EP0_BUFSIZE, GFP_KERNEL);
5668 +       if (!req->buf)
5669 +               goto autoconf_fail;
5670 +
5671 +       req->complete = ep0_complete;
5672 +
5673 +       /* allocate the data buffers */
5674 +       for (i = 0; i < NUM_BUFFERS; ++i) {
5675 +               struct sti_buffhd       *bh = &sti->buffhds[i];
5676 +
5677 +               /*
5678 +                * Allocate for the bulk-in endpoint. We assume that
5679 +                * the buffer will also work with the bulk-out (and
5680 +                * interrupt-in) endpoint.
5681 +                */
5682 +               bh->buf = kmalloc(mod_data.buflen, GFP_KERNEL);
5683 +               if (!bh->buf)
5684 +                       goto autoconf_fail;
5685 +
5686 +               bh->next = bh + 1;
5687 +       }
5688 +       sti->buffhds[NUM_BUFFERS - 1].next = &sti->buffhds[0];
5689 +
5690 +       /* this should reflect the actual gadget power source */
5691 +       usb_gadget_set_selfpowered(gadget);
5692 +
5693 +       snprintf(manufacturer, sizeof manufacturer, "%s %s with %s",
5694 +                       init_utsname()->sysname, init_utsname()->release,
5695 +                       gadget->name);
5696 +
5697 +       DBG(sti, "manufacturer: %s\n", manufacturer);
5698 +
5699 +       /*
5700 +        * on a real device, serial[] would be loaded from permanent
5701 +        * storage. We just encode it from the driver version string.
5702 +        */
5703 +       for (i = 0; i < sizeof(serial) - 2; i += 2) {
5704 +               unsigned char           c = DRIVER_VERSION[i / 2];
5705 +
5706 +               if (!c)
5707 +                       break;
5708 +
5709 +               snprintf(&serial[i], sizeof(&serial[i]), "%02X", c);
5710 +       }
5711 +
5712 +       /* fill remained device info */
5713 +       sti_device_info.manufacturer_len = sizeof(manufacturer);
5714 +       str_to_uni16(manufacturer, sti_device_info.manufacturer);
5715 +
5716 +       sti_device_info.model_len = sizeof(longname);
5717 +       str_to_uni16(longname, sti_device_info.model);
5718 +
5719 +       sti_device_info.device_version_len = sizeof(device_version);
5720 +       str_to_uni16(device_version, sti_device_info.device_version);
5721 +
5722 +       sti_device_info.serial_number_len = sizeof(serial);
5723 +       str_to_uni16(serial, sti_device_info.serial_number);
5724 +
5725 +       /* create main kernel thread */
5726 +       sti->thread_task = kthread_create(sti_main_thread, sti,
5727 +                       "still-image-gadget");
5728 +
5729 +       if (IS_ERR(sti->thread_task)) {
5730 +               rc = PTR_ERR(sti->thread_task);
5731 +               goto autoconf_fail;
5732 +       }
5733 +
5734 +       INFO(sti, DRIVER_DESC ", version: " DRIVER_VERSION "\n");
5735 +       INFO(sti, "VendorID=x%04x, ProductID=x%04x, Release=x%04x\n",
5736 +                       mod_data.vendor, mod_data.product, mod_data.release);
5737 +       INFO(sti, "I/O thread pid: %d, buflen=%u\n",
5738 +                       task_pid_nr(sti->thread_task), mod_data.buflen);
5739 +
5740 +       set_bit(REGISTERED, &sti->atomic_bitflags);
5741 +
5742 +       /* tell the thread to start working */
5743 +       wake_up_process(sti->thread_task);
5744 +
5745 +       DBG(sti, "bind\n");
5746 +       return 0;
5747 +
5748 +autoconf_fail:
5749 +       ERROR(sti, "unable to autoconfigure all endpoints\n");
5750 +       rc = -ENOTSUPP;
5751 +out:
5752 +       /* the thread is dead */
5753 +       sti->state = STI_STATE_TERMINATED;
5754 +
5755 +       sti_unbind(gadget);
5756 +       complete(&sti->thread_notifier);
5757 +
5758 +       VDBG(sti, "<---> %s()\n", __func__);
5759 +       return rc;
5760 +}
5761 +
5762 +
5763 +/*-------------------------------------------------------------------------*/
5764 +
5765 +static void sti_suspend(struct usb_gadget *gadget)
5766 +{
5767 +       struct sti_dev          *sti = get_gadget_data(gadget);
5768 +
5769 +       DBG(sti, "suspend\n");
5770 +       set_bit(SUSPENDED, &sti->atomic_bitflags);
5771 +}
5772 +
5773 +
5774 +static void sti_resume(struct usb_gadget *gadget)
5775 +{
5776 +       struct sti_dev          *sti = get_gadget_data(gadget);
5777 +
5778 +       DBG(sti, "resume\n");
5779 +       clear_bit(SUSPENDED, &sti->atomic_bitflags);
5780 +}
5781 +
5782 +
5783 +/*-------------------------------------------------------------------------*/
5784 +
5785 +static struct usb_gadget_driver                sti_driver = {
5786 +#ifdef CONFIG_USB_GADGET_DUALSPEED
5787 +       .speed          = USB_SPEED_HIGH,
5788 +#else
5789 +       .speed          = USB_SPEED_FULL,
5790 +#endif
5791 +       .function       = (char *) longname,
5792 +       .bind           = sti_bind,
5793 +       .unbind         = sti_unbind,
5794 +       .disconnect     = sti_disconnect,
5795 +       .setup          = sti_setup,
5796 +       .suspend        = sti_suspend,
5797 +       .resume         = sti_resume,
5798 +
5799 +       .driver         = {
5800 +               .name           = (char *) shortname,
5801 +               .owner          = THIS_MODULE,
5802 +               /* .release = ... */
5803 +               /* .suspend = ... */
5804 +               /* .resume = ...  */
5805 +       },
5806 +};
5807 +
5808 +
5809 +static int __init sti_alloc(void)
5810 +{
5811 +       struct sti_dev          *sti;
5812 +
5813 +       sti = kzalloc(sizeof *sti, GFP_KERNEL);
5814 +       if (!sti)
5815 +               return -ENOMEM;
5816 +
5817 +       spin_lock_init(&sti->lock);
5818 +       init_rwsem(&sti->filesem);
5819 +       kref_init(&sti->ref);
5820 +       init_completion(&sti->thread_notifier);
5821 +
5822 +       the_sti = sti;
5823 +
5824 +       return 0;
5825 +}
5826 +
5827 +
5828 +static int __init sti_init(void)
5829 +{
5830 +       int             rc;
5831 +       struct sti_dev  *sti;
5832 +
5833 +       rc = sti_alloc();
5834 +       if (rc)
5835 +               return rc;
5836 +
5837 +       sti = the_sti;
5838 +
5839 +       rc = usb_gadget_register_driver(&sti_driver);
5840 +       if (rc)
5841 +               kref_put(&sti->ref, sti_release);
5842 +
5843 +       return rc;
5844 +}
5845 +module_init(sti_init);
5846 +
5847 +
5848 +static void __exit sti_cleanup(void)
5849 +{
5850 +       struct sti_dev  *sti = the_sti;
5851 +
5852 +       /* unregister the driver if the thread hasn't already done */
5853 +       if (test_and_clear_bit(REGISTERED, &sti->atomic_bitflags))
5854 +               usb_gadget_unregister_driver(&sti_driver);
5855 +
5856 +       /* wait for the thread to finish up */
5857 +       wait_for_completion(&sti->thread_notifier);
5858 +
5859 +       kref_put(&sti->ref, sti_release);
5860 +}
5861 +module_exit(sti_cleanup);
5862 diff --git a/drivers/usb/otg/Kconfig b/drivers/usb/otg/Kconfig
5863 index 3d2d3e5..69ff37b 100644
5864 --- a/drivers/usb/otg/Kconfig
5865 +++ b/drivers/usb/otg/Kconfig
5866 @@ -69,4 +69,18 @@ config NOP_USB_XCEIV
5867          built-in with usb ip or which are autonomous and doesn't require any
5868          phy programming such as ISP1x04 etc.
5869  
5870 +config USB_LANGWELL_OTG
5871 +       tristate "Intel Langwell USB OTG dual-role support"
5872 +       depends on USB && X86_MRST
5873 +       select USB_OTG
5874 +       select USB_OTG_UTILS
5875 +       help
5876 +         Say Y here if you want to build Intel Langwell USB OTG
5877 +         transciever driver in kernel. This driver implements role
5878 +         switch between EHCI host driver and Langwell USB OTG
5879 +         client driver.
5880 +
5881 +         To compile this driver as a module, choose M here: the
5882 +         module will be called langwell_otg.
5883 +
5884  endif # USB || OTG
5885 diff --git a/drivers/usb/otg/Makefile b/drivers/usb/otg/Makefile
5886 index aeb49a8..b6609db 100644
5887 --- a/drivers/usb/otg/Makefile
5888 +++ b/drivers/usb/otg/Makefile
5889 @@ -9,6 +9,7 @@ obj-$(CONFIG_USB_OTG_UTILS)     += otg.o
5890  obj-$(CONFIG_USB_GPIO_VBUS)    += gpio_vbus.o
5891  obj-$(CONFIG_ISP1301_OMAP)     += isp1301_omap.o
5892  obj-$(CONFIG_TWL4030_USB)      += twl4030-usb.o
5893 +obj-$(CONFIG_USB_LANGWELL_OTG) += langwell_otg.o
5894  obj-$(CONFIG_NOP_USB_XCEIV)    += nop-usb-xceiv.o
5895  obj-$(CONFIG_USB_ULPI)         += ulpi.o
5896  
5897 diff --git a/drivers/usb/otg/langwell_otg.c b/drivers/usb/otg/langwell_otg.c
5898 new file mode 100644
5899 index 0000000..46ae881
5900 --- /dev/null
5901 +++ b/drivers/usb/otg/langwell_otg.c
5902 @@ -0,0 +1,2260 @@
5903 +/*
5904 + * Intel Langwell USB OTG transceiver driver
5905 + * Copyright (C) 2008 - 2009, Intel Corporation.
5906 + *
5907 + * This program is free software; you can redistribute it and/or modify it
5908 + * under the terms and conditions of the GNU General Public License,
5909 + * version 2, as published by the Free Software Foundation.
5910 + *
5911 + * This program is distributed in the hope it will be useful, but WITHOUT
5912 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
5913 + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
5914 + * more details.
5915 + *
5916 + * You should have received a copy of the GNU General Public License along with
5917 + * this program; if not, write to the Free Software Foundation, Inc.,
5918 + * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
5919 + *
5920 + */
5921 +/* This driver helps to switch Langwell OTG controller function between host
5922 + * and peripheral. It works with EHCI driver and Langwell client controller
5923 + * driver together.
5924 + */
5925 +#include <linux/module.h>
5926 +#include <linux/init.h>
5927 +#include <linux/pci.h>
5928 +#include <linux/errno.h>
5929 +#include <linux/interrupt.h>
5930 +#include <linux/kernel.h>
5931 +#include <linux/device.h>
5932 +#include <linux/moduleparam.h>
5933 +#include <linux/usb/ch9.h>
5934 +#include <linux/usb/gadget.h>
5935 +#include <linux/usb.h>
5936 +#include <linux/usb/otg.h>
5937 +#include <linux/notifier.h>
5938 +#include <asm/ipc_defs.h>
5939 +#include <linux/delay.h>
5940 +#include "../core/hcd.h"
5941 +
5942 +#include <linux/usb/langwell_otg.h>
5943 +
5944 +#define        DRIVER_DESC             "Intel Langwell USB OTG transceiver driver"
5945 +#define        DRIVER_VERSION          "March 19, 2010"
5946 +
5947 +MODULE_DESCRIPTION(DRIVER_DESC);
5948 +MODULE_AUTHOR("Henry Yuan <hang.yuan@intel.com>, Hao Wu <hao.wu@intel.com>");
5949 +MODULE_VERSION(DRIVER_VERSION);
5950 +MODULE_LICENSE("GPL");
5951 +
5952 +static const char driver_name[] = "langwell_otg";
5953 +
5954 +static int langwell_otg_probe(struct pci_dev *pdev,
5955 +                       const struct pci_device_id *id);
5956 +static void langwell_otg_remove(struct pci_dev *pdev);
5957 +static int langwell_otg_suspend(struct pci_dev *pdev, pm_message_t message);
5958 +static int langwell_otg_resume(struct pci_dev *pdev);
5959 +
5960 +static int langwell_otg_set_host(struct otg_transceiver *otg,
5961 +                               struct usb_bus *host);
5962 +static int langwell_otg_set_peripheral(struct otg_transceiver *otg,
5963 +                               struct usb_gadget *gadget);
5964 +static int langwell_otg_start_srp(struct otg_transceiver *otg);
5965 +
5966 +static const struct pci_device_id pci_ids[] = {{
5967 +       .class =        ((PCI_CLASS_SERIAL_USB << 8) | 0xfe),
5968 +       .class_mask =   ~0,
5969 +       .vendor =       0x8086,
5970 +       .device =       0x0811,
5971 +       .subvendor =    PCI_ANY_ID,
5972 +       .subdevice =    PCI_ANY_ID,
5973 +}, { /* end: all zeroes */ }
5974 +};
5975 +
5976 +static struct pci_driver otg_pci_driver = {
5977 +       .name =         (char *) driver_name,
5978 +       .id_table =     pci_ids,
5979 +
5980 +       .probe =        langwell_otg_probe,
5981 +       .remove =       langwell_otg_remove,
5982 +
5983 +       .suspend =      langwell_otg_suspend,
5984 +       .resume =       langwell_otg_resume,
5985 +};
5986 +
5987 +static const char *state_string(enum usb_otg_state state)
5988 +{
5989 +       switch (state) {
5990 +       case OTG_STATE_A_IDLE:
5991 +               return "a_idle";
5992 +       case OTG_STATE_A_WAIT_VRISE:
5993 +               return "a_wait_vrise";
5994 +       case OTG_STATE_A_WAIT_BCON:
5995 +               return "a_wait_bcon";
5996 +       case OTG_STATE_A_HOST:
5997 +               return "a_host";
5998 +       case OTG_STATE_A_SUSPEND:
5999 +               return "a_suspend";
6000 +       case OTG_STATE_A_PERIPHERAL:
6001 +               return "a_peripheral";
6002 +       case OTG_STATE_A_WAIT_VFALL:
6003 +               return "a_wait_vfall";
6004 +       case OTG_STATE_A_VBUS_ERR:
6005 +               return "a_vbus_err";
6006 +       case OTG_STATE_B_IDLE:
6007 +               return "b_idle";
6008 +       case OTG_STATE_B_SRP_INIT:
6009 +               return "b_srp_init";
6010 +       case OTG_STATE_B_PERIPHERAL:
6011 +               return "b_peripheral";
6012 +       case OTG_STATE_B_WAIT_ACON:
6013 +               return "b_wait_acon";
6014 +       case OTG_STATE_B_HOST:
6015 +               return "b_host";
6016 +       default:
6017 +               return "UNDEFINED";
6018 +       }
6019 +}
6020 +
6021 +/* HSM timers */
6022 +static inline struct langwell_otg_timer *otg_timer_initializer
6023 +(void (*function)(unsigned long), unsigned long expires, unsigned long data)
6024 +{
6025 +       struct langwell_otg_timer *timer;
6026 +       timer = kmalloc(sizeof(struct langwell_otg_timer), GFP_KERNEL);
6027 +       timer->function = function;
6028 +       timer->expires = expires;
6029 +       timer->data = data;
6030 +       return timer;
6031 +}
6032 +
6033 +static struct langwell_otg_timer *a_wait_vrise_tmr, *a_aidl_bdis_tmr,
6034 +       *b_se0_srp_tmr, *b_srp_init_tmr;
6035 +
6036 +static struct list_head active_timers;
6037 +
6038 +static struct langwell_otg *the_transceiver;
6039 +
6040 +/* host/client notify transceiver when event affects HNP state */
6041 +void langwell_update_transceiver()
6042 +{
6043 +       struct langwell_otg *langwell = the_transceiver;
6044 +
6045 +       otg_dbg("transceiver is updated\n");
6046 +
6047 +       if (!langwell->qwork)
6048 +               return ;
6049 +
6050 +       queue_work(langwell->qwork, &langwell->work);
6051 +}
6052 +EXPORT_SYMBOL(langwell_update_transceiver);
6053 +
6054 +static int langwell_otg_set_host(struct otg_transceiver *otg,
6055 +                                       struct usb_bus *host)
6056 +{
6057 +       otg->host = host;
6058 +
6059 +       return 0;
6060 +}
6061 +
6062 +static int langwell_otg_set_peripheral(struct otg_transceiver *otg,
6063 +                                       struct usb_gadget *gadget)
6064 +{
6065 +       otg->gadget = gadget;
6066 +
6067 +       return 0;
6068 +}
6069 +
6070 +static int langwell_otg_set_power(struct otg_transceiver *otg,
6071 +                               unsigned mA)
6072 +{
6073 +       return 0;
6074 +}
6075 +
6076 +/* A-device drives vbus, controlled through PMIC CHRGCNTL register*/
6077 +static void langwell_otg_drv_vbus(int on)
6078 +{
6079 +       struct ipc_pmic_reg_data        pmic_data = {0};
6080 +       struct ipc_pmic_reg_data        data = {0};
6081 +
6082 +       data.pmic_reg_data[0].register_address = 0xd2;
6083 +       data.ioc = 0;
6084 +       data.num_entries = 1;
6085 +
6086 +       if (ipc_pmic_register_read(&data)) {
6087 +               otg_dbg("Failed to read PMIC register 0x00.\n");
6088 +               return;
6089 +       }
6090 +
6091 +       if (data.pmic_reg_data[0].value & 0x20)
6092 +               otg_dbg("battery attached(%x)\n", data.pmic_reg_data[0].value);
6093 +       else {
6094 +               otg_dbg("no battery detected\n");
6095 +               return;
6096 +       }
6097 +
6098 +       pmic_data.ioc = 0;
6099 +       pmic_data.pmic_reg_data[0].register_address = 0xd4;
6100 +       pmic_data.num_entries = 1;
6101 +       if (on)
6102 +               pmic_data.pmic_reg_data[0].value = 0x20;
6103 +       else
6104 +               pmic_data.pmic_reg_data[0].value = 0xc0;
6105 +
6106 +       if (ipc_pmic_register_write(&pmic_data, TRUE))
6107 +               otg_dbg("Failed to write PMIC.\n");
6108 +}
6109 +
6110 +/* charge vbus or discharge vbus through a resistor to ground */
6111 +static void langwell_otg_chrg_vbus(int on)
6112 +{
6113 +
6114 +       u32     val;
6115 +
6116 +       val = readl(the_transceiver->regs + CI_OTGSC);
6117 +
6118 +       if (on)
6119 +               writel((val & ~OTGSC_INTSTS_MASK) | OTGSC_VC,
6120 +                               the_transceiver->regs + CI_OTGSC);
6121 +       else
6122 +               writel((val & ~OTGSC_INTSTS_MASK) | OTGSC_VD,
6123 +                               the_transceiver->regs + CI_OTGSC);
6124 +
6125 +}
6126 +
6127 +/* Start SRP */
6128 +static int langwell_otg_start_srp(struct otg_transceiver *otg)
6129 +{
6130 +       u32     val;
6131 +
6132 +       otg_dbg("Start SRP ->\n");
6133 +
6134 +       val = readl(the_transceiver->regs + CI_OTGSC);
6135 +
6136 +       writel((val & ~OTGSC_INTSTS_MASK) | OTGSC_HADP,
6137 +               the_transceiver->regs + CI_OTGSC);
6138 +
6139 +       /* Check if the data plus is finished or not */
6140 +       msleep(8);
6141 +       val = readl(the_transceiver->regs + CI_OTGSC);
6142 +       if (val & (OTGSC_HADP | OTGSC_DP))
6143 +               otg_dbg("DataLine SRP Error\n");
6144 +
6145 +       /* Disable interrupt - b_sess_vld */
6146 +       val = readl(the_transceiver->regs + CI_OTGSC);
6147 +       val &= (~(OTGSC_BSVIE | OTGSC_BSEIE));
6148 +       writel(val, the_transceiver->regs + CI_OTGSC);
6149 +
6150 +       /* Start VBus SRP */
6151 +       langwell_otg_drv_vbus(1);
6152 +       msleep(15);
6153 +       langwell_otg_drv_vbus(0);
6154 +
6155 +       /* Enable interrupt - b_sess_vld*/
6156 +       val = readl(the_transceiver->regs + CI_OTGSC);
6157 +       val |= (OTGSC_BSVIE | OTGSC_BSEIE);
6158 +       writel(val, the_transceiver->regs + CI_OTGSC);
6159 +
6160 +       otg_dbg("Start SRP <-\n");
6161 +       return 0;
6162 +}
6163 +
6164 +/* stop SOF via bus_suspend */
6165 +static void langwell_otg_loc_sof(int on)
6166 +{
6167 +       struct usb_hcd  *hcd;
6168 +       int             err;
6169 +
6170 +       otg_dbg("loc_sof -> %d\n", on);
6171 +
6172 +       hcd = bus_to_hcd(the_transceiver->otg.host);
6173 +       if (on)
6174 +               err = hcd->driver->bus_resume(hcd);
6175 +       else
6176 +               err = hcd->driver->bus_suspend(hcd);
6177 +
6178 +       if (err)
6179 +               otg_dbg("Failed to resume/suspend bus - %d\n", err);
6180 +}
6181 +
6182 +static int langwell_otg_check_otgsc(void)
6183 +{
6184 +       struct langwell_otg     *langwell;
6185 +       u32                     val_otgsc, val_usbcfg;
6186 +
6187 +       langwell = the_transceiver;
6188 +
6189 +       val_otgsc = readl(langwell->regs + CI_OTGSC);
6190 +       val_usbcfg = readl(langwell->usbcfg);
6191 +
6192 +       otg_dbg("check sync OTGSC and USBCFG\n");
6193 +       otg_dbg("OTGSC = %08x, USBCFG = %08x\n", val_otgsc, val_usbcfg);
6194 +       otg_dbg("OTGSC_AVV = %d\n", !!(val_otgsc & OTGSC_AVV));
6195 +       otg_dbg("USBCFG.VBUSVAL = %d\n", !!(val_usbcfg & USBCFG_VBUSVAL));
6196 +       otg_dbg("OTGSC_ASV = %d\n", !!(val_otgsc & OTGSC_ASV));
6197 +       otg_dbg("USBCFG.AVALID = %d\n", !!(val_usbcfg & USBCFG_AVALID));
6198 +       otg_dbg("OTGSC_BSV = %d\n", !!(val_otgsc & OTGSC_BSV));
6199 +       otg_dbg("USBCFG.BVALID = %d\n", !!(val_usbcfg & USBCFG_BVALID));
6200 +       otg_dbg("OTGSC_BSE = %d\n", !!(val_otgsc & OTGSC_BSE));
6201 +       otg_dbg("USBCFG.SESEND = %d\n", !!(val_usbcfg & USBCFG_SESEND));
6202 +
6203 +       /* Check USBCFG VBusValid/AValid/BValid/SessEnd */
6204 +       if (!!(val_otgsc & OTGSC_AVV) ^ !!(val_usbcfg & USBCFG_VBUSVAL)) {
6205 +               otg_dbg("OTGSC AVV and USBCFG VBUSVAL are not sync.\n");
6206 +               return -1;
6207 +       } else if (!!(val_otgsc & OTGSC_ASV) ^ !!(val_usbcfg & USBCFG_AVALID)) {
6208 +               otg_dbg("OTGSC ASV and USBCFG AVALID are not sync.\n");
6209 +               return -1;
6210 +       } else if (!!(val_otgsc & OTGSC_BSV) ^ !!(val_usbcfg & USBCFG_BVALID)) {
6211 +               otg_dbg("OTGSC BSV and USBCFG BVALID are not sync.\n");
6212 +               return -1;
6213 +       } else if (!!(val_otgsc & OTGSC_BSE) ^ !!(val_usbcfg & USBCFG_SESEND)) {
6214 +               otg_dbg("OTGSC BSE and USBCFG SESSEN are not sync.\n");
6215 +               return -1;
6216 +       }
6217 +
6218 +       otg_dbg("OTGSC and USBCFG are synced\n");
6219 +
6220 +       return 0;
6221 +}
6222 +
6223 +static void langwell_otg_phy_low_power(int on)
6224 +{
6225 +       u8      val, phcd;
6226 +       int     retval;
6227 +
6228 +       otg_dbg("phy low power mode-> %d start\n", on);
6229 +
6230 +       phcd = 0x40;
6231 +
6232 +       val = readb(the_transceiver->regs + CI_HOSTPC1 + 2);
6233 +
6234 +       if (on) {
6235 +               /* Due to hardware issue, after set PHCD, sync will failed
6236 +                * between USBCFG and OTGSC, so before set PHCD, check if
6237 +                * sync is in process now. If the answer is "yes", then do
6238 +                * not touch PHCD bit */
6239 +               retval = langwell_otg_check_otgsc();
6240 +               if (retval) {
6241 +                       otg_dbg("Skip PHCD programming..\n");
6242 +                       return ;
6243 +               }
6244 +
6245 +               writeb(val | phcd, the_transceiver->regs + CI_HOSTPC1 + 2);
6246 +       } else
6247 +               writeb(val & ~phcd, the_transceiver->regs + CI_HOSTPC1 + 2);
6248 +
6249 +       otg_dbg("phy low power mode<- %d done\n", on);
6250 +}
6251 +
6252 +/* After drv vbus, add 2 ms delay to set PHCD */
6253 +static void langwell_otg_phy_low_power_wait(int on)
6254 +{
6255 +       otg_dbg("2 ms delay before set PHY low power mode\n");
6256 +
6257 +       mdelay(2);
6258 +       langwell_otg_phy_low_power(on);
6259 +}
6260 +
6261 +/* Enable/Disable OTG interrupts */
6262 +static void langwell_otg_intr(int on)
6263 +{
6264 +       u32 val;
6265 +
6266 +       otg_dbg("interrupt -> %d\n", on);
6267 +
6268 +       val = readl(the_transceiver->regs + CI_OTGSC);
6269 +
6270 +       /* OTGSC_INT_MASK doesn't contains 1msInt */
6271 +       if (on) {
6272 +               val = val | (OTGSC_INT_MASK);
6273 +               writel(val, the_transceiver->regs + CI_OTGSC);
6274 +       } else {
6275 +               val = val & ~(OTGSC_INT_MASK);
6276 +               writel(val, the_transceiver->regs + CI_OTGSC);
6277 +       }
6278 +}
6279 +
6280 +/* set HAAR: Hardware Assist Auto-Reset */
6281 +static void langwell_otg_HAAR(int on)
6282 +{
6283 +       u32     val;
6284 +
6285 +       otg_dbg("HAAR -> %d\n", on);
6286 +
6287 +       val = readl(the_transceiver->regs + CI_OTGSC);
6288 +       if (on)
6289 +               writel((val & ~OTGSC_INTSTS_MASK) | OTGSC_HAAR,
6290 +                               the_transceiver->regs + CI_OTGSC);
6291 +       else
6292 +               writel((val & ~OTGSC_INTSTS_MASK) & ~OTGSC_HAAR,
6293 +                               the_transceiver->regs + CI_OTGSC);
6294 +}
6295 +
6296 +/* set HABA: Hardware Assist B-Disconnect to A-Connect */
6297 +static void langwell_otg_HABA(int on)
6298 +{
6299 +       u32     val;
6300 +
6301 +       otg_dbg("HABA -> %d\n", on);
6302 +
6303 +       val = readl(the_transceiver->regs + CI_OTGSC);
6304 +       if (on)
6305 +               writel((val & ~OTGSC_INTSTS_MASK) | OTGSC_HABA,
6306 +                               the_transceiver->regs + CI_OTGSC);
6307 +       else
6308 +               writel((val & ~OTGSC_INTSTS_MASK) & ~OTGSC_HABA,
6309 +                               the_transceiver->regs + CI_OTGSC);
6310 +}
6311 +
6312 +static int langwell_otg_check_se0_srp(int on)
6313 +{
6314 +       u32 val;
6315 +
6316 +       int delay_time = TB_SE0_SRP * 10; /* step is 100us */
6317 +
6318 +       otg_dbg("check_se0_srp -> \n");
6319 +
6320 +       do {
6321 +               udelay(100);
6322 +               if (!delay_time--)
6323 +                       break;
6324 +               val = readl(the_transceiver->regs + CI_PORTSC1);
6325 +               val &= PORTSC_LS;
6326 +       } while (!val);
6327 +
6328 +       otg_dbg("check_se0_srp <- \n");
6329 +       return val;
6330 +}
6331 +
6332 +/* The timeout callback function to set time out bit */
6333 +static void set_tmout(unsigned long indicator)
6334 +{
6335 +       *(int *)indicator = 1;
6336 +}
6337 +
6338 +void langwell_otg_nsf_msg(unsigned long indicator)
6339 +{
6340 +       switch (indicator) {
6341 +       case 2:
6342 +       case 4:
6343 +       case 6:
6344 +       case 7:
6345 +               printk(KERN_ERR "OTG:NSF-%lu - deivce not responding\n",
6346 +                               indicator);
6347 +               break;
6348 +       case 3:
6349 +               printk(KERN_ERR "OTG:NSF-%lu - deivce not supported\n",
6350 +                               indicator);
6351 +               break;
6352 +       default:
6353 +               printk(KERN_ERR "Do not have this kind of NSF\n");
6354 +               break;
6355 +       }
6356 +}
6357 +
6358 +/* Initialize timers */
6359 +static void langwell_otg_init_timers(struct otg_hsm *hsm)
6360 +{
6361 +       /* HSM used timers */
6362 +       a_wait_vrise_tmr = otg_timer_initializer(&set_tmout, TA_WAIT_VRISE,
6363 +                               (unsigned long)&hsm->a_wait_vrise_tmout);
6364 +       a_aidl_bdis_tmr = otg_timer_initializer(&set_tmout, TA_AIDL_BDIS,
6365 +                               (unsigned long)&hsm->a_aidl_bdis_tmout);
6366 +       b_se0_srp_tmr = otg_timer_initializer(&set_tmout, TB_SE0_SRP,
6367 +                               (unsigned long)&hsm->b_se0_srp);
6368 +       b_srp_init_tmr = otg_timer_initializer(&set_tmout, TB_SRP_INIT,
6369 +                               (unsigned long)&hsm->b_srp_init_tmout);
6370 +}
6371 +
6372 +/* Free timers */
6373 +static void langwell_otg_free_timers(void)
6374 +{
6375 +       kfree(a_wait_vrise_tmr);
6376 +       kfree(a_aidl_bdis_tmr);
6377 +       kfree(b_se0_srp_tmr);
6378 +       kfree(b_srp_init_tmr);
6379 +}
6380 +
6381 +/* The timeout callback function to set time out bit */
6382 +static void langwell_otg_timer_fn(unsigned long indicator)
6383 +{
6384 +       struct langwell_otg *langwell;
6385 +
6386 +       langwell = the_transceiver;
6387 +
6388 +       *(int *)indicator = 1;
6389 +
6390 +       otg_dbg("kernel timer - timeout\n");
6391 +
6392 +       queue_work(langwell->qwork, &langwell->work);
6393 +}
6394 +
6395 +/* kernel timer used instead of HW based interrupt */
6396 +static void langwell_otg_add_ktimer(enum langwell_otg_timer_type timers)
6397 +{
6398 +       struct langwell_otg *langwell;
6399 +       unsigned long j = jiffies;
6400 +       unsigned long data, time;
6401 +
6402 +       langwell = the_transceiver;
6403 +
6404 +       switch (timers) {
6405 +       case TA_WAIT_VRISE_TMR:
6406 +               langwell->hsm.a_wait_vrise_tmout = 0;
6407 +               data = (unsigned long)&langwell->hsm.a_wait_vrise_tmout;
6408 +               time = TA_WAIT_VRISE;
6409 +               break;
6410 +       case TA_WAIT_BCON_TMR:
6411 +               langwell->hsm.a_wait_bcon_tmout = 0;
6412 +               data = (unsigned long)&langwell->hsm.a_wait_bcon_tmout;
6413 +               time = TA_WAIT_BCON;
6414 +               break;
6415 +       case TA_AIDL_BDIS_TMR:
6416 +               langwell->hsm.a_aidl_bdis_tmout = 0;
6417 +               data = (unsigned long)&langwell->hsm.a_aidl_bdis_tmout;
6418 +               time = TA_AIDL_BDIS;
6419 +               break;
6420 +       case TB_ASE0_BRST_TMR:
6421 +               langwell->hsm.b_ase0_brst_tmout = 0;
6422 +               data = (unsigned long)&langwell->hsm.b_ase0_brst_tmout;
6423 +               time = TB_ASE0_BRST;
6424 +               break;
6425 +       case TB_SRP_INIT_TMR:
6426 +               langwell->hsm.b_srp_init_tmout = 0;
6427 +               data = (unsigned long)&langwell->hsm.b_srp_init_tmout;
6428 +               time = TB_SRP_INIT;
6429 +               break;
6430 +       case TB_SRP_FAIL_TMR:
6431 +               langwell->hsm.b_srp_fail_tmout = 0;
6432 +               data = (unsigned long)&langwell->hsm.b_srp_fail_tmout;
6433 +               time = TB_SRP_FAIL;
6434 +               break;
6435 +       case TB_BUS_SUSPEND_TMR:
6436 +               langwell->hsm.b_bus_suspend_tmout = 0;
6437 +               data = (unsigned long)&langwell->hsm.b_bus_suspend_tmout;
6438 +               time = TB_BUS_SUSPEND;
6439 +               break;
6440 +       default:
6441 +               otg_dbg("OTG: unkown timer, can not enable such timer\n");
6442 +               return;
6443 +       }
6444 +
6445 +       langwell->hsm_timer.data = data;
6446 +       langwell->hsm_timer.function = langwell_otg_timer_fn;
6447 +       langwell->hsm_timer.expires = j + time * HZ / 1000; /* milliseconds */
6448 +
6449 +       add_timer(&langwell->hsm_timer);
6450 +
6451 +       otg_dbg("OTG: add timer successfully\n");
6452 +}
6453 +
6454 +/* Add timer to timer list */
6455 +static void langwell_otg_add_timer(void *gtimer)
6456 +{
6457 +       struct langwell_otg_timer *timer = (struct langwell_otg_timer *)gtimer;
6458 +       struct langwell_otg_timer *tmp_timer;
6459 +       u32     val32;
6460 +
6461 +       /* Check if the timer is already in the active list,
6462 +        * if so update timer count
6463 +        */
6464 +       list_for_each_entry(tmp_timer, &active_timers, list)
6465 +               if (tmp_timer == timer) {
6466 +                       timer->count = timer->expires;
6467 +                       return;
6468 +               }
6469 +       timer->count = timer->expires;
6470 +
6471 +       if (list_empty(&active_timers)) {
6472 +               val32 = readl(the_transceiver->regs + CI_OTGSC);
6473 +               writel(val32 | OTGSC_1MSE, the_transceiver->regs + CI_OTGSC);
6474 +       }
6475 +
6476 +       list_add_tail(&timer->list, &active_timers);
6477 +}
6478 +
6479 +/* Remove timer from the timer list; clear timeout status */
6480 +static void langwell_otg_del_timer(void *gtimer)
6481 +{
6482 +       struct langwell_otg_timer *timer = (struct langwell_otg_timer *)gtimer;
6483 +       struct langwell_otg_timer *tmp_timer, *del_tmp;
6484 +       u32 val32;
6485 +
6486 +       list_for_each_entry_safe(tmp_timer, del_tmp, &active_timers, list)
6487 +               if (tmp_timer == timer)
6488 +                       list_del(&timer->list);
6489 +
6490 +       if (list_empty(&active_timers)) {
6491 +               val32 = readl(the_transceiver->regs + CI_OTGSC);
6492 +               writel(val32 & ~OTGSC_1MSE, the_transceiver->regs + CI_OTGSC);
6493 +       }
6494 +}
6495 +
6496 +/* Reduce timer count by 1, and find timeout conditions.*/
6497 +static int langwell_otg_tick_timer(u32 *int_sts)
6498 +{
6499 +       struct langwell_otg_timer *tmp_timer, *del_tmp;
6500 +       int expired = 0;
6501 +
6502 +       list_for_each_entry_safe(tmp_timer, del_tmp, &active_timers, list) {
6503 +               tmp_timer->count--;
6504 +               /* check if timer expires */
6505 +               if (!tmp_timer->count) {
6506 +                       list_del(&tmp_timer->list);
6507 +                       tmp_timer->function(tmp_timer->data);
6508 +                       expired = 1;
6509 +               }
6510 +       }
6511 +
6512 +       if (list_empty(&active_timers)) {
6513 +               otg_dbg("tick timer: disable 1ms int\n");
6514 +               *int_sts = *int_sts & ~OTGSC_1MSE;
6515 +       }
6516 +       return expired;
6517 +}
6518 +
6519 +static void reset_otg(void)
6520 +{
6521 +       u32     val;
6522 +       int     delay_time = 1000;
6523 +
6524 +       otg_dbg("reseting OTG controller ...\n");
6525 +       val = readl(the_transceiver->regs + CI_USBCMD);
6526 +       writel(val | USBCMD_RST, the_transceiver->regs + CI_USBCMD);
6527 +       do {
6528 +               udelay(100);
6529 +               if (!delay_time--)
6530 +                       otg_dbg("reset timeout\n");
6531 +               val = readl(the_transceiver->regs + CI_USBCMD);
6532 +               val &= USBCMD_RST;
6533 +       } while (val != 0);
6534 +       otg_dbg("reset done.\n");
6535 +}
6536 +
6537 +static void set_host_mode(void)
6538 +{
6539 +       u32     val;
6540 +
6541 +       reset_otg();
6542 +       val = readl(the_transceiver->regs + CI_USBMODE);
6543 +       val = (val & (~USBMODE_CM)) | USBMODE_HOST;
6544 +       writel(val, the_transceiver->regs + CI_USBMODE);
6545 +}
6546 +
6547 +static void set_client_mode(void)
6548 +{
6549 +       u32     val;
6550 +
6551 +       reset_otg();
6552 +       val = readl(the_transceiver->regs + CI_USBMODE);
6553 +       val = (val & (~USBMODE_CM)) | USBMODE_DEVICE;
6554 +       writel(val, the_transceiver->regs + CI_USBMODE);
6555 +}
6556 +
6557 +static void init_hsm(void)
6558 +{
6559 +       struct langwell_otg     *langwell = the_transceiver;
6560 +       u32                     val32;
6561 +
6562 +       /* read OTGSC after reset */
6563 +       val32 = readl(langwell->regs + CI_OTGSC);
6564 +       otg_dbg("%s: OTGSC init value = 0x%x\n", __func__, val32);
6565 +
6566 +       /* set init state */
6567 +       if (val32 & OTGSC_ID) {
6568 +               langwell->hsm.id = 1;
6569 +               langwell->otg.default_a = 0;
6570 +               set_client_mode();
6571 +               langwell->otg.state = OTG_STATE_B_IDLE;
6572 +               langwell_otg_drv_vbus(0);
6573 +       } else {
6574 +               langwell->hsm.id = 0;
6575 +               langwell->otg.default_a = 1;
6576 +               set_host_mode();
6577 +               langwell->otg.state = OTG_STATE_A_IDLE;
6578 +       }
6579 +
6580 +       /* set session indicator */
6581 +       if (val32 & OTGSC_BSE)
6582 +               langwell->hsm.b_sess_end = 1;
6583 +       if (val32 & OTGSC_BSV)
6584 +               langwell->hsm.b_sess_vld = 1;
6585 +       if (val32 & OTGSC_ASV)
6586 +               langwell->hsm.a_sess_vld = 1;
6587 +       if (val32 & OTGSC_AVV)
6588 +               langwell->hsm.a_vbus_vld = 1;
6589 +
6590 +       /* defautly power the bus */
6591 +       langwell->hsm.a_bus_req = 1;
6592 +       langwell->hsm.a_bus_drop = 0;
6593 +       /* defautly don't request bus as B device */
6594 +       langwell->hsm.b_bus_req = 0;
6595 +       /* no system error */
6596 +       langwell->hsm.a_clr_err = 0;
6597 +
6598 +       langwell_otg_phy_low_power_wait(1);
6599 +}
6600 +
6601 +static void update_hsm(void)
6602 +{
6603 +       struct langwell_otg     *langwell = the_transceiver;
6604 +       u32                     val32;
6605 +
6606 +       /* read OTGSC */
6607 +       val32 = readl(langwell->regs + CI_OTGSC);
6608 +       otg_dbg("%s: OTGSC current value = 0x%x\n", __func__, val32);
6609 +
6610 +       langwell->hsm.id = !!(val32 & OTGSC_ID);
6611 +       langwell->hsm.b_sess_end = !!(val32 & OTGSC_BSE);
6612 +       langwell->hsm.b_sess_vld = !!(val32 & OTGSC_BSV);
6613 +       langwell->hsm.a_sess_vld = !!(val32 & OTGSC_ASV);
6614 +       langwell->hsm.a_vbus_vld = !!(val32 & OTGSC_AVV);
6615 +}
6616 +
6617 +static irqreturn_t otg_dummy_irq(int irq, void *_dev)
6618 +{
6619 +       void __iomem    *reg_base = _dev;
6620 +       u32     val;
6621 +       u32     int_mask = 0;
6622 +
6623 +       val = readl(reg_base + CI_USBMODE);
6624 +       if ((val & USBMODE_CM) != USBMODE_DEVICE)
6625 +               return IRQ_NONE;
6626 +
6627 +       val = readl(reg_base + CI_USBSTS);
6628 +       int_mask = val & INTR_DUMMY_MASK;
6629 +
6630 +       if (int_mask == 0)
6631 +               return IRQ_NONE;
6632 +
6633 +       /* clear hsm.b_conn here since host driver can't detect it
6634 +       *  otg_dummy_irq called means B-disconnect happened.
6635 +       */
6636 +       if (the_transceiver->hsm.b_conn) {
6637 +               the_transceiver->hsm.b_conn = 0;
6638 +               if (spin_trylock(&the_transceiver->wq_lock)) {
6639 +                       queue_work(the_transceiver->qwork,
6640 +                               &the_transceiver->work);
6641 +                       spin_unlock(&the_transceiver->wq_lock);
6642 +               }
6643 +       }
6644 +       /* Clear interrupts */
6645 +       writel(int_mask, reg_base + CI_USBSTS);
6646 +       return IRQ_HANDLED;
6647 +}
6648 +
6649 +static irqreturn_t otg_irq(int irq, void *_dev)
6650 +{
6651 +       struct  langwell_otg *langwell = _dev;
6652 +       u32     int_sts, int_en;
6653 +       u32     int_mask = 0;
6654 +       int     flag = 0;
6655 +
6656 +       int_sts = readl(langwell->regs + CI_OTGSC);
6657 +       int_en = (int_sts & OTGSC_INTEN_MASK) >> 8;
6658 +       int_mask = int_sts & int_en;
6659 +       if (int_mask == 0)
6660 +               return IRQ_NONE;
6661 +
6662 +       if (int_mask & OTGSC_IDIS) {
6663 +               otg_dbg("%s: id change int\n", __func__);
6664 +               langwell->hsm.id = (int_sts & OTGSC_ID) ? 1 : 0;
6665 +               flag = 1;
6666 +       }
6667 +       if (int_mask & OTGSC_DPIS) {
6668 +               otg_dbg("%s: data pulse int\n", __func__);
6669 +               langwell->hsm.a_srp_det = (int_sts & OTGSC_DPS) ? 1 : 0;
6670 +               flag = 1;
6671 +       }
6672 +       if (int_mask & OTGSC_BSEIS) {
6673 +               otg_dbg("%s: b session end int\n", __func__);
6674 +               langwell->hsm.b_sess_end = (int_sts & OTGSC_BSE) ? 1 : 0;
6675 +               flag = 1;
6676 +       }
6677 +       if (int_mask & OTGSC_BSVIS) {
6678 +               otg_dbg("%s: b session valid int\n", __func__);
6679 +               langwell->hsm.b_sess_vld = (int_sts & OTGSC_BSV) ? 1 : 0;
6680 +               flag = 1;
6681 +       }
6682 +       if (int_mask & OTGSC_ASVIS) {
6683 +               otg_dbg("%s: a session valid int\n", __func__);
6684 +               langwell->hsm.a_sess_vld = (int_sts & OTGSC_ASV) ? 1 : 0;
6685 +               flag = 1;
6686 +       }
6687 +       if (int_mask & OTGSC_AVVIS) {
6688 +               otg_dbg("%s: a vbus valid int\n", __func__);
6689 +               langwell->hsm.a_vbus_vld = (int_sts & OTGSC_AVV) ? 1 : 0;
6690 +               flag = 1;
6691 +       }
6692 +
6693 +       if (int_mask & OTGSC_1MSS) {
6694 +               /* need to schedule otg_work if any timer is expired */
6695 +               if (langwell_otg_tick_timer(&int_sts))
6696 +                       flag = 1;
6697 +       }
6698 +
6699 +       writel((int_sts & ~OTGSC_INTSTS_MASK) | int_mask,
6700 +                       langwell->regs + CI_OTGSC);
6701 +       if (flag)
6702 +               queue_work(langwell->qwork, &langwell->work);
6703 +
6704 +       return IRQ_HANDLED;
6705 +}
6706 +
6707 +static void langwell_otg_work(struct work_struct *work)
6708 +{
6709 +       struct langwell_otg *langwell = container_of(work,
6710 +                                       struct langwell_otg, work);
6711 +       int     retval;
6712 +
6713 +       otg_dbg("%s: old state = %s\n", __func__,
6714 +                       state_string(langwell->otg.state));
6715 +
6716 +       switch (langwell->otg.state) {
6717 +       case OTG_STATE_UNDEFINED:
6718 +       case OTG_STATE_B_IDLE:
6719 +               if (!langwell->hsm.id) {
6720 +                       langwell_otg_del_timer(b_srp_init_tmr);
6721 +                       del_timer_sync(&langwell->hsm_timer);
6722 +                       langwell->otg.default_a = 1;
6723 +                       langwell->hsm.a_srp_det = 0;
6724 +                       langwell_otg_chrg_vbus(0);
6725 +                       set_host_mode();
6726 +                       langwell_otg_phy_low_power(1);
6727 +                       langwell->otg.state = OTG_STATE_A_IDLE;
6728 +                       queue_work(langwell->qwork, &langwell->work);
6729 +               } else if (langwell->hsm.b_srp_init_tmout) {
6730 +                       langwell->hsm.b_srp_init_tmout = 0;
6731 +                       printk(KERN_WARNING "USB OTG: SRP init timeout\n");
6732 +               } else if (langwell->hsm.b_srp_fail_tmout) {
6733 +                       langwell->hsm.b_srp_fail_tmout = 0;
6734 +                       langwell->hsm.b_bus_req = 0;
6735 +                       langwell_otg_nsf_msg(6);
6736 +               } else if (langwell->hsm.b_sess_vld) {
6737 +                       langwell_otg_del_timer(b_srp_init_tmr);
6738 +                       del_timer_sync(&langwell->hsm_timer);
6739 +                       langwell->hsm.b_sess_end = 0;
6740 +                       langwell->hsm.a_bus_suspend = 0;
6741 +                       langwell_otg_chrg_vbus(0);
6742 +                       if (langwell->client_ops) {
6743 +                               langwell->client_ops->resume(langwell->pdev);
6744 +                               langwell->otg.state = OTG_STATE_B_PERIPHERAL;
6745 +                       } else
6746 +                               otg_dbg("client driver not loaded.\n");
6747 +
6748 +               } else if (langwell->hsm.b_bus_req &&
6749 +                               (langwell->hsm.b_sess_end)) {
6750 +                       del_timer_sync(&langwell->hsm_timer);
6751 +                       /* workaround for b_se0_srp detection */
6752 +                       retval = langwell_otg_check_se0_srp(0);
6753 +                       if (retval) {
6754 +                               langwell->hsm.b_bus_req = 0;
6755 +                               otg_dbg("LS is not SE0, try again later\n");
6756 +                       } else {
6757 +                               /* clear the PHCD before start srp */
6758 +                               langwell_otg_phy_low_power(0);
6759 +
6760 +                               /* Start SRP */
6761 +                               langwell_otg_add_timer(b_srp_init_tmr);
6762 +                               langwell_otg_start_srp(&langwell->otg);
6763 +                               langwell_otg_del_timer(b_srp_init_tmr);
6764 +                               langwell_otg_add_ktimer(TB_SRP_FAIL_TMR);
6765 +
6766 +                               /* reset PHY low power mode here */
6767 +                               langwell_otg_phy_low_power_wait(1);
6768 +                       }
6769 +               }
6770 +               break;
6771 +       case OTG_STATE_B_SRP_INIT:
6772 +               if (!langwell->hsm.id) {
6773 +                       langwell->otg.default_a = 1;
6774 +                       langwell->hsm.a_srp_det = 0;
6775 +                       langwell_otg_drv_vbus(0);
6776 +                       langwell_otg_chrg_vbus(0);
6777 +                       set_host_mode();
6778 +                       langwell_otg_phy_low_power(1);
6779 +                       langwell->otg.state = OTG_STATE_A_IDLE;
6780 +                       queue_work(langwell->qwork, &langwell->work);
6781 +               } else if (langwell->hsm.b_sess_vld) {
6782 +                       langwell_otg_chrg_vbus(0);
6783 +                       if (langwell->client_ops) {
6784 +                               langwell->client_ops->resume(langwell->pdev);
6785 +                               langwell->otg.state = OTG_STATE_B_PERIPHERAL;
6786 +                       } else
6787 +                               otg_dbg("client driver not loaded.\n");
6788 +               }
6789 +               break;
6790 +       case OTG_STATE_B_PERIPHERAL:
6791 +               if (!langwell->hsm.id) {
6792 +                       langwell->otg.default_a = 1;
6793 +                       langwell->hsm.a_srp_det = 0;
6794 +
6795 +                       langwell_otg_chrg_vbus(0);
6796 +
6797 +                       if (langwell->client_ops) {
6798 +                               langwell->client_ops->suspend(langwell->pdev,
6799 +                                       PMSG_FREEZE);
6800 +                       } else
6801 +                               otg_dbg("client driver has been removed.\n");
6802 +
6803 +                       set_host_mode();
6804 +                       langwell_otg_phy_low_power(1);
6805 +                       langwell->otg.state = OTG_STATE_A_IDLE;
6806 +                       queue_work(langwell->qwork, &langwell->work);
6807 +               } else if (!langwell->hsm.b_sess_vld) {
6808 +                       langwell->hsm.b_hnp_enable = 0;
6809 +
6810 +                       if (langwell->client_ops) {
6811 +                               langwell->client_ops->suspend(langwell->pdev,
6812 +                                       PMSG_FREEZE);
6813 +                       } else
6814 +                               otg_dbg("client driver has been removed.\n");
6815 +
6816 +                       langwell->otg.state = OTG_STATE_B_IDLE;
6817 +               } else if (langwell->hsm.b_bus_req && langwell->hsm.b_hnp_enable
6818 +                       && langwell->hsm.a_bus_suspend) {
6819 +
6820 +                       if (langwell->client_ops) {
6821 +                               langwell->client_ops->suspend(langwell->pdev,
6822 +                                       PMSG_FREEZE);
6823 +                       } else
6824 +                               otg_dbg("client driver has been removed.\n");
6825 +
6826 +                       langwell_otg_HAAR(1);
6827 +                       langwell->hsm.a_conn = 0;
6828 +
6829 +                       if (langwell->host_ops) {
6830 +                               langwell->host_ops->probe(langwell->pdev,
6831 +                                       langwell->host_ops->id_table);
6832 +                               langwell->otg.state = OTG_STATE_B_WAIT_ACON;
6833 +                       } else
6834 +                               otg_dbg("host driver not loaded.\n");
6835 +
6836 +                       langwell->hsm.a_bus_resume = 0;
6837 +                       langwell_otg_add_ktimer(TB_ASE0_BRST_TMR);
6838 +               }
6839 +               break;
6840 +
6841 +       case OTG_STATE_B_WAIT_ACON:
6842 +               if (!langwell->hsm.id) {
6843 +                       /* delete hsm timer for a_wait_bcon_tmr */
6844 +                       del_timer_sync(&langwell->hsm_timer);
6845 +
6846 +                       langwell->otg.default_a = 1;
6847 +                       langwell->hsm.a_srp_det = 0;
6848 +
6849 +                       langwell_otg_chrg_vbus(0);
6850 +
6851 +                       langwell_otg_HAAR(0);
6852 +                       if (langwell->host_ops)
6853 +                               langwell->host_ops->remove(langwell->pdev);
6854 +                       else
6855 +                               otg_dbg("host driver has been removed.\n");
6856 +
6857 +                       set_host_mode();
6858 +                       langwell_otg_phy_low_power(1);
6859 +                       langwell->otg.state = OTG_STATE_A_IDLE;
6860 +                       queue_work(langwell->qwork, &langwell->work);
6861 +               } else if (!langwell->hsm.b_sess_vld) {
6862 +                       /* delete hsm timer for a_wait_bcon_tmr */
6863 +                       del_timer_sync(&langwell->hsm_timer);
6864 +
6865 +                       langwell->hsm.b_hnp_enable = 0;
6866 +                       langwell->hsm.b_bus_req = 0;
6867 +                       langwell_otg_chrg_vbus(0);
6868 +                       langwell_otg_HAAR(0);
6869 +
6870 +                       if (langwell->host_ops)
6871 +                               langwell->host_ops->remove(langwell->pdev);
6872 +                       else
6873 +                               otg_dbg("host driver has been removed.\n");
6874 +
6875 +                       set_client_mode();
6876 +                       langwell_otg_phy_low_power(1);
6877 +                       langwell->otg.state = OTG_STATE_B_IDLE;
6878 +               } else if (langwell->hsm.a_conn) {
6879 +                       /* delete hsm timer for a_wait_bcon_tmr */
6880 +                       del_timer_sync(&langwell->hsm_timer);
6881 +
6882 +                       langwell_otg_HAAR(0);
6883 +                       langwell->otg.state = OTG_STATE_B_HOST;
6884 +                       queue_work(langwell->qwork, &langwell->work);
6885 +               } else if (langwell->hsm.a_bus_resume ||
6886 +                               langwell->hsm.b_ase0_brst_tmout) {
6887 +                       /* delete hsm timer for a_wait_bcon_tmr */
6888 +                       del_timer_sync(&langwell->hsm_timer);
6889 +
6890 +                       langwell_otg_HAAR(0);
6891 +                       langwell_otg_nsf_msg(7);
6892 +
6893 +                       if (langwell->host_ops)
6894 +                               langwell->host_ops->remove(langwell->pdev);
6895 +                       else
6896 +                               otg_dbg("host driver has been removed.\n");
6897 +
6898 +                       langwell->hsm.a_bus_suspend = 0;
6899 +                       langwell->hsm.b_bus_req = 0;
6900 +
6901 +                       if (langwell->client_ops)
6902 +                               langwell->client_ops->resume(langwell->pdev);
6903 +                       else
6904 +                               otg_dbg("client driver not loaded.\n");
6905 +
6906 +                       langwell->otg.state = OTG_STATE_B_PERIPHERAL;
6907 +               }
6908 +               break;
6909 +
6910 +       case OTG_STATE_B_HOST:
6911 +               if (!langwell->hsm.id) {
6912 +                       langwell->otg.default_a = 1;
6913 +                       langwell->hsm.a_srp_det = 0;
6914 +
6915 +                       langwell_otg_chrg_vbus(0);
6916 +                       if (langwell->host_ops)
6917 +                               langwell->host_ops->remove(langwell->pdev);
6918 +                       else
6919 +                               otg_dbg("host driver has been removed.\n");
6920 +
6921 +                       set_host_mode();
6922 +                       langwell_otg_phy_low_power(1);
6923 +                       langwell->otg.state = OTG_STATE_A_IDLE;
6924 +                       queue_work(langwell->qwork, &langwell->work);
6925 +               } else if (!langwell->hsm.b_sess_vld) {
6926 +                       langwell->hsm.b_hnp_enable = 0;
6927 +                       langwell->hsm.b_bus_req = 0;
6928 +                       langwell_otg_chrg_vbus(0);
6929 +                       if (langwell->host_ops)
6930 +                               langwell->host_ops->remove(langwell->pdev);
6931 +                       else
6932 +                               otg_dbg("host driver has been removed.\n");
6933 +
6934 +                       set_client_mode();
6935 +                       langwell_otg_phy_low_power(1);
6936 +                       langwell->otg.state = OTG_STATE_B_IDLE;
6937 +               } else if ((!langwell->hsm.b_bus_req) ||
6938 +                               (!langwell->hsm.a_conn)) {
6939 +                       langwell->hsm.b_bus_req = 0;
6940 +                       langwell_otg_loc_sof(0);
6941 +                       if (langwell->host_ops)
6942 +                               langwell->host_ops->remove(langwell->pdev);
6943 +                       else
6944 +                               otg_dbg("host driver has been removed.\n");
6945 +
6946 +                       langwell->hsm.a_bus_suspend = 0;
6947 +
6948 +                       if (langwell->client_ops)
6949 +                               langwell->client_ops->resume(langwell->pdev);
6950 +                       else
6951 +                               otg_dbg("client driver not loaded.\n");
6952 +
6953 +                       langwell->otg.state = OTG_STATE_B_PERIPHERAL;
6954 +               }
6955 +               break;
6956 +
6957 +       case OTG_STATE_A_IDLE:
6958 +               langwell->otg.default_a = 1;
6959 +               if (langwell->hsm.id) {
6960 +                       langwell->otg.default_a = 0;
6961 +                       langwell->hsm.b_bus_req = 0;
6962 +                       langwell->hsm.vbus_srp_up = 0;
6963 +                       langwell_otg_chrg_vbus(0);
6964 +                       set_client_mode();
6965 +                       langwell_otg_phy_low_power(1);
6966 +                       langwell->otg.state = OTG_STATE_B_IDLE;
6967 +                       queue_work(langwell->qwork, &langwell->work);
6968 +               } else if (!langwell->hsm.a_bus_drop &&
6969 +                       (langwell->hsm.a_srp_det || langwell->hsm.a_bus_req)) {
6970 +                       langwell_otg_phy_low_power(0);
6971 +                       langwell_otg_drv_vbus(1);
6972 +                       langwell->hsm.a_srp_det = 1;
6973 +                       langwell->hsm.vbus_srp_up = 0;
6974 +                       langwell->hsm.a_wait_vrise_tmout = 0;
6975 +                       langwell_otg_add_timer(a_wait_vrise_tmr);
6976 +                       langwell->otg.state = OTG_STATE_A_WAIT_VRISE;
6977 +                       queue_work(langwell->qwork, &langwell->work);
6978 +               } else if (!langwell->hsm.a_bus_drop &&
6979 +                               langwell->hsm.a_sess_vld) {
6980 +                       langwell->hsm.vbus_srp_up = 1;
6981 +               } else if (!langwell->hsm.a_sess_vld &&
6982 +                               langwell->hsm.vbus_srp_up) {
6983 +                       msleep(10);
6984 +                       langwell_otg_phy_low_power(0);
6985 +                       langwell_otg_drv_vbus(1);
6986 +                       langwell->hsm.a_srp_det = 1;
6987 +                       langwell->hsm.vbus_srp_up = 0;
6988 +                       langwell->hsm.a_wait_vrise_tmout = 0;
6989 +                       langwell_otg_add_timer(a_wait_vrise_tmr);
6990 +                       langwell->otg.state = OTG_STATE_A_WAIT_VRISE;
6991 +                       queue_work(langwell->qwork, &langwell->work);
6992 +               } else if (!langwell->hsm.a_sess_vld &&
6993 +                               !langwell->hsm.vbus_srp_up) {
6994 +                       langwell_otg_phy_low_power(1);
6995 +               }
6996 +               break;
6997 +       case OTG_STATE_A_WAIT_VRISE:
6998 +               if (langwell->hsm.id) {
6999 +                       langwell_otg_del_timer(a_wait_vrise_tmr);
7000 +                       langwell->hsm.b_bus_req = 0;
7001 +                       langwell->otg.default_a = 0;
7002 +                       langwell_otg_drv_vbus(0);
7003 +                       set_client_mode();
7004 +                       langwell_otg_phy_low_power_wait(1);
7005 +                       langwell->otg.state = OTG_STATE_B_IDLE;
7006 +               } else if (langwell->hsm.a_vbus_vld) {
7007 +                       langwell_otg_del_timer(a_wait_vrise_tmr);
7008 +                       if (langwell->host_ops)
7009 +                               langwell->host_ops->probe(langwell->pdev,
7010 +                                               langwell->host_ops->id_table);
7011 +                       else {
7012 +                               otg_dbg("host driver not loaded.\n");
7013 +                               break;
7014 +                       }
7015 +                       langwell->hsm.b_conn = 0;
7016 +                       /* Replace HW timer with kernel timer */
7017 +                       langwell_otg_add_ktimer(TA_WAIT_BCON_TMR);
7018 +                       langwell->otg.state = OTG_STATE_A_WAIT_BCON;
7019 +               } else if (langwell->hsm.a_wait_vrise_tmout) {
7020 +                       if (langwell->hsm.a_vbus_vld) {
7021 +                               if (langwell->host_ops)
7022 +                                       langwell->host_ops->probe(
7023 +                                               langwell->pdev,
7024 +                                               langwell->host_ops->id_table);
7025 +                               else {
7026 +                                       otg_dbg("host driver not loaded.\n");
7027 +                                       break;
7028 +                               }
7029 +                               langwell->hsm.b_conn = 0;
7030 +                               /* change to kernel timer */
7031 +                               langwell_otg_add_ktimer(TA_WAIT_BCON_TMR);
7032 +                               langwell->otg.state = OTG_STATE_A_WAIT_BCON;
7033 +                       } else {
7034 +                               langwell_otg_drv_vbus(0);
7035 +                               langwell_otg_phy_low_power_wait(1);
7036 +                               langwell->otg.state = OTG_STATE_A_VBUS_ERR;
7037 +                       }
7038 +               }
7039 +               break;
7040 +       case OTG_STATE_A_WAIT_BCON:
7041 +               if (langwell->hsm.id) {
7042 +                       /* delete hsm timer for a_wait_bcon_tmr */
7043 +                       del_timer_sync(&langwell->hsm_timer);
7044 +
7045 +                       langwell->otg.default_a = 0;
7046 +                       langwell->hsm.b_bus_req = 0;
7047 +                       if (langwell->host_ops)
7048 +                               langwell->host_ops->remove(langwell->pdev);
7049 +                       else
7050 +                               otg_dbg("host driver has been removed.\n");
7051 +                       langwell_otg_drv_vbus(0);
7052 +                       set_client_mode();
7053 +                       langwell_otg_phy_low_power_wait(1);
7054 +                       langwell->otg.state = OTG_STATE_B_IDLE;
7055 +                       queue_work(langwell->qwork, &langwell->work);
7056 +               } else if (!langwell->hsm.a_vbus_vld) {
7057 +                       /* delete hsm timer for a_wait_bcon_tmr */
7058 +                       del_timer_sync(&langwell->hsm_timer);
7059 +
7060 +                       if (langwell->host_ops)
7061 +                               langwell->host_ops->remove(langwell->pdev);
7062 +                       else
7063 +                               otg_dbg("host driver has been removed.\n");
7064 +                       langwell_otg_drv_vbus(0);
7065 +                       langwell_otg_phy_low_power_wait(1);
7066 +                       langwell->otg.state = OTG_STATE_A_VBUS_ERR;
7067 +               } else if (langwell->hsm.a_bus_drop ||
7068 +                               (langwell->hsm.a_wait_bcon_tmout &&
7069 +                               !langwell->hsm.a_bus_req)) {
7070 +                       /* delete hsm timer for a_wait_bcon_tmr */
7071 +                       del_timer_sync(&langwell->hsm_timer);
7072 +
7073 +                       if (langwell->host_ops)
7074 +                               langwell->host_ops->remove(langwell->pdev);
7075 +                       else
7076 +                               otg_dbg("host driver has been removed.\n");
7077 +                       langwell_otg_drv_vbus(0);
7078 +                       langwell->otg.state = OTG_STATE_A_WAIT_VFALL;
7079 +               } else if (langwell->hsm.b_conn) {
7080 +                       /* delete hsm timer for a_wait_bcon_tmr */
7081 +                       del_timer_sync(&langwell->hsm_timer);
7082 +
7083 +                       langwell->hsm.a_suspend_req = 0;
7084 +                       langwell->otg.state = OTG_STATE_A_HOST;
7085 +                       if (langwell->hsm.a_srp_det &&
7086 +                                       !langwell->otg.host->b_hnp_enable) {
7087 +                               /* SRP capable peripheral-only device */
7088 +                               langwell->hsm.a_bus_req = 1;
7089 +                               langwell->hsm.a_srp_det = 0;
7090 +                       } else if (!langwell->hsm.a_bus_req &&
7091 +                                       langwell->otg.host->b_hnp_enable) {
7092 +                               /* It is not safe enough to do a fast
7093 +                                * transistion from A_WAIT_BCON to
7094 +                                * A_SUSPEND */
7095 +                               msleep(10000);
7096 +                               if (langwell->hsm.a_bus_req)
7097 +                                       break;
7098 +
7099 +                               if (request_irq(langwell->pdev->irq,
7100 +                                       otg_dummy_irq, IRQF_SHARED,
7101 +                                       driver_name, langwell->regs) != 0) {
7102 +                                       otg_dbg("request interrupt %d fail\n",
7103 +                                       langwell->pdev->irq);
7104 +                               }
7105 +
7106 +                               langwell_otg_HABA(1);
7107 +                               langwell->hsm.b_bus_resume = 0;
7108 +                               langwell->hsm.a_aidl_bdis_tmout = 0;
7109 +                               langwell_otg_add_timer(a_aidl_bdis_tmr);
7110 +
7111 +                               langwell_otg_loc_sof(0);
7112 +                               /* clear PHCD to enable HW timer */
7113 +                               langwell_otg_phy_low_power(0);
7114 +                               langwell->otg.state = OTG_STATE_A_SUSPEND;
7115 +                       } else if (!langwell->hsm.a_bus_req &&
7116 +                               !langwell->otg.host->b_hnp_enable) {
7117 +                               struct pci_dev *pdev = langwell->pdev;
7118 +                               if (langwell->host_ops)
7119 +                                       langwell->host_ops->remove(pdev);
7120 +                               else
7121 +                                       otg_dbg("host driver removed.\n");
7122 +                               langwell_otg_drv_vbus(0);
7123 +                               langwell->otg.state = OTG_STATE_A_WAIT_VFALL;
7124 +                       }
7125 +               }
7126 +               break;
7127 +       case OTG_STATE_A_HOST:
7128 +               if (langwell->hsm.id) {
7129 +                       langwell->otg.default_a = 0;
7130 +                       langwell->hsm.b_bus_req = 0;
7131 +                       if (langwell->host_ops)
7132 +                               langwell->host_ops->remove(langwell->pdev);
7133 +                       else
7134 +                               otg_dbg("host driver has been removed.\n");
7135 +                       langwell_otg_drv_vbus(0);
7136 +                       set_client_mode();
7137 +                       langwell_otg_phy_low_power_wait(1);
7138 +                       langwell->otg.state = OTG_STATE_B_IDLE;
7139 +                       queue_work(langwell->qwork, &langwell->work);
7140 +               } else if (langwell->hsm.a_bus_drop ||
7141 +                               (!langwell->otg.host->b_hnp_enable &&
7142 +                                       !langwell->hsm.a_bus_req)) {
7143 +                       if (langwell->host_ops)
7144 +                               langwell->host_ops->remove(langwell->pdev);
7145 +                       else
7146 +                               otg_dbg("host driver has been removed.\n");
7147 +                       langwell_otg_drv_vbus(0);
7148 +                       langwell->otg.state = OTG_STATE_A_WAIT_VFALL;
7149 +               } else if (!langwell->hsm.a_vbus_vld) {
7150 +                       if (langwell->host_ops)
7151 +                               langwell->host_ops->remove(langwell->pdev);
7152 +                       else
7153 +                               otg_dbg("host driver has been removed.\n");
7154 +                       langwell_otg_drv_vbus(0);
7155 +                       langwell_otg_phy_low_power_wait(1);
7156 +                       langwell->otg.state = OTG_STATE_A_VBUS_ERR;
7157 +               } else if (langwell->otg.host->b_hnp_enable
7158 +                               && !langwell->hsm.a_bus_req) {
7159 +                       /* Set HABA to enable hardware assistance to signal
7160 +                        *  A-connect after receiver B-disconnect. Hardware
7161 +                        *  will then set client mode and enable URE, SLE and
7162 +                        *  PCE after the assistance. otg_dummy_irq is used to
7163 +                        *  clean these ints when client driver is not resumed.
7164 +                        */
7165 +                       if (request_irq(langwell->pdev->irq,
7166 +                               otg_dummy_irq, IRQF_SHARED, driver_name,
7167 +                               langwell->regs) != 0) {
7168 +                               otg_dbg("request interrupt %d failed\n",
7169 +                                               langwell->pdev->irq);
7170 +                       }
7171 +
7172 +                       /* set HABA */
7173 +                       langwell_otg_HABA(1);
7174 +                       langwell->hsm.b_bus_resume = 0;
7175 +                       langwell->hsm.a_aidl_bdis_tmout = 0;
7176 +                       langwell_otg_add_timer(a_aidl_bdis_tmr);
7177 +                       langwell_otg_loc_sof(0);
7178 +                       /* clear PHCD to enable HW timer */
7179 +                       langwell_otg_phy_low_power(0);
7180 +                       langwell->otg.state = OTG_STATE_A_SUSPEND;
7181 +               } else if (!langwell->hsm.b_conn || !langwell->hsm.a_bus_req) {
7182 +                       langwell->hsm.a_wait_bcon_tmout = 0;
7183 +                       /* add kernel timer */
7184 +                       langwell_otg_add_ktimer(TA_WAIT_BCON_TMR);
7185 +                       langwell->otg.state = OTG_STATE_A_WAIT_BCON;
7186 +               }
7187 +               break;
7188 +       case OTG_STATE_A_SUSPEND:
7189 +               if (langwell->hsm.id) {
7190 +                       langwell_otg_del_timer(a_aidl_bdis_tmr);
7191 +                       langwell_otg_HABA(0);
7192 +                       free_irq(langwell->pdev->irq, langwell->regs);
7193 +                       langwell->otg.default_a = 0;
7194 +                       langwell->hsm.b_bus_req = 0;
7195 +                       if (langwell->host_ops)
7196 +                               langwell->host_ops->remove(langwell->pdev);
7197 +                       else
7198 +                               otg_dbg("host driver has been removed.\n");
7199 +                       langwell_otg_drv_vbus(0);
7200 +                       set_client_mode();
7201 +                       langwell_otg_phy_low_power(1);
7202 +                       langwell->otg.state = OTG_STATE_B_IDLE;
7203 +                       queue_work(langwell->qwork, &langwell->work);
7204 +               } else if (langwell->hsm.a_bus_req ||
7205 +                               langwell->hsm.b_bus_resume) {
7206 +                       langwell_otg_del_timer(a_aidl_bdis_tmr);
7207 +                       langwell_otg_HABA(0);
7208 +                       free_irq(langwell->pdev->irq, langwell->regs);
7209 +                       langwell->hsm.a_suspend_req = 0;
7210 +                       langwell_otg_loc_sof(1);
7211 +                       langwell->otg.state = OTG_STATE_A_HOST;
7212 +               } else if (langwell->hsm.a_aidl_bdis_tmout ||
7213 +                               langwell->hsm.a_bus_drop) {
7214 +                       langwell_otg_del_timer(a_aidl_bdis_tmr);
7215 +                       langwell_otg_HABA(0);
7216 +                       free_irq(langwell->pdev->irq, langwell->regs);
7217 +                       if (langwell->host_ops)
7218 +                               langwell->host_ops->remove(langwell->pdev);
7219 +                       else
7220 +                               otg_dbg("host driver has been removed.\n");
7221 +                       langwell_otg_drv_vbus(0);
7222 +                       langwell->otg.state = OTG_STATE_A_WAIT_VFALL;
7223 +               } else if (!langwell->hsm.b_conn &&
7224 +                               langwell->otg.host->b_hnp_enable) {
7225 +                       langwell_otg_del_timer(a_aidl_bdis_tmr);
7226 +                       langwell_otg_HABA(0);
7227 +                       free_irq(langwell->pdev->irq, langwell->regs);
7228 +
7229 +                       if (langwell->host_ops)
7230 +                               langwell->host_ops->remove(langwell->pdev);
7231 +                       else
7232 +                               otg_dbg("host driver has been removed.\n");
7233 +
7234 +                       langwell->hsm.b_bus_suspend = 0;
7235 +                       langwell->hsm.b_bus_suspend_vld = 0;
7236 +
7237 +                       /* msleep(200); */
7238 +                       if (langwell->client_ops)
7239 +                               langwell->client_ops->resume(langwell->pdev);
7240 +                       else
7241 +                               otg_dbg("client driver not loaded.\n");
7242 +
7243 +                       langwell_otg_add_ktimer(TB_BUS_SUSPEND_TMR);
7244 +                       langwell->otg.state = OTG_STATE_A_PERIPHERAL;
7245 +                       break;
7246 +               } else if (!langwell->hsm.a_vbus_vld) {
7247 +                       langwell_otg_del_timer(a_aidl_bdis_tmr);
7248 +                       langwell_otg_HABA(0);
7249 +                       free_irq(langwell->pdev->irq, langwell->regs);
7250 +                       if (langwell->host_ops)
7251 +                               langwell->host_ops->remove(langwell->pdev);
7252 +                       else
7253 +                               otg_dbg("host driver has been removed.\n");
7254 +                       langwell_otg_drv_vbus(0);
7255 +                       langwell_otg_phy_low_power_wait(1);
7256 +                       langwell->otg.state = OTG_STATE_A_VBUS_ERR;
7257 +               }
7258 +               break;
7259 +       case OTG_STATE_A_PERIPHERAL:
7260 +               if (langwell->hsm.id) {
7261 +                       /* delete hsm timer for b_bus_suspend_tmr */
7262 +                       del_timer_sync(&langwell->hsm_timer);
7263 +                       langwell->otg.default_a = 0;
7264 +                       langwell->hsm.b_bus_req = 0;
7265 +                       if (langwell->client_ops)
7266 +                               langwell->client_ops->suspend(langwell->pdev,
7267 +                                       PMSG_FREEZE);
7268 +                       else
7269 +                               otg_dbg("client driver has been removed.\n");
7270 +                       langwell_otg_drv_vbus(0);
7271 +                       set_client_mode();
7272 +                       langwell_otg_phy_low_power_wait(1);
7273 +                       langwell->otg.state = OTG_STATE_B_IDLE;
7274 +                       queue_work(langwell->qwork, &langwell->work);
7275 +               } else if (!langwell->hsm.a_vbus_vld) {
7276 +                       /* delete hsm timer for b_bus_suspend_tmr */
7277 +                       del_timer_sync(&langwell->hsm_timer);
7278 +                       if (langwell->client_ops)
7279 +                               langwell->client_ops->suspend(langwell->pdev,
7280 +                                       PMSG_FREEZE);
7281 +                       else
7282 +                               otg_dbg("client driver has been removed.\n");
7283 +                       langwell_otg_drv_vbus(0);
7284 +                       langwell_otg_phy_low_power_wait(1);
7285 +                       langwell->otg.state = OTG_STATE_A_VBUS_ERR;
7286 +               } else if (langwell->hsm.a_bus_drop) {
7287 +                       /* delete hsm timer for b_bus_suspend_tmr */
7288 +                       del_timer_sync(&langwell->hsm_timer);
7289 +                       if (langwell->client_ops)
7290 +                               langwell->client_ops->suspend(langwell->pdev,
7291 +                                       PMSG_FREEZE);
7292 +                       else
7293 +                               otg_dbg("client driver has been removed.\n");
7294 +                       langwell_otg_drv_vbus(0);
7295 +                       langwell->otg.state = OTG_STATE_A_WAIT_VFALL;
7296 +               } else if (langwell->hsm.b_bus_suspend) {
7297 +                       /* delete hsm timer for b_bus_suspend_tmr */
7298 +                       del_timer_sync(&langwell->hsm_timer);
7299 +                       if (langwell->client_ops)
7300 +                               langwell->client_ops->suspend(langwell->pdev,
7301 +                                       PMSG_FREEZE);
7302 +                       else
7303 +                               otg_dbg("client driver has been removed.\n");
7304 +                       if (langwell->host_ops)
7305 +                               langwell->host_ops->probe(langwell->pdev,
7306 +                                               langwell->host_ops->id_table);
7307 +                       else
7308 +                               otg_dbg("host driver not loaded.\n");
7309 +                       langwell_otg_add_ktimer(TA_WAIT_BCON_TMR);
7310 +                       langwell->otg.state = OTG_STATE_A_WAIT_BCON;
7311 +               } else if (langwell->hsm.b_bus_suspend_tmout) {
7312 +                       u32     val;
7313 +                       val = readl(langwell->regs + CI_PORTSC1);
7314 +                       if (!(val & PORTSC_SUSP))
7315 +                               break;
7316 +                       if (langwell->client_ops)
7317 +                               langwell->client_ops->suspend(langwell->pdev,
7318 +                                               PMSG_FREEZE);
7319 +                       else
7320 +                               otg_dbg("client driver has been removed.\n");
7321 +                       if (langwell->host_ops)
7322 +                               langwell->host_ops->probe(langwell->pdev,
7323 +                                               langwell->host_ops->id_table);
7324 +                       else
7325 +                               otg_dbg("host driver not loaded.\n");
7326 +                       /* replaced with kernel timer */
7327 +                       langwell_otg_add_ktimer(TA_WAIT_BCON_TMR);
7328 +                       langwell->otg.state = OTG_STATE_A_WAIT_BCON;
7329 +               }
7330 +               break;
7331 +       case OTG_STATE_A_VBUS_ERR:
7332 +               if (langwell->hsm.id) {
7333 +                       langwell->otg.default_a = 0;
7334 +                       langwell->hsm.a_clr_err = 0;
7335 +                       langwell->hsm.a_srp_det = 0;
7336 +                       set_client_mode();
7337 +                       langwell_otg_phy_low_power(1);
7338 +                       langwell->otg.state = OTG_STATE_B_IDLE;
7339 +                       queue_work(langwell->qwork, &langwell->work);
7340 +               } else if (langwell->hsm.a_clr_err) {
7341 +                       langwell->hsm.a_clr_err = 0;
7342 +                       langwell->hsm.a_srp_det = 0;
7343 +                       reset_otg();
7344 +                       init_hsm();
7345 +                       if (langwell->otg.state == OTG_STATE_A_IDLE)
7346 +                               queue_work(langwell->qwork, &langwell->work);
7347 +               } else {
7348 +                       /* FIXME: Because FW will clear PHCD bit when any VBus
7349 +                        *  event detected. Reset PHCD to 1 again */
7350 +                       langwell_otg_phy_low_power(1);
7351 +               }
7352 +               break;
7353 +       case OTG_STATE_A_WAIT_VFALL:
7354 +               if (langwell->hsm.id) {
7355 +                       langwell->otg.default_a = 0;
7356 +                       set_client_mode();
7357 +                       langwell_otg_phy_low_power(1);
7358 +                       langwell->otg.state = OTG_STATE_B_IDLE;
7359 +                       queue_work(langwell->qwork, &langwell->work);
7360 +               } else if (langwell->hsm.a_bus_req) {
7361 +                       langwell_otg_drv_vbus(1);
7362 +                       langwell->hsm.a_wait_vrise_tmout = 0;
7363 +                       langwell_otg_add_timer(a_wait_vrise_tmr);
7364 +                       langwell->otg.state = OTG_STATE_A_WAIT_VRISE;
7365 +               } else if (!langwell->hsm.a_sess_vld) {
7366 +                       langwell->hsm.a_srp_det = 0;
7367 +                       set_host_mode();
7368 +                       langwell_otg_phy_low_power(1);
7369 +                       langwell->otg.state = OTG_STATE_A_IDLE;
7370 +               }
7371 +               break;
7372 +       default:
7373 +               ;
7374 +       }
7375 +
7376 +       otg_dbg("%s: new state = %s\n", __func__,
7377 +                       state_string(langwell->otg.state));
7378 +}
7379 +
7380 +       static ssize_t
7381 +show_registers(struct device *_dev, struct device_attribute *attr, char *buf)
7382 +{
7383 +       struct langwell_otg *langwell;
7384 +       char *next;
7385 +       unsigned size;
7386 +       unsigned t;
7387 +
7388 +       langwell = the_transceiver;
7389 +       next = buf;
7390 +       size = PAGE_SIZE;
7391 +
7392 +       t = scnprintf(next, size,
7393 +               "\n"
7394 +               "USBCMD = 0x%08x \n"
7395 +               "USBSTS = 0x%08x \n"
7396 +               "USBINTR = 0x%08x \n"
7397 +               "ASYNCLISTADDR = 0x%08x \n"
7398 +               "PORTSC1 = 0x%08x \n"
7399 +               "HOSTPC1 = 0x%08x \n"
7400 +               "OTGSC = 0x%08x \n"
7401 +               "USBMODE = 0x%08x \n",
7402 +               readl(langwell->regs + 0x30),
7403 +               readl(langwell->regs + 0x34),
7404 +               readl(langwell->regs + 0x38),
7405 +               readl(langwell->regs + 0x48),
7406 +               readl(langwell->regs + 0x74),
7407 +               readl(langwell->regs + 0xb4),
7408 +               readl(langwell->regs + 0xf4),
7409 +               readl(langwell->regs + 0xf8)
7410 +               );
7411 +       size -= t;
7412 +       next += t;
7413 +
7414 +       return PAGE_SIZE - size;
7415 +}
7416 +static DEVICE_ATTR(registers, S_IRUGO, show_registers, NULL);
7417 +
7418 +static ssize_t
7419 +show_hsm(struct device *_dev, struct device_attribute *attr, char *buf)
7420 +{
7421 +       struct langwell_otg *langwell;
7422 +       char *next;
7423 +       unsigned size;
7424 +       unsigned t;
7425 +       enum usb_otg_state state;
7426 +
7427 +       langwell = the_transceiver;
7428 +       next = buf;
7429 +       size = PAGE_SIZE;
7430 +       state = langwell->otg.state;
7431 +
7432 +       /* Add a_set_b_hnp_en */
7433 +       if (state == OTG_STATE_A_HOST || state == OTG_STATE_A_SUSPEND)
7434 +               langwell->hsm.a_set_b_hnp_en = langwell->otg.host->b_hnp_enable;
7435 +       else
7436 +               langwell->hsm.a_set_b_hnp_en = 0;
7437 +
7438 +       t = scnprintf(next, size,
7439 +               "\n"
7440 +               "current state = %s\n"
7441 +               "a_bus_resume = \t%d\n"
7442 +               "a_bus_suspend = \t%d\n"
7443 +               "a_conn = \t%d\n"
7444 +               "a_sess_vld = \t%d\n"
7445 +               "a_srp_det = \t%d\n"
7446 +               "a_vbus_vld = \t%d\n"
7447 +               "b_bus_resume = \t%d\n"
7448 +               "b_bus_suspend = \t%d\n"
7449 +               "b_conn = \t%d\n"
7450 +               "b_se0_srp = \t%d\n"
7451 +               "b_sess_end = \t%d\n"
7452 +               "b_sess_vld = \t%d\n"
7453 +               "id = \t%d\n"
7454 +               "a_set_b_hnp_en = \t%d\n"
7455 +               "b_srp_done = \t%d\n"
7456 +               "b_hnp_enable = \t%d\n"
7457 +               "a_wait_vrise_tmout = \t%d\n"
7458 +               "a_wait_bcon_tmout = \t%d\n"
7459 +               "a_aidl_bdis_tmout = \t%d\n"
7460 +               "b_ase0_brst_tmout = \t%d\n"
7461 +               "a_bus_drop = \t%d\n"
7462 +               "a_bus_req = \t%d\n"
7463 +               "a_clr_err = \t%d\n"
7464 +               "a_suspend_req = \t%d\n"
7465 +               "b_bus_req = \t%d\n"
7466 +               "b_bus_suspend_tmout = \t%d\n"
7467 +               "b_bus_suspend_vld = \t%d\n",
7468 +               state_string(langwell->otg.state),
7469 +               langwell->hsm.a_bus_resume,
7470 +               langwell->hsm.a_bus_suspend,
7471 +               langwell->hsm.a_conn,
7472 +               langwell->hsm.a_sess_vld,
7473 +               langwell->hsm.a_srp_det,
7474 +               langwell->hsm.a_vbus_vld,
7475 +               langwell->hsm.b_bus_resume,
7476 +               langwell->hsm.b_bus_suspend,
7477 +               langwell->hsm.b_conn,
7478 +               langwell->hsm.b_se0_srp,
7479 +               langwell->hsm.b_sess_end,
7480 +               langwell->hsm.b_sess_vld,
7481 +               langwell->hsm.id,
7482 +               langwell->hsm.a_set_b_hnp_en,
7483 +               langwell->hsm.b_srp_done,
7484 +               langwell->hsm.b_hnp_enable,
7485 +               langwell->hsm.a_wait_vrise_tmout,
7486 +               langwell->hsm.a_wait_bcon_tmout,
7487 +               langwell->hsm.a_aidl_bdis_tmout,
7488 +               langwell->hsm.b_ase0_brst_tmout,
7489 +               langwell->hsm.a_bus_drop,
7490 +               langwell->hsm.a_bus_req,
7491 +               langwell->hsm.a_clr_err,
7492 +               langwell->hsm.a_suspend_req,
7493 +               langwell->hsm.b_bus_req,
7494 +               langwell->hsm.b_bus_suspend_tmout,
7495 +               langwell->hsm.b_bus_suspend_vld
7496 +               );
7497 +       size -= t;
7498 +       next += t;
7499 +
7500 +       return PAGE_SIZE - size;
7501 +}
7502 +static DEVICE_ATTR(hsm, S_IRUGO, show_hsm, NULL);
7503 +
7504 +static ssize_t
7505 +get_a_bus_req(struct device *dev, struct device_attribute *attr, char *buf)
7506 +{
7507 +       struct langwell_otg *langwell;
7508 +       char *next;
7509 +       unsigned size;
7510 +       unsigned t;
7511 +
7512 +       langwell =  the_transceiver;
7513 +       next = buf;
7514 +       size = PAGE_SIZE;
7515 +
7516 +       t = scnprintf(next, size, "%d", langwell->hsm.a_bus_req);
7517 +       size -= t;
7518 +       next += t;
7519 +
7520 +       return PAGE_SIZE - size;
7521 +}
7522 +
7523 +static ssize_t
7524 +set_a_bus_req(struct device *dev, struct device_attribute *attr,
7525 +               const char *buf, size_t count)
7526 +{
7527 +       struct langwell_otg *langwell;
7528 +       langwell = the_transceiver;
7529 +       if (!langwell->otg.default_a)
7530 +               return -1;
7531 +       if (count > 2)
7532 +               return -1;
7533 +
7534 +       if (buf[0] == '0') {
7535 +               langwell->hsm.a_bus_req = 0;
7536 +               otg_dbg("a_bus_req = 0\n");
7537 +       } else if (buf[0] == '1') {
7538 +               /* If a_bus_drop is TRUE, a_bus_req can't be set */
7539 +               if (langwell->hsm.a_bus_drop)
7540 +                       return -1;
7541 +               langwell->hsm.a_bus_req = 1;
7542 +               otg_dbg("a_bus_req = 1\n");
7543 +       }
7544 +
7545 +       langwell_update_transceiver();
7546 +
7547 +       return count;
7548 +}
7549 +static DEVICE_ATTR(a_bus_req, S_IRUGO | S_IWUGO, get_a_bus_req, set_a_bus_req);
7550 +
7551 +static ssize_t
7552 +get_a_bus_drop(struct device *dev, struct device_attribute *attr, char *buf)
7553 +{
7554 +       struct langwell_otg *langwell;
7555 +       char *next;
7556 +       unsigned size;
7557 +       unsigned t;
7558 +
7559 +       langwell =  the_transceiver;
7560 +       next = buf;
7561 +       size = PAGE_SIZE;
7562 +
7563 +       t = scnprintf(next, size, "%d", langwell->hsm.a_bus_drop);
7564 +       size -= t;
7565 +       next += t;
7566 +
7567 +       return PAGE_SIZE - size;
7568 +}
7569 +
7570 +static ssize_t
7571 +set_a_bus_drop(struct device *dev, struct device_attribute *attr,
7572 +               const char *buf, size_t count)
7573 +{
7574 +       struct langwell_otg *langwell;
7575 +       langwell = the_transceiver;
7576 +       if (!langwell->otg.default_a)
7577 +               return -1;
7578 +       if (count > 2)
7579 +               return -1;
7580 +
7581 +       if (buf[0] == '0') {
7582 +               langwell->hsm.a_bus_drop = 0;
7583 +               otg_dbg("a_bus_drop = 0\n");
7584 +       } else if (buf[0] == '1') {
7585 +               langwell->hsm.a_bus_drop = 1;
7586 +               langwell->hsm.a_bus_req = 0;
7587 +               otg_dbg("a_bus_drop = 1, then a_bus_req = 0\n");
7588 +       }
7589 +
7590 +       langwell_update_transceiver();
7591 +
7592 +       return count;
7593 +}
7594 +static DEVICE_ATTR(a_bus_drop, S_IRUGO | S_IWUGO,
7595 +       get_a_bus_drop, set_a_bus_drop);
7596 +
7597 +static ssize_t
7598 +get_b_bus_req(struct device *dev, struct device_attribute *attr, char *buf)
7599 +{
7600 +       struct langwell_otg *langwell;
7601 +       char *next;
7602 +       unsigned size;
7603 +       unsigned t;
7604 +
7605 +       langwell =  the_transceiver;
7606 +       next = buf;
7607 +       size = PAGE_SIZE;
7608 +
7609 +       t = scnprintf(next, size, "%d", langwell->hsm.b_bus_req);
7610 +       size -= t;
7611 +       next += t;
7612 +
7613 +       return PAGE_SIZE - size;
7614 +}
7615 +
7616 +static ssize_t
7617 +set_b_bus_req(struct device *dev, struct device_attribute *attr,
7618 +               const char *buf, size_t count)
7619 +{
7620 +       struct langwell_otg *langwell;
7621 +       langwell = the_transceiver;
7622 +
7623 +       if (langwell->otg.default_a)
7624 +               return -1;
7625 +
7626 +       if (count > 2)
7627 +               return -1;
7628 +
7629 +       if (buf[0] == '0') {
7630 +               langwell->hsm.b_bus_req = 0;
7631 +               otg_dbg("b_bus_req = 0\n");
7632 +       } else if (buf[0] == '1') {
7633 +               langwell->hsm.b_bus_req = 1;
7634 +               otg_dbg("b_bus_req = 1\n");
7635 +       }
7636 +
7637 +       langwell_update_transceiver();
7638 +
7639 +       return count;
7640 +}
7641 +static DEVICE_ATTR(b_bus_req, S_IRUGO | S_IWUGO, get_b_bus_req, set_b_bus_req);
7642 +
7643 +static ssize_t
7644 +set_a_clr_err(struct device *dev, struct device_attribute *attr,
7645 +               const char *buf, size_t count)
7646 +{
7647 +       struct langwell_otg *langwell;
7648 +       langwell = the_transceiver;
7649 +
7650 +       if (!langwell->otg.default_a)
7651 +               return -1;
7652 +       if (count > 2)
7653 +               return -1;
7654 +
7655 +       if (buf[0] == '1') {
7656 +               langwell->hsm.a_clr_err = 1;
7657 +               otg_dbg("a_clr_err = 1\n");
7658 +       }
7659 +
7660 +       langwell_update_transceiver();
7661 +
7662 +       return count;
7663 +}
7664 +static DEVICE_ATTR(a_clr_err, S_IWUGO, NULL, set_a_clr_err);
7665 +
7666 +static struct attribute *inputs_attrs[] = {
7667 +       &dev_attr_a_bus_req.attr,
7668 +       &dev_attr_a_bus_drop.attr,
7669 +       &dev_attr_b_bus_req.attr,
7670 +       &dev_attr_a_clr_err.attr,
7671 +       NULL,
7672 +};
7673 +
7674 +static struct attribute_group debug_dev_attr_group = {
7675 +       .name = "inputs",
7676 +       .attrs = inputs_attrs,
7677 +};
7678 +
7679 +int langwell_register_host(struct pci_driver *host_driver)
7680 +{
7681 +       int     ret = 0;
7682 +
7683 +       the_transceiver->host_ops = host_driver;
7684 +       queue_work(the_transceiver->qwork, &the_transceiver->work);
7685 +       otg_dbg("host controller driver is registered\n");
7686 +
7687 +       return ret;
7688 +}
7689 +EXPORT_SYMBOL(langwell_register_host);
7690 +
7691 +void langwell_unregister_host(struct pci_driver *host_driver)
7692 +{
7693 +       if (the_transceiver->host_ops)
7694 +               the_transceiver->host_ops->remove(the_transceiver->pdev);
7695 +       the_transceiver->host_ops = NULL;
7696 +       the_transceiver->hsm.a_bus_drop = 1;
7697 +       queue_work(the_transceiver->qwork, &the_transceiver->work);
7698 +       otg_dbg("host controller driver is unregistered\n");
7699 +}
7700 +EXPORT_SYMBOL(langwell_unregister_host);
7701 +
7702 +int langwell_register_peripheral(struct pci_driver *client_driver)
7703 +{
7704 +       int     ret = 0;
7705 +
7706 +       if (client_driver)
7707 +               ret = client_driver->probe(the_transceiver->pdev,
7708 +                               client_driver->id_table);
7709 +       if (!ret) {
7710 +               the_transceiver->client_ops = client_driver;
7711 +               queue_work(the_transceiver->qwork, &the_transceiver->work);
7712 +               otg_dbg("client controller driver is registered\n");
7713 +       }
7714 +
7715 +       return ret;
7716 +}
7717 +EXPORT_SYMBOL(langwell_register_peripheral);
7718 +
7719 +void langwell_unregister_peripheral(struct pci_driver *client_driver)
7720 +{
7721 +       if (the_transceiver->client_ops)
7722 +               the_transceiver->client_ops->remove(the_transceiver->pdev);
7723 +       the_transceiver->client_ops = NULL;
7724 +       the_transceiver->hsm.b_bus_req = 0;
7725 +       queue_work(the_transceiver->qwork, &the_transceiver->work);
7726 +       otg_dbg("client controller driver is unregistered\n");
7727 +}
7728 +EXPORT_SYMBOL(langwell_unregister_peripheral);
7729 +
7730 +static int langwell_otg_probe(struct pci_dev *pdev,
7731 +               const struct pci_device_id *id)
7732 +{
7733 +       unsigned long           resource, len;
7734 +       void __iomem            *base = NULL;
7735 +       int                     retval;
7736 +       u32                     val32;
7737 +       struct langwell_otg     *langwell;
7738 +       char                    qname[] = "langwell_otg_queue";
7739 +
7740 +       retval = 0;
7741 +       otg_dbg("\notg controller is detected.\n");
7742 +       if (pci_enable_device(pdev) < 0) {
7743 +               retval = -ENODEV;
7744 +               goto done;
7745 +       }
7746 +
7747 +       langwell = kzalloc(sizeof *langwell, GFP_KERNEL);
7748 +       if (langwell == NULL) {
7749 +               retval = -ENOMEM;
7750 +               goto done;
7751 +       }
7752 +       the_transceiver = langwell;
7753 +
7754 +       /* control register: BAR 0 */
7755 +       resource = pci_resource_start(pdev, 0);
7756 +       len = pci_resource_len(pdev, 0);
7757 +       if (!request_mem_region(resource, len, driver_name)) {
7758 +               retval = -EBUSY;
7759 +               goto err;
7760 +       }
7761 +       langwell->region = 1;
7762 +
7763 +       base = ioremap_nocache(resource, len);
7764 +       if (base == NULL) {
7765 +               retval = -EFAULT;
7766 +               goto err;
7767 +       }
7768 +       langwell->regs = base;
7769 +
7770 +       if (!request_mem_region(USBCFG_ADDR, USBCFG_LEN, driver_name)) {
7771 +               retval = -EBUSY;
7772 +               goto err;
7773 +       }
7774 +       langwell->cfg_region = 1;
7775 +
7776 +       /* For the SCCB.USBCFG register */
7777 +       base = ioremap_nocache(USBCFG_ADDR, USBCFG_LEN);
7778 +       if (base == NULL) {
7779 +               retval = -EFAULT;
7780 +               goto err;
7781 +       }
7782 +       langwell->usbcfg = base;
7783 +
7784 +       if (!pdev->irq) {
7785 +               otg_dbg("No IRQ.\n");
7786 +               retval = -ENODEV;
7787 +               goto err;
7788 +       }
7789 +
7790 +       langwell->qwork = create_singlethread_workqueue(qname);
7791 +       if (!langwell->qwork) {
7792 +               otg_dbg("cannot create workqueue %s\n", qname);
7793 +               retval = -ENOMEM;
7794 +               goto err;
7795 +       }
7796 +       INIT_WORK(&langwell->work, langwell_otg_work);
7797 +
7798 +       /* OTG common part */
7799 +       langwell->pdev = pdev;
7800 +       langwell->otg.dev = &pdev->dev;
7801 +       langwell->otg.label = driver_name;
7802 +       langwell->otg.set_host = langwell_otg_set_host;
7803 +       langwell->otg.set_peripheral = langwell_otg_set_peripheral;
7804 +       langwell->otg.set_power = langwell_otg_set_power;
7805 +       langwell->otg.start_srp = langwell_otg_start_srp;
7806 +       langwell->otg.state = OTG_STATE_UNDEFINED;
7807 +       if (otg_set_transceiver(&langwell->otg)) {
7808 +               otg_dbg("can't set transceiver\n");
7809 +               retval = -EBUSY;
7810 +               goto err;
7811 +       }
7812 +
7813 +       reset_otg();
7814 +       init_hsm();
7815 +
7816 +       spin_lock_init(&langwell->lock);
7817 +       spin_lock_init(&langwell->wq_lock);
7818 +       INIT_LIST_HEAD(&active_timers);
7819 +       langwell_otg_init_timers(&langwell->hsm);
7820 +       init_timer(&langwell->hsm_timer);
7821 +
7822 +       if (request_irq(pdev->irq, otg_irq, IRQF_SHARED,
7823 +                               driver_name, langwell) != 0) {
7824 +               otg_dbg("request interrupt %d failed\n", pdev->irq);
7825 +               retval = -EBUSY;
7826 +               goto err;
7827 +       }
7828 +
7829 +       /* enable OTGSC int */
7830 +       val32 = OTGSC_DPIE | OTGSC_BSEIE | OTGSC_BSVIE |
7831 +               OTGSC_ASVIE | OTGSC_AVVIE | OTGSC_IDIE | OTGSC_IDPU;
7832 +       writel(val32, langwell->regs + CI_OTGSC);
7833 +
7834 +       retval = device_create_file(&pdev->dev, &dev_attr_registers);
7835 +       if (retval < 0) {
7836 +               otg_dbg("Can't register sysfs attribute: %d\n", retval);
7837 +               goto err;
7838 +       }
7839 +
7840 +       retval = device_create_file(&pdev->dev, &dev_attr_hsm);
7841 +       if (retval < 0) {
7842 +               otg_dbg("Can't hsm sysfs attribute: %d\n", retval);
7843 +               goto err;
7844 +       }
7845 +
7846 +       retval = sysfs_create_group(&pdev->dev.kobj, &debug_dev_attr_group);
7847 +       if (retval < 0) {
7848 +               otg_dbg("Can't register sysfs attr group: %d\n", retval);
7849 +               goto err;
7850 +       }
7851 +
7852 +       if (langwell->otg.state == OTG_STATE_A_IDLE)
7853 +               queue_work(langwell->qwork, &langwell->work);
7854 +
7855 +       return 0;
7856 +
7857 +err:
7858 +       if (the_transceiver)
7859 +               langwell_otg_remove(pdev);
7860 +done:
7861 +       return retval;
7862 +}
7863 +
7864 +static void langwell_otg_remove(struct pci_dev *pdev)
7865 +{
7866 +       struct langwell_otg *langwell;
7867 +
7868 +       langwell = the_transceiver;
7869 +
7870 +       if (langwell->qwork) {
7871 +               flush_workqueue(langwell->qwork);
7872 +               destroy_workqueue(langwell->qwork);
7873 +       }
7874 +       langwell_otg_free_timers();
7875 +
7876 +       /* disable OTGSC interrupt as OTGSC doesn't change in reset */
7877 +       writel(0, langwell->regs + CI_OTGSC);
7878 +
7879 +       if (pdev->irq)
7880 +               free_irq(pdev->irq, langwell);
7881 +       if (langwell->usbcfg)
7882 +               iounmap(langwell->usbcfg);
7883 +       if (langwell->cfg_region)
7884 +               release_mem_region(USBCFG_ADDR, USBCFG_LEN);
7885 +       if (langwell->regs)
7886 +               iounmap(langwell->regs);
7887 +       if (langwell->region)
7888 +               release_mem_region(pci_resource_start(pdev, 0),
7889 +                               pci_resource_len(pdev, 0));
7890 +
7891 +       otg_set_transceiver(NULL);
7892 +       pci_disable_device(pdev);
7893 +       sysfs_remove_group(&pdev->dev.kobj, &debug_dev_attr_group);
7894 +       device_remove_file(&pdev->dev, &dev_attr_hsm);
7895 +       device_remove_file(&pdev->dev, &dev_attr_registers);
7896 +       kfree(langwell);
7897 +       langwell = NULL;
7898 +}
7899 +
7900 +static void transceiver_suspend(struct pci_dev *pdev)
7901 +{
7902 +       pci_save_state(pdev);
7903 +       pci_set_power_state(pdev, PCI_D3hot);
7904 +       langwell_otg_phy_low_power(1);
7905 +}
7906 +
7907 +static int langwell_otg_suspend(struct pci_dev *pdev, pm_message_t message)
7908 +{
7909 +       struct langwell_otg     *langwell;
7910 +       struct pci_driver       *ops;
7911 +       int                     ret = 0;
7912 +
7913 +       langwell = the_transceiver;
7914 +
7915 +       /* Disbale OTG interrupts */
7916 +       langwell_otg_intr(0);
7917 +
7918 +       if (pdev->irq)
7919 +               free_irq(pdev->irq, langwell);
7920 +
7921 +       /* Prevent more otg_work */
7922 +       flush_workqueue(langwell->qwork);
7923 +       destroy_workqueue(langwell->qwork);
7924 +       langwell->qwork = NULL;
7925 +
7926 +       /* start actions */
7927 +       switch (langwell->otg.state) {
7928 +       case OTG_STATE_A_WAIT_VFALL:
7929 +               langwell->otg.state = OTG_STATE_A_IDLE;
7930 +       case OTG_STATE_A_IDLE:
7931 +       case OTG_STATE_A_VBUS_ERR:
7932 +       case OTG_STATE_B_IDLE:
7933 +               transceiver_suspend(pdev);
7934 +               break;
7935 +       case OTG_STATE_A_WAIT_VRISE:
7936 +               langwell_otg_del_timer(a_wait_vrise_tmr);
7937 +               langwell->hsm.a_srp_det = 0;
7938 +               langwell_otg_drv_vbus(0);
7939 +               langwell->otg.state = OTG_STATE_A_IDLE;
7940 +               transceiver_suspend(pdev);
7941 +               break;
7942 +       case OTG_STATE_A_WAIT_BCON:
7943 +               del_timer_sync(&langwell->hsm_timer);
7944 +               ops = langwell->host_ops;
7945 +
7946 +               switch (message.event) {
7947 +               case PM_EVENT_SUSPEND:
7948 +                       if (ops && ops->driver.pm && ops->driver.pm->suspend)
7949 +                               ret = ops->driver.pm->suspend(&pdev->dev);
7950 +                       break;
7951 +               case PM_EVENT_FREEZE:
7952 +                       if (ops && ops->driver.pm && ops->driver.pm->freeze)
7953 +                               ret = ops->driver.pm->freeze(&pdev->dev);
7954 +                       break;
7955 +               case PM_EVENT_HIBERNATE:
7956 +                       if (ops && ops->driver.pm && ops->driver.pm->poweroff)
7957 +                               ret = ops->driver.pm->poweroff(&pdev->dev);
7958 +                       break;
7959 +               default:
7960 +                       otg_dbg("not suspend/freeze/hibernate pm event\n");
7961 +                       ret = -EINVAL;
7962 +                       break;
7963 +               }
7964 +
7965 +               if (ret) {
7966 +                       otg_dbg("pm suspend function error = %d\n", ret);
7967 +                       /* restart timer */
7968 +                       langwell_otg_add_ktimer(TA_WAIT_BCON_TMR);
7969 +                       goto error;
7970 +               }
7971 +
7972 +               if (ops && ops->remove)
7973 +                       ops->remove(pdev);
7974 +               else
7975 +                       otg_dbg("host driver has been removed.\n");
7976 +
7977 +               langwell->hsm.a_srp_det = 0;
7978 +               langwell_otg_drv_vbus(0);
7979 +               langwell->otg.state = OTG_STATE_A_IDLE;
7980 +               transceiver_suspend(pdev);
7981 +               break;
7982 +       case OTG_STATE_A_HOST:
7983 +               ops = langwell->host_ops;
7984 +
7985 +               switch (message.event) {
7986 +               case PM_EVENT_SUSPEND:
7987 +                       if (ops && ops->driver.pm && ops->driver.pm->suspend)
7988 +                               ret = ops->driver.pm->suspend(&pdev->dev);
7989 +                       break;
7990 +               case PM_EVENT_FREEZE:
7991 +                       if (ops && ops->driver.pm && ops->driver.pm->freeze)
7992 +                               ret = ops->driver.pm->freeze(&pdev->dev);
7993 +                       break;
7994 +               case PM_EVENT_HIBERNATE:
7995 +                       if (ops && ops->driver.pm && ops->driver.pm->poweroff)
7996 +                               ret = ops->driver.pm->poweroff(&pdev->dev);
7997 +                       break;
7998 +               default:
7999 +                       otg_dbg("not suspend/freeze/hibernate pm event\n");
8000 +                       ret = -EINVAL;
8001 +                       break;
8002 +               }
8003 +
8004 +               if (ret) {
8005 +                       otg_dbg("pm suspend function error = %d\n", ret);
8006 +                       goto error;
8007 +               }
8008 +
8009 +               if (ops && ops->remove)
8010 +                       ops->remove(pdev);
8011 +               else
8012 +                       otg_dbg("host driver has been removed.\n");
8013 +
8014 +               langwell->hsm.a_srp_det = 0;
8015 +               langwell_otg_drv_vbus(0);
8016 +               langwell->otg.state = OTG_STATE_A_IDLE;
8017 +               transceiver_suspend(pdev);
8018 +               break;
8019 +       case OTG_STATE_A_SUSPEND:
8020 +               langwell_otg_del_timer(a_aidl_bdis_tmr);
8021 +               langwell_otg_HABA(0);
8022 +               if (langwell->host_ops && langwell->host_ops->remove)
8023 +                       langwell->host_ops->remove(pdev);
8024 +               else
8025 +                       otg_dbg("host driver has been removed.\n");
8026 +               langwell->hsm.a_srp_det = 0;
8027 +               langwell_otg_drv_vbus(0);
8028 +               langwell->otg.state = OTG_STATE_A_IDLE;
8029 +               transceiver_suspend(pdev);
8030 +               break;
8031 +       case OTG_STATE_A_PERIPHERAL:
8032 +               del_timer_sync(&langwell->hsm_timer);
8033 +               if (langwell->client_ops && langwell->client_ops->suspend)
8034 +                       ret = langwell->client_ops->suspend(pdev, message);
8035 +               else
8036 +                       otg_dbg("client driver has been removed.\n");
8037 +
8038 +               if (ret) {
8039 +                       otg_dbg("pm suspend function error = %d\n", ret);
8040 +                       goto error;
8041 +               }
8042 +
8043 +               langwell_otg_drv_vbus(0);
8044 +               langwell->hsm.a_srp_det = 0;
8045 +               langwell->otg.state = OTG_STATE_A_IDLE;
8046 +               transceiver_suspend(pdev);
8047 +               break;
8048 +       case OTG_STATE_B_HOST:
8049 +               if (langwell->host_ops && langwell->host_ops->remove)
8050 +                       langwell->host_ops->remove(pdev);
8051 +               else
8052 +                       otg_dbg("host driver has been removed.\n");
8053 +               langwell->hsm.b_bus_req = 0;
8054 +               langwell->otg.state = OTG_STATE_B_IDLE;
8055 +               transceiver_suspend(pdev);
8056 +               break;
8057 +       case OTG_STATE_B_PERIPHERAL:
8058 +               if (langwell->client_ops && langwell->client_ops->suspend)
8059 +                       ret = langwell->client_ops->suspend(pdev, message);
8060 +               else
8061 +                       otg_dbg("client driver has been removed.\n");
8062 +
8063 +               if (ret) {
8064 +                       otg_dbg("pm suspend function error = %d\n", ret);
8065 +                       goto error;
8066 +               }
8067 +
8068 +               langwell->otg.state = OTG_STATE_B_IDLE;
8069 +               transceiver_suspend(pdev);
8070 +               break;
8071 +       case OTG_STATE_B_WAIT_ACON:
8072 +               /* delete hsm timer for b_ase0_brst_tmr */
8073 +               del_timer_sync(&langwell->hsm_timer);
8074 +
8075 +               langwell_otg_HAAR(0);
8076 +               if (langwell->host_ops && langwell->host_ops->remove)
8077 +                       langwell->host_ops->remove(pdev);
8078 +               else
8079 +                       otg_dbg("host driver has been removed.\n");
8080 +               langwell->hsm.b_bus_req = 0;
8081 +               langwell->otg.state = OTG_STATE_B_IDLE;
8082 +               transceiver_suspend(pdev);
8083 +               break;
8084 +       default:
8085 +               otg_dbg("error state before suspend\n ");
8086 +               break;
8087 +       }
8088 +
8089 +       return ret;
8090 +error:
8091 +       langwell->qwork = create_singlethread_workqueue("langwell_otg_queue");
8092 +       if (!langwell->qwork) {
8093 +               otg_dbg("cannot create workqueue langwell_otg_queue\n");
8094 +               return -ENOMEM;
8095 +       }
8096 +
8097 +       if (request_irq(pdev->irq, otg_irq, IRQF_SHARED,
8098 +                               driver_name, the_transceiver) != 0) {
8099 +               otg_dbg("request interrupt %d failed\n", pdev->irq);
8100 +               return -EBUSY;
8101 +       }
8102 +
8103 +       /* enable OTG interrupts */
8104 +       langwell_otg_intr(1);
8105 +
8106 +       return ret;
8107 +}
8108 +
8109 +static void transceiver_resume(struct pci_dev *pdev)
8110 +{
8111 +       pci_restore_state(pdev);
8112 +       pci_set_power_state(pdev, PCI_D0);
8113 +}
8114 +
8115 +static int langwell_otg_resume(struct pci_dev *pdev)
8116 +{
8117 +       struct langwell_otg     *langwell;
8118 +       int                     ret = 0;
8119 +
8120 +       langwell = the_transceiver;
8121 +
8122 +       transceiver_resume(pdev);
8123 +
8124 +       langwell->qwork = create_singlethread_workqueue("langwell_otg_queue");
8125 +       if (!langwell->qwork) {
8126 +               otg_dbg("cannot create workqueue langwell_otg_queue\n");
8127 +               ret = -ENOMEM;
8128 +               goto error;
8129 +       }
8130 +
8131 +       if (request_irq(pdev->irq, otg_irq, IRQF_SHARED,
8132 +                               driver_name, the_transceiver) != 0) {
8133 +               otg_dbg("request interrupt %d failed\n", pdev->irq);
8134 +               ret = -EBUSY;
8135 +               goto error;
8136 +       }
8137 +
8138 +       /* enable OTG interrupts */
8139 +       langwell_otg_intr(1);
8140 +
8141 +       update_hsm();
8142 +
8143 +       langwell_update_transceiver();
8144 +
8145 +       return ret;
8146 +error:
8147 +       langwell_otg_intr(0);
8148 +       transceiver_suspend(pdev);
8149 +       return ret;
8150 +}
8151 +
8152 +static int __init langwell_otg_init(void)
8153 +{
8154 +       return pci_register_driver(&otg_pci_driver);
8155 +}
8156 +module_init(langwell_otg_init);
8157 +
8158 +static void __exit langwell_otg_cleanup(void)
8159 +{
8160 +       pci_unregister_driver(&otg_pci_driver);
8161 +}
8162 +module_exit(langwell_otg_cleanup);
8163 diff --git a/include/linux/usb/langwell_otg.h b/include/linux/usb/langwell_otg.h
8164 new file mode 100644
8165 index 0000000..cbb204b
8166 --- /dev/null
8167 +++ b/include/linux/usb/langwell_otg.h
8168 @@ -0,0 +1,201 @@
8169 +/*
8170 + * Intel Langwell USB OTG transceiver driver
8171 + * Copyright (C) 2008, Intel Corporation.
8172 + *
8173 + * This program is free software; you can redistribute it and/or modify it
8174 + * under the terms and conditions of the GNU General Public License,
8175 + * version 2, as published by the Free Software Foundation.
8176 + *
8177 + * This program is distributed in the hope it will be useful, but WITHOUT
8178 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
8179 + * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
8180 + * more details.
8181 + *
8182 + * You should have received a copy of the GNU General Public License along with
8183 + * this program; if not, write to the Free Software Foundation, Inc.,
8184 + * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
8185 + *
8186 + */
8187 +
8188 +#ifndef __LANGWELL_OTG_H__
8189 +#define __LANGWELL_OTG_H__
8190 +
8191 +/* notify transceiver driver about OTG events */
8192 +extern void langwell_update_transceiver(void);
8193 +/* HCD register bus driver */
8194 +extern int langwell_register_host(struct pci_driver *host_driver);
8195 +/* HCD unregister bus driver */
8196 +extern void langwell_unregister_host(struct pci_driver *host_driver);
8197 +/* DCD register bus driver */
8198 +extern int langwell_register_peripheral(struct pci_driver *client_driver);
8199 +/* DCD unregister bus driver */
8200 +extern void langwell_unregister_peripheral(struct pci_driver *client_driver);
8201 +/* No silent failure, output warning message */
8202 +extern void langwell_otg_nsf_msg(unsigned long message);
8203 +
8204 +#define CI_USBCMD              0x30
8205 +#      define USBCMD_RST               BIT(1)
8206 +#      define USBCMD_RS                BIT(0)
8207 +#define CI_USBSTS              0x34
8208 +#      define USBSTS_SLI               BIT(8)
8209 +#      define USBSTS_URI               BIT(6)
8210 +#      define USBSTS_PCI               BIT(2)
8211 +#define CI_PORTSC1             0x74
8212 +#      define PORTSC_PP                BIT(12)
8213 +#      define PORTSC_LS                (BIT(11) | BIT(10))
8214 +#      define PORTSC_SUSP              BIT(7)
8215 +#      define PORTSC_CCS               BIT(0)
8216 +#define CI_HOSTPC1             0xb4
8217 +#      define HOSTPC1_PHCD             BIT(22)
8218 +#define CI_OTGSC               0xf4
8219 +#      define OTGSC_DPIE               BIT(30)
8220 +#      define OTGSC_1MSE               BIT(29)
8221 +#      define OTGSC_BSEIE              BIT(28)
8222 +#      define OTGSC_BSVIE              BIT(27)
8223 +#      define OTGSC_ASVIE              BIT(26)
8224 +#      define OTGSC_AVVIE              BIT(25)
8225 +#      define OTGSC_IDIE               BIT(24)
8226 +#      define OTGSC_DPIS               BIT(22)
8227 +#      define OTGSC_1MSS               BIT(21)
8228 +#      define OTGSC_BSEIS              BIT(20)
8229 +#      define OTGSC_BSVIS              BIT(19)
8230 +#      define OTGSC_ASVIS              BIT(18)
8231 +#      define OTGSC_AVVIS              BIT(17)
8232 +#      define OTGSC_IDIS               BIT(16)
8233 +#      define OTGSC_DPS                BIT(14)
8234 +#      define OTGSC_1MST               BIT(13)
8235 +#      define OTGSC_BSE                BIT(12)
8236 +#      define OTGSC_BSV                BIT(11)
8237 +#      define OTGSC_ASV                BIT(10)
8238 +#      define OTGSC_AVV                BIT(9)
8239 +#      define OTGSC_ID                 BIT(8)
8240 +#      define OTGSC_HABA               BIT(7)
8241 +#      define OTGSC_HADP               BIT(6)
8242 +#      define OTGSC_IDPU               BIT(5)
8243 +#      define OTGSC_DP                 BIT(4)
8244 +#      define OTGSC_OT                 BIT(3)
8245 +#      define OTGSC_HAAR               BIT(2)
8246 +#      define OTGSC_VC                 BIT(1)
8247 +#      define OTGSC_VD                 BIT(0)
8248 +#      define OTGSC_INTEN_MASK         (0x7f << 24)
8249 +#      define OTGSC_INT_MASK           (0x5f << 24)
8250 +#      define OTGSC_INTSTS_MASK        (0x7f << 16)
8251 +#define CI_USBMODE             0xf8
8252 +#      define USBMODE_CM               (BIT(1) | BIT(0))
8253 +#      define USBMODE_IDLE             0
8254 +#      define USBMODE_DEVICE           0x2
8255 +#      define USBMODE_HOST             0x3
8256 +#define USBCFG_ADDR                    0xff10801c
8257 +#define USBCFG_LEN                     4
8258 +#      define USBCFG_VBUSVAL           BIT(14)
8259 +#      define USBCFG_AVALID            BIT(13)
8260 +#      define USBCFG_BVALID            BIT(12)
8261 +#      define USBCFG_SESEND            BIT(11)
8262 +
8263 +#define INTR_DUMMY_MASK (USBSTS_SLI | USBSTS_URI | USBSTS_PCI)
8264 +
8265 +struct otg_hsm {
8266 +       /* Input */
8267 +       int a_bus_resume;
8268 +       int a_bus_suspend;
8269 +       int a_conn;
8270 +       int a_sess_vld;
8271 +       int a_srp_det;
8272 +       int a_vbus_vld;
8273 +       int b_bus_resume;
8274 +       int b_bus_suspend;
8275 +       int b_conn;
8276 +       int b_se0_srp;
8277 +       int b_sess_end;
8278 +       int b_sess_vld;
8279 +       int id;
8280 +
8281 +       /* Internal variables */
8282 +       int a_set_b_hnp_en;
8283 +       int b_srp_done;
8284 +       int b_hnp_enable;
8285 +
8286 +       /* Timeout indicator for timers */
8287 +       int a_wait_vrise_tmout;
8288 +       int a_wait_bcon_tmout;
8289 +       int a_aidl_bdis_tmout;
8290 +       int b_ase0_brst_tmout;
8291 +       int b_bus_suspend_tmout;
8292 +       int b_srp_init_tmout;
8293 +       int b_srp_fail_tmout;
8294 +
8295 +       /* Informative variables */
8296 +       int a_bus_drop;
8297 +       int a_bus_req;
8298 +       int a_clr_err;
8299 +       int a_suspend_req;
8300 +       int b_bus_req;
8301 +
8302 +       /* Output */
8303 +       int drv_vbus;
8304 +       int loc_conn;
8305 +       int loc_sof;
8306 +
8307 +       /* Others */
8308 +       int b_bus_suspend_vld;
8309 +       int vbus_srp_up;
8310 +};
8311 +
8312 +enum langwell_otg_timer_type {
8313 +       TA_WAIT_VRISE_TMR,
8314 +       TA_WAIT_BCON_TMR,
8315 +       TA_AIDL_BDIS_TMR,
8316 +       TB_ASE0_BRST_TMR,
8317 +       TB_SE0_SRP_TMR,
8318 +       TB_SRP_INIT_TMR,
8319 +       TB_SRP_FAIL_TMR,
8320 +       TB_BUS_SUSPEND_TMR
8321 +};
8322 +
8323 +#define TA_WAIT_VRISE  100
8324 +#define TA_WAIT_BCON   30000
8325 +#define TA_AIDL_BDIS   15000
8326 +#define TB_ASE0_BRST   5000
8327 +#define TB_SE0_SRP     2
8328 +#define TB_SRP_INIT    100
8329 +#define TB_SRP_FAIL    5500
8330 +#define TB_BUS_SUSPEND 500
8331 +
8332 +struct langwell_otg_timer {
8333 +       unsigned long expires;  /* Number of count increase to timeout */
8334 +       unsigned long count;    /* Tick counter */
8335 +       void (*function)(unsigned long);        /* Timeout function */
8336 +       unsigned long data;     /* Data passed to function */
8337 +       struct list_head list;
8338 +};
8339 +
8340 +struct langwell_otg {
8341 +       struct otg_transceiver  otg;
8342 +       struct otg_hsm          hsm;
8343 +       void __iomem            *regs;
8344 +       void __iomem            *usbcfg;        /* SCCB USB config Reg */
8345 +       unsigned                region;
8346 +       unsigned                cfg_region;
8347 +       struct pci_driver       *host_ops;
8348 +       struct pci_driver       *client_ops;
8349 +       struct pci_dev          *pdev;
8350 +       struct work_struct      work;
8351 +       struct workqueue_struct *qwork;
8352 +       struct timer_list       hsm_timer;
8353 +       spinlock_t              lock;
8354 +       spinlock_t              wq_lock;
8355 +};
8356 +
8357 +static inline struct langwell_otg *otg_to_langwell(struct otg_transceiver *otg)
8358 +{
8359 +       return container_of(otg, struct langwell_otg, otg);
8360 +}
8361 +
8362 +#ifdef DEBUG
8363 +#define otg_dbg(fmt, args...) \
8364 +       printk(KERN_DEBUG fmt , ## args)
8365 +#else
8366 +#define otg_dbg(fmt, args...) \
8367 +       do { } while (0)
8368 +#endif /* DEBUG */
8369 +#endif /* __LANGWELL_OTG_H__ */
8370 diff --git a/include/linux/usb/langwell_udc.h b/include/linux/usb/langwell_udc.h
8371 index c949178..fe2c698 100644
8372 --- a/include/linux/usb/langwell_udc.h
8373 +++ b/include/linux/usb/langwell_udc.h
8374 @@ -306,5 +306,18 @@ struct langwell_op_regs {
8375  #define        EPCTRL_RXS      BIT(0)  /* RX endpoint STALL */
8376  } __attribute__ ((packed));
8377  
8378 +
8379 +/* export function declaration */
8380 +
8381 +/* gets the maximum power consumption */
8382 +extern int langwell_udc_maxpower(int *mA);
8383 +
8384 +/* return errors of langwell_udc_maxpower() */
8385 +#define        EOTGFAIL        1
8386 +#define        EOTGNODEVICE    2
8387 +#define        EOTGCHARGER     3
8388 +#define        EOTGDISCONN     4
8389 +#define        EOTGINVAL       5
8390 +
8391  #endif /* __LANGWELL_UDC_H */
8392  
8393 -- 
8394 1.5.4.5
8395