Disable PCMCIA for adm5120, request IRQ for the USB driver, fix duplicate lines in...
[openwrt.git] / target / linux / adm5120-2.6 / files / drivers / usb / host / adm5120-hcd.c
1 /*
2  *      HCD driver for ADM5120 SoC
3  *
4  *      Copyright (C) 2005 Jeroen Vreeken (pe1rxq@amsat.org)
5  *
6  *      Based on the ADMtek 2.4 driver
7  *      (C) Copyright 2003 Junius Chen <juniusc@admtek.com.tw>
8  *      Which again was based on the ohci and uhci drivers.
9  */
10
11 #include <linux/module.h>
12 #include <linux/delay.h>
13 #include <linux/debugfs.h>
14 #include <linux/seq_file.h>
15 #include <linux/errno.h>
16 #include <linux/init.h>
17 #include <linux/list.h>
18 #include <linux/usb.h>
19 #include <linux/platform_device.h>
20
21 #include <asm/io.h>
22 #include <asm/irq.h>
23 #include <asm/system.h>
24 #include <asm/byteorder.h>
25 #include <asm/mach-adm5120/adm5120_info.h>
26
27 #include "../core/hcd.h"
28
29 MODULE_DESCRIPTION("ADM5120 USB Host Controller Driver");
30 MODULE_LICENSE("GPL");
31 MODULE_AUTHOR("Jeroen Vreeken (pe1rxq@amsat.org)");
32
33 #define ADMHCD_REG_CONTROL              0x00
34 #define ADMHCD_REG_INTSTATUS            0x04
35 #define ADMHCD_REG_INTENABLE            0x08
36 #define ADMHCD_REG_HOSTCONTROL          0x10
37 #define ADMHCD_REG_FMINTERVAL           0x18
38 #define ADMHCD_REG_FMNUMBER             0x1c
39 #define ADMHCD_REG_LSTHRESH             0x70
40 #define ADMHCD_REG_RHDESCR              0x74
41 #define ADMHCD_REG_PORTSTATUS0          0x78
42 #define ADMHCD_REG_PORTSTATUS1          0x7c
43 #define ADMHCD_REG_HOSTHEAD             0x80
44
45
46 #define ADMHCD_NUMPORTS         2
47
48 #define ADMHCD_HOST_EN          0x00000001      /* Host enable */
49 #define ADMHCD_SW_INTREQ        0x00000002      /* request software int */
50 #define ADMHCD_SW_RESET         0x00000008      /* Reset */
51
52 #define ADMHCD_INT_TD           0x00100000      /* TD completed */
53 #define ADMHCD_INT_SW           0x20000000      /* software interrupt */
54 #define ADMHCD_INT_FATAL        0x40000000      /* Fatal interrupt */
55 #define ADMHCD_INT_ACT          0x80000000      /* Interrupt active */
56
57 #define ADMHCD_STATE_RST        0x00000000      /* bus state reset */
58 #define ADMHCD_STATE_RES        0x00000001      /* bus state resume */
59 #define ADMHCD_STATE_OP         0x00000002      /* bus state operational */
60 #define ADMHCD_STATE_SUS        0x00000003      /* bus state suspended */
61 #define ADMHCD_DMA_EN           0x00000004      /* enable dma engine */
62
63 #define ADMHCD_NPS              0x00000020      /* No Power Switch */
64 #define ADMHCD_LPSC             0x04000000      /* Local power switch change */
65
66 #define ADMHCD_CCS              0x00000001      /* current connect status */
67 #define ADMHCD_PES              0x00000002      /* port enable status */
68 #define ADMHCD_PSS              0x00000004      /* port suspend status */
69 #define ADMHCD_POCI             0x00000008      /* port overcurrent indicator */
70 #define ADMHCD_PRS              0x00000010      /* port reset status */
71 #define ADMHCD_PPS              0x00000100      /* port power status */
72 #define ADMHCD_LSDA             0x00000200      /* low speed device attached */
73 #define ADMHCD_CSC              0x00010000      /* connect status change */
74 #define ADMHCD_PESC             0x00020000      /* enable status change */
75 #define ADMHCD_PSSC             0x00040000      /* suspend status change */
76 #define ADMHCD_OCIC             0x00080000      /* overcurrent change*/
77 #define ADMHCD_PRSC             0x00100000      /* reset status change */
78
79
80 struct admhcd_ed {
81         /* Don't change first four, they used for DMA */
82         u32                             control;
83         struct admhcd_td                *tail;
84         struct admhcd_td                *head;
85         struct admhcd_ed                *next;
86         /* the rest is for the driver only: */
87         struct admhcd_td                *cur;
88         struct usb_host_endpoint        *ep;
89         struct urb                      *urb;
90         struct admhcd_ed                *real;
91 } __attribute__ ((packed));
92
93 #define ADMHCD_ED_EPSHIFT       7               /* Shift for endpoint number */
94 #define ADMHCD_ED_INT           0x00000800      /* Is this an int endpoint */
95 #define ADMHCD_ED_SPEED         0x00002000      /* Is it a high speed dev? */
96 #define ADMHCD_ED_SKIP          0x00004000      /* Skip this ED */
97 #define ADMHCD_ED_FORMAT        0x00008000      /* Is this an isoc endpoint */
98 #define ADMHCD_ED_MAXSHIFT      16              /* Shift for max packet size */
99
100 struct admhcd_td {
101         /* Don't change first four, they are used for DMA */
102         u32                     control;
103         u32                     buffer;
104         u32                     buflen;
105         struct admhcd_td        *next;
106         /* the rest is for the driver only: */
107         struct urb              *urb;
108         struct admhcd_td        *real;
109 } __attribute__ ((packed));
110
111 #define ADMHCD_TD_OWN           0x80000000
112 #define ADMHCD_TD_TOGGLE        0x00000000
113 #define ADMHCD_TD_DATA0         0x01000000
114 #define ADMHCD_TD_DATA1         0x01800000
115 #define ADMHCD_TD_OUT           0x00200000
116 #define ADMHCD_TD_IN            0x00400000
117 #define ADMHCD_TD_SETUP         0x00000000
118 #define ADMHCD_TD_ISO           0x00010000
119 #define ADMHCD_TD_R             0x00040000
120 #define ADMHCD_TD_INTEN         0x00010000
121
122 static int admhcd_td_err[16] = {
123         0,              /* No */
124         -EREMOTEIO,             /* CRC */
125         -EREMOTEIO,     /* bit stuff */
126         -EREMOTEIO,             /* data toggle */
127         -EPIPE,         /* stall */
128         -ETIMEDOUT,     /* timeout */
129         -EPROTO,        /* pid err */
130         -EPROTO,        /* unexpected pid */
131         -EREMOTEIO,     /* data overrun */
132         -EREMOTEIO,     /* data underrun */
133         -ETIMEDOUT,     /* 1010 */
134         -ETIMEDOUT,     /* 1011 */
135         -EREMOTEIO,     /* buffer overrun */
136         -EREMOTEIO,     /* buffer underrun */
137         -ETIMEDOUT,     /* 1110 */
138         -ETIMEDOUT,     /* 1111 */
139 };
140
141 #define ADMHCD_TD_ERRMASK       0x38000000
142 #define ADMHCD_TD_ERRSHIFT      27
143
144 #define TD(td)  ((struct admhcd_td *)(((u32)(td)) & ~0xf))
145 #define ED(ed)  ((struct admhcd_ed *)(((u32)(ed)) & ~0xf))
146
147 struct admhcd {
148         spinlock_t      lock;
149
150         void __iomem *addr_reg;
151         void __iomem *data_reg;
152         /* Root hub registers */
153         u32 rhdesca;
154         u32 rhdescb;
155         u32 rhstatus;
156         u32 rhport[2];
157
158         /* async schedule: control, bulk */
159         struct list_head async;
160         u32             base;
161         u32             dma_en;
162         unsigned long   flags;
163
164 };
165
166 static inline struct admhcd *hcd_to_admhcd(struct usb_hcd *hcd)
167 {
168         return (struct admhcd *)(hcd->hcd_priv);
169 }
170
171 static inline struct usb_hcd *admhcd_to_hcd(struct admhcd *admhcd)
172 {
173         return container_of((void *)admhcd, struct usb_hcd, hcd_priv);
174 }
175
176 static char hcd_name[] = "adm5120-hcd";
177
178 static u32 admhcd_reg_get(struct admhcd *ahcd, int reg)
179 {
180         return *(volatile u32 *)KSEG1ADDR(ahcd->base+reg);
181 }
182
183 static void admhcd_reg_set(struct admhcd *ahcd, int reg, u32 val)
184 {
185         *(volatile u32 *)KSEG1ADDR(ahcd->base+reg) = val;
186 }
187
188 static void admhcd_lock(struct admhcd *ahcd)
189 {
190         spin_lock_irqsave(&ahcd->lock, ahcd->flags);
191         ahcd->dma_en = admhcd_reg_get(ahcd, ADMHCD_REG_HOSTCONTROL) &
192             ADMHCD_DMA_EN;
193         admhcd_reg_set(ahcd, ADMHCD_REG_HOSTCONTROL, ADMHCD_STATE_OP);
194 }
195
196 static void admhcd_unlock(struct admhcd *ahcd)
197 {
198         admhcd_reg_set(ahcd, ADMHCD_REG_HOSTCONTROL,
199             ADMHCD_STATE_OP | ahcd->dma_en);
200         spin_unlock_irqrestore(&ahcd->lock, ahcd->flags);
201 }
202
203 static struct admhcd_td *admhcd_td_alloc(struct admhcd_ed *ed, struct urb *urb)
204 {
205         struct admhcd_td *tdn, *td;
206
207         tdn = kmalloc(sizeof(struct admhcd_td), GFP_ATOMIC);
208         if (!tdn)
209                 return NULL;
210         tdn->real = tdn;
211         tdn = (struct admhcd_td *)KSEG1ADDR(tdn);
212         memset(tdn, 0, sizeof(struct admhcd_td));
213         if (ed->cur == NULL) {
214                 ed->cur = tdn;
215                 ed->head = tdn;
216                 ed->tail = tdn;
217                 td = tdn;
218         } else {
219                 /* Supply back the old tail and link in new td as tail */
220                 td = TD(ed->tail);
221                 TD(ed->tail)->next = tdn;
222                 ed->tail = tdn;
223         }
224         td->urb = urb;
225
226         return td;
227 }
228
229 static void admhcd_td_free(struct admhcd_ed *ed, struct urb *urb)
230 {
231         struct admhcd_td *td, **tdp;
232
233         if (urb == NULL)
234                 ed->control |= ADMHCD_ED_SKIP;
235         tdp = &ed->cur;
236         td = ed->cur;
237         do {
238                 if (td->urb == urb)
239                         break;
240                 tdp = &td->next;
241                 td = TD(td->next);
242         } while (td);
243         while (td && td->urb == urb) {
244                 *tdp = TD(td->next);
245                 kfree(td->real);
246                 td = *tdp;
247         }
248 }
249
250 /* Find an endpoint's descriptor, if needed allocate a new one and link it
251    in the DMA chain
252  */
253 static struct admhcd_ed *admhcd_get_ed(struct admhcd *ahcd,
254     struct usb_host_endpoint *ep, struct urb *urb)
255 {
256         struct admhcd_ed *hosthead;
257         struct admhcd_ed *found = NULL, *ed = NULL;
258         unsigned int pipe = urb->pipe;
259
260         admhcd_lock(ahcd);
261         hosthead = (struct admhcd_ed *)admhcd_reg_get(ahcd, ADMHCD_REG_HOSTHEAD);
262         if (hosthead) {
263                 for (ed = hosthead;; ed = ED(ed->next)) {
264                         if (ed->ep == ep) {
265                                 found = ed;
266                                 break;
267                         }
268                         if (ED(ed->next) == hosthead)
269                                 break;
270                 }
271         }
272         if (!found) {
273                 found = kmalloc(sizeof(struct admhcd_ed), GFP_ATOMIC);
274                 if (!found)
275                         goto out;
276                 memset(found, 0, sizeof(struct admhcd_ed));
277                 found->real = found;
278                 found->ep = ep;
279                 found = (struct admhcd_ed *)KSEG1ADDR(found);
280                 found->control = usb_pipedevice(pipe) |
281                     (usb_pipeendpoint(pipe) << ADMHCD_ED_EPSHIFT) |
282                     (usb_pipeint(pipe) ? ADMHCD_ED_INT : 0) |
283                     (urb->dev->speed == USB_SPEED_FULL ? ADMHCD_ED_SPEED : 0) |
284                     (usb_pipeisoc(pipe) ? ADMHCD_ED_FORMAT : 0) |
285                     (usb_maxpacket(urb->dev, pipe, usb_pipeout(pipe)) << ADMHCD_ED_MAXSHIFT);
286                 /* Alloc first dummy td */
287                 admhcd_td_alloc(found, NULL);
288                 if (hosthead) {
289                         found->next = hosthead;
290                         ed->next = found;
291                 } else {
292                         found->next = found;
293                         admhcd_reg_set(ahcd, ADMHCD_REG_HOSTHEAD, (u32)found);
294                 }
295         }
296 out:
297         admhcd_unlock(ahcd);
298         return found;
299 }
300
301 static struct admhcd_td *admhcd_td_fill(u32 control, struct admhcd_td *td,
302     dma_addr_t data, int len)
303 {
304         td->buffer = data;
305         td->buflen = len;
306         td->control = control;
307         return TD(td->next);
308 }
309
310 static void admhcd_ed_start(struct admhcd *ahcd, struct admhcd_ed *ed)
311 {
312         struct admhcd_td *td = ed->cur;
313
314         if (ed->urb)
315                 return;
316         if (td->urb) {
317                 ed->urb = td->urb;
318                 while (1) {
319                         td->control |= ADMHCD_TD_OWN;
320                         if (TD(td->next)->urb != td->urb) {
321                                 td->buflen |= ADMHCD_TD_INTEN;
322                                 break;
323                         }
324                         td = TD(td->next);
325                 }
326         }
327         ed->head = TD(ed->head);
328         ahcd->dma_en |= ADMHCD_DMA_EN;
329 }
330
331 static irqreturn_t adm5120hcd_irq(int irq, void *ptr, struct pt_regs *regs)
332 {
333         struct usb_hcd *hcd = (struct usb_hcd *)ptr;
334         struct admhcd *ahcd = hcd_to_admhcd(hcd);
335         u32 intstatus;
336
337         intstatus = admhcd_reg_get(ahcd, ADMHCD_REG_INTSTATUS);
338         if (intstatus & ADMHCD_INT_FATAL) {
339                 admhcd_reg_set(ahcd, ADMHCD_REG_INTSTATUS, ADMHCD_INT_FATAL);
340                 //
341         }
342         if (intstatus & ADMHCD_INT_SW) {
343                 admhcd_reg_set(ahcd, ADMHCD_REG_INTSTATUS, ADMHCD_INT_SW);
344                 //
345         }
346         if (intstatus & ADMHCD_INT_TD) {
347                 struct admhcd_ed *ed, *head;
348
349                 admhcd_reg_set(ahcd, ADMHCD_REG_INTSTATUS, ADMHCD_INT_TD);
350
351                 head = (struct admhcd_ed *)admhcd_reg_get(ahcd, ADMHCD_REG_HOSTHEAD);
352                 ed = head;
353                 if (ed) do {
354                         /* Is it a finished TD? */
355                         if (ed->urb && !(ed->cur->control & ADMHCD_TD_OWN)) {
356                                 struct admhcd_td *td;
357                                 int error;
358
359                                 td = ed->cur;
360                                 error = (td->control & ADMHCD_TD_ERRMASK) >>
361                                     ADMHCD_TD_ERRSHIFT;
362                                 ed->urb->status = admhcd_td_err[error];
363                                 admhcd_td_free(ed, ed->urb);
364                                 // Calculate real length!!!
365                                 ed->urb->actual_length = ed->urb->transfer_buffer_length;
366                                 ed->urb->hcpriv = NULL;
367                                 usb_hcd_giveback_urb(hcd, ed->urb);
368                                 ed->urb = NULL;
369                         }
370                         admhcd_ed_start(ahcd, ed);
371                         ed = ED(ed->next);
372                 } while (ed != head);
373         }
374
375         return IRQ_HANDLED;
376 }
377
378 static int admhcd_urb_enqueue(struct usb_hcd *hcd, struct usb_host_endpoint *ep,
379     struct urb *urb, gfp_t mem_flags)
380 {
381         struct admhcd *ahcd = hcd_to_admhcd(hcd);
382         struct admhcd_ed *ed;
383         struct admhcd_td *td;
384         int size = 0, i, zero = 0, ret = 0;
385         unsigned int pipe = urb->pipe, toggle = 0;
386         dma_addr_t data = (dma_addr_t)urb->transfer_buffer;
387         int data_len = urb->transfer_buffer_length;
388
389         ed = admhcd_get_ed(ahcd, ep, urb);
390         if (!ed)
391                 return -ENOMEM;
392
393         switch(usb_pipetype(pipe)) {
394                 case PIPE_CONTROL:
395                         size = 2;
396                 case PIPE_INTERRUPT:
397                 case PIPE_BULK:
398                 default:
399                         size += urb->transfer_buffer_length / 4096;
400                         if (urb->transfer_buffer_length % 4096)
401                                 size++;
402                         if (size == 0)
403                                 size++;
404                         else if (urb->transfer_flags & URB_ZERO_PACKET &&
405                             !(urb->transfer_buffer_length %
406                               usb_maxpacket(urb->dev, pipe, usb_pipeout(pipe)))) {
407                                 size++;
408                                 zero = 1;
409                         }
410                         break;
411                 case PIPE_ISOCHRONOUS:
412                         size = urb->number_of_packets;
413                         break;
414         }
415
416         admhcd_lock(ahcd);
417         /* Remember the first td */
418         td = admhcd_td_alloc(ed, urb);
419         if (!td) {
420                 ret = -ENOMEM;
421                 goto out;
422         }
423         /* Allocate additionall tds first */
424         for (i = 1; i < size; i++) {
425                 if (admhcd_td_alloc(ed, urb) == NULL) {
426                         admhcd_td_free(ed, urb);
427                         ret = -ENOMEM;
428                         goto out;
429                 }
430         }
431
432         if (usb_gettoggle(urb->dev, usb_pipeendpoint(pipe), usb_pipeout(pipe)))
433                 toggle = ADMHCD_TD_TOGGLE;
434         else {
435                 toggle = ADMHCD_TD_DATA0;
436                 usb_settoggle(urb->dev, usb_pipeendpoint(pipe),
437                     usb_pipeout(pipe), 1);
438         }
439
440         switch(usb_pipetype(pipe)) {
441                 case PIPE_CONTROL:
442                         td = admhcd_td_fill(ADMHCD_TD_SETUP | ADMHCD_TD_DATA0,
443                             td, (dma_addr_t)urb->setup_packet, 8);
444                         while (data_len > 0) {
445                                 td = admhcd_td_fill(ADMHCD_TD_DATA1
446                                     | ADMHCD_TD_R |
447                                     (usb_pipeout(pipe) ?
448                                     ADMHCD_TD_OUT : ADMHCD_TD_IN), td,
449                                     data, data_len % 4097);
450                                 data_len -= 4096;
451                         }
452                         admhcd_td_fill(ADMHCD_TD_DATA1 | (usb_pipeout(pipe) ?
453                             ADMHCD_TD_IN : ADMHCD_TD_OUT), td,
454                             data, 0);
455                         break;
456                 case PIPE_INTERRUPT:
457                 case PIPE_BULK:
458                         //info ok for interrupt?
459                         i = 0;
460                         while(data_len > 4096) {
461                                 td = admhcd_td_fill((usb_pipeout(pipe) ?
462                                     ADMHCD_TD_OUT :
463                                     ADMHCD_TD_IN | ADMHCD_TD_R) |
464                                     (i ? ADMHCD_TD_TOGGLE : toggle), td,
465                                     data, 4096);
466                                 data += 4096;
467                                 data_len -= 4096;
468                                 i++;
469                         }
470                         td = admhcd_td_fill((usb_pipeout(pipe) ?
471                             ADMHCD_TD_OUT : ADMHCD_TD_IN) |
472                             (i ? ADMHCD_TD_TOGGLE : toggle), td, data, data_len);
473                         i++;
474                         if (zero)
475                                 admhcd_td_fill((usb_pipeout(pipe) ?
476                                     ADMHCD_TD_OUT : ADMHCD_TD_IN) |
477                                     (i ? ADMHCD_TD_TOGGLE : toggle), td, 0, 0);
478                         break;
479                 case PIPE_ISOCHRONOUS:
480                         for (i = 0; i < urb->number_of_packets; i++) {
481                                 td = admhcd_td_fill(ADMHCD_TD_ISO |
482                                     ((urb->start_frame + i) & 0xffff), td,
483                                     data + urb->iso_frame_desc[i].offset,
484                                     urb->iso_frame_desc[i].length);
485                         }
486                         break;
487         }
488         urb->hcpriv = ed;
489         admhcd_ed_start(ahcd, ed);
490 out:
491         admhcd_unlock(ahcd);
492         return ret;
493 }
494
495 static int admhcd_urb_dequeue(struct usb_hcd *hcd, struct urb *urb)
496 {
497         struct admhcd *ahcd = hcd_to_admhcd(hcd);
498         struct admhcd_ed *ed;
499
500         admhcd_lock(ahcd);
501
502         ed = urb->hcpriv;
503         if (ed && ed->urb != urb)
504                 admhcd_td_free(ed, urb);
505
506         admhcd_unlock(ahcd);
507         return 0;
508 }
509
510 static void admhcd_endpoint_disable(struct usb_hcd *hcd, struct usb_host_endpoint *ep)
511 {
512         struct admhcd *ahcd = hcd_to_admhcd(hcd);
513         struct admhcd_ed *ed, *edt, *head;
514
515         admhcd_lock(ahcd);
516
517         head = (struct admhcd_ed *)admhcd_reg_get(ahcd, ADMHCD_REG_HOSTHEAD);
518         if (!head)
519                 goto out;
520         for (ed = head; ED(ed->next) != head; ed = ED(ed->next))
521                 if (ed->ep == ep)
522                         break;
523         if (ed->ep != ep)
524                 goto out;
525         while (ed->cur)
526                 admhcd_td_free(ed, ed->cur->urb);
527         if (head == ed) {
528                 if (ED(ed->next) == ed) {
529                         admhcd_reg_set(ahcd, ADMHCD_REG_HOSTHEAD, 0);
530                         ahcd->dma_en = 0;
531                         goto out_free;
532                 }
533                 head = ED(ed->next);
534                 for (edt = head; ED(edt->next) != head; edt = ED(edt->next));
535                 edt->next = ED(ed->next);
536                 admhcd_reg_set(ahcd, ADMHCD_REG_HOSTHEAD, (u32)ed->next);
537                 goto out_free;
538         }
539         for (edt = head; edt->next != ed; edt = edt->next);
540         edt->next = ed->next;
541 out_free:
542         kfree(ed->real);
543 out:
544         admhcd_unlock(ahcd);
545 }
546
547 static int admhcd_get_frame_number(struct usb_hcd *hcd)
548 {
549         struct admhcd *ahcd = hcd_to_admhcd(hcd);
550
551         return admhcd_reg_get(ahcd, ADMHCD_REG_FMNUMBER) & 0x0000ffff;
552 }
553
554 static int admhcd_hub_status_data(struct usb_hcd *hcd, char *buf)
555 {
556         struct admhcd *ahcd = hcd_to_admhcd(hcd);
557         int port;
558
559         *buf = 0;
560         for (port = 0; port < ADMHCD_NUMPORTS; port++) {
561                 if (admhcd_reg_get(ahcd, ADMHCD_REG_PORTSTATUS0 + port*4) &
562                     (ADMHCD_CSC | ADMHCD_PESC | ADMHCD_PSSC | ADMHCD_OCIC |
563                      ADMHCD_PRSC))
564                         *buf |= (1 << (port + 1));
565         }
566         return !!*buf;
567 }
568
569 static __u8 root_hub_hub_des[] = {
570         0x09,           /* __u8  bLength; */
571         0x29,           /* __u8  bDescriptorType; Hub-descriptor */
572         0x02,           /* __u8  bNbrPorts; */
573         0x0a, 0x00,     /* __u16 wHubCharacteristics; */
574         0x01,           /* __u8  bPwrOn2pwrGood; 2ms */
575         0x00,           /* __u8  bHubContrCurrent; 0mA */
576         0x00,           /* __u8  DeviceRemovable; */
577         0xff,           /* __u8  PortPwrCtrlMask; */
578 };
579
580 static int admhcd_hub_control(struct usb_hcd *hcd, u16 typeReq, u16 wValue,
581     u16 wIndex, char *buf, u16 wLength)
582 {
583         struct admhcd *ahcd = hcd_to_admhcd(hcd);
584         int retval = 0, len;
585         unsigned int port = wIndex -1;
586
587         switch (typeReq) {
588
589         case GetHubStatus:
590                 *(__le32 *)buf = cpu_to_le32(0);
591                 break;
592         case GetPortStatus:
593                 if (port >= ADMHCD_NUMPORTS)
594                         goto err;
595                 *(__le32 *)buf = cpu_to_le32(
596                     admhcd_reg_get(ahcd, ADMHCD_REG_PORTSTATUS0 + port*4));
597                 break;
598         case SetHubFeature:             /* We don't implement these */
599         case ClearHubFeature:
600                 switch (wValue) {
601                 case C_HUB_OVER_CURRENT:
602                 case C_HUB_LOCAL_POWER:
603                         break;
604                 default:
605                         goto err;
606                 }
607         case SetPortFeature:
608                 if (port >= ADMHCD_NUMPORTS)
609                         goto err;
610
611                 switch (wValue) {
612                 case USB_PORT_FEAT_SUSPEND:
613                         admhcd_reg_set(ahcd, ADMHCD_REG_PORTSTATUS0 + port*4,
614                             ADMHCD_PSS);
615                         break;
616                 case USB_PORT_FEAT_RESET:
617                         if (admhcd_reg_get(ahcd, ADMHCD_REG_PORTSTATUS0 + port*4)
618                             & ADMHCD_CCS) {
619                                 admhcd_reg_set(ahcd,
620                                     ADMHCD_REG_PORTSTATUS0 + port*4,
621                                     ADMHCD_PRS | ADMHCD_CSC);
622                                 mdelay(50);
623                                 admhcd_reg_set(ahcd,
624                                     ADMHCD_REG_PORTSTATUS0 + port*4,
625                                     ADMHCD_PES | ADMHCD_CSC);
626                         }
627                         break;
628                 case USB_PORT_FEAT_POWER:
629                         admhcd_reg_set(ahcd, ADMHCD_REG_PORTSTATUS0 + port*4,
630                             ADMHCD_PPS);
631                         break;
632                 default:
633                         goto err;
634                 }
635                 break;
636         case ClearPortFeature:
637                 if (port >= ADMHCD_NUMPORTS)
638                         goto err;
639
640                 switch (wValue) {
641                 case USB_PORT_FEAT_ENABLE:
642                         admhcd_reg_set(ahcd, ADMHCD_REG_PORTSTATUS0 + port*4,
643                             ADMHCD_CCS);
644                         break;
645                 case USB_PORT_FEAT_C_ENABLE:
646                         admhcd_reg_set(ahcd, ADMHCD_REG_PORTSTATUS0 + port*4,
647                             ADMHCD_PESC);
648                         break;
649                 case USB_PORT_FEAT_SUSPEND:
650                         admhcd_reg_set(ahcd, ADMHCD_REG_PORTSTATUS0 + port*4,
651                             ADMHCD_POCI);
652                         break;
653                 case USB_PORT_FEAT_C_SUSPEND:
654                         admhcd_reg_set(ahcd, ADMHCD_REG_PORTSTATUS0 + port*4,
655                             ADMHCD_PSSC);
656                 case USB_PORT_FEAT_POWER:
657                         admhcd_reg_set(ahcd, ADMHCD_REG_PORTSTATUS0 + port*4,
658                             ADMHCD_LSDA);
659                         break;
660                 case USB_PORT_FEAT_C_CONNECTION:
661                         admhcd_reg_set(ahcd, ADMHCD_REG_PORTSTATUS0 + port*4,
662                             ADMHCD_CSC);
663                         break;
664                 case USB_PORT_FEAT_C_OVER_CURRENT:
665                         admhcd_reg_set(ahcd, ADMHCD_REG_PORTSTATUS0 + port*4,
666                             ADMHCD_OCIC);
667                         break;
668                 case USB_PORT_FEAT_C_RESET:
669                         admhcd_reg_set(ahcd, ADMHCD_REG_PORTSTATUS0 + port*4,
670                             ADMHCD_PRSC);
671                         break;
672                 default:
673                         goto err;
674                 }
675                 break;
676         case GetHubDescriptor:
677                 len = min_t(unsigned int, sizeof(root_hub_hub_des), wLength);
678                 memcpy(buf, root_hub_hub_des, len);
679                 break;
680         default:
681 err:
682                 retval = -EPIPE;
683         }
684
685         return retval;
686 }
687
688 static struct hc_driver adm5120_hc_driver = {
689         .description =          hcd_name,
690         .product_desc =         "ADM5120 HCD",
691         .hcd_priv_size =        sizeof(struct admhcd),
692         .flags =                HCD_USB11,
693         .urb_enqueue =          admhcd_urb_enqueue,
694         .urb_dequeue =          admhcd_urb_dequeue,
695         .endpoint_disable =     admhcd_endpoint_disable,
696         .get_frame_number =     admhcd_get_frame_number,
697         .hub_status_data =      admhcd_hub_status_data,
698         .hub_control =          admhcd_hub_control,
699 };
700
701 #define resource_len(r) (((r)->end - (r)->start) + 1)
702
703 static int __init adm5120hcd_probe(struct platform_device *pdev)
704 {
705         struct usb_hcd *hcd;
706         struct admhcd *ahcd;
707         struct resource *addr, *data;
708         void __iomem *addr_reg;
709         void __iomem *data_reg;
710         int irq, err = 0;
711
712         if (pdev->num_resources < 3) {
713                 err = -ENODEV;
714                 goto out;
715         }
716
717         data = platform_get_resource(pdev, IORESOURCE_MEM, 0);
718         addr = platform_get_resource(pdev, IORESOURCE_MEM, 1);
719
720         if (request_irq(data.start, adm5120hcd_irq, 0, hcd_name, hcd)) {
721                 printk(KERN_WARNING "Could not request IRQ\n");
722                 err = -EBUSY;
723                 goto out;
724         }
725
726         if (!addr || !data || irq < 0) {
727                 err = -ENODEV;
728                 goto out;
729         }
730
731         if (pdev->dev.dma_mask) {
732                 printk(KERN_DEBUG "DMA not supported\n");
733                 err = -EINVAL;
734                 goto out;
735         }
736
737         if (!request_mem_region(addr->start, 2, hcd_name)) {
738                 err = -EBUSY;
739                 goto out;
740         }
741         addr_reg = ioremap(addr->start, resource_len(addr));
742         if (addr_reg == NULL) {
743                 err = -ENOMEM;
744                 goto out_mem;
745         }
746         if (!request_mem_region(data->start, 2, hcd_name)) {
747                 err = -EBUSY;
748                 goto out_unmap;
749         }
750         data_reg = ioremap(data->start, resource_len(data));
751         if (data_reg == NULL) {
752                 err = -ENOMEM;
753                 goto out_mem;
754         }
755
756
757         hcd = usb_create_hcd(&adm5120_hc_driver, &pdev->dev, pdev->dev.bus_id);
758         if (!hcd)
759                 goto out_mem;
760
761         ahcd = hcd_to_admhcd(hcd);
762         ahcd->data_reg = data_reg;
763         ahcd->addr_reg = addr_reg;
764         spin_lock_init(&ahcd->lock);
765         INIT_LIST_HEAD(&ahcd->async);
766
767         /* Initialise the HCD registers */
768         admhcd_reg_set(ahcd, ADMHCD_REG_INTENABLE, 0);
769         mdelay(10);
770         admhcd_reg_set(ahcd, ADMHCD_REG_CONTROL, ADMHCD_SW_RESET);
771         while (admhcd_reg_get(ahcd, ADMHCD_REG_CONTROL) & ADMHCD_SW_RESET)
772                 mdelay(1);
773
774         admhcd_reg_set(ahcd, ADMHCD_REG_CONTROL, ADMHCD_HOST_EN);
775         admhcd_reg_set(ahcd, ADMHCD_REG_HOSTHEAD, 0x00000000);
776         admhcd_reg_set(ahcd, ADMHCD_REG_FMINTERVAL, 0x20002edf);
777         admhcd_reg_set(ahcd, ADMHCD_REG_LSTHRESH, 0x628);
778         admhcd_reg_set(ahcd, ADMHCD_REG_INTENABLE,
779             ADMHCD_INT_ACT | ADMHCD_INT_FATAL | ADMHCD_INT_SW | ADMHCD_INT_TD);
780         admhcd_reg_set(ahcd, ADMHCD_REG_INTSTATUS,
781             ADMHCD_INT_ACT | ADMHCD_INT_FATAL | ADMHCD_INT_SW | ADMHCD_INT_TD);
782         admhcd_reg_set(ahcd, ADMHCD_REG_RHDESCR, ADMHCD_NPS | ADMHCD_LPSC);
783         admhcd_reg_set(ahcd, ADMHCD_REG_HOSTCONTROL, ADMHCD_STATE_OP);
784
785         err = usb_add_hcd(hcd, irq, IRQF_DISABLED);
786         if (err)
787                 goto out_dev;
788
789         return 0;
790
791 out_dev:
792         usb_put_hcd(hcd);
793 out_unmap:
794         iounmap(addr_reg);
795 out_mem:
796         release_mem_region(addr->start, 2);
797 out:
798         return err;
799 }
800
801 static int __init_or_module adm5120hcd_remove(struct platform_device *pdev)
802 {
803         struct usb_hcd *hcd = platform_get_drvdata(pdev);
804         struct admhcd *ahcd;
805
806         if (!hcd)
807                 return 0;
808         ahcd = hcd_to_admhcd(hcd);
809         usb_remove_hcd(hcd);
810
811         usb_put_hcd(hcd);
812         return 0;
813 }
814
815 static struct platform_driver adm5120hcd_driver = {
816         .probe =        adm5120hcd_probe,
817         .remove =       adm5120hcd_remove,
818         .driver =       {
819                 .name   = "adm5120-hcd",
820                 .owner  = THIS_MODULE,
821         },
822 };
823
824 static int __init adm5120hcd_init(void)
825 {
826         if (usb_disabled())
827                 return -ENODEV;
828         if (!adm5120_board.has_usb)
829                 return -ENODEV;
830
831         return platform_driver_register(&adm5120hcd_driver);
832 }
833
834 static void __exit adm5120hcd_exit(void)
835 {
836         platform_driver_unregister(&adm5120hcd_driver);
837 }
838
839 module_init(adm5120hcd_init);
840 module_exit(adm5120hcd_exit);