1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36#include <common.h>
37
38
39#if defined(CONFIG_USB_OHCI) && defined(CONFIG_S3C24X0)
40
41#include <asm/arch/s3c24x0_cpu.h>
42#include <asm/io.h>
43#include <malloc.h>
44#include <usb.h>
45#include "usb_ohci.h"
46
47#define OHCI_USE_NPS
48#undef OHCI_VERBOSE_DEBUG
49
50
51
52#define OHCI_CONTROL_INIT \
53 (OHCI_CTRL_CBSR & 0x3) | OHCI_CTRL_IE | OHCI_CTRL_PLE
54
55#define min_t(type, x, y) \
56 ({ type __x = (x); type __y = (y); __x < __y ? __x : __y; })
57
58#undef DEBUG
59#ifdef DEBUG
60#define dbg(format, arg...) printf("DEBUG: " format "\n", ## arg)
61#else
62#define dbg(format, arg...) do {} while(0)
63#endif
64#define err(format, arg...) printf("ERROR: " format "\n", ## arg)
65#undef SHOW_INFO
66#ifdef SHOW_INFO
67#define info(format, arg...) printf("INFO: " format "\n", ## arg)
68#else
69#define info(format, arg...) do {} while(0)
70#endif
71
72#define m16_swap(x) swap_16(x)
73#define m32_swap(x) swap_32(x)
74
75
76static struct ohci gohci;
77
78struct ohci_hcca ghcca[1];
79
80struct ohci_hcca *phcca;
81
82struct ohci_device ohci_dev;
83
84struct urb_priv urb_priv;
85
86int got_rhsc;
87
88struct usb_device *devgone;
89
90int urb_finished = 0;
91
92
93
94
95
96
97
98#define OHCI_QUIRK_AMD756 0xabcd
99#define read_roothub(hc, register, mask) ({ \
100 u32 temp = readl (&hc->regs->roothub.register); \
101 if (hc->flags & OHCI_QUIRK_AMD756) \
102 while (temp & mask) \
103 temp = readl (&hc->regs->roothub.register); \
104 temp; })
105
106static u32 roothub_a(struct ohci *hc)
107{
108 return read_roothub(hc, a, 0xfc0fe000);
109}
110static inline u32 roothub_b(struct ohci *hc)
111{
112 return readl(&hc->regs->roothub.b);
113}
114static inline u32 roothub_status(struct ohci *hc)
115{
116 return readl(&hc->regs->roothub.status);
117}
118static u32 roothub_portstatus(struct ohci *hc, int i)
119{
120 return read_roothub(hc, portstatus[i], 0xffe0fce0);
121}
122
123
124static int hc_interrupt(void);
125static void td_submit_job(struct usb_device *dev, unsigned long pipe,
126 void *buffer, int transfer_len,
127 struct devrequest *setup, struct urb_priv *urb,
128 int interval);
129
130
131
132
133
134
135
136static void urb_free_priv(struct urb_priv *urb)
137{
138 int i;
139 int last;
140 struct td *td;
141
142 last = urb->length - 1;
143 if (last >= 0) {
144 for (i = 0; i <= last; i++) {
145 td = urb->td[i];
146 if (td) {
147 td->usb_dev = NULL;
148 urb->td[i] = NULL;
149 }
150 }
151 }
152}
153
154
155
156#ifdef DEBUG
157static int sohci_get_current_frame_number(struct usb_device *dev);
158
159
160
161
162static void pkt_print(struct usb_device *dev, unsigned long pipe, void *buffer,
163 int transfer_len, struct devrequest *setup, char *str,
164 int small)
165{
166 struct urb_priv *purb = &urb_priv;
167
168 dbg("%s URB:[%4x] dev:%2d,ep:%2d-%c,type:%s,len:%d/%d stat:%#lx",
169 str,
170 sohci_get_current_frame_number(dev),
171 usb_pipedevice(pipe),
172 usb_pipeendpoint(pipe),
173 usb_pipeout(pipe) ? 'O' : 'I',
174 usb_pipetype(pipe) < 2 ?
175 (usb_pipeint(pipe) ? "INTR" : "ISOC") :
176 (usb_pipecontrol(pipe) ? "CTRL" : "BULK"),
177 purb->actual_length, transfer_len, dev->status);
178#ifdef OHCI_VERBOSE_DEBUG
179 if (!small) {
180 int i, len;
181
182 if (usb_pipecontrol(pipe)) {
183 printf(__FILE__ ": cmd(8):");
184 for (i = 0; i < 8; i++)
185 printf(" %02x", ((__u8 *) setup)[i]);
186 printf("\n");
187 }
188 if (transfer_len > 0 && buffer) {
189 printf(__FILE__ ": data(%d/%d):",
190 purb->actual_length, transfer_len);
191 len = usb_pipeout(pipe) ?
192 transfer_len : purb->actual_length;
193 for (i = 0; i < 16 && i < len; i++)
194 printf(" %02x", ((__u8 *) buffer)[i]);
195 printf("%s\n", i < len ? "..." : "");
196 }
197 }
198#endif
199}
200
201
202
203void ep_print_int_eds(struct ohci *ohci, char *str)
204{
205 int i, j;
206 __u32 *ed_p;
207 for (i = 0; i < 32; i++) {
208 j = 5;
209 ed_p = &(ohci->hcca->int_table[i]);
210 if (*ed_p == 0)
211 continue;
212 printf(__FILE__ ": %s branch int %2d(%2x):", str, i, i);
213 while (*ed_p != 0 && j--) {
214 struct ed *ed = (struct ed *) m32_swap(ed_p);
215 printf(" ed: %4x;", ed->hwINFO);
216 ed_p = &ed->hwNextED;
217 }
218 printf("\n");
219 }
220}
221
222static void ohci_dump_intr_mask(char *label, __u32 mask)
223{
224 dbg("%s: 0x%08x%s%s%s%s%s%s%s%s%s",
225 label,
226 mask,
227 (mask & OHCI_INTR_MIE) ? " MIE" : "",
228 (mask & OHCI_INTR_OC) ? " OC" : "",
229 (mask & OHCI_INTR_RHSC) ? " RHSC" : "",
230 (mask & OHCI_INTR_FNO) ? " FNO" : "",
231 (mask & OHCI_INTR_UE) ? " UE" : "",
232 (mask & OHCI_INTR_RD) ? " RD" : "",
233 (mask & OHCI_INTR_SF) ? " SF" : "",
234 (mask & OHCI_INTR_WDH) ? " WDH" : "",
235 (mask & OHCI_INTR_SO) ? " SO" : "");
236}
237
238static void maybe_print_eds(char *label, __u32 value)
239{
240 struct ed *edp = (struct ed *) value;
241
242 if (value) {
243 dbg("%s %08x", label, value);
244 dbg("%08x", edp->hwINFO);
245 dbg("%08x", edp->hwTailP);
246 dbg("%08x", edp->hwHeadP);
247 dbg("%08x", edp->hwNextED);
248 }
249}
250
251static char *hcfs2string(int state)
252{
253 switch (state) {
254 case OHCI_USB_RESET:
255 return "reset";
256 case OHCI_USB_RESUME:
257 return "resume";
258 case OHCI_USB_OPER:
259 return "operational";
260 case OHCI_USB_SUSPEND:
261 return "suspend";
262 }
263 return "?";
264}
265
266
267static void ohci_dump_status(struct ohci *controller)
268{
269 struct ohci_regs *regs = controller->regs;
270 __u32 temp;
271
272 temp = readl(®s->revision) & 0xff;
273 if (temp != 0x10)
274 dbg("spec %d.%d", (temp >> 4), (temp & 0x0f));
275
276 temp = readl(®s->control);
277 dbg("control: 0x%08x%s%s%s HCFS=%s%s%s%s%s CBSR=%d", temp,
278 (temp & OHCI_CTRL_RWE) ? " RWE" : "",
279 (temp & OHCI_CTRL_RWC) ? " RWC" : "",
280 (temp & OHCI_CTRL_IR) ? " IR" : "",
281 hcfs2string(temp & OHCI_CTRL_HCFS),
282 (temp & OHCI_CTRL_BLE) ? " BLE" : "",
283 (temp & OHCI_CTRL_CLE) ? " CLE" : "",
284 (temp & OHCI_CTRL_IE) ? " IE" : "",
285 (temp & OHCI_CTRL_PLE) ? " PLE" : "", temp & OHCI_CTRL_CBSR);
286
287 temp = readl(®s->cmdstatus);
288 dbg("cmdstatus: 0x%08x SOC=%d%s%s%s%s", temp,
289 (temp & OHCI_SOC) >> 16,
290 (temp & OHCI_OCR) ? " OCR" : "",
291 (temp & OHCI_BLF) ? " BLF" : "",
292 (temp & OHCI_CLF) ? " CLF" : "", (temp & OHCI_HCR) ? " HCR" : "");
293
294 ohci_dump_intr_mask("intrstatus", readl(®s->intrstatus));
295 ohci_dump_intr_mask("intrenable", readl(®s->intrenable));
296
297 maybe_print_eds("ed_periodcurrent", readl(®s->ed_periodcurrent));
298
299 maybe_print_eds("ed_controlhead", readl(®s->ed_controlhead));
300 maybe_print_eds("ed_controlcurrent", readl(®s->ed_controlcurrent));
301
302 maybe_print_eds("ed_bulkhead", readl(®s->ed_bulkhead));
303 maybe_print_eds("ed_bulkcurrent", readl(®s->ed_bulkcurrent));
304
305 maybe_print_eds("donehead", readl(®s->donehead));
306}
307
308static void ohci_dump_roothub(struct ohci *controller, int verbose)
309{
310 __u32 temp, ndp, i;
311
312 temp = roothub_a(controller);
313 ndp = (temp & RH_A_NDP);
314
315 if (verbose) {
316 dbg("roothub.a: %08x POTPGT=%d%s%s%s%s%s NDP=%d", temp,
317 ((temp & RH_A_POTPGT) >> 24) & 0xff,
318 (temp & RH_A_NOCP) ? " NOCP" : "",
319 (temp & RH_A_OCPM) ? " OCPM" : "",
320 (temp & RH_A_DT) ? " DT" : "",
321 (temp & RH_A_NPS) ? " NPS" : "",
322 (temp & RH_A_PSM) ? " PSM" : "", ndp);
323 temp = roothub_b(controller);
324 dbg("roothub.b: %08x PPCM=%04x DR=%04x",
325 temp, (temp & RH_B_PPCM) >> 16, (temp & RH_B_DR)
326 );
327 temp = roothub_status(controller);
328 dbg("roothub.status: %08x%s%s%s%s%s%s",
329 temp,
330 (temp & RH_HS_CRWE) ? " CRWE" : "",
331 (temp & RH_HS_OCIC) ? " OCIC" : "",
332 (temp & RH_HS_LPSC) ? " LPSC" : "",
333 (temp & RH_HS_DRWE) ? " DRWE" : "",
334 (temp & RH_HS_OCI) ? " OCI" : "",
335 (temp & RH_HS_LPS) ? " LPS" : "");
336 }
337
338 for (i = 0; i < ndp; i++) {
339 temp = roothub_portstatus(controller, i);
340 dbg("roothub.portstatus [%d] = 0x%08x%s%s%s%s%s%s%s%s%s%s%s%s",
341 i,
342 temp,
343 (temp & RH_PS_PRSC) ? " PRSC" : "",
344 (temp & RH_PS_OCIC) ? " OCIC" : "",
345 (temp & RH_PS_PSSC) ? " PSSC" : "",
346 (temp & RH_PS_PESC) ? " PESC" : "",
347 (temp & RH_PS_CSC) ? " CSC" : "",
348 (temp & RH_PS_LSDA) ? " LSDA" : "",
349 (temp & RH_PS_PPS) ? " PPS" : "",
350 (temp & RH_PS_PRS) ? " PRS" : "",
351 (temp & RH_PS_POCI) ? " POCI" : "",
352 (temp & RH_PS_PSS) ? " PSS" : "",
353 (temp & RH_PS_PES) ? " PES" : "",
354 (temp & RH_PS_CCS) ? " CCS" : "");
355 }
356}
357
358static void ohci_dump(struct ohci *controller, int verbose)
359{
360 dbg("OHCI controller usb-%s state", controller->slot_name);
361
362
363 ohci_dump_status(controller);
364 if (verbose)
365 ep_print_int_eds(controller, "hcca");
366 dbg("hcca frame #%04x", controller->hcca->frame_no);
367 ohci_dump_roothub(controller, 1);
368}
369
370#endif
371
372
373
374
375
376
377
378int sohci_submit_job(struct usb_device *dev, unsigned long pipe, void *buffer,
379 int transfer_len, struct devrequest *setup, int interval)
380{
381 struct ohci *ohci;
382 struct ed *ed;
383 struct urb_priv *purb_priv;
384 int i, size = 0;
385
386 ohci = &gohci;
387
388
389
390 if (ohci->disabled) {
391 err("sohci_submit_job: EPIPE");
392 return -1;
393 }
394
395
396
397
398 if (!urb_finished) {
399 err("sohci_submit_job: URB NOT FINISHED");
400 return -1;
401 }
402
403
404 urb_finished = 0;
405
406
407 ed = ep_add_ed(dev, pipe);
408 if (!ed) {
409 err("sohci_submit_job: ENOMEM");
410 return -1;
411 }
412
413
414 switch (usb_pipetype(pipe)) {
415 case PIPE_BULK:
416
417 size = (transfer_len - 1) / 4096 + 1;
418 break;
419 case PIPE_CONTROL:
420
421 size = (transfer_len == 0) ? 2 : (transfer_len - 1) / 4096 + 3;
422 break;
423 }
424
425 if (size >= (N_URB_TD - 1)) {
426 err("need %d TDs, only have %d", size, N_URB_TD);
427 return -1;
428 }
429 purb_priv = &urb_priv;
430 purb_priv->pipe = pipe;
431
432
433 purb_priv->length = size;
434 purb_priv->ed = ed;
435 purb_priv->actual_length = 0;
436
437
438
439 for (i = 0; i < size; i++) {
440 purb_priv->td[i] = td_alloc(dev);
441 if (!purb_priv->td[i]) {
442 purb_priv->length = i;
443 urb_free_priv(purb_priv);
444 err("sohci_submit_job: ENOMEM");
445 return -1;
446 }
447 }
448
449 if (ed->state == ED_NEW || (ed->state & ED_DEL)) {
450 urb_free_priv(purb_priv);
451 err("sohci_submit_job: EINVAL");
452 return -1;
453 }
454
455
456 if (ed->state != ED_OPER)
457 ep_link(ohci, ed);
458
459
460 td_submit_job(dev, pipe, buffer, transfer_len, setup, purb_priv,
461 interval);
462
463 return 0;
464}
465
466
467
468#ifdef DEBUG
469
470
471static int sohci_get_current_frame_number(struct usb_device *usb_dev)
472{
473 struct ohci *ohci = &gohci;
474
475 return m16_swap(ohci->hcca->frame_no);
476}
477#endif
478
479
480
481
482
483
484
485static int ep_link(struct ohci *ohci, struct ed *edi)
486{
487 struct ed *ed = edi;
488
489 ed->state = ED_OPER;
490
491 switch (ed->type) {
492 case PIPE_CONTROL:
493 ed->hwNextED = 0;
494 if (ohci->ed_controltail == NULL) {
495 writel((u32)ed, &ohci->regs->ed_controlhead);
496 } else {
497 ohci->ed_controltail->hwNextED = (__u32) m32_swap(ed);
498 }
499 ed->ed_prev = ohci->ed_controltail;
500 if (!ohci->ed_controltail && !ohci->ed_rm_list[0] &&
501 !ohci->ed_rm_list[1] && !ohci->sleeping) {
502 ohci->hc_control |= OHCI_CTRL_CLE;
503 writel(ohci->hc_control, &ohci->regs->control);
504 }
505 ohci->ed_controltail = edi;
506 break;
507
508 case PIPE_BULK:
509 ed->hwNextED = 0;
510 if (ohci->ed_bulktail == NULL) {
511 writel((u32)ed, &ohci->regs->ed_bulkhead);
512 } else {
513 ohci->ed_bulktail->hwNextED = (__u32) m32_swap(ed);
514 }
515 ed->ed_prev = ohci->ed_bulktail;
516 if (!ohci->ed_bulktail && !ohci->ed_rm_list[0] &&
517 !ohci->ed_rm_list[1] && !ohci->sleeping) {
518 ohci->hc_control |= OHCI_CTRL_BLE;
519 writel(ohci->hc_control, &ohci->regs->control);
520 }
521 ohci->ed_bulktail = edi;
522 break;
523 }
524 return 0;
525}
526
527
528
529
530
531
532
533
534static int ep_unlink(struct ohci *ohci, struct ed *ed)
535{
536 struct ed *next;
537 ed->hwINFO |= m32_swap(OHCI_ED_SKIP);
538
539 switch (ed->type) {
540 case PIPE_CONTROL:
541 if (ed->ed_prev == NULL) {
542 if (!ed->hwNextED) {
543 ohci->hc_control &= ~OHCI_CTRL_CLE;
544 writel(ohci->hc_control, &ohci->regs->control);
545 }
546 writel(m32_swap(*((__u32 *) &ed->hwNextED)),
547 &ohci->regs->ed_controlhead);
548 } else {
549 ed->ed_prev->hwNextED = ed->hwNextED;
550 }
551 if (ohci->ed_controltail == ed) {
552 ohci->ed_controltail = ed->ed_prev;
553 } else {
554 next = (struct ed *)m32_swap(*((__u32 *)&ed->hwNextED));
555 next->ed_prev = ed->ed_prev;
556 }
557 break;
558
559 case PIPE_BULK:
560 if (ed->ed_prev == NULL) {
561 if (!ed->hwNextED) {
562 ohci->hc_control &= ~OHCI_CTRL_BLE;
563 writel(ohci->hc_control, &ohci->regs->control);
564 }
565 writel(m32_swap(*((__u32 *) &ed->hwNextED)),
566 &ohci->regs->ed_bulkhead);
567 } else {
568 ed->ed_prev->hwNextED = ed->hwNextED;
569 }
570 if (ohci->ed_bulktail == ed) {
571 ohci->ed_bulktail = ed->ed_prev;
572 } else {
573 next = (struct ed *)m32_swap(*((__u32 *)&ed->hwNextED));
574 next->ed_prev = ed->ed_prev;
575 }
576 break;
577 }
578 ed->state = ED_UNLINK;
579 return 0;
580}
581
582
583
584
585
586
587
588
589
590
591static struct ed *ep_add_ed(struct usb_device *usb_dev, unsigned long pipe)
592{
593 struct td *td;
594 struct ed *ed_ret;
595 struct ed *ed;
596
597 ed = ed_ret = &ohci_dev.ed[(usb_pipeendpoint(pipe) << 1) |
598 (usb_pipecontrol(pipe) ? 0 :
599 usb_pipeout(pipe))];
600
601 if ((ed->state & ED_DEL) || (ed->state & ED_URB_DEL)) {
602 err("ep_add_ed: pending delete");
603
604 return NULL;
605 }
606
607 if (ed->state == ED_NEW) {
608 ed->hwINFO = m32_swap(OHCI_ED_SKIP);
609
610 td = td_alloc(usb_dev);
611 ed->hwTailP = (__u32) m32_swap(td);
612 ed->hwHeadP = ed->hwTailP;
613 ed->state = ED_UNLINK;
614 ed->type = usb_pipetype(pipe);
615 ohci_dev.ed_cnt++;
616 }
617
618 ed->hwINFO = m32_swap(usb_pipedevice(pipe)
619 | usb_pipeendpoint(pipe) << 7
620 | (usb_pipeisoc(pipe) ? 0x8000 : 0)
621 | (usb_pipecontrol(pipe) ? 0 :
622 (usb_pipeout(pipe) ? 0x800 : 0x1000))
623 | usb_pipeslow(pipe) << 13 |
624 usb_maxpacket(usb_dev, pipe) << 16);
625
626 return ed_ret;
627}
628
629
630
631
632
633
634
635static void td_fill(struct ohci *ohci, unsigned int info, void *data, int len,
636 struct usb_device *dev, int index,
637 struct urb_priv *urb_priv)
638{
639 struct td *td, *td_pt;
640#ifdef OHCI_FILL_TRACE
641 int i;
642#endif
643
644 if (index > urb_priv->length) {
645 err("index > length");
646 return;
647 }
648
649 td_pt = urb_priv->td[index];
650 td_pt->hwNextTD = 0;
651
652
653 td = urb_priv->td[index] =
654 (struct td *) (m32_swap(urb_priv->ed->hwTailP) & ~0xf);
655
656 td->ed = urb_priv->ed;
657 td->next_dl_td = NULL;
658 td->index = index;
659 td->data = (__u32) data;
660#ifdef OHCI_FILL_TRACE
661 if (usb_pipebulk(urb_priv->pipe) && usb_pipeout(urb_priv->pipe)) {
662 for (i = 0; i < len; i++)
663 printf("td->data[%d] %#2x ", i,
664 ((unsigned char *)td->data)[i]);
665 printf("\n");
666 }
667#endif
668 if (!len)
669 data = 0;
670
671 td->hwINFO = (__u32) m32_swap(info);
672 td->hwCBP = (__u32) m32_swap(data);
673 if (data)
674 td->hwBE = (__u32) m32_swap(data + len - 1);
675 else
676 td->hwBE = 0;
677 td->hwNextTD = (__u32) m32_swap(td_pt);
678
679
680 td->ed->hwTailP = td->hwNextTD;
681}
682
683
684
685
686
687static void td_submit_job(struct usb_device *dev, unsigned long pipe,
688 void *buffer, int transfer_len,
689 struct devrequest *setup, struct urb_priv *urb,
690 int interval)
691{
692 struct ohci *ohci = &gohci;
693 int data_len = transfer_len;
694 void *data;
695 int cnt = 0;
696 __u32 info = 0;
697 unsigned int toggle = 0;
698
699
700
701 if (usb_gettoggle(dev, usb_pipeendpoint(pipe), usb_pipeout(pipe))) {
702 toggle = TD_T_TOGGLE;
703 } else {
704 toggle = TD_T_DATA0;
705 usb_settoggle(dev, usb_pipeendpoint(pipe), usb_pipeout(pipe),
706 1);
707 }
708 urb->td_cnt = 0;
709 if (data_len)
710 data = buffer;
711 else
712 data = 0;
713
714 switch (usb_pipetype(pipe)) {
715 case PIPE_BULK:
716 info = usb_pipeout(pipe) ? TD_CC | TD_DP_OUT : TD_CC | TD_DP_IN;
717 while (data_len > 4096) {
718 td_fill(ohci, info | (cnt ? TD_T_TOGGLE : toggle), data,
719 4096, dev, cnt, urb);
720 data += 4096;
721 data_len -= 4096;
722 cnt++;
723 }
724 info = usb_pipeout(pipe) ?
725 TD_CC | TD_DP_OUT :
726 TD_CC | TD_R | TD_DP_IN;
727 td_fill(ohci, info | (cnt ? TD_T_TOGGLE : toggle), data,
728 data_len, dev, cnt, urb);
729 cnt++;
730
731 if (!ohci->sleeping)
732
733 writel(OHCI_BLF, &ohci->regs->cmdstatus);
734 break;
735
736 case PIPE_CONTROL:
737 info = TD_CC | TD_DP_SETUP | TD_T_DATA0;
738 td_fill(ohci, info, setup, 8, dev, cnt++, urb);
739 if (data_len > 0) {
740 info = usb_pipeout(pipe) ?
741 TD_CC | TD_R | TD_DP_OUT | TD_T_DATA1 :
742 TD_CC | TD_R | TD_DP_IN | TD_T_DATA1;
743
744 td_fill(ohci, info, data, data_len, dev, cnt++, urb);
745 }
746 info = usb_pipeout(pipe) ?
747 TD_CC | TD_DP_IN | TD_T_DATA1 :
748 TD_CC | TD_DP_OUT | TD_T_DATA1;
749 td_fill(ohci, info, data, 0, dev, cnt++, urb);
750 if (!ohci->sleeping)
751
752 writel(OHCI_CLF, &ohci->regs->cmdstatus);
753 break;
754 }
755 if (urb->length != cnt)
756 dbg("TD LENGTH %d != CNT %d", urb->length, cnt);
757}
758
759
760
761
762
763
764
765
766static void dl_transfer_length(struct td *td)
767{
768 __u32 tdINFO, tdBE, tdCBP;
769 struct urb_priv *lurb_priv = &urb_priv;
770
771 tdINFO = m32_swap(td->hwINFO);
772 tdBE = m32_swap(td->hwBE);
773 tdCBP = m32_swap(td->hwCBP);
774
775 if (!(usb_pipecontrol(lurb_priv->pipe) &&
776 ((td->index == 0) || (td->index == lurb_priv->length - 1)))) {
777 if (tdBE != 0) {
778 if (td->hwCBP == 0)
779 lurb_priv->actual_length += tdBE - td->data + 1;
780 else
781 lurb_priv->actual_length += tdCBP - td->data;
782 }
783 }
784}
785
786
787
788
789
790
791static struct td *dl_reverse_done_list(struct ohci *ohci)
792{
793 __u32 td_list_hc;
794 __u32 tmp;
795 struct td *td_rev = NULL;
796 struct td *td_list = NULL;
797 struct urb_priv *lurb_priv = NULL;
798
799 td_list_hc = m32_swap(ohci->hcca->done_head) & 0xfffffff0;
800 ohci->hcca->done_head = 0;
801
802 while (td_list_hc) {
803 td_list = (struct td *) td_list_hc;
804
805 if (TD_CC_GET(m32_swap(td_list->hwINFO))) {
806 lurb_priv = &urb_priv;
807 dbg(" USB-error/status: %x : %p",
808 TD_CC_GET(m32_swap(td_list->hwINFO)), td_list);
809 if (td_list->ed->hwHeadP & m32_swap(0x1)) {
810 if (lurb_priv &&
811 ((td_list->index+1) < lurb_priv->length)) {
812 tmp = lurb_priv->length - 1;
813 td_list->ed->hwHeadP =
814 (lurb_priv->td[tmp]->hwNextTD &
815 m32_swap(0xfffffff0)) |
816 (td_list->ed->hwHeadP &
817 m32_swap(0x2));
818 lurb_priv->td_cnt += lurb_priv->length -
819 td_list->index - 1;
820 } else
821 td_list->ed->hwHeadP &=
822 m32_swap(0xfffffff2);
823 }
824 }
825
826 td_list->next_dl_td = td_rev;
827 td_rev = td_list;
828 td_list_hc = m32_swap(td_list->hwNextTD) & 0xfffffff0;
829 }
830
831 return td_list;
832}
833
834
835
836
837static int dl_done_list(struct ohci *ohci, struct td *td_list)
838{
839 struct td *td_list_next = NULL;
840 struct ed *ed;
841 int cc = 0;
842 int stat = 0;
843
844 struct urb_priv *lurb_priv;
845 __u32 tdINFO, edHeadP, edTailP;
846
847 while (td_list) {
848 td_list_next = td_list->next_dl_td;
849
850 lurb_priv = &urb_priv;
851 tdINFO = m32_swap(td_list->hwINFO);
852
853 ed = td_list->ed;
854
855 dl_transfer_length(td_list);
856
857
858 cc = TD_CC_GET(tdINFO);
859 if (cc != 0) {
860 dbg("ConditionCode %#x", cc);
861 stat = cc_to_error[cc];
862 }
863
864
865
866 if (++(lurb_priv->td_cnt) == lurb_priv->length) {
867 if ((ed->state & (ED_OPER | ED_UNLINK)))
868 urb_finished = 1;
869 else
870 dbg("dl_done_list: strange.., ED state %x, "
871 "ed->state\n");
872 } else
873 dbg("dl_done_list: processing TD %x, len %x\n",
874 lurb_priv->td_cnt, lurb_priv->length);
875
876 if (ed->state != ED_NEW) {
877 edHeadP = m32_swap(ed->hwHeadP) & 0xfffffff0;
878 edTailP = m32_swap(ed->hwTailP);
879
880
881 if ((edHeadP == edTailP) && (ed->state == ED_OPER))
882 ep_unlink(ohci, ed);
883 }
884
885 td_list = td_list_next;
886 }
887 return stat;
888}
889
890
891
892
893
894
895static __u8 root_hub_dev_des[] = {
896 0x12,
897 0x01,
898 0x10,
899 0x01,
900 0x09,
901 0x00,
902 0x00,
903 0x08,
904 0x00,
905 0x00,
906 0x00,
907 0x00,
908 0x00,
909 0x00,
910 0x00,
911 0x01,
912 0x00,
913 0x01
914};
915
916
917static __u8 root_hub_config_des[] = {
918 0x09,
919 0x02,
920 0x19,
921 0x00,
922 0x01,
923 0x01,
924 0x00,
925 0x40,
926
927
928 0x00,
929
930
931 0x09,
932 0x04,
933 0x00,
934 0x00,
935 0x01,
936 0x09,
937 0x00,
938 0x00,
939 0x00,
940
941
942 0x07,
943 0x05,
944 0x81,
945 0x03,
946 0x02,
947 0x00,
948 0xff
949};
950
951static unsigned char root_hub_str_index0[] = {
952 0x04,
953 0x03,
954 0x09,
955 0x04,
956};
957
958static unsigned char root_hub_str_index1[] = {
959 28,
960 0x03,
961 'O',
962 0,
963 'H',
964 0,
965 'C',
966 0,
967 'I',
968 0,
969 ' ',
970 0,
971 'R',
972 0,
973 'o',
974 0,
975 'o',
976 0,
977 't',
978 0,
979 ' ',
980 0,
981 'H',
982 0,
983 'u',
984 0,
985 'b',
986 0,
987};
988
989
990
991
992
993
994#define OK(x) len = (x); break
995#ifdef DEBUG
996#define WR_RH_STAT(x) \
997{ \
998 info("WR:status %#8x", (x)); \
999 writel((x), &gohci.regs->roothub.status); \
1000}
1001#define WR_RH_PORTSTAT(x) \
1002{ \
1003 info("WR:portstatus[%d] %#8x", wIndex-1, (x)); \
1004 writel((x), &gohci.regs->roothub.portstatus[wIndex-1]); \
1005}
1006#else
1007#define WR_RH_STAT(x) \
1008 writel((x), &gohci.regs->roothub.status)
1009#define WR_RH_PORTSTAT(x)\
1010 writel((x), &gohci.regs->roothub.portstatus[wIndex-1])
1011#endif
1012#define RD_RH_STAT roothub_status(&gohci)
1013#define RD_RH_PORTSTAT roothub_portstatus(&gohci, wIndex-1)
1014
1015
1016
1017int rh_check_port_status(struct ohci *controller)
1018{
1019 __u32 temp, ndp, i;
1020 int res;
1021
1022 res = -1;
1023 temp = roothub_a(controller);
1024 ndp = (temp & RH_A_NDP);
1025 for (i = 0; i < ndp; i++) {
1026 temp = roothub_portstatus(controller, i);
1027
1028 if (((temp & (RH_PS_PESC | RH_PS_CSC)) ==
1029 (RH_PS_PESC | RH_PS_CSC)) && ((temp & RH_PS_CCS) == 0)) {
1030 res = i;
1031 break;
1032 }
1033 }
1034 return res;
1035}
1036
1037static int ohci_submit_rh_msg(struct usb_device *dev, unsigned long pipe,
1038 void *buffer, int transfer_len,
1039 struct devrequest *cmd)
1040{
1041 void *data = buffer;
1042 int leni = transfer_len;
1043 int len = 0;
1044 int stat = 0;
1045 __u32 datab[4];
1046 __u8 *data_buf = (__u8 *) datab;
1047 __u16 bmRType_bReq;
1048 __u16 wValue;
1049 __u16 wIndex;
1050 __u16 wLength;
1051
1052#ifdef DEBUG
1053 urb_priv.actual_length = 0;
1054 pkt_print(dev, pipe, buffer, transfer_len, cmd, "SUB(rh)",
1055 usb_pipein(pipe));
1056#else
1057 wait_ms(1);
1058#endif
1059 if (usb_pipeint(pipe)) {
1060 info("Root-Hub submit IRQ: NOT implemented");
1061 return 0;
1062 }
1063
1064 bmRType_bReq = cmd->requesttype | (cmd->request << 8);
1065 wValue = m16_swap(cmd->value);
1066 wIndex = m16_swap(cmd->index);
1067 wLength = m16_swap(cmd->length);
1068
1069 info("Root-Hub: adr: %2x cmd(%1x): %08x %04x %04x %04x",
1070 dev->devnum, 8, bmRType_bReq, wValue, wIndex, wLength);
1071
1072 switch (bmRType_bReq) {
1073
1074
1075
1076
1077
1078
1079
1080
1081 case RH_GET_STATUS:
1082 *(__u16 *) data_buf = m16_swap(1);
1083 OK(2);
1084 case RH_GET_STATUS | RH_INTERFACE:
1085 *(__u16 *) data_buf = m16_swap(0);
1086 OK(2);
1087 case RH_GET_STATUS | RH_ENDPOINT:
1088 *(__u16 *) data_buf = m16_swap(0);
1089 OK(2);
1090 case RH_GET_STATUS | RH_CLASS:
1091 *(__u32 *) data_buf =
1092 m32_swap(RD_RH_STAT & ~(RH_HS_CRWE | RH_HS_DRWE));
1093 OK(4);
1094 case RH_GET_STATUS | RH_OTHER | RH_CLASS:
1095 *(__u32 *) data_buf = m32_swap(RD_RH_PORTSTAT);
1096 OK(4);
1097
1098 case RH_CLEAR_FEATURE | RH_ENDPOINT:
1099 switch (wValue) {
1100 case (RH_ENDPOINT_STALL):
1101 OK(0);
1102 }
1103 break;
1104
1105 case RH_CLEAR_FEATURE | RH_CLASS:
1106 switch (wValue) {
1107 case RH_C_HUB_LOCAL_POWER:
1108 OK(0);
1109 case (RH_C_HUB_OVER_CURRENT):
1110 WR_RH_STAT(RH_HS_OCIC);
1111 OK(0);
1112 }
1113 break;
1114
1115 case RH_CLEAR_FEATURE | RH_OTHER | RH_CLASS:
1116 switch (wValue) {
1117 case (RH_PORT_ENABLE):
1118 WR_RH_PORTSTAT(RH_PS_CCS);
1119 OK(0);
1120 case (RH_PORT_SUSPEND):
1121 WR_RH_PORTSTAT(RH_PS_POCI);
1122 OK(0);
1123 case (RH_PORT_POWER):
1124 WR_RH_PORTSTAT(RH_PS_LSDA);
1125 OK(0);
1126 case (RH_C_PORT_CONNECTION):
1127 WR_RH_PORTSTAT(RH_PS_CSC);
1128 OK(0);
1129 case (RH_C_PORT_ENABLE):
1130 WR_RH_PORTSTAT(RH_PS_PESC);
1131 OK(0);
1132 case (RH_C_PORT_SUSPEND):
1133 WR_RH_PORTSTAT(RH_PS_PSSC);
1134 OK(0);
1135 case (RH_C_PORT_OVER_CURRENT):
1136 WR_RH_PORTSTAT(RH_PS_OCIC);
1137 OK(0);
1138 case (RH_C_PORT_RESET):
1139 WR_RH_PORTSTAT(RH_PS_PRSC);
1140 OK(0);
1141 }
1142 break;
1143
1144 case RH_SET_FEATURE | RH_OTHER | RH_CLASS:
1145 switch (wValue) {
1146 case (RH_PORT_SUSPEND):
1147 WR_RH_PORTSTAT(RH_PS_PSS);
1148 OK(0);
1149 case (RH_PORT_RESET):
1150 if (RD_RH_PORTSTAT & RH_PS_CCS)
1151 WR_RH_PORTSTAT(RH_PS_PRS);
1152 OK(0);
1153 case (RH_PORT_POWER):
1154 WR_RH_PORTSTAT(RH_PS_PPS);
1155 OK(0);
1156 case (RH_PORT_ENABLE):
1157 if (RD_RH_PORTSTAT & RH_PS_CCS)
1158 WR_RH_PORTSTAT(RH_PS_PES);
1159 OK(0);
1160 }
1161 break;
1162
1163 case RH_SET_ADDRESS:
1164 gohci.rh.devnum = wValue;
1165 OK(0);
1166
1167 case RH_GET_DESCRIPTOR:
1168 switch ((wValue & 0xff00) >> 8) {
1169 case (0x01):
1170 len = min_t(unsigned int,
1171 leni,
1172 min_t(unsigned int,
1173 sizeof(root_hub_dev_des), wLength));
1174 data_buf = root_hub_dev_des;
1175 OK(len);
1176 case (0x02):
1177 len = min_t(unsigned int,
1178 leni,
1179 min_t(unsigned int,
1180 sizeof(root_hub_config_des),
1181 wLength));
1182 data_buf = root_hub_config_des;
1183 OK(len);
1184 case (0x03):
1185 if (wValue == 0x0300) {
1186 len = min_t(unsigned int,
1187 leni,
1188 min_t(unsigned int,
1189 sizeof(root_hub_str_index0),
1190 wLength));
1191 data_buf = root_hub_str_index0;
1192 OK(len);
1193 }
1194 if (wValue == 0x0301) {
1195 len = min_t(unsigned int,
1196 leni,
1197 min_t(unsigned int,
1198 sizeof(root_hub_str_index1),
1199 wLength));
1200 data_buf = root_hub_str_index1;
1201 OK(len);
1202 }
1203 default:
1204 stat = USB_ST_STALLED;
1205 }
1206 break;
1207
1208 case RH_GET_DESCRIPTOR | RH_CLASS:
1209 {
1210 __u32 temp = roothub_a(&gohci);
1211
1212 data_buf[0] = 9;
1213 data_buf[1] = 0x29;
1214 data_buf[2] = temp & RH_A_NDP;
1215 data_buf[3] = 0;
1216 if (temp & RH_A_PSM)
1217
1218 data_buf[3] |= 0x1;
1219 if (temp & RH_A_NOCP)
1220
1221 data_buf[3] |= 0x10;
1222 else if (temp & RH_A_OCPM)
1223
1224 data_buf[3] |= 0x8;
1225
1226
1227 datab[1] = 0;
1228 data_buf[5] = (temp & RH_A_POTPGT) >> 24;
1229 temp = roothub_b(&gohci);
1230 data_buf[7] = temp & RH_B_DR;
1231 if (data_buf[2] < 7) {
1232 data_buf[8] = 0xff;
1233 } else {
1234 data_buf[0] += 2;
1235 data_buf[8] = (temp & RH_B_DR) >> 8;
1236 data_buf[10] = data_buf[9] = 0xff;
1237 }
1238
1239 len = min_t(unsigned int, leni,
1240 min_t(unsigned int, data_buf[0], wLength));
1241 OK(len);
1242 }
1243
1244 case RH_GET_CONFIGURATION:
1245 *(__u8 *) data_buf = 0x01;
1246 OK(1);
1247
1248 case RH_SET_CONFIGURATION:
1249 WR_RH_STAT(0x10000);
1250 OK(0);
1251
1252 default:
1253 dbg("unsupported root hub command");
1254 stat = USB_ST_STALLED;
1255 }
1256
1257#ifdef DEBUG
1258 ohci_dump_roothub(&gohci, 1);
1259#else
1260 wait_ms(1);
1261#endif
1262
1263 len = min_t(int, len, leni);
1264 if (data != data_buf)
1265 memcpy(data, data_buf, len);
1266 dev->act_len = len;
1267 dev->status = stat;
1268
1269#ifdef DEBUG
1270 if (transfer_len)
1271 urb_priv.actual_length = transfer_len;
1272 pkt_print(dev, pipe, buffer, transfer_len, cmd, "RET(rh)",
1273 0 );
1274#else
1275 wait_ms(1);
1276#endif
1277
1278 return stat;
1279}
1280
1281
1282
1283
1284
1285int submit_common_msg(struct usb_device *dev, unsigned long pipe, void *buffer,
1286 int transfer_len, struct devrequest *setup, int interval)
1287{
1288 int stat = 0;
1289 int maxsize = usb_maxpacket(dev, pipe);
1290 int timeout;
1291
1292
1293 if (devgone == dev) {
1294 dev->status = USB_ST_CRC_ERR;
1295 return 0;
1296 }
1297#ifdef DEBUG
1298 urb_priv.actual_length = 0;
1299 pkt_print(dev, pipe, buffer, transfer_len, setup, "SUB",
1300 usb_pipein(pipe));
1301#else
1302 wait_ms(1);
1303#endif
1304 if (!maxsize) {
1305 err("submit_common_message: pipesize for pipe %lx is zero",
1306 pipe);
1307 return -1;
1308 }
1309
1310 if (sohci_submit_job(dev, pipe, buffer, transfer_len, setup, interval) <
1311 0) {
1312 err("sohci_submit_job failed");
1313 return -1;
1314 }
1315
1316 wait_ms(10);
1317
1318
1319
1320#define BULK_TO 5000
1321 if (usb_pipebulk(pipe))
1322 timeout = BULK_TO;
1323 else
1324 timeout = 100;
1325
1326
1327 for (;;) {
1328
1329 stat = hc_interrupt();
1330
1331 if (stat < 0) {
1332 stat = USB_ST_CRC_ERR;
1333 break;
1334 }
1335
1336
1337
1338
1339
1340
1341
1342
1343
1344
1345 if ((stat >= 0) && (stat != 0xff) && (urb_finished)) {
1346
1347 break;
1348 }
1349
1350 if (--timeout) {
1351 wait_ms(1);
1352 if (!urb_finished)
1353 dbg("\%");
1354
1355 } else {
1356 err("CTL:TIMEOUT ");
1357 dbg("submit_common_msg: TO status %x\n", stat);
1358 stat = USB_ST_CRC_ERR;
1359 urb_finished = 1;
1360 break;
1361 }
1362 }
1363
1364#if 0
1365
1366 if (got_rhsc) {
1367#ifdef DEBUG
1368 ohci_dump_roothub(&gohci, 1);
1369#endif
1370 got_rhsc = 0;
1371
1372 timeout = rh_check_port_status(&gohci);
1373 if (timeout >= 0) {
1374#if 0
1375
1376
1377 usb_hub_port_connect_change(gohci.rh.dev, timeout - 1);
1378#endif
1379
1380
1381
1382
1383
1384 devgone = dev;
1385 }
1386 }
1387#endif
1388
1389 dev->status = stat;
1390 dev->act_len = transfer_len;
1391
1392#ifdef DEBUG
1393 pkt_print(dev, pipe, buffer, transfer_len, setup, "RET(ctlr)",
1394 usb_pipein(pipe));
1395#else
1396 wait_ms(1);
1397#endif
1398
1399
1400 urb_free_priv(&urb_priv);
1401 return 0;
1402}
1403
1404
1405int submit_bulk_msg(struct usb_device *dev, unsigned long pipe, void *buffer,
1406 int transfer_len)
1407{
1408 info("submit_bulk_msg");
1409 return submit_common_msg(dev, pipe, buffer, transfer_len, NULL, 0);
1410}
1411
1412int submit_control_msg(struct usb_device *dev, unsigned long pipe, void *buffer,
1413 int transfer_len, struct devrequest *setup)
1414{
1415 int maxsize = usb_maxpacket(dev, pipe);
1416
1417 info("submit_control_msg");
1418#ifdef DEBUG
1419 urb_priv.actual_length = 0;
1420 pkt_print(dev, pipe, buffer, transfer_len, setup, "SUB",
1421 usb_pipein(pipe));
1422#else
1423 wait_ms(1);
1424#endif
1425 if (!maxsize) {
1426 err("submit_control_message: pipesize for pipe %lx is zero",
1427 pipe);
1428 return -1;
1429 }
1430 if (((pipe >> 8) & 0x7f) == gohci.rh.devnum) {
1431 gohci.rh.dev = dev;
1432
1433 return ohci_submit_rh_msg(dev, pipe, buffer, transfer_len,
1434 setup);
1435 }
1436
1437 return submit_common_msg(dev, pipe, buffer, transfer_len, setup, 0);
1438}
1439
1440int submit_int_msg(struct usb_device *dev, unsigned long pipe, void *buffer,
1441 int transfer_len, int interval)
1442{
1443 info("submit_int_msg");
1444 return -1;
1445}
1446
1447
1448
1449
1450
1451
1452
1453static int hc_reset(struct ohci *ohci)
1454{
1455 int timeout = 30;
1456 int smm_timeout = 50;
1457
1458 if (readl(&ohci->regs->control) & OHCI_CTRL_IR) {
1459
1460 writel(OHCI_OCR, &ohci->regs->cmdstatus);
1461 info("USB HC TakeOver from SMM");
1462 while (readl(&ohci->regs->control) & OHCI_CTRL_IR) {
1463 wait_ms(10);
1464 if (--smm_timeout == 0) {
1465 err("USB HC TakeOver failed!");
1466 return -1;
1467 }
1468 }
1469 }
1470
1471
1472 writel(OHCI_INTR_MIE, &ohci->regs->intrdisable);
1473
1474 dbg("USB HC reset_hc usb-%s: ctrl = 0x%X ;",
1475 ohci->slot_name, readl(&ohci->regs->control));
1476
1477
1478 writel(0, &ohci->regs->control);
1479
1480
1481 writel(OHCI_HCR, &ohci->regs->cmdstatus);
1482 while ((readl(&ohci->regs->cmdstatus) & OHCI_HCR) != 0) {
1483 if (--timeout == 0) {
1484 err("USB HC reset timed out!");
1485 return -1;
1486 }
1487 udelay(1);
1488 }
1489 return 0;
1490}
1491
1492
1493
1494
1495
1496
1497
1498static int hc_start(struct ohci *ohci)
1499{
1500 __u32 mask;
1501 unsigned int fminterval;
1502
1503 ohci->disabled = 1;
1504
1505
1506
1507
1508 writel(0, &ohci->regs->ed_controlhead);
1509 writel(0, &ohci->regs->ed_bulkhead);
1510
1511
1512 writel((__u32) ohci->hcca, &ohci->regs->hcca);
1513
1514 fminterval = 0x2edf;
1515 writel((fminterval * 9) / 10, &ohci->regs->periodicstart);
1516 fminterval |= ((((fminterval - 210) * 6) / 7) << 16);
1517 writel(fminterval, &ohci->regs->fminterval);
1518 writel(0x628, &ohci->regs->lsthresh);
1519
1520
1521 ohci->hc_control = OHCI_CONTROL_INIT | OHCI_USB_OPER;
1522 ohci->disabled = 0;
1523 writel(ohci->hc_control, &ohci->regs->control);
1524
1525
1526 mask = (OHCI_INTR_SO | OHCI_INTR_WDH | OHCI_INTR_SF | OHCI_INTR_RD |
1527 OHCI_INTR_UE | OHCI_INTR_FNO | OHCI_INTR_RHSC |
1528 OHCI_INTR_OC | OHCI_INTR_MIE);
1529 writel(mask, &ohci->regs->intrdisable);
1530
1531 mask &= ~OHCI_INTR_MIE;
1532 writel(mask, &ohci->regs->intrstatus);
1533
1534 mask = OHCI_INTR_RHSC | OHCI_INTR_UE | OHCI_INTR_WDH | OHCI_INTR_SO;
1535 writel(mask, &ohci->regs->intrenable);
1536
1537#ifdef OHCI_USE_NPS
1538
1539 writel((roothub_a(ohci) | RH_A_NPS) & ~RH_A_PSM,
1540 &ohci->regs->roothub.a);
1541 writel(RH_HS_LPSC, &ohci->regs->roothub.status);
1542#endif
1543
1544#define mdelay(n) ({unsigned long msec=(n); while (msec--) udelay(1000);})
1545
1546 mdelay((roothub_a(ohci) >> 23) & 0x1fe);
1547
1548
1549 ohci->rh.devnum = 0;
1550
1551 return 0;
1552}
1553
1554
1555
1556
1557
1558static int hc_interrupt(void)
1559{
1560 struct ohci *ohci = &gohci;
1561 struct ohci_regs *regs = ohci->regs;
1562 int ints;
1563 int stat = -1;
1564
1565 if ((ohci->hcca->done_head != 0) &&
1566 !(m32_swap(ohci->hcca->done_head) & 0x01)) {
1567
1568 ints = OHCI_INTR_WDH;
1569
1570 } else {
1571 ints = readl(®s->intrstatus);
1572 if (ints == ~(u32) 0) {
1573 ohci->disabled++;
1574 err("%s device removed!", ohci->slot_name);
1575 return -1;
1576 }
1577 ints &= readl(®s->intrenable);
1578 if (ints == 0) {
1579 dbg("hc_interrupt: returning..\n");
1580 return 0xff;
1581 }
1582 }
1583
1584
1585
1586
1587 if (ints & OHCI_INTR_RHSC) {
1588 got_rhsc = 1;
1589 stat = 0xff;
1590 }
1591
1592 if (ints & OHCI_INTR_UE) {
1593 ohci->disabled++;
1594 err("OHCI Unrecoverable Error, controller usb-%s disabled",
1595 ohci->slot_name);
1596
1597
1598#ifdef DEBUG
1599 ohci_dump(ohci, 1);
1600#else
1601 wait_ms(1);
1602#endif
1603
1604
1605
1606
1607 hc_reset(ohci);
1608 return -1;
1609 }
1610
1611 if (ints & OHCI_INTR_WDH) {
1612 wait_ms(1);
1613
1614 writel(OHCI_INTR_WDH, ®s->intrdisable);
1615 stat = dl_done_list(&gohci, dl_reverse_done_list(&gohci));
1616 writel(OHCI_INTR_WDH, ®s->intrenable);
1617 }
1618
1619 if (ints & OHCI_INTR_SO) {
1620 dbg("USB Schedule overrun\n");
1621 writel(OHCI_INTR_SO, ®s->intrenable);
1622 stat = -1;
1623 }
1624
1625
1626 if (ints & OHCI_INTR_SF) {
1627 unsigned int frame = m16_swap(ohci->hcca->frame_no) & 1;
1628 wait_ms(1);
1629 writel(OHCI_INTR_SF, ®s->intrdisable);
1630 if (ohci->ed_rm_list[frame] != NULL)
1631 writel(OHCI_INTR_SF, ®s->intrenable);
1632 stat = 0xff;
1633 }
1634
1635 writel(ints, ®s->intrstatus);
1636 return stat;
1637}
1638
1639
1640
1641
1642
1643
1644
1645static void hc_release_ohci(struct ohci *ohci)
1646{
1647 dbg("USB HC release ohci usb-%s", ohci->slot_name);
1648
1649 if (!ohci->disabled)
1650 hc_reset(ohci);
1651}
1652
1653
1654
1655
1656
1657
1658static char ohci_inited = 0;
1659
1660int usb_lowlevel_init(void)
1661{
1662 struct s3c24x0_clock_power *clk_power = s3c24x0_get_base_clock_power();
1663 struct s3c24x0_gpio *gpio = s3c24x0_get_base_gpio();
1664
1665
1666
1667
1668
1669 clk_power->upllcon = ((40 << 12) + (1 << 4) + 2);
1670 gpio->misccr |= 0x8;
1671
1672
1673
1674
1675 clk_power->clkcon |= (1 << 4);
1676
1677 memset(&gohci, 0, sizeof(struct ohci));
1678 memset(&urb_priv, 0, sizeof(struct urb_priv));
1679
1680
1681 if ((__u32) &ghcca[0] & 0xff) {
1682 err("HCCA not aligned!!");
1683 return -1;
1684 }
1685 phcca = &ghcca[0];
1686 info("aligned ghcca %p", phcca);
1687 memset(&ohci_dev, 0, sizeof(struct ohci_device));
1688 if ((__u32) &ohci_dev.ed[0] & 0x7) {
1689 err("EDs not aligned!!");
1690 return -1;
1691 }
1692 memset(gtd, 0, sizeof(struct td) * (NUM_TD + 1));
1693 if ((__u32) gtd & 0x7) {
1694 err("TDs not aligned!!");
1695 return -1;
1696 }
1697 ptd = gtd;
1698 gohci.hcca = phcca;
1699 memset(phcca, 0, sizeof(struct ohci_hcca));
1700
1701 gohci.disabled = 1;
1702 gohci.sleeping = 0;
1703 gohci.irq = -1;
1704 gohci.regs = (struct ohci_regs *)S3C24X0_USB_HOST_BASE;
1705
1706 gohci.flags = 0;
1707 gohci.slot_name = "s3c2400";
1708
1709 if (hc_reset(&gohci) < 0) {
1710 hc_release_ohci(&gohci);
1711
1712 clk_power->clkcon &= ~(1 << 4);
1713 return -1;
1714 }
1715
1716
1717 gohci.hc_control = OHCI_USB_RESET;
1718 writel(gohci.hc_control, &gohci.regs->control);
1719 wait_ms(10);
1720
1721 if (hc_start(&gohci) < 0) {
1722 err("can't start usb-%s", gohci.slot_name);
1723 hc_release_ohci(&gohci);
1724
1725 clk_power->clkcon &= ~(1 << 4);
1726 return -1;
1727 }
1728#ifdef DEBUG
1729 ohci_dump(&gohci, 1);
1730#else
1731 wait_ms(1);
1732#endif
1733 ohci_inited = 1;
1734 urb_finished = 1;
1735
1736 return 0;
1737}
1738
1739int usb_lowlevel_stop(void)
1740{
1741 struct s3c24x0_clock_power *clk_power = s3c24x0_get_base_clock_power();
1742
1743
1744
1745 if (!ohci_inited)
1746 return 0;
1747
1748
1749 hc_reset(&gohci);
1750
1751 clk_power->clkcon &= ~(1 << 4);
1752 return 0;
1753}
1754
1755#endif
1756