23
#include "qemu/osdep.h"
24
#include "qemu/timer.h"
26
#include "hw/usb/hcd-musb.h"
31
#define MUSB_HDRC_FADDR 0x00
32
#define MUSB_HDRC_POWER 0x01
34
#define MUSB_HDRC_INTRTX 0x02
35
#define MUSB_HDRC_INTRRX 0x04
36
#define MUSB_HDRC_INTRTXE 0x06
37
#define MUSB_HDRC_INTRRXE 0x08
38
#define MUSB_HDRC_INTRUSB 0x0a
39
#define MUSB_HDRC_INTRUSBE 0x0b
40
#define MUSB_HDRC_FRAME 0x0c
41
#define MUSB_HDRC_INDEX 0x0e
42
#define MUSB_HDRC_TESTMODE 0x0f
45
#define MUSB_HDRC_EP_IDX 0x10
48
#define MUSB_HDRC_FIFO 0x20
51
#define MUSB_HDRC_DEVCTL 0x60
54
#define MUSB_HDRC_TXFIFOSZ 0x62
55
#define MUSB_HDRC_RXFIFOSZ 0x63
56
#define MUSB_HDRC_TXFIFOADDR 0x64
57
#define MUSB_HDRC_RXFIFOADDR 0x66
60
#define MUSB_HDRC_VCTRL 0x68
61
#define MUSB_HDRC_HWVERS 0x6c
65
#define MUSB_HDRC_ULPI_VBUSCTL 0x70
66
#define MUSB_HDRC_ULPI_REGDATA 0x74
67
#define MUSB_HDRC_ULPI_REGADDR 0x75
68
#define MUSB_HDRC_ULPI_REGCTL 0x76
71
#define MUSB_HDRC_ENDCOUNT 0x78
72
#define MUSB_HDRC_DMARAMCFG 0x79
73
#define MUSB_HDRC_PHYWAIT 0x7a
74
#define MUSB_HDRC_PHYVPLEN 0x7b
75
#define MUSB_HDRC_HS_EOF1 0x7c
76
#define MUSB_HDRC_FS_EOF1 0x7d
77
#define MUSB_HDRC_LS_EOF1 0x7e
80
#define MUSB_HDRC_BUSCTL 0x80
83
#define MUSB_HDRC_EP 0x100
86
#define MUSB_HDRC_TXMAXP 0x00
87
#define MUSB_HDRC_TXCSR 0x02
88
#define MUSB_HDRC_CSR0 MUSB_HDRC_TXCSR
89
#define MUSB_HDRC_RXMAXP 0x04
90
#define MUSB_HDRC_RXCSR 0x06
91
#define MUSB_HDRC_RXCOUNT 0x08
92
#define MUSB_HDRC_COUNT0 MUSB_HDRC_RXCOUNT
93
#define MUSB_HDRC_TXTYPE 0x0a
94
#define MUSB_HDRC_TYPE0 MUSB_HDRC_TXTYPE
95
#define MUSB_HDRC_TXINTERVAL 0x0b
96
#define MUSB_HDRC_NAKLIMIT0 MUSB_HDRC_TXINTERVAL
97
#define MUSB_HDRC_RXTYPE 0x0c
98
#define MUSB_HDRC_RXINTERVAL 0x0d
99
#define MUSB_HDRC_FIFOSIZE 0x0f
100
#define MUSB_HDRC_CONFIGDATA MGC_O_HDRC_FIFOSIZE
103
#define MUSB_HDRC_TXFUNCADDR 0x00
104
#define MUSB_HDRC_TXHUBADDR 0x02
105
#define MUSB_HDRC_TXHUBPORT 0x03
107
#define MUSB_HDRC_RXFUNCADDR 0x04
108
#define MUSB_HDRC_RXHUBADDR 0x06
109
#define MUSB_HDRC_RXHUBPORT 0x07
116
#define MGC_M_POWER_ISOUPDATE 0x80
117
#define MGC_M_POWER_SOFTCONN 0x40
118
#define MGC_M_POWER_HSENAB 0x20
119
#define MGC_M_POWER_HSMODE 0x10
120
#define MGC_M_POWER_RESET 0x08
121
#define MGC_M_POWER_RESUME 0x04
122
#define MGC_M_POWER_SUSPENDM 0x02
123
#define MGC_M_POWER_ENSUSPEND 0x01
126
#define MGC_M_INTR_SUSPEND 0x01
127
#define MGC_M_INTR_RESUME 0x02
128
#define MGC_M_INTR_RESET 0x04
129
#define MGC_M_INTR_BABBLE 0x04
130
#define MGC_M_INTR_SOF 0x08
131
#define MGC_M_INTR_CONNECT 0x10
132
#define MGC_M_INTR_DISCONNECT 0x20
133
#define MGC_M_INTR_SESSREQ 0x40
134
#define MGC_M_INTR_VBUSERROR 0x80
135
#define MGC_M_INTR_EP0 0x01
138
#define MGC_M_DEVCTL_BDEVICE 0x80
139
#define MGC_M_DEVCTL_FSDEV 0x40
140
#define MGC_M_DEVCTL_LSDEV 0x20
141
#define MGC_M_DEVCTL_VBUS 0x18
142
#define MGC_S_DEVCTL_VBUS 3
143
#define MGC_M_DEVCTL_HM 0x04
144
#define MGC_M_DEVCTL_HR 0x02
145
#define MGC_M_DEVCTL_SESSION 0x01
148
#define MGC_M_TEST_FORCE_HOST 0x80
149
#define MGC_M_TEST_FIFO_ACCESS 0x40
150
#define MGC_M_TEST_FORCE_FS 0x20
151
#define MGC_M_TEST_FORCE_HS 0x10
152
#define MGC_M_TEST_PACKET 0x08
153
#define MGC_M_TEST_K 0x04
154
#define MGC_M_TEST_J 0x02
155
#define MGC_M_TEST_SE0_NAK 0x01
158
#define MGC_M_CSR0_FLUSHFIFO 0x0100
159
#define MGC_M_CSR0_TXPKTRDY 0x0002
160
#define MGC_M_CSR0_RXPKTRDY 0x0001
163
#define MGC_M_CSR0_P_SVDSETUPEND 0x0080
164
#define MGC_M_CSR0_P_SVDRXPKTRDY 0x0040
165
#define MGC_M_CSR0_P_SENDSTALL 0x0020
166
#define MGC_M_CSR0_P_SETUPEND 0x0010
167
#define MGC_M_CSR0_P_DATAEND 0x0008
168
#define MGC_M_CSR0_P_SENTSTALL 0x0004
171
#define MGC_M_CSR0_H_NO_PING 0x0800
172
#define MGC_M_CSR0_H_WR_DATATOGGLE 0x0400
173
#define MGC_M_CSR0_H_DATATOGGLE 0x0200
174
#define MGC_M_CSR0_H_NAKTIMEOUT 0x0080
175
#define MGC_M_CSR0_H_STATUSPKT 0x0040
176
#define MGC_M_CSR0_H_REQPKT 0x0020
177
#define MGC_M_CSR0_H_ERROR 0x0010
178
#define MGC_M_CSR0_H_SETUPPKT 0x0008
179
#define MGC_M_CSR0_H_RXSTALL 0x0004
182
#define MGC_M_CONFIGDATA_MPRXE 0x80
183
#define MGC_M_CONFIGDATA_MPTXE 0x40
184
#define MGC_M_CONFIGDATA_BIGENDIAN 0x20
185
#define MGC_M_CONFIGDATA_HBRXE 0x10
186
#define MGC_M_CONFIGDATA_HBTXE 0x08
187
#define MGC_M_CONFIGDATA_DYNFIFO 0x04
188
#define MGC_M_CONFIGDATA_SOFTCONE 0x02
189
#define MGC_M_CONFIGDATA_UTMIDW 0x01
192
#define MGC_M_TXCSR_AUTOSET 0x8000
193
#define MGC_M_TXCSR_ISO 0x4000
194
#define MGC_M_TXCSR_MODE 0x2000
195
#define MGC_M_TXCSR_DMAENAB 0x1000
196
#define MGC_M_TXCSR_FRCDATATOG 0x0800
197
#define MGC_M_TXCSR_DMAMODE 0x0400
198
#define MGC_M_TXCSR_CLRDATATOG 0x0040
199
#define MGC_M_TXCSR_FLUSHFIFO 0x0008
200
#define MGC_M_TXCSR_FIFONOTEMPTY 0x0002
201
#define MGC_M_TXCSR_TXPKTRDY 0x0001
204
#define MGC_M_TXCSR_P_INCOMPTX 0x0080
205
#define MGC_M_TXCSR_P_SENTSTALL 0x0020
206
#define MGC_M_TXCSR_P_SENDSTALL 0x0010
207
#define MGC_M_TXCSR_P_UNDERRUN 0x0004
210
#define MGC_M_TXCSR_H_WR_DATATOGGLE 0x0200
211
#define MGC_M_TXCSR_H_DATATOGGLE 0x0100
212
#define MGC_M_TXCSR_H_NAKTIMEOUT 0x0080
213
#define MGC_M_TXCSR_H_RXSTALL 0x0020
214
#define MGC_M_TXCSR_H_ERROR 0x0004
217
#define MGC_M_RXCSR_AUTOCLEAR 0x8000
218
#define MGC_M_RXCSR_DMAENAB 0x2000
219
#define MGC_M_RXCSR_DISNYET 0x1000
220
#define MGC_M_RXCSR_DMAMODE 0x0800
221
#define MGC_M_RXCSR_INCOMPRX 0x0100
222
#define MGC_M_RXCSR_CLRDATATOG 0x0080
223
#define MGC_M_RXCSR_FLUSHFIFO 0x0010
224
#define MGC_M_RXCSR_DATAERROR 0x0008
225
#define MGC_M_RXCSR_FIFOFULL 0x0002
226
#define MGC_M_RXCSR_RXPKTRDY 0x0001
229
#define MGC_M_RXCSR_P_ISO 0x4000
230
#define MGC_M_RXCSR_P_SENTSTALL 0x0040
231
#define MGC_M_RXCSR_P_SENDSTALL 0x0020
232
#define MGC_M_RXCSR_P_OVERRUN 0x0004
235
#define MGC_M_RXCSR_H_AUTOREQ 0x4000
236
#define MGC_M_RXCSR_H_WR_DATATOGGLE 0x0400
237
#define MGC_M_RXCSR_H_DATATOGGLE 0x0200
238
#define MGC_M_RXCSR_H_RXSTALL 0x0040
239
#define MGC_M_RXCSR_H_REQPKT 0x0020
240
#define MGC_M_RXCSR_H_ERROR 0x0004
243
#define MGC_M_HUBADDR_MULTI_TT 0x80
246
#define MGC_M_ULPI_VBCTL_USEEXTVBUSIND 0x02
247
#define MGC_M_ULPI_VBCTL_USEEXTVBUS 0x01
248
#define MGC_M_ULPI_REGCTL_INT_ENABLE 0x08
249
#define MGC_M_ULPI_REGCTL_READNOTWRITE 0x04
250
#define MGC_M_ULPI_REGCTL_COMPLETE 0x02
251
#define MGC_M_ULPI_REGCTL_REG 0x01
256
#define TRACE(fmt, ...) fprintf(stderr, "%s@%d: " fmt "\n", __func__, \
257
__LINE__, ##__VA_ARGS__)
263
static void musb_attach(USBPort *port);
264
static void musb_detach(USBPort *port);
265
static void musb_child_detach(USBPort *port, USBDevice *child);
266
static void musb_schedule_cb(USBPort *port, USBPacket *p);
267
static void musb_async_cancel_device(MUSBState *s, USBDevice *dev);
269
static USBPortOps musb_port_ops = {
270
.attach = musb_attach,
271
.detach = musb_detach,
272
.child_detach = musb_child_detach,
273
.complete = musb_schedule_cb,
276
static USBBusOps musb_bus_ops = {
279
typedef struct MUSBPacket MUSBPacket;
280
typedef struct MUSBEndPoint MUSBEndPoint;
305
MUSBPacket packey[2];
313
USBCallback *delayed_cb[2];
314
QEMUTimer *intv_timer[2];
318
qemu_irq irqs[musb_irq_max];
344
void musb_reset(MUSBState *s)
350
s->power = MGC_M_POWER_HSENAB;
361
memset(s->buf, 0, sizeof(s->buf));
364
s->ep[0].config = MGC_M_CONFIGDATA_SOFTCONE | MGC_M_CONFIGDATA_DYNFIFO;
365
for (i = 0; i < 16; i ++) {
366
s->ep[i].fifosize = 64;
367
s->ep[i].maxp[0] = 0x40;
368
s->ep[i].maxp[1] = 0x40;
371
usb_packet_init(&s->ep[i].packey[0].p);
372
usb_packet_init(&s->ep[i].packey[1].p);
376
struct MUSBState *musb_init(DeviceState *parent_device, int gpio_base)
378
MUSBState *s = g_malloc0(sizeof(*s));
381
for (i = 0; i < musb_irq_max; i++) {
382
s->irqs[i] = qdev_get_gpio_in(parent_device, gpio_base + i);
387
usb_bus_new(&s->bus, sizeof(s->bus), &musb_bus_ops, parent_device);
388
usb_register_port(&s->bus, &s->port, s, 0, &musb_port_ops,
389
USB_SPEED_MASK_LOW | USB_SPEED_MASK_FULL);
394
static void musb_vbus_set(MUSBState *s, int level)
397
s->devctl |= 3 << MGC_S_DEVCTL_VBUS;
399
s->devctl &= ~MGC_M_DEVCTL_VBUS;
401
qemu_set_irq(s->irqs[musb_set_vbus], level);
404
static void musb_intr_set(MUSBState *s, int line, int level)
407
s->intr &= ~(1 << line);
408
qemu_irq_lower(s->irqs[line]);
409
} else if (s->mask & (1 << line)) {
410
s->intr |= 1 << line;
411
qemu_irq_raise(s->irqs[line]);
415
static void musb_tx_intr_set(MUSBState *s, int line, int level)
418
s->tx_intr &= ~(1 << line);
420
qemu_irq_lower(s->irqs[musb_irq_tx]);
421
} else if (s->tx_mask & (1 << line)) {
422
s->tx_intr |= 1 << line;
423
qemu_irq_raise(s->irqs[musb_irq_tx]);
427
static void musb_rx_intr_set(MUSBState *s, int line, int level)
431
s->rx_intr &= ~(1 << line);
433
qemu_irq_lower(s->irqs[musb_irq_rx]);
434
} else if (s->rx_mask & (1 << line)) {
435
s->rx_intr |= 1 << line;
436
qemu_irq_raise(s->irqs[musb_irq_rx]);
439
musb_tx_intr_set(s, line, level);
442
uint32_t musb_core_intr_get(MUSBState *s)
444
return (s->rx_intr << 15) | s->tx_intr;
447
void musb_core_intr_clear(MUSBState *s, uint32_t mask)
450
s->rx_intr &= mask >> 15;
452
qemu_irq_lower(s->irqs[musb_irq_rx]);
456
s->tx_intr &= mask & 0xffff;
458
qemu_irq_lower(s->irqs[musb_irq_tx]);
462
void musb_set_size(MUSBState *s, int epnum, int size, int is_tx)
464
s->ep[epnum].ext_size[!is_tx] = size;
465
s->ep[epnum].fifostart[0] = 0;
466
s->ep[epnum].fifostart[1] = 0;
467
s->ep[epnum].fifolen[0] = 0;
468
s->ep[epnum].fifolen[1] = 0;
471
static void musb_session_update(MUSBState *s, int prev_dev, int prev_sess)
473
int detect_prev = prev_dev && prev_sess;
474
int detect = !!s->port.dev && s->session;
476
if (detect && !detect_prev) {
480
musb_intr_set(s, musb_irq_connect, 1);
482
if (s->port.dev->speed == USB_SPEED_LOW) {
483
s->devctl &= ~MGC_M_DEVCTL_FSDEV;
484
s->devctl |= MGC_M_DEVCTL_LSDEV;
486
s->devctl |= MGC_M_DEVCTL_FSDEV;
487
s->devctl &= ~MGC_M_DEVCTL_LSDEV;
491
s->devctl &= ~MGC_M_DEVCTL_BDEVICE;
494
s->devctl |= MGC_M_DEVCTL_HM;
498
} else if (!detect && detect_prev) {
506
static void musb_attach(USBPort *port)
508
MUSBState *s = (MUSBState *) port->opaque;
510
musb_intr_set(s, musb_irq_vbus_request, 1);
511
musb_session_update(s, 0, s->session);
514
static void musb_detach(USBPort *port)
516
MUSBState *s = (MUSBState *) port->opaque;
518
musb_async_cancel_device(s, port->dev);
520
musb_intr_set(s, musb_irq_disconnect, 1);
521
musb_session_update(s, 1, s->session);
524
static void musb_child_detach(USBPort *port, USBDevice *child)
526
MUSBState *s = (MUSBState *) port->opaque;
528
musb_async_cancel_device(s, child);
531
static void musb_cb_tick0(void *opaque)
533
MUSBEndPoint *ep = (MUSBEndPoint *) opaque;
535
ep->delayed_cb[0](&ep->packey[0].p, opaque);
538
static void musb_cb_tick1(void *opaque)
540
MUSBEndPoint *ep = (MUSBEndPoint *) opaque;
542
ep->delayed_cb[1](&ep->packey[1].p, opaque);
545
#define musb_cb_tick (dir ? musb_cb_tick1 : musb_cb_tick0)
547
static void musb_schedule_cb(USBPort *port, USBPacket *packey)
549
MUSBPacket *p = container_of(packey, MUSBPacket, p);
550
MUSBEndPoint *ep = p->ep;
554
if (ep->status[dir] == USB_RET_NAK)
555
timeout = ep->timeout[dir];
556
else if (ep->interrupt[dir])
563
if (!ep->intv_timer[dir])
564
ep->intv_timer[dir] = timer_new_ns(QEMU_CLOCK_VIRTUAL, musb_cb_tick, ep);
566
timer_mod(ep->intv_timer[dir], qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL) +
567
muldiv64(timeout, NANOSECONDS_PER_SECOND, 8000));
570
static int musb_timeout(int ttype, int speed, int val)
577
case USB_ENDPOINT_XFER_CONTROL:
580
else if (speed == USB_SPEED_HIGH)
581
return 1 << (val - 1);
583
return 8 << (val - 1);
585
case USB_ENDPOINT_XFER_INT:
586
if (speed == USB_SPEED_HIGH)
590
return 1 << (val - 1);
594
case USB_ENDPOINT_XFER_BULK:
595
case USB_ENDPOINT_XFER_ISOC:
598
else if (speed == USB_SPEED_HIGH)
599
return 1 << (val - 1);
601
return 8 << (val - 1);
605
hw_error("bad interval\n");
608
static void musb_packet(MUSBState *s, MUSBEndPoint *ep,
609
int epnum, int pid, int len, USBCallback cb, int dir)
613
int idx = epnum && dir;
622
ttype = epnum ? (ep->type[idx] >> 4) & 3 : 0;
624
ep->timeout[dir] = musb_timeout(ttype,
625
ep->type[idx] >> 6, ep->interval[idx]);
626
ep->interrupt[dir] = ttype == USB_ENDPOINT_XFER_INT;
627
ep->delayed_cb[dir] = cb;
630
dev = usb_find_device(&s->port, ep->faddr[idx]);
634
uep = usb_ep_get(dev, pid, ep->type[idx] & 0xf);
635
id = pid | (dev->addr << 16) | (uep->nr << 8);
636
usb_packet_setup(&ep->packey[dir].p, pid, uep, 0, id, false, true);
637
usb_packet_addbuf(&ep->packey[dir].p, ep->buf[idx], len);
638
ep->packey[dir].ep = ep;
639
ep->packey[dir].dir = dir;
641
usb_handle_packet(dev, &ep->packey[dir].p);
643
if (ep->packey[dir].p.status == USB_RET_ASYNC) {
644
usb_device_flush_ep_queue(dev, uep);
645
ep->status[dir] = len;
649
if (ep->packey[dir].p.status == USB_RET_SUCCESS) {
650
ep->status[dir] = ep->packey[dir].p.actual_length;
652
ep->status[dir] = ep->packey[dir].p.status;
654
musb_schedule_cb(&s->port, &ep->packey[dir].p);
657
static void musb_tx_packet_complete(USBPacket *packey, void *opaque)
661
MUSBEndPoint *ep = (MUSBEndPoint *) opaque;
662
int epnum = ep->epnum;
663
MUSBState *s = ep->musb;
665
ep->fifostart[0] = 0;
668
if (ep->status[0] != USB_RET_NAK) {
671
ep->csr[0] &= ~(MGC_M_TXCSR_FIFONOTEMPTY | MGC_M_TXCSR_TXPKTRDY);
673
ep->csr[0] &= ~MGC_M_CSR0_TXPKTRDY;
680
ep->csr[0] &= ~(MGC_M_TXCSR_H_ERROR | MGC_M_TXCSR_H_RXSTALL |
681
MGC_M_TXCSR_H_NAKTIMEOUT);
683
ep->csr[0] &= ~(MGC_M_CSR0_H_ERROR | MGC_M_CSR0_H_RXSTALL |
684
MGC_M_CSR0_H_NAKTIMEOUT | MGC_M_CSR0_H_NO_PING);
686
if (ep->status[0] == USB_RET_STALL) {
691
ep->csr[0] |= MGC_M_TXCSR_H_RXSTALL;
693
ep->csr[0] |= MGC_M_CSR0_H_RXSTALL;
696
if (ep->status[0] == USB_RET_NAK) {
701
if (ep->interrupt[0]) {
706
ep->csr[0] |= MGC_M_TXCSR_H_NAKTIMEOUT;
708
ep->csr[0] |= MGC_M_CSR0_H_NAKTIMEOUT;
711
if (ep->status[0] < 0) {
712
if (ep->status[0] == USB_RET_BABBLE)
713
musb_intr_set(s, musb_irq_rst_babble, 1);
718
ep->csr[0] |= MGC_M_TXCSR_H_ERROR;
720
ep->csr[0] |= MGC_M_CSR0_H_ERROR;
722
musb_tx_intr_set(s, epnum, 1);
728
if (!epnum && ep->packey[0].pid == USB_TOKEN_SETUP)
729
s->setup_len = ep->packey[0].data[6];
734
musb_tx_intr_set(s, epnum, 1);
737
static void musb_rx_packet_complete(USBPacket *packey, void *opaque)
741
MUSBEndPoint *ep = (MUSBEndPoint *) opaque;
742
int epnum = ep->epnum;
743
MUSBState *s = ep->musb;
745
ep->fifostart[1] = 0;
749
if (ep->status[1] != USB_RET_NAK) {
751
ep->csr[1] &= ~MGC_M_RXCSR_H_REQPKT;
753
ep->csr[0] &= ~MGC_M_CSR0_H_REQPKT;
759
ep->csr[1] &= ~(MGC_M_RXCSR_H_ERROR | MGC_M_RXCSR_H_RXSTALL |
760
MGC_M_RXCSR_DATAERROR);
762
ep->csr[0] &= ~(MGC_M_CSR0_H_ERROR | MGC_M_CSR0_H_RXSTALL |
763
MGC_M_CSR0_H_NAKTIMEOUT | MGC_M_CSR0_H_NO_PING);
765
if (ep->status[1] == USB_RET_STALL) {
768
ep->csr[1] |= MGC_M_RXCSR_H_RXSTALL;
770
ep->csr[0] |= MGC_M_CSR0_H_RXSTALL;
773
if (ep->status[1] == USB_RET_NAK) {
778
if (ep->interrupt[1]) {
779
musb_packet(s, ep, epnum, USB_TOKEN_IN,
780
packey->iov.size, musb_rx_packet_complete, 1);
784
ep->csr[1] |= MGC_M_RXCSR_DATAERROR;
786
ep->csr[0] |= MGC_M_CSR0_H_NAKTIMEOUT;
789
if (ep->status[1] < 0) {
790
if (ep->status[1] == USB_RET_BABBLE) {
791
musb_intr_set(s, musb_irq_rst_babble, 1);
797
ep->csr[1] |= MGC_M_RXCSR_H_ERROR;
799
ep->csr[0] |= MGC_M_CSR0_H_ERROR;
801
musb_rx_intr_set(s, epnum, 1);
807
if (!(ep->csr[1] & (MGC_M_RXCSR_H_RXSTALL | MGC_M_RXCSR_DATAERROR))) {
808
ep->csr[1] |= MGC_M_RXCSR_FIFOFULL | MGC_M_RXCSR_RXPKTRDY;
810
ep->csr[0] |= MGC_M_CSR0_RXPKTRDY;
812
ep->rxcount = ep->status[1];
817
musb_rx_intr_set(s, epnum, 1);
820
static void musb_async_cancel_device(MUSBState *s, USBDevice *dev)
824
for (ep = 0; ep < 16; ep++) {
825
for (dir = 0; dir < 2; dir++) {
826
if (!usb_packet_is_inflight(&s->ep[ep].packey[dir].p) ||
827
s->ep[ep].packey[dir].p.ep->dev != dev) {
830
usb_cancel_packet(&s->ep[ep].packey[dir].p);
836
static void musb_tx_rdy(MUSBState *s, int epnum)
838
MUSBEndPoint *ep = s->ep + epnum;
840
int total, valid = 0;
841
TRACE("start %d, len %d", ep->fifostart[0], ep->fifolen[0] );
842
ep->fifostart[0] += ep->fifolen[0];
847
total = ep->maxp[0] & 0x3ff;
849
if (ep->ext_size[0]) {
850
total = ep->ext_size[0];
856
if (epnum && (ep->fifostart[0]) < total)
860
total = ep->fifostart[0];
863
if (!epnum && (ep->csr[0] & MGC_M_CSR0_H_SETUPPKT)) {
864
pid = USB_TOKEN_SETUP;
866
TRACE("illegal SETUPPKT length of %i bytes", total);
872
musb_packet(s, ep, epnum, pid, total, musb_tx_packet_complete, 0);
875
static void musb_rx_req(MUSBState *s, int epnum)
877
MUSBEndPoint *ep = s->ep + epnum;
882
if (ep->packey[1].p.pid == USB_TOKEN_IN && ep->status[1] >= 0 &&
883
(ep->fifostart[1]) + ep->rxcount <
884
ep->packey[1].p.iov.size) {
885
TRACE("0x%08x, %d", ep->fifostart[1], ep->rxcount );
886
ep->fifostart[1] += ep->rxcount;
889
ep->rxcount = MIN(ep->packey[0].p.iov.size - (ep->fifostart[1]),
892
ep->csr[1] &= ~MGC_M_RXCSR_H_REQPKT;
894
ep->csr[0] &= ~MGC_M_CSR0_H_REQPKT;
897
ep->csr[1] &= ~(MGC_M_RXCSR_H_ERROR | MGC_M_RXCSR_H_RXSTALL |
898
MGC_M_RXCSR_DATAERROR);
900
ep->csr[0] &= ~(MGC_M_CSR0_H_ERROR | MGC_M_CSR0_H_RXSTALL |
901
MGC_M_CSR0_H_NAKTIMEOUT | MGC_M_CSR0_H_NO_PING);
903
ep->csr[1] |= MGC_M_RXCSR_FIFOFULL | MGC_M_RXCSR_RXPKTRDY;
905
ep->csr[0] |= MGC_M_CSR0_RXPKTRDY;
906
musb_rx_intr_set(s, epnum, 1);
922
total = MIN(ep->maxp[1] & 0x3ff, sizeof(s->buf));
927
if (ep->packey[0].p.devaddr == 2) {
928
total = MIN(s->setup_len, 8);
930
total = MIN(s->setup_len, 64);
932
s->setup_len -= total;
936
musb_packet(s, ep, epnum, USB_TOKEN_IN, total, musb_rx_packet_complete, 1);
939
static uint8_t musb_read_fifo(MUSBEndPoint *ep)
942
if (ep->fifolen[1] >= 64) {
944
TRACE("EP%d FIFO is now empty, stop reading", ep->epnum);
950
ep->csr[1] &= ~MGC_M_RXCSR_FIFOFULL;
951
value=ep->buf[1][ep->fifostart[1] + ep->fifolen[1] ++];
952
TRACE("EP%d 0x%02x, %d", ep->epnum, value, ep->fifolen[1] );
956
static void musb_write_fifo(MUSBEndPoint *ep, uint8_t value)
958
TRACE("EP%d = %02x", ep->epnum, value);
959
if (ep->fifolen[0] >= 64) {
961
TRACE("EP%d FIFO exceeded 64 bytes, stop feeding data", ep->epnum);
965
ep->buf[0][ep->fifostart[0] + ep->fifolen[0] ++] = value;
966
ep->csr[0] |= MGC_M_TXCSR_FIFONOTEMPTY;
969
static void musb_ep_frame_cancel(MUSBEndPoint *ep, int dir)
971
if (ep->intv_timer[dir])
972
timer_del(ep->intv_timer[dir]);
976
static uint8_t musb_busctl_readb(void *opaque, int ep, int addr)
978
MUSBState *s = (MUSBState *) opaque;
982
case MUSB_HDRC_TXHUBADDR:
983
return s->ep[ep].haddr[0];
984
case MUSB_HDRC_TXHUBPORT:
985
return s->ep[ep].hport[0];
986
case MUSB_HDRC_RXHUBADDR:
987
return s->ep[ep].haddr[1];
988
case MUSB_HDRC_RXHUBPORT:
989
return s->ep[ep].hport[1];
992
TRACE("unknown register 0x%02x", addr);
997
static void musb_busctl_writeb(void *opaque, int ep, int addr, uint8_t value)
999
MUSBState *s = (MUSBState *) opaque;
1002
case MUSB_HDRC_TXFUNCADDR:
1003
s->ep[ep].faddr[0] = value;
1005
case MUSB_HDRC_RXFUNCADDR:
1006
s->ep[ep].faddr[1] = value;
1008
case MUSB_HDRC_TXHUBADDR:
1009
s->ep[ep].haddr[0] = value;
1011
case MUSB_HDRC_TXHUBPORT:
1012
s->ep[ep].hport[0] = value;
1014
case MUSB_HDRC_RXHUBADDR:
1015
s->ep[ep].haddr[1] = value;
1017
case MUSB_HDRC_RXHUBPORT:
1018
s->ep[ep].hport[1] = value;
1022
TRACE("unknown register 0x%02x", addr);
1027
static uint16_t musb_busctl_readh(void *opaque, int ep, int addr)
1029
MUSBState *s = (MUSBState *) opaque;
1032
case MUSB_HDRC_TXFUNCADDR:
1033
return s->ep[ep].faddr[0];
1034
case MUSB_HDRC_RXFUNCADDR:
1035
return s->ep[ep].faddr[1];
1038
return musb_busctl_readb(s, ep, addr) |
1039
(musb_busctl_readb(s, ep, addr | 1) << 8);
1043
static void musb_busctl_writeh(void *opaque, int ep, int addr, uint16_t value)
1045
MUSBState *s = (MUSBState *) opaque;
1048
case MUSB_HDRC_TXFUNCADDR:
1049
s->ep[ep].faddr[0] = value;
1051
case MUSB_HDRC_RXFUNCADDR:
1052
s->ep[ep].faddr[1] = value;
1056
musb_busctl_writeb(s, ep, addr, value & 0xff);
1057
musb_busctl_writeb(s, ep, addr | 1, value >> 8);
1062
static uint8_t musb_ep_readb(void *opaque, int ep, int addr)
1064
MUSBState *s = (MUSBState *) opaque;
1067
case MUSB_HDRC_TXTYPE:
1068
return s->ep[ep].type[0];
1069
case MUSB_HDRC_TXINTERVAL:
1070
return s->ep[ep].interval[0];
1071
case MUSB_HDRC_RXTYPE:
1072
return s->ep[ep].type[1];
1073
case MUSB_HDRC_RXINTERVAL:
1074
return s->ep[ep].interval[1];
1075
case (MUSB_HDRC_FIFOSIZE & ~1):
1077
case MUSB_HDRC_FIFOSIZE:
1078
return ep ? s->ep[ep].fifosize : s->ep[ep].config;
1079
case MUSB_HDRC_RXCOUNT:
1080
return s->ep[ep].rxcount;
1083
TRACE("unknown register 0x%02x", addr);
1088
static void musb_ep_writeb(void *opaque, int ep, int addr, uint8_t value)
1090
MUSBState *s = (MUSBState *) opaque;
1093
case MUSB_HDRC_TXTYPE:
1094
s->ep[ep].type[0] = value;
1096
case MUSB_HDRC_TXINTERVAL:
1097
s->ep[ep].interval[0] = value;
1098
musb_ep_frame_cancel(&s->ep[ep], 0);
1100
case MUSB_HDRC_RXTYPE:
1101
s->ep[ep].type[1] = value;
1103
case MUSB_HDRC_RXINTERVAL:
1104
s->ep[ep].interval[1] = value;
1105
musb_ep_frame_cancel(&s->ep[ep], 1);
1107
case (MUSB_HDRC_FIFOSIZE & ~1):
1109
case MUSB_HDRC_FIFOSIZE:
1110
TRACE("somebody messes with fifosize (now %i bytes)", value);
1111
s->ep[ep].fifosize = value;
1114
TRACE("unknown register 0x%02x", addr);
1119
static uint16_t musb_ep_readh(void *opaque, int ep, int addr)
1121
MUSBState *s = (MUSBState *) opaque;
1125
case MUSB_HDRC_TXMAXP:
1126
return s->ep[ep].maxp[0];
1127
case MUSB_HDRC_TXCSR:
1128
return s->ep[ep].csr[0];
1129
case MUSB_HDRC_RXMAXP:
1130
return s->ep[ep].maxp[1];
1131
case MUSB_HDRC_RXCSR:
1132
ret = s->ep[ep].csr[1];
1136
if (s->ep[ep].csr[1] & MGC_M_RXCSR_AUTOCLEAR)
1137
s->ep[ep].csr[1] &= ~MGC_M_RXCSR_RXPKTRDY;
1140
case MUSB_HDRC_RXCOUNT:
1141
return s->ep[ep].rxcount;
1144
return musb_ep_readb(s, ep, addr) |
1145
(musb_ep_readb(s, ep, addr | 1) << 8);
1149
static void musb_ep_writeh(void *opaque, int ep, int addr, uint16_t value)
1151
MUSBState *s = (MUSBState *) opaque;
1154
case MUSB_HDRC_TXMAXP:
1155
s->ep[ep].maxp[0] = value;
1157
case MUSB_HDRC_TXCSR:
1159
s->ep[ep].csr[0] &= value & 0xa6;
1160
s->ep[ep].csr[0] |= value & 0xff59;
1162
s->ep[ep].csr[0] &= value & 0x85;
1163
s->ep[ep].csr[0] |= value & 0xf7a;
1166
musb_ep_frame_cancel(&s->ep[ep], 0);
1168
if ((ep && (value & MGC_M_TXCSR_FLUSHFIFO)) ||
1169
(!ep && (value & MGC_M_CSR0_FLUSHFIFO))) {
1170
s->ep[ep].fifolen[0] = 0;
1171
s->ep[ep].fifostart[0] = 0;
1174
~(MGC_M_TXCSR_FIFONOTEMPTY | MGC_M_TXCSR_TXPKTRDY);
1177
~(MGC_M_CSR0_TXPKTRDY | MGC_M_CSR0_RXPKTRDY);
1182
(value & MGC_M_TXCSR_TXPKTRDY) &&
1183
!(value & MGC_M_TXCSR_H_NAKTIMEOUT)) ||
1185
(value & MGC_M_TXCSR_TXPKTRDY)) ||
1189
(value & MGC_M_CSR0_TXPKTRDY) &&
1190
!(value & MGC_M_CSR0_H_NAKTIMEOUT)))
1192
(value & MGC_M_CSR0_TXPKTRDY)))
1196
(value & MGC_M_CSR0_H_REQPKT) &&
1198
!(value & (MGC_M_CSR0_H_NAKTIMEOUT |
1199
MGC_M_CSR0_RXPKTRDY)))
1201
!(value & MGC_M_CSR0_RXPKTRDY))
1206
case MUSB_HDRC_RXMAXP:
1207
s->ep[ep].maxp[1] = value;
1209
case MUSB_HDRC_RXCSR:
1212
(value & MGC_M_RXCSR_H_AUTOREQ) &&
1213
!(value & MGC_M_RXCSR_RXPKTRDY) &&
1214
(s->ep[ep].csr[1] & MGC_M_RXCSR_RXPKTRDY))
1215
value |= MGC_M_RXCSR_H_REQPKT;
1217
s->ep[ep].csr[1] &= 0x102 | (value & 0x4d);
1218
s->ep[ep].csr[1] |= value & 0xfeb0;
1220
musb_ep_frame_cancel(&s->ep[ep], 1);
1222
if (value & MGC_M_RXCSR_FLUSHFIFO) {
1223
s->ep[ep].fifolen[1] = 0;
1224
s->ep[ep].fifostart[1] = 0;
1225
s->ep[ep].csr[1] &= ~(MGC_M_RXCSR_FIFOFULL | MGC_M_RXCSR_RXPKTRDY);
1230
if ((value & MGC_M_RXCSR_H_REQPKT) && !(value & MGC_M_RXCSR_DATAERROR))
1232
if (value & MGC_M_RXCSR_H_REQPKT)
1236
case MUSB_HDRC_RXCOUNT:
1237
s->ep[ep].rxcount = value;
1241
musb_ep_writeb(s, ep, addr, value & 0xff);
1242
musb_ep_writeb(s, ep, addr | 1, value >> 8);
1247
static uint32_t musb_readb(void *opaque, hwaddr addr)
1249
MUSBState *s = (MUSBState *) opaque;
1254
case MUSB_HDRC_FADDR:
1256
case MUSB_HDRC_POWER:
1258
case MUSB_HDRC_INTRUSB:
1260
for (i = 0; i < sizeof(ret) * 8; i ++)
1262
musb_intr_set(s, i, 0);
1264
case MUSB_HDRC_INTRUSBE:
1266
case MUSB_HDRC_INDEX:
1268
case MUSB_HDRC_TESTMODE:
1271
case MUSB_HDRC_EP_IDX ... (MUSB_HDRC_EP_IDX + 0xf):
1272
return musb_ep_readb(s, s->idx, addr & 0xf);
1274
case MUSB_HDRC_DEVCTL:
1277
case MUSB_HDRC_TXFIFOSZ:
1278
case MUSB_HDRC_RXFIFOSZ:
1279
case MUSB_HDRC_VCTRL:
1283
case MUSB_HDRC_HWVERS:
1284
return (1 << 10) | 400;
1286
case (MUSB_HDRC_VCTRL | 1):
1287
case (MUSB_HDRC_HWVERS | 1):
1288
case (MUSB_HDRC_DEVCTL | 1):
1291
case MUSB_HDRC_BUSCTL ... (MUSB_HDRC_BUSCTL + 0x7f):
1292
ep = (addr >> 3) & 0xf;
1293
return musb_busctl_readb(s, ep, addr & 0x7);
1295
case MUSB_HDRC_EP ... (MUSB_HDRC_EP + 0xff):
1296
ep = (addr >> 4) & 0xf;
1297
return musb_ep_readb(s, ep, addr & 0xf);
1299
case MUSB_HDRC_FIFO ... (MUSB_HDRC_FIFO + 0x3f):
1300
ep = ((addr - MUSB_HDRC_FIFO) >> 2) & 0xf;
1301
return musb_read_fifo(s->ep + ep);
1304
TRACE("unknown register 0x%02x", (int) addr);
1309
static void musb_writeb(void *opaque, hwaddr addr, uint32_t value)
1311
MUSBState *s = (MUSBState *) opaque;
1315
case MUSB_HDRC_FADDR:
1316
s->faddr = value & 0x7f;
1318
case MUSB_HDRC_POWER:
1319
s->power = (value & 0xef) | (s->power & 0x10);
1321
if ((value & MGC_M_POWER_RESET) && s->port.dev) {
1322
usb_device_reset(s->port.dev);
1324
if ((value & MGC_M_POWER_HSENAB) &&
1325
s->port.dev->speed == USB_SPEED_HIGH)
1326
s->power |= MGC_M_POWER_HSMODE;
1329
if (value & MGC_M_POWER_SUSPENDM) {
1334
if (value & MGC_M_POWER_RESUME) {
1339
case MUSB_HDRC_INTRUSB:
1341
case MUSB_HDRC_INTRUSBE:
1342
s->mask = value & 0xff;
1344
case MUSB_HDRC_INDEX:
1345
s->idx = value & 0xf;
1347
case MUSB_HDRC_TESTMODE:
1350
case MUSB_HDRC_EP_IDX ... (MUSB_HDRC_EP_IDX + 0xf):
1351
musb_ep_writeb(s, s->idx, addr & 0xf, value);
1354
case MUSB_HDRC_DEVCTL:
1355
s->session = !!(value & MGC_M_DEVCTL_SESSION);
1356
musb_session_update(s,
1358
!!(s->devctl & MGC_M_DEVCTL_SESSION));
1361
s->devctl &= ~MGC_M_DEVCTL_SESSION;
1362
s->devctl |= value & MGC_M_DEVCTL_SESSION;
1365
case MUSB_HDRC_TXFIFOSZ:
1366
case MUSB_HDRC_RXFIFOSZ:
1367
case MUSB_HDRC_VCTRL:
1371
case (MUSB_HDRC_VCTRL | 1):
1372
case (MUSB_HDRC_DEVCTL | 1):
1375
case MUSB_HDRC_BUSCTL ... (MUSB_HDRC_BUSCTL + 0x7f):
1376
ep = (addr >> 3) & 0xf;
1377
musb_busctl_writeb(s, ep, addr & 0x7, value);
1380
case MUSB_HDRC_EP ... (MUSB_HDRC_EP + 0xff):
1381
ep = (addr >> 4) & 0xf;
1382
musb_ep_writeb(s, ep, addr & 0xf, value);
1385
case MUSB_HDRC_FIFO ... (MUSB_HDRC_FIFO + 0x3f):
1386
ep = ((addr - MUSB_HDRC_FIFO) >> 2) & 0xf;
1387
musb_write_fifo(s->ep + ep, value & 0xff);
1391
TRACE("unknown register 0x%02x", (int) addr);
1396
static uint32_t musb_readh(void *opaque, hwaddr addr)
1398
MUSBState *s = (MUSBState *) opaque;
1403
case MUSB_HDRC_INTRTX:
1406
for (i = 0; i < sizeof(ret) * 8; i ++)
1408
musb_tx_intr_set(s, i, 0);
1410
case MUSB_HDRC_INTRRX:
1413
for (i = 0; i < sizeof(ret) * 8; i ++)
1415
musb_rx_intr_set(s, i, 0);
1417
case MUSB_HDRC_INTRTXE:
1419
case MUSB_HDRC_INTRRXE:
1422
case MUSB_HDRC_FRAME:
1425
case MUSB_HDRC_TXFIFOADDR:
1426
return s->ep[s->idx].fifoaddr[0];
1427
case MUSB_HDRC_RXFIFOADDR:
1428
return s->ep[s->idx].fifoaddr[1];
1430
case MUSB_HDRC_EP_IDX ... (MUSB_HDRC_EP_IDX + 0xf):
1431
return musb_ep_readh(s, s->idx, addr & 0xf);
1433
case MUSB_HDRC_BUSCTL ... (MUSB_HDRC_BUSCTL + 0x7f):
1434
ep = (addr >> 3) & 0xf;
1435
return musb_busctl_readh(s, ep, addr & 0x7);
1437
case MUSB_HDRC_EP ... (MUSB_HDRC_EP + 0xff):
1438
ep = (addr >> 4) & 0xf;
1439
return musb_ep_readh(s, ep, addr & 0xf);
1441
case MUSB_HDRC_FIFO ... (MUSB_HDRC_FIFO + 0x3f):
1442
ep = ((addr - MUSB_HDRC_FIFO) >> 2) & 0xf;
1443
return (musb_read_fifo(s->ep + ep) | musb_read_fifo(s->ep + ep) << 8);
1446
return musb_readb(s, addr) | (musb_readb(s, addr | 1) << 8);
1450
static void musb_writeh(void *opaque, hwaddr addr, uint32_t value)
1452
MUSBState *s = (MUSBState *) opaque;
1456
case MUSB_HDRC_INTRTXE:
1462
case MUSB_HDRC_INTRRXE:
1466
case MUSB_HDRC_FRAME:
1469
case MUSB_HDRC_TXFIFOADDR:
1470
s->ep[s->idx].fifoaddr[0] = value;
1471
s->ep[s->idx].buf[0] =
1472
s->buf + ((value << 3) & 0x7ff );
1474
case MUSB_HDRC_RXFIFOADDR:
1475
s->ep[s->idx].fifoaddr[1] = value;
1476
s->ep[s->idx].buf[1] =
1477
s->buf + ((value << 3) & 0x7ff);
1480
case MUSB_HDRC_EP_IDX ... (MUSB_HDRC_EP_IDX + 0xf):
1481
musb_ep_writeh(s, s->idx, addr & 0xf, value);
1484
case MUSB_HDRC_BUSCTL ... (MUSB_HDRC_BUSCTL + 0x7f):
1485
ep = (addr >> 3) & 0xf;
1486
musb_busctl_writeh(s, ep, addr & 0x7, value);
1489
case MUSB_HDRC_EP ... (MUSB_HDRC_EP + 0xff):
1490
ep = (addr >> 4) & 0xf;
1491
musb_ep_writeh(s, ep, addr & 0xf, value);
1494
case MUSB_HDRC_FIFO ... (MUSB_HDRC_FIFO + 0x3f):
1495
ep = ((addr - MUSB_HDRC_FIFO) >> 2) & 0xf;
1496
musb_write_fifo(s->ep + ep, value & 0xff);
1497
musb_write_fifo(s->ep + ep, (value >> 8) & 0xff);
1501
musb_writeb(s, addr, value & 0xff);
1502
musb_writeb(s, addr | 1, value >> 8);
1506
static uint32_t musb_readw(void *opaque, hwaddr addr)
1508
MUSBState *s = (MUSBState *) opaque;
1512
case MUSB_HDRC_FIFO ... (MUSB_HDRC_FIFO + 0x3f):
1513
ep = ((addr - MUSB_HDRC_FIFO) >> 2) & 0xf;
1514
return ( musb_read_fifo(s->ep + ep) |
1515
musb_read_fifo(s->ep + ep) << 8 |
1516
musb_read_fifo(s->ep + ep) << 16 |
1517
musb_read_fifo(s->ep + ep) << 24 );
1519
TRACE("unknown register 0x%02x", (int) addr);
1524
static void musb_writew(void *opaque, hwaddr addr, uint32_t value)
1526
MUSBState *s = (MUSBState *) opaque;
1530
case MUSB_HDRC_FIFO ... (MUSB_HDRC_FIFO + 0x3f):
1531
ep = ((addr - MUSB_HDRC_FIFO) >> 2) & 0xf;
1532
musb_write_fifo(s->ep + ep, value & 0xff);
1533
musb_write_fifo(s->ep + ep, (value >> 8 ) & 0xff);
1534
musb_write_fifo(s->ep + ep, (value >> 16) & 0xff);
1535
musb_write_fifo(s->ep + ep, (value >> 24) & 0xff);
1538
TRACE("unknown register 0x%02x", (int) addr);
1543
MUSBReadFunc * const musb_read[] = {
1549
MUSBWriteFunc * const musb_write[] = {