qemu/hw/usb/hcd-dwc2.c
<<
>>
Prefs
   1/*
   2 * dwc-hsotg (dwc2) USB host controller emulation
   3 *
   4 * Based on hw/usb/hcd-ehci.c and hw/usb/hcd-ohci.c
   5 *
   6 * Note that to use this emulation with the dwc-otg driver in the
   7 * Raspbian kernel, you must pass the option "dwc_otg.fiq_fsm_enable=0"
   8 * on the kernel command line.
   9 *
  10 * Some useful documentation used to develop this emulation can be
  11 * found online (as of April 2020) at:
  12 *
  13 * http://www.capital-micro.com/PDF/CME-M7_Family_User_Guide_EN.pdf
  14 * which has a pretty complete description of the controller starting
  15 * on page 370.
  16 *
  17 * https://sourceforge.net/p/wive-ng/wive-ng-mt/ci/master/tree/docs/DataSheets/RT3050_5x_V2.0_081408_0902.pdf
  18 * which has a description of the controller registers starting on
  19 * page 130.
  20 *
  21 * Copyright (c) 2020 Paul Zimmerman <pauldzim@gmail.com>
  22 *
  23 * This program is free software; you can redistribute it and/or modify
  24 * it under the terms of the GNU General Public License as published by
  25 * the Free Software Foundation; either version 2 of the License, or
  26 * (at your option) any later version.
  27 *
  28 * This program is distributed in the hope that it will be useful,
  29 * but WITHOUT ANY WARRANTY; without even the implied warranty of
  30 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  31 * GNU General Public License for more details.
  32 */
  33
  34#include "qemu/osdep.h"
  35#include "qemu/units.h"
  36#include "qapi/error.h"
  37#include "hw/usb/dwc2-regs.h"
  38#include "hw/usb/hcd-dwc2.h"
  39#include "migration/vmstate.h"
  40#include "trace.h"
  41#include "qemu/log.h"
  42#include "qemu/error-report.h"
  43#include "qemu/main-loop.h"
  44#include "hw/qdev-properties.h"
  45
  46#define USB_HZ_FS       12000000
  47#define USB_HZ_HS       96000000
  48#define USB_FRMINTVL    12000
  49
  50/* nifty macros from Arnon's EHCI version  */
  51#define get_field(data, field) \
  52    (((data) & field##_MASK) >> field##_SHIFT)
  53
  54#define set_field(data, newval, field) do { \
  55    uint32_t val = *(data); \
  56    val &= ~field##_MASK; \
  57    val |= ((newval) << field##_SHIFT) & field##_MASK; \
  58    *(data) = val; \
  59} while (0)
  60
  61#define get_bit(data, bitmask) \
  62    (!!((data) & (bitmask)))
  63
  64/* update irq line */
  65static inline void dwc2_update_irq(DWC2State *s)
  66{
  67    static int oldlevel;
  68    int level = 0;
  69
  70    if ((s->gintsts & s->gintmsk) && (s->gahbcfg & GAHBCFG_GLBL_INTR_EN)) {
  71        level = 1;
  72    }
  73    if (level != oldlevel) {
  74        oldlevel = level;
  75        trace_usb_dwc2_update_irq(level);
  76        qemu_set_irq(s->irq, level);
  77    }
  78}
  79
  80/* flag interrupt condition */
  81static inline void dwc2_raise_global_irq(DWC2State *s, uint32_t intr)
  82{
  83    if (!(s->gintsts & intr)) {
  84        s->gintsts |= intr;
  85        trace_usb_dwc2_raise_global_irq(intr);
  86        dwc2_update_irq(s);
  87    }
  88}
  89
  90static inline void dwc2_lower_global_irq(DWC2State *s, uint32_t intr)
  91{
  92    if (s->gintsts & intr) {
  93        s->gintsts &= ~intr;
  94        trace_usb_dwc2_lower_global_irq(intr);
  95        dwc2_update_irq(s);
  96    }
  97}
  98
  99static inline void dwc2_raise_host_irq(DWC2State *s, uint32_t host_intr)
 100{
 101    if (!(s->haint & host_intr)) {
 102        s->haint |= host_intr;
 103        s->haint &= 0xffff;
 104        trace_usb_dwc2_raise_host_irq(host_intr);
 105        if (s->haint & s->haintmsk) {
 106            dwc2_raise_global_irq(s, GINTSTS_HCHINT);
 107        }
 108    }
 109}
 110
 111static inline void dwc2_lower_host_irq(DWC2State *s, uint32_t host_intr)
 112{
 113    if (s->haint & host_intr) {
 114        s->haint &= ~host_intr;
 115        trace_usb_dwc2_lower_host_irq(host_intr);
 116        if (!(s->haint & s->haintmsk)) {
 117            dwc2_lower_global_irq(s, GINTSTS_HCHINT);
 118        }
 119    }
 120}
 121
 122static inline void dwc2_update_hc_irq(DWC2State *s, int index)
 123{
 124    uint32_t host_intr = 1 << (index >> 3);
 125
 126    if (s->hreg1[index + 2] & s->hreg1[index + 3]) {
 127        dwc2_raise_host_irq(s, host_intr);
 128    } else {
 129        dwc2_lower_host_irq(s, host_intr);
 130    }
 131}
 132
 133/* set a timer for EOF */
 134static void dwc2_eof_timer(DWC2State *s)
 135{
 136    timer_mod(s->eof_timer, s->sof_time + s->usb_frame_time);
 137}
 138
 139/* Set a timer for EOF and generate SOF event */
 140static void dwc2_sof(DWC2State *s)
 141{
 142    s->sof_time += s->usb_frame_time;
 143    trace_usb_dwc2_sof(s->sof_time);
 144    dwc2_eof_timer(s);
 145    dwc2_raise_global_irq(s, GINTSTS_SOF);
 146}
 147
 148/* Do frame processing on frame boundary */
 149static void dwc2_frame_boundary(void *opaque)
 150{
 151    DWC2State *s = opaque;
 152    int64_t now;
 153    uint16_t frcnt;
 154
 155    now = qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL);
 156
 157    /* Frame boundary, so do EOF stuff here */
 158
 159    /* Increment frame number */
 160    frcnt = (uint16_t)((now - s->sof_time) / s->fi);
 161    s->frame_number = (s->frame_number + frcnt) & 0xffff;
 162    s->hfnum = s->frame_number & HFNUM_MAX_FRNUM;
 163
 164    /* Do SOF stuff here */
 165    dwc2_sof(s);
 166}
 167
 168/* Start sending SOF tokens on the USB bus */
 169static void dwc2_bus_start(DWC2State *s)
 170{
 171    trace_usb_dwc2_bus_start();
 172    s->sof_time = qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL);
 173    dwc2_eof_timer(s);
 174}
 175
 176/* Stop sending SOF tokens on the USB bus */
 177static void dwc2_bus_stop(DWC2State *s)
 178{
 179    trace_usb_dwc2_bus_stop();
 180    timer_del(s->eof_timer);
 181}
 182
 183static USBDevice *dwc2_find_device(DWC2State *s, uint8_t addr)
 184{
 185    USBDevice *dev;
 186
 187    trace_usb_dwc2_find_device(addr);
 188
 189    if (!(s->hprt0 & HPRT0_ENA)) {
 190        trace_usb_dwc2_port_disabled(0);
 191    } else {
 192        dev = usb_find_device(&s->uport, addr);
 193        if (dev != NULL) {
 194            trace_usb_dwc2_device_found(0);
 195            return dev;
 196        }
 197    }
 198
 199    trace_usb_dwc2_device_not_found();
 200    return NULL;
 201}
 202
 203static const char *pstatus[] = {
 204    "USB_RET_SUCCESS", "USB_RET_NODEV", "USB_RET_NAK", "USB_RET_STALL",
 205    "USB_RET_BABBLE", "USB_RET_IOERROR", "USB_RET_ASYNC",
 206    "USB_RET_ADD_TO_QUEUE", "USB_RET_REMOVE_FROM_QUEUE"
 207};
 208
 209static uint32_t pintr[] = {
 210    HCINTMSK_XFERCOMPL, HCINTMSK_XACTERR, HCINTMSK_NAK, HCINTMSK_STALL,
 211    HCINTMSK_BBLERR, HCINTMSK_XACTERR, HCINTMSK_XACTERR, HCINTMSK_XACTERR,
 212    HCINTMSK_XACTERR
 213};
 214
 215static const char *types[] = {
 216    "Ctrl", "Isoc", "Bulk", "Intr"
 217};
 218
 219static const char *dirs[] = {
 220    "Out", "In"
 221};
 222
 223static void dwc2_handle_packet(DWC2State *s, uint32_t devadr, USBDevice *dev,
 224                               USBEndpoint *ep, uint32_t index, bool send)
 225{
 226    DWC2Packet *p;
 227    uint32_t hcchar = s->hreg1[index];
 228    uint32_t hctsiz = s->hreg1[index + 4];
 229    uint32_t hcdma = s->hreg1[index + 5];
 230    uint32_t chan, epnum, epdir, eptype, mps, pid, pcnt, len, tlen, intr = 0;
 231    uint32_t tpcnt, stsidx, actual = 0;
 232    bool do_intr = false, done = false;
 233
 234    epnum = get_field(hcchar, HCCHAR_EPNUM);
 235    epdir = get_bit(hcchar, HCCHAR_EPDIR);
 236    eptype = get_field(hcchar, HCCHAR_EPTYPE);
 237    mps = get_field(hcchar, HCCHAR_MPS);
 238    pid = get_field(hctsiz, TSIZ_SC_MC_PID);
 239    pcnt = get_field(hctsiz, TSIZ_PKTCNT);
 240    len = get_field(hctsiz, TSIZ_XFERSIZE);
 241    if (len > DWC2_MAX_XFER_SIZE) {
 242        qemu_log_mask(LOG_GUEST_ERROR,
 243                      "%s: HCTSIZ transfer size too large\n", __func__);
 244        return;
 245    }
 246
 247    chan = index >> 3;
 248    p = &s->packet[chan];
 249
 250    trace_usb_dwc2_handle_packet(chan, dev, &p->packet, epnum, types[eptype],
 251                                 dirs[epdir], mps, len, pcnt);
 252
 253    if (mps == 0) {
 254        qemu_log_mask(LOG_GUEST_ERROR,
 255                "%s: Bad HCCHAR_MPS set to zero\n", __func__);
 256        return;
 257    }
 258
 259    if (eptype == USB_ENDPOINT_XFER_CONTROL && pid == TSIZ_SC_MC_PID_SETUP) {
 260        pid = USB_TOKEN_SETUP;
 261    } else {
 262        pid = epdir ? USB_TOKEN_IN : USB_TOKEN_OUT;
 263    }
 264
 265    if (send) {
 266        tlen = len;
 267        if (p->small) {
 268            if (tlen > mps) {
 269                tlen = mps;
 270            }
 271        }
 272
 273        if (pid != USB_TOKEN_IN) {
 274            trace_usb_dwc2_memory_read(hcdma, tlen);
 275            if (dma_memory_read(&s->dma_as, hcdma,
 276                                s->usb_buf[chan], tlen) != MEMTX_OK) {
 277                qemu_log_mask(LOG_GUEST_ERROR, "%s: dma_memory_read failed\n",
 278                              __func__);
 279            }
 280        }
 281
 282        usb_packet_init(&p->packet);
 283        usb_packet_setup(&p->packet, pid, ep, 0, hcdma,
 284                         pid != USB_TOKEN_IN, true);
 285        usb_packet_addbuf(&p->packet, s->usb_buf[chan], tlen);
 286        p->async = DWC2_ASYNC_NONE;
 287        usb_handle_packet(dev, &p->packet);
 288    } else {
 289        tlen = p->len;
 290    }
 291
 292    stsidx = -p->packet.status;
 293    assert(stsidx < sizeof(pstatus) / sizeof(*pstatus));
 294    actual = p->packet.actual_length;
 295    trace_usb_dwc2_packet_status(pstatus[stsidx], actual);
 296
 297babble:
 298    if (p->packet.status != USB_RET_SUCCESS &&
 299            p->packet.status != USB_RET_NAK &&
 300            p->packet.status != USB_RET_STALL &&
 301            p->packet.status != USB_RET_ASYNC) {
 302        trace_usb_dwc2_packet_error(pstatus[stsidx]);
 303    }
 304
 305    if (p->packet.status == USB_RET_ASYNC) {
 306        trace_usb_dwc2_async_packet(&p->packet, chan, dev, epnum,
 307                                    dirs[epdir], tlen);
 308        usb_device_flush_ep_queue(dev, ep);
 309        assert(p->async != DWC2_ASYNC_INFLIGHT);
 310        p->devadr = devadr;
 311        p->epnum = epnum;
 312        p->epdir = epdir;
 313        p->mps = mps;
 314        p->pid = pid;
 315        p->index = index;
 316        p->pcnt = pcnt;
 317        p->len = tlen;
 318        p->async = DWC2_ASYNC_INFLIGHT;
 319        p->needs_service = false;
 320        return;
 321    }
 322
 323    if (p->packet.status == USB_RET_SUCCESS) {
 324        if (actual > tlen) {
 325            p->packet.status = USB_RET_BABBLE;
 326            goto babble;
 327        }
 328
 329        if (pid == USB_TOKEN_IN) {
 330            trace_usb_dwc2_memory_write(hcdma, actual);
 331            if (dma_memory_write(&s->dma_as, hcdma, s->usb_buf[chan],
 332                                 actual) != MEMTX_OK) {
 333                qemu_log_mask(LOG_GUEST_ERROR, "%s: dma_memory_write failed\n",
 334                              __func__);
 335            }
 336        }
 337
 338        tpcnt = actual / mps;
 339        if (actual % mps) {
 340            tpcnt++;
 341            if (pid == USB_TOKEN_IN) {
 342                done = true;
 343            }
 344        }
 345
 346        pcnt -= tpcnt < pcnt ? tpcnt : pcnt;
 347        set_field(&hctsiz, pcnt, TSIZ_PKTCNT);
 348        len -= actual < len ? actual : len;
 349        set_field(&hctsiz, len, TSIZ_XFERSIZE);
 350        s->hreg1[index + 4] = hctsiz;
 351        hcdma += actual;
 352        s->hreg1[index + 5] = hcdma;
 353
 354        if (!pcnt || len == 0 || actual == 0) {
 355            done = true;
 356        }
 357    } else {
 358        intr |= pintr[stsidx];
 359        if (p->packet.status == USB_RET_NAK &&
 360            (eptype == USB_ENDPOINT_XFER_CONTROL ||
 361             eptype == USB_ENDPOINT_XFER_BULK)) {
 362            /*
 363             * for ctrl/bulk, automatically retry on NAK,
 364             * but send the interrupt anyway
 365             */
 366            intr &= ~HCINTMSK_RESERVED14_31;
 367            s->hreg1[index + 2] |= intr;
 368            do_intr = true;
 369        } else {
 370            intr |= HCINTMSK_CHHLTD;
 371            done = true;
 372        }
 373    }
 374
 375    usb_packet_cleanup(&p->packet);
 376
 377    if (done) {
 378        hcchar &= ~HCCHAR_CHENA;
 379        s->hreg1[index] = hcchar;
 380        if (!(intr & HCINTMSK_CHHLTD)) {
 381            intr |= HCINTMSK_CHHLTD | HCINTMSK_XFERCOMPL;
 382        }
 383        intr &= ~HCINTMSK_RESERVED14_31;
 384        s->hreg1[index + 2] |= intr;
 385        p->needs_service = false;
 386        trace_usb_dwc2_packet_done(pstatus[stsidx], actual, len, pcnt);
 387        dwc2_update_hc_irq(s, index);
 388        return;
 389    }
 390
 391    p->devadr = devadr;
 392    p->epnum = epnum;
 393    p->epdir = epdir;
 394    p->mps = mps;
 395    p->pid = pid;
 396    p->index = index;
 397    p->pcnt = pcnt;
 398    p->len = len;
 399    p->needs_service = true;
 400    trace_usb_dwc2_packet_next(pstatus[stsidx], len, pcnt);
 401    if (do_intr) {
 402        dwc2_update_hc_irq(s, index);
 403    }
 404}
 405
 406/* Attach or detach a device on root hub */
 407
 408static const char *speeds[] = {
 409    "low", "full", "high"
 410};
 411
 412static void dwc2_attach(USBPort *port)
 413{
 414    DWC2State *s = port->opaque;
 415    int hispd = 0;
 416
 417    trace_usb_dwc2_attach(port);
 418    assert(port->index == 0);
 419
 420    if (!port->dev || !port->dev->attached) {
 421        return;
 422    }
 423
 424    assert(port->dev->speed <= USB_SPEED_HIGH);
 425    trace_usb_dwc2_attach_speed(speeds[port->dev->speed]);
 426    s->hprt0 &= ~HPRT0_SPD_MASK;
 427
 428    switch (port->dev->speed) {
 429    case USB_SPEED_LOW:
 430        s->hprt0 |= HPRT0_SPD_LOW_SPEED << HPRT0_SPD_SHIFT;
 431        break;
 432    case USB_SPEED_FULL:
 433        s->hprt0 |= HPRT0_SPD_FULL_SPEED << HPRT0_SPD_SHIFT;
 434        break;
 435    case USB_SPEED_HIGH:
 436        s->hprt0 |= HPRT0_SPD_HIGH_SPEED << HPRT0_SPD_SHIFT;
 437        hispd = 1;
 438        break;
 439    }
 440
 441    if (hispd) {
 442        s->usb_frame_time = NANOSECONDS_PER_SECOND / 8000;        /* 125000 */
 443        if (NANOSECONDS_PER_SECOND >= USB_HZ_HS) {
 444            s->usb_bit_time = NANOSECONDS_PER_SECOND / USB_HZ_HS; /* 10.4 */
 445        } else {
 446            s->usb_bit_time = 1;
 447        }
 448    } else {
 449        s->usb_frame_time = NANOSECONDS_PER_SECOND / 1000;        /* 1000000 */
 450        if (NANOSECONDS_PER_SECOND >= USB_HZ_FS) {
 451            s->usb_bit_time = NANOSECONDS_PER_SECOND / USB_HZ_FS; /* 83.3 */
 452        } else {
 453            s->usb_bit_time = 1;
 454        }
 455    }
 456
 457    s->fi = USB_FRMINTVL - 1;
 458    s->hprt0 |= HPRT0_CONNDET | HPRT0_CONNSTS;
 459
 460    dwc2_bus_start(s);
 461    dwc2_raise_global_irq(s, GINTSTS_PRTINT);
 462}
 463
 464static void dwc2_detach(USBPort *port)
 465{
 466    DWC2State *s = port->opaque;
 467
 468    trace_usb_dwc2_detach(port);
 469    assert(port->index == 0);
 470
 471    dwc2_bus_stop(s);
 472
 473    s->hprt0 &= ~(HPRT0_SPD_MASK | HPRT0_SUSP | HPRT0_ENA | HPRT0_CONNSTS);
 474    s->hprt0 |= HPRT0_CONNDET | HPRT0_ENACHG;
 475
 476    dwc2_raise_global_irq(s, GINTSTS_PRTINT);
 477}
 478
 479static void dwc2_child_detach(USBPort *port, USBDevice *child)
 480{
 481    trace_usb_dwc2_child_detach(port, child);
 482    assert(port->index == 0);
 483}
 484
 485static void dwc2_wakeup(USBPort *port)
 486{
 487    DWC2State *s = port->opaque;
 488
 489    trace_usb_dwc2_wakeup(port);
 490    assert(port->index == 0);
 491
 492    if (s->hprt0 & HPRT0_SUSP) {
 493        s->hprt0 |= HPRT0_RES;
 494        dwc2_raise_global_irq(s, GINTSTS_PRTINT);
 495    }
 496
 497    qemu_bh_schedule(s->async_bh);
 498}
 499
 500static void dwc2_async_packet_complete(USBPort *port, USBPacket *packet)
 501{
 502    DWC2State *s = port->opaque;
 503    DWC2Packet *p;
 504    USBDevice *dev;
 505    USBEndpoint *ep;
 506
 507    assert(port->index == 0);
 508    p = container_of(packet, DWC2Packet, packet);
 509    dev = dwc2_find_device(s, p->devadr);
 510    ep = usb_ep_get(dev, p->pid, p->epnum);
 511    trace_usb_dwc2_async_packet_complete(port, packet, p->index >> 3, dev,
 512                                         p->epnum, dirs[p->epdir], p->len);
 513    assert(p->async == DWC2_ASYNC_INFLIGHT);
 514
 515    if (packet->status == USB_RET_REMOVE_FROM_QUEUE) {
 516        usb_cancel_packet(packet);
 517        usb_packet_cleanup(packet);
 518        return;
 519    }
 520
 521    dwc2_handle_packet(s, p->devadr, dev, ep, p->index, false);
 522
 523    p->async = DWC2_ASYNC_FINISHED;
 524    qemu_bh_schedule(s->async_bh);
 525}
 526
 527static USBPortOps dwc2_port_ops = {
 528    .attach = dwc2_attach,
 529    .detach = dwc2_detach,
 530    .child_detach = dwc2_child_detach,
 531    .wakeup = dwc2_wakeup,
 532    .complete = dwc2_async_packet_complete,
 533};
 534
 535static uint32_t dwc2_get_frame_remaining(DWC2State *s)
 536{
 537    uint32_t fr = 0;
 538    int64_t tks;
 539
 540    tks = qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL) - s->sof_time;
 541    if (tks < 0) {
 542        tks = 0;
 543    }
 544
 545    /* avoid muldiv if possible */
 546    if (tks >= s->usb_frame_time) {
 547        goto out;
 548    }
 549    if (tks < s->usb_bit_time) {
 550        fr = s->fi;
 551        goto out;
 552    }
 553
 554    /* tks = number of ns since SOF, divided by 83 (fs) or 10 (hs) */
 555    tks = tks / s->usb_bit_time;
 556    if (tks >= (int64_t)s->fi) {
 557        goto out;
 558    }
 559
 560    /* remaining = frame interval minus tks */
 561    fr = (uint32_t)((int64_t)s->fi - tks);
 562
 563out:
 564    return fr;
 565}
 566
 567static void dwc2_work_bh(void *opaque)
 568{
 569    DWC2State *s = opaque;
 570    DWC2Packet *p;
 571    USBDevice *dev;
 572    USBEndpoint *ep;
 573    int64_t t_now, expire_time;
 574    int chan;
 575    bool found = false;
 576
 577    trace_usb_dwc2_work_bh();
 578    if (s->working) {
 579        return;
 580    }
 581    s->working = true;
 582
 583    t_now = qemu_clock_get_ns(QEMU_CLOCK_VIRTUAL);
 584    chan = s->next_chan;
 585
 586    do {
 587        p = &s->packet[chan];
 588        if (p->needs_service) {
 589            dev = dwc2_find_device(s, p->devadr);
 590            ep = usb_ep_get(dev, p->pid, p->epnum);
 591            trace_usb_dwc2_work_bh_service(s->next_chan, chan, dev, p->epnum);
 592            dwc2_handle_packet(s, p->devadr, dev, ep, p->index, true);
 593            found = true;
 594        }
 595        if (++chan == DWC2_NB_CHAN) {
 596            chan = 0;
 597        }
 598        if (found) {
 599            s->next_chan = chan;
 600            trace_usb_dwc2_work_bh_next(chan);
 601        }
 602    } while (chan != s->next_chan);
 603
 604    if (found) {
 605        expire_time = t_now + NANOSECONDS_PER_SECOND / 4000;
 606        timer_mod(s->frame_timer, expire_time);
 607    }
 608    s->working = false;
 609}
 610
 611static void dwc2_enable_chan(DWC2State *s,  uint32_t index)
 612{
 613    USBDevice *dev;
 614    USBEndpoint *ep;
 615    uint32_t hcchar;
 616    uint32_t hctsiz;
 617    uint32_t devadr, epnum, epdir, eptype, pid, len;
 618    DWC2Packet *p;
 619
 620    assert((index >> 3) < DWC2_NB_CHAN);
 621    p = &s->packet[index >> 3];
 622    hcchar = s->hreg1[index];
 623    hctsiz = s->hreg1[index + 4];
 624    devadr = get_field(hcchar, HCCHAR_DEVADDR);
 625    epnum = get_field(hcchar, HCCHAR_EPNUM);
 626    epdir = get_bit(hcchar, HCCHAR_EPDIR);
 627    eptype = get_field(hcchar, HCCHAR_EPTYPE);
 628    pid = get_field(hctsiz, TSIZ_SC_MC_PID);
 629    len = get_field(hctsiz, TSIZ_XFERSIZE);
 630
 631    dev = dwc2_find_device(s, devadr);
 632
 633    trace_usb_dwc2_enable_chan(index >> 3, dev, &p->packet, epnum);
 634    if (dev == NULL) {
 635        return;
 636    }
 637
 638    if (eptype == USB_ENDPOINT_XFER_CONTROL && pid == TSIZ_SC_MC_PID_SETUP) {
 639        pid = USB_TOKEN_SETUP;
 640    } else {
 641        pid = epdir ? USB_TOKEN_IN : USB_TOKEN_OUT;
 642    }
 643
 644    ep = usb_ep_get(dev, pid, epnum);
 645
 646    /*
 647     * Hack: Networking doesn't like us delivering large transfers, it kind
 648     * of works but the latency is horrible. So if the transfer is <= the mtu
 649     * size, we take that as a hint that this might be a network transfer,
 650     * and do the transfer packet-by-packet.
 651     */
 652    if (len > 1536) {
 653        p->small = false;
 654    } else {
 655        p->small = true;
 656    }
 657
 658    dwc2_handle_packet(s, devadr, dev, ep, index, true);
 659    qemu_bh_schedule(s->async_bh);
 660}
 661
 662static const char *glbregnm[] = {
 663    "GOTGCTL  ", "GOTGINT  ", "GAHBCFG  ", "GUSBCFG  ", "GRSTCTL  ",
 664    "GINTSTS  ", "GINTMSK  ", "GRXSTSR  ", "GRXSTSP  ", "GRXFSIZ  ",
 665    "GNPTXFSIZ", "GNPTXSTS ", "GI2CCTL  ", "GPVNDCTL ", "GGPIO    ",
 666    "GUID     ", "GSNPSID  ", "GHWCFG1  ", "GHWCFG2  ", "GHWCFG3  ",
 667    "GHWCFG4  ", "GLPMCFG  ", "GPWRDN   ", "GDFIFOCFG", "GADPCTL  ",
 668    "GREFCLK  ", "GINTMSK2 ", "GINTSTS2 "
 669};
 670
 671static uint64_t dwc2_glbreg_read(void *ptr, hwaddr addr, int index,
 672                                 unsigned size)
 673{
 674    DWC2State *s = ptr;
 675    uint32_t val;
 676
 677    if (addr > GINTSTS2) {
 678        qemu_log_mask(LOG_GUEST_ERROR, "%s: Bad offset 0x%"HWADDR_PRIx"\n",
 679                      __func__, addr);
 680        return 0;
 681    }
 682
 683    val = s->glbreg[index];
 684
 685    switch (addr) {
 686    case GRSTCTL:
 687        /* clear any self-clearing bits that were set */
 688        val &= ~(GRSTCTL_TXFFLSH | GRSTCTL_RXFFLSH | GRSTCTL_IN_TKNQ_FLSH |
 689                 GRSTCTL_FRMCNTRRST | GRSTCTL_HSFTRST | GRSTCTL_CSFTRST);
 690        s->glbreg[index] = val;
 691        break;
 692    default:
 693        break;
 694    }
 695
 696    trace_usb_dwc2_glbreg_read(addr, glbregnm[index], val);
 697    return val;
 698}
 699
 700static void dwc2_glbreg_write(void *ptr, hwaddr addr, int index, uint64_t val,
 701                              unsigned size)
 702{
 703    DWC2State *s = ptr;
 704    uint64_t orig = val;
 705    uint32_t *mmio;
 706    uint32_t old;
 707    int iflg = 0;
 708
 709    if (addr > GINTSTS2) {
 710        qemu_log_mask(LOG_GUEST_ERROR, "%s: Bad offset 0x%"HWADDR_PRIx"\n",
 711                      __func__, addr);
 712        return;
 713    }
 714
 715    mmio = &s->glbreg[index];
 716    old = *mmio;
 717
 718    switch (addr) {
 719    case GOTGCTL:
 720        /* don't allow setting of read-only bits */
 721        val &= ~(GOTGCTL_MULT_VALID_BC_MASK | GOTGCTL_BSESVLD |
 722                 GOTGCTL_ASESVLD | GOTGCTL_DBNC_SHORT | GOTGCTL_CONID_B |
 723                 GOTGCTL_HSTNEGSCS | GOTGCTL_SESREQSCS);
 724        /* don't allow clearing of read-only bits */
 725        val |= old & (GOTGCTL_MULT_VALID_BC_MASK | GOTGCTL_BSESVLD |
 726                      GOTGCTL_ASESVLD | GOTGCTL_DBNC_SHORT | GOTGCTL_CONID_B |
 727                      GOTGCTL_HSTNEGSCS | GOTGCTL_SESREQSCS);
 728        break;
 729    case GAHBCFG:
 730        if ((val & GAHBCFG_GLBL_INTR_EN) && !(old & GAHBCFG_GLBL_INTR_EN)) {
 731            iflg = 1;
 732        }
 733        break;
 734    case GRSTCTL:
 735        val |= GRSTCTL_AHBIDLE;
 736        val &= ~GRSTCTL_DMAREQ;
 737        if (!(old & GRSTCTL_TXFFLSH) && (val & GRSTCTL_TXFFLSH)) {
 738                /* TODO - TX fifo flush */
 739            qemu_log_mask(LOG_UNIMP, "%s: Tx FIFO flush not implemented\n",
 740                          __func__);
 741        }
 742        if (!(old & GRSTCTL_RXFFLSH) && (val & GRSTCTL_RXFFLSH)) {
 743                /* TODO - RX fifo flush */
 744            qemu_log_mask(LOG_UNIMP, "%s: Rx FIFO flush not implemented\n",
 745                          __func__);
 746        }
 747        if (!(old & GRSTCTL_IN_TKNQ_FLSH) && (val & GRSTCTL_IN_TKNQ_FLSH)) {
 748                /* TODO - device IN token queue flush */
 749            qemu_log_mask(LOG_UNIMP, "%s: Token queue flush not implemented\n",
 750                          __func__);
 751        }
 752        if (!(old & GRSTCTL_FRMCNTRRST) && (val & GRSTCTL_FRMCNTRRST)) {
 753                /* TODO - host frame counter reset */
 754            qemu_log_mask(LOG_UNIMP,
 755                          "%s: Frame counter reset not implemented\n",
 756                          __func__);
 757        }
 758        if (!(old & GRSTCTL_HSFTRST) && (val & GRSTCTL_HSFTRST)) {
 759                /* TODO - host soft reset */
 760            qemu_log_mask(LOG_UNIMP, "%s: Host soft reset not implemented\n",
 761                          __func__);
 762        }
 763        if (!(old & GRSTCTL_CSFTRST) && (val & GRSTCTL_CSFTRST)) {
 764                /* TODO - core soft reset */
 765            qemu_log_mask(LOG_UNIMP, "%s: Core soft reset not implemented\n",
 766                          __func__);
 767        }
 768        /* don't allow clearing of self-clearing bits */
 769        val |= old & (GRSTCTL_TXFFLSH | GRSTCTL_RXFFLSH |
 770                      GRSTCTL_IN_TKNQ_FLSH | GRSTCTL_FRMCNTRRST |
 771                      GRSTCTL_HSFTRST | GRSTCTL_CSFTRST);
 772        break;
 773    case GINTSTS:
 774        /* clear the write-1-to-clear bits */
 775        val |= ~old;
 776        val = ~val;
 777        /* don't allow clearing of read-only bits */
 778        val |= old & (GINTSTS_PTXFEMP | GINTSTS_HCHINT | GINTSTS_PRTINT |
 779                      GINTSTS_OEPINT | GINTSTS_IEPINT | GINTSTS_GOUTNAKEFF |
 780                      GINTSTS_GINNAKEFF | GINTSTS_NPTXFEMP | GINTSTS_RXFLVL |
 781                      GINTSTS_OTGINT | GINTSTS_CURMODE_HOST);
 782        iflg = 1;
 783        break;
 784    case GINTMSK:
 785        iflg = 1;
 786        break;
 787    default:
 788        break;
 789    }
 790
 791    trace_usb_dwc2_glbreg_write(addr, glbregnm[index], orig, old, val);
 792    *mmio = val;
 793
 794    if (iflg) {
 795        dwc2_update_irq(s);
 796    }
 797}
 798
 799static uint64_t dwc2_fszreg_read(void *ptr, hwaddr addr, int index,
 800                                 unsigned size)
 801{
 802    DWC2State *s = ptr;
 803    uint32_t val;
 804
 805    if (addr != HPTXFSIZ) {
 806        qemu_log_mask(LOG_GUEST_ERROR, "%s: Bad offset 0x%"HWADDR_PRIx"\n",
 807                      __func__, addr);
 808        return 0;
 809    }
 810
 811    val = s->fszreg[index];
 812
 813    trace_usb_dwc2_fszreg_read(addr, val);
 814    return val;
 815}
 816
 817static void dwc2_fszreg_write(void *ptr, hwaddr addr, int index, uint64_t val,
 818                              unsigned size)
 819{
 820    DWC2State *s = ptr;
 821    uint64_t orig = val;
 822    uint32_t *mmio;
 823    uint32_t old;
 824
 825    if (addr != HPTXFSIZ) {
 826        qemu_log_mask(LOG_GUEST_ERROR, "%s: Bad offset 0x%"HWADDR_PRIx"\n",
 827                      __func__, addr);
 828        return;
 829    }
 830
 831    mmio = &s->fszreg[index];
 832    old = *mmio;
 833
 834    trace_usb_dwc2_fszreg_write(addr, orig, old, val);
 835    *mmio = val;
 836}
 837
 838static const char *hreg0nm[] = {
 839    "HCFG     ", "HFIR     ", "HFNUM    ", "<rsvd>   ", "HPTXSTS  ",
 840    "HAINT    ", "HAINTMSK ", "HFLBADDR ", "<rsvd>   ", "<rsvd>   ",
 841    "<rsvd>   ", "<rsvd>   ", "<rsvd>   ", "<rsvd>   ", "<rsvd>   ",
 842    "<rsvd>   ", "HPRT0    "
 843};
 844
 845static uint64_t dwc2_hreg0_read(void *ptr, hwaddr addr, int index,
 846                                unsigned size)
 847{
 848    DWC2State *s = ptr;
 849    uint32_t val;
 850
 851    if (addr < HCFG || addr > HPRT0) {
 852        qemu_log_mask(LOG_GUEST_ERROR, "%s: Bad offset 0x%"HWADDR_PRIx"\n",
 853                      __func__, addr);
 854        return 0;
 855    }
 856
 857    val = s->hreg0[index];
 858
 859    switch (addr) {
 860    case HFNUM:
 861        val = (dwc2_get_frame_remaining(s) << HFNUM_FRREM_SHIFT) |
 862              (s->hfnum << HFNUM_FRNUM_SHIFT);
 863        break;
 864    default:
 865        break;
 866    }
 867
 868    trace_usb_dwc2_hreg0_read(addr, hreg0nm[index], val);
 869    return val;
 870}
 871
 872static void dwc2_hreg0_write(void *ptr, hwaddr addr, int index, uint64_t val,
 873                             unsigned size)
 874{
 875    DWC2State *s = ptr;
 876    USBDevice *dev = s->uport.dev;
 877    uint64_t orig = val;
 878    uint32_t *mmio;
 879    uint32_t tval, told, old;
 880    int prst = 0;
 881    int iflg = 0;
 882
 883    if (addr < HCFG || addr > HPRT0) {
 884        qemu_log_mask(LOG_GUEST_ERROR, "%s: Bad offset 0x%"HWADDR_PRIx"\n",
 885                      __func__, addr);
 886        return;
 887    }
 888
 889    mmio = &s->hreg0[index];
 890    old = *mmio;
 891
 892    switch (addr) {
 893    case HFIR:
 894        break;
 895    case HFNUM:
 896    case HPTXSTS:
 897    case HAINT:
 898        qemu_log_mask(LOG_GUEST_ERROR, "%s: write to read-only register\n",
 899                      __func__);
 900        return;
 901    case HAINTMSK:
 902        val &= 0xffff;
 903        break;
 904    case HPRT0:
 905        /* don't allow clearing of read-only bits */
 906        val |= old & (HPRT0_SPD_MASK | HPRT0_LNSTS_MASK | HPRT0_OVRCURRACT |
 907                      HPRT0_CONNSTS);
 908        /* don't allow clearing of self-clearing bits */
 909        val |= old & (HPRT0_SUSP | HPRT0_RES);
 910        /* don't allow setting of self-setting bits */
 911        if (!(old & HPRT0_ENA) && (val & HPRT0_ENA)) {
 912            val &= ~HPRT0_ENA;
 913        }
 914        /* clear the write-1-to-clear bits */
 915        tval = val & (HPRT0_OVRCURRCHG | HPRT0_ENACHG | HPRT0_ENA |
 916                      HPRT0_CONNDET);
 917        told = old & (HPRT0_OVRCURRCHG | HPRT0_ENACHG | HPRT0_ENA |
 918                      HPRT0_CONNDET);
 919        tval |= ~told;
 920        tval = ~tval;
 921        tval &= (HPRT0_OVRCURRCHG | HPRT0_ENACHG | HPRT0_ENA |
 922                 HPRT0_CONNDET);
 923        val &= ~(HPRT0_OVRCURRCHG | HPRT0_ENACHG | HPRT0_ENA |
 924                 HPRT0_CONNDET);
 925        val |= tval;
 926        if (!(val & HPRT0_RST) && (old & HPRT0_RST)) {
 927            if (dev && dev->attached) {
 928                val |= HPRT0_ENA | HPRT0_ENACHG;
 929                prst = 1;
 930            }
 931        }
 932        if (val & (HPRT0_OVRCURRCHG | HPRT0_ENACHG | HPRT0_CONNDET)) {
 933            iflg = 1;
 934        } else {
 935            iflg = -1;
 936        }
 937        break;
 938    default:
 939        break;
 940    }
 941
 942    if (prst) {
 943        trace_usb_dwc2_hreg0_write(addr, hreg0nm[index], orig, old,
 944                                   val & ~HPRT0_CONNDET);
 945        trace_usb_dwc2_hreg0_action("call usb_port_reset");
 946        usb_port_reset(&s->uport);
 947        val &= ~HPRT0_CONNDET;
 948    } else {
 949        trace_usb_dwc2_hreg0_write(addr, hreg0nm[index], orig, old, val);
 950    }
 951
 952    *mmio = val;
 953
 954    if (iflg > 0) {
 955        trace_usb_dwc2_hreg0_action("enable PRTINT");
 956        dwc2_raise_global_irq(s, GINTSTS_PRTINT);
 957    } else if (iflg < 0) {
 958        trace_usb_dwc2_hreg0_action("disable PRTINT");
 959        dwc2_lower_global_irq(s, GINTSTS_PRTINT);
 960    }
 961}
 962
 963static const char *hreg1nm[] = {
 964    "HCCHAR  ", "HCSPLT  ", "HCINT   ", "HCINTMSK", "HCTSIZ  ", "HCDMA   ",
 965    "<rsvd>  ", "HCDMAB  "
 966};
 967
 968static uint64_t dwc2_hreg1_read(void *ptr, hwaddr addr, int index,
 969                                unsigned size)
 970{
 971    DWC2State *s = ptr;
 972    uint32_t val;
 973
 974    if (addr < HCCHAR(0) || addr > HCDMAB(DWC2_NB_CHAN - 1)) {
 975        qemu_log_mask(LOG_GUEST_ERROR, "%s: Bad offset 0x%"HWADDR_PRIx"\n",
 976                      __func__, addr);
 977        return 0;
 978    }
 979
 980    val = s->hreg1[index];
 981
 982    trace_usb_dwc2_hreg1_read(addr, hreg1nm[index & 7], addr >> 5, val);
 983    return val;
 984}
 985
 986static void dwc2_hreg1_write(void *ptr, hwaddr addr, int index, uint64_t val,
 987                             unsigned size)
 988{
 989    DWC2State *s = ptr;
 990    uint64_t orig = val;
 991    uint32_t *mmio;
 992    uint32_t old;
 993    int iflg = 0;
 994    int enflg = 0;
 995    int disflg = 0;
 996
 997    if (addr < HCCHAR(0) || addr > HCDMAB(DWC2_NB_CHAN - 1)) {
 998        qemu_log_mask(LOG_GUEST_ERROR, "%s: Bad offset 0x%"HWADDR_PRIx"\n",
 999                      __func__, addr);
1000        return;
1001    }
1002
1003    mmio = &s->hreg1[index];
1004    old = *mmio;
1005
1006    switch (HSOTG_REG(0x500) + (addr & 0x1c)) {
1007    case HCCHAR(0):
1008        if ((val & HCCHAR_CHDIS) && !(old & HCCHAR_CHDIS)) {
1009            val &= ~(HCCHAR_CHENA | HCCHAR_CHDIS);
1010            disflg = 1;
1011        } else {
1012            val |= old & HCCHAR_CHDIS;
1013            if ((val & HCCHAR_CHENA) && !(old & HCCHAR_CHENA)) {
1014                val &= ~HCCHAR_CHDIS;
1015                enflg = 1;
1016            } else {
1017                val |= old & HCCHAR_CHENA;
1018            }
1019        }
1020        break;
1021    case HCINT(0):
1022        /* clear the write-1-to-clear bits */
1023        val |= ~old;
1024        val = ~val;
1025        val &= ~HCINTMSK_RESERVED14_31;
1026        iflg = 1;
1027        break;
1028    case HCINTMSK(0):
1029        val &= ~HCINTMSK_RESERVED14_31;
1030        iflg = 1;
1031        break;
1032    case HCDMAB(0):
1033        qemu_log_mask(LOG_GUEST_ERROR, "%s: write to read-only register\n",
1034                      __func__);
1035        return;
1036    default:
1037        break;
1038    }
1039
1040    trace_usb_dwc2_hreg1_write(addr, hreg1nm[index & 7], index >> 3, orig,
1041                               old, val);
1042    *mmio = val;
1043
1044    if (disflg) {
1045        /* set ChHltd in HCINT */
1046        s->hreg1[(index & ~7) + 2] |= HCINTMSK_CHHLTD;
1047        iflg = 1;
1048    }
1049
1050    if (enflg) {
1051        dwc2_enable_chan(s, index & ~7);
1052    }
1053
1054    if (iflg) {
1055        dwc2_update_hc_irq(s, index & ~7);
1056    }
1057}
1058
1059static const char *pcgregnm[] = {
1060        "PCGCTL   ", "PCGCCTL1 "
1061};
1062
1063static uint64_t dwc2_pcgreg_read(void *ptr, hwaddr addr, int index,
1064                                 unsigned size)
1065{
1066    DWC2State *s = ptr;
1067    uint32_t val;
1068
1069    if (addr < PCGCTL || addr > PCGCCTL1) {
1070        qemu_log_mask(LOG_GUEST_ERROR, "%s: Bad offset 0x%"HWADDR_PRIx"\n",
1071                      __func__, addr);
1072        return 0;
1073    }
1074
1075    val = s->pcgreg[index];
1076
1077    trace_usb_dwc2_pcgreg_read(addr, pcgregnm[index], val);
1078    return val;
1079}
1080
1081static void dwc2_pcgreg_write(void *ptr, hwaddr addr, int index,
1082                              uint64_t val, unsigned size)
1083{
1084    DWC2State *s = ptr;
1085    uint64_t orig = val;
1086    uint32_t *mmio;
1087    uint32_t old;
1088
1089    if (addr < PCGCTL || addr > PCGCCTL1) {
1090        qemu_log_mask(LOG_GUEST_ERROR, "%s: Bad offset 0x%"HWADDR_PRIx"\n",
1091                      __func__, addr);
1092        return;
1093    }
1094
1095    mmio = &s->pcgreg[index];
1096    old = *mmio;
1097
1098    trace_usb_dwc2_pcgreg_write(addr, pcgregnm[index], orig, old, val);
1099    *mmio = val;
1100}
1101
1102static uint64_t dwc2_hsotg_read(void *ptr, hwaddr addr, unsigned size)
1103{
1104    uint64_t val;
1105
1106    switch (addr) {
1107    case HSOTG_REG(0x000) ... HSOTG_REG(0x0fc):
1108        val = dwc2_glbreg_read(ptr, addr, (addr - HSOTG_REG(0x000)) >> 2, size);
1109        break;
1110    case HSOTG_REG(0x100):
1111        val = dwc2_fszreg_read(ptr, addr, (addr - HSOTG_REG(0x100)) >> 2, size);
1112        break;
1113    case HSOTG_REG(0x104) ... HSOTG_REG(0x3fc):
1114        /* Gadget-mode registers, just return 0 for now */
1115        val = 0;
1116        break;
1117    case HSOTG_REG(0x400) ... HSOTG_REG(0x4fc):
1118        val = dwc2_hreg0_read(ptr, addr, (addr - HSOTG_REG(0x400)) >> 2, size);
1119        break;
1120    case HSOTG_REG(0x500) ... HSOTG_REG(0x7fc):
1121        val = dwc2_hreg1_read(ptr, addr, (addr - HSOTG_REG(0x500)) >> 2, size);
1122        break;
1123    case HSOTG_REG(0x800) ... HSOTG_REG(0xdfc):
1124        /* Gadget-mode registers, just return 0 for now */
1125        val = 0;
1126        break;
1127    case HSOTG_REG(0xe00) ... HSOTG_REG(0xffc):
1128        val = dwc2_pcgreg_read(ptr, addr, (addr - HSOTG_REG(0xe00)) >> 2, size);
1129        break;
1130    default:
1131        g_assert_not_reached();
1132    }
1133
1134    return val;
1135}
1136
1137static void dwc2_hsotg_write(void *ptr, hwaddr addr, uint64_t val,
1138                             unsigned size)
1139{
1140    switch (addr) {
1141    case HSOTG_REG(0x000) ... HSOTG_REG(0x0fc):
1142        dwc2_glbreg_write(ptr, addr, (addr - HSOTG_REG(0x000)) >> 2, val, size);
1143        break;
1144    case HSOTG_REG(0x100):
1145        dwc2_fszreg_write(ptr, addr, (addr - HSOTG_REG(0x100)) >> 2, val, size);
1146        break;
1147    case HSOTG_REG(0x104) ... HSOTG_REG(0x3fc):
1148        /* Gadget-mode registers, do nothing for now */
1149        break;
1150    case HSOTG_REG(0x400) ... HSOTG_REG(0x4fc):
1151        dwc2_hreg0_write(ptr, addr, (addr - HSOTG_REG(0x400)) >> 2, val, size);
1152        break;
1153    case HSOTG_REG(0x500) ... HSOTG_REG(0x7fc):
1154        dwc2_hreg1_write(ptr, addr, (addr - HSOTG_REG(0x500)) >> 2, val, size);
1155        break;
1156    case HSOTG_REG(0x800) ... HSOTG_REG(0xdfc):
1157        /* Gadget-mode registers, do nothing for now */
1158        break;
1159    case HSOTG_REG(0xe00) ... HSOTG_REG(0xffc):
1160        dwc2_pcgreg_write(ptr, addr, (addr - HSOTG_REG(0xe00)) >> 2, val, size);
1161        break;
1162    default:
1163        g_assert_not_reached();
1164    }
1165}
1166
1167static const MemoryRegionOps dwc2_mmio_hsotg_ops = {
1168    .read = dwc2_hsotg_read,
1169    .write = dwc2_hsotg_write,
1170    .impl.min_access_size = 4,
1171    .impl.max_access_size = 4,
1172    .endianness = DEVICE_LITTLE_ENDIAN,
1173};
1174
1175static uint64_t dwc2_hreg2_read(void *ptr, hwaddr addr, unsigned size)
1176{
1177    /* TODO - implement FIFOs to support slave mode */
1178    trace_usb_dwc2_hreg2_read(addr, addr >> 12, 0);
1179    qemu_log_mask(LOG_UNIMP, "%s: FIFO read not implemented\n", __func__);
1180    return 0;
1181}
1182
1183static void dwc2_hreg2_write(void *ptr, hwaddr addr, uint64_t val,
1184                             unsigned size)
1185{
1186    uint64_t orig = val;
1187
1188    /* TODO - implement FIFOs to support slave mode */
1189    trace_usb_dwc2_hreg2_write(addr, addr >> 12, orig, 0, val);
1190    qemu_log_mask(LOG_UNIMP, "%s: FIFO write not implemented\n", __func__);
1191}
1192
1193static const MemoryRegionOps dwc2_mmio_hreg2_ops = {
1194    .read = dwc2_hreg2_read,
1195    .write = dwc2_hreg2_write,
1196    .impl.min_access_size = 4,
1197    .impl.max_access_size = 4,
1198    .endianness = DEVICE_LITTLE_ENDIAN,
1199};
1200
1201static void dwc2_wakeup_endpoint(USBBus *bus, USBEndpoint *ep,
1202                                 unsigned int stream)
1203{
1204    DWC2State *s = container_of(bus, DWC2State, bus);
1205
1206    trace_usb_dwc2_wakeup_endpoint(ep, stream);
1207
1208    /* TODO - do something here? */
1209    qemu_bh_schedule(s->async_bh);
1210}
1211
1212static USBBusOps dwc2_bus_ops = {
1213    .wakeup_endpoint = dwc2_wakeup_endpoint,
1214};
1215
1216static void dwc2_work_timer(void *opaque)
1217{
1218    DWC2State *s = opaque;
1219
1220    trace_usb_dwc2_work_timer();
1221    qemu_bh_schedule(s->async_bh);
1222}
1223
1224static void dwc2_reset_enter(Object *obj, ResetType type)
1225{
1226    DWC2Class *c = DWC2_USB_GET_CLASS(obj);
1227    DWC2State *s = DWC2_USB(obj);
1228    int i;
1229
1230    trace_usb_dwc2_reset_enter();
1231
1232    if (c->parent_phases.enter) {
1233        c->parent_phases.enter(obj, type);
1234    }
1235
1236    timer_del(s->frame_timer);
1237    qemu_bh_cancel(s->async_bh);
1238
1239    if (s->uport.dev && s->uport.dev->attached) {
1240        usb_detach(&s->uport);
1241    }
1242
1243    dwc2_bus_stop(s);
1244
1245    s->gotgctl = GOTGCTL_BSESVLD | GOTGCTL_ASESVLD | GOTGCTL_CONID_B;
1246    s->gotgint = 0;
1247    s->gahbcfg = 0;
1248    s->gusbcfg = 5 << GUSBCFG_USBTRDTIM_SHIFT;
1249    s->grstctl = GRSTCTL_AHBIDLE;
1250    s->gintsts = GINTSTS_CONIDSTSCHNG | GINTSTS_PTXFEMP | GINTSTS_NPTXFEMP |
1251                 GINTSTS_CURMODE_HOST;
1252    s->gintmsk = 0;
1253    s->grxstsr = 0;
1254    s->grxstsp = 0;
1255    s->grxfsiz = 1024;
1256    s->gnptxfsiz = 1024 << FIFOSIZE_DEPTH_SHIFT;
1257    s->gnptxsts = (4 << FIFOSIZE_DEPTH_SHIFT) | 1024;
1258    s->gi2cctl = GI2CCTL_I2CDATSE0 | GI2CCTL_ACK;
1259    s->gpvndctl = 0;
1260    s->ggpio = 0;
1261    s->guid = 0;
1262    s->gsnpsid = 0x4f54294a;
1263    s->ghwcfg1 = 0;
1264    s->ghwcfg2 = (8 << GHWCFG2_DEV_TOKEN_Q_DEPTH_SHIFT) |
1265                 (4 << GHWCFG2_HOST_PERIO_TX_Q_DEPTH_SHIFT) |
1266                 (4 << GHWCFG2_NONPERIO_TX_Q_DEPTH_SHIFT) |
1267                 GHWCFG2_DYNAMIC_FIFO |
1268                 GHWCFG2_PERIO_EP_SUPPORTED |
1269                 ((DWC2_NB_CHAN - 1) << GHWCFG2_NUM_HOST_CHAN_SHIFT) |
1270                 (GHWCFG2_INT_DMA_ARCH << GHWCFG2_ARCHITECTURE_SHIFT) |
1271                 (GHWCFG2_OP_MODE_NO_SRP_CAPABLE_HOST << GHWCFG2_OP_MODE_SHIFT);
1272    s->ghwcfg3 = (4096 << GHWCFG3_DFIFO_DEPTH_SHIFT) |
1273                 (4 << GHWCFG3_PACKET_SIZE_CNTR_WIDTH_SHIFT) |
1274                 (4 << GHWCFG3_XFER_SIZE_CNTR_WIDTH_SHIFT);
1275    s->ghwcfg4 = 0;
1276    s->glpmcfg = 0;
1277    s->gpwrdn = GPWRDN_PWRDNRSTN;
1278    s->gdfifocfg = 0;
1279    s->gadpctl = 0;
1280    s->grefclk = 0;
1281    s->gintmsk2 = 0;
1282    s->gintsts2 = 0;
1283
1284    s->hptxfsiz = 500 << FIFOSIZE_DEPTH_SHIFT;
1285
1286    s->hcfg = 2 << HCFG_RESVALID_SHIFT;
1287    s->hfir = 60000;
1288    s->hfnum = 0x3fff;
1289    s->hptxsts = (16 << TXSTS_QSPCAVAIL_SHIFT) | 32768;
1290    s->haint = 0;
1291    s->haintmsk = 0;
1292    s->hprt0 = 0;
1293
1294    memset(s->hreg1, 0, sizeof(s->hreg1));
1295    memset(s->pcgreg, 0, sizeof(s->pcgreg));
1296
1297    s->sof_time = 0;
1298    s->frame_number = 0;
1299    s->fi = USB_FRMINTVL - 1;
1300    s->next_chan = 0;
1301    s->working = false;
1302
1303    for (i = 0; i < DWC2_NB_CHAN; i++) {
1304        s->packet[i].needs_service = false;
1305    }
1306}
1307
1308static void dwc2_reset_hold(Object *obj)
1309{
1310    DWC2Class *c = DWC2_USB_GET_CLASS(obj);
1311    DWC2State *s = DWC2_USB(obj);
1312
1313    trace_usb_dwc2_reset_hold();
1314
1315    if (c->parent_phases.hold) {
1316        c->parent_phases.hold(obj);
1317    }
1318
1319    dwc2_update_irq(s);
1320}
1321
1322static void dwc2_reset_exit(Object *obj)
1323{
1324    DWC2Class *c = DWC2_USB_GET_CLASS(obj);
1325    DWC2State *s = DWC2_USB(obj);
1326
1327    trace_usb_dwc2_reset_exit();
1328
1329    if (c->parent_phases.exit) {
1330        c->parent_phases.exit(obj);
1331    }
1332
1333    s->hprt0 = HPRT0_PWR;
1334    if (s->uport.dev && s->uport.dev->attached) {
1335        usb_attach(&s->uport);
1336        usb_device_reset(s->uport.dev);
1337    }
1338}
1339
1340static void dwc2_realize(DeviceState *dev, Error **errp)
1341{
1342    SysBusDevice *sbd = SYS_BUS_DEVICE(dev);
1343    DWC2State *s = DWC2_USB(dev);
1344    Object *obj;
1345
1346    obj = object_property_get_link(OBJECT(dev), "dma-mr", &error_abort);
1347
1348    s->dma_mr = MEMORY_REGION(obj);
1349    address_space_init(&s->dma_as, s->dma_mr, "dwc2");
1350
1351    usb_bus_new(&s->bus, sizeof(s->bus), &dwc2_bus_ops, dev);
1352    usb_register_port(&s->bus, &s->uport, s, 0, &dwc2_port_ops,
1353                      USB_SPEED_MASK_LOW | USB_SPEED_MASK_FULL |
1354                      (s->usb_version == 2 ? USB_SPEED_MASK_HIGH : 0));
1355    s->uport.dev = 0;
1356
1357    s->usb_frame_time = NANOSECONDS_PER_SECOND / 1000;          /* 1000000 */
1358    if (NANOSECONDS_PER_SECOND >= USB_HZ_FS) {
1359        s->usb_bit_time = NANOSECONDS_PER_SECOND / USB_HZ_FS;   /* 83.3 */
1360    } else {
1361        s->usb_bit_time = 1;
1362    }
1363
1364    s->fi = USB_FRMINTVL - 1;
1365    s->eof_timer = timer_new_ns(QEMU_CLOCK_VIRTUAL, dwc2_frame_boundary, s);
1366    s->frame_timer = timer_new_ns(QEMU_CLOCK_VIRTUAL, dwc2_work_timer, s);
1367    s->async_bh = qemu_bh_new(dwc2_work_bh, s);
1368
1369    sysbus_init_irq(sbd, &s->irq);
1370}
1371
1372static void dwc2_init(Object *obj)
1373{
1374    SysBusDevice *sbd = SYS_BUS_DEVICE(obj);
1375    DWC2State *s = DWC2_USB(obj);
1376
1377    memory_region_init(&s->container, obj, "dwc2", DWC2_MMIO_SIZE);
1378    sysbus_init_mmio(sbd, &s->container);
1379
1380    memory_region_init_io(&s->hsotg, obj, &dwc2_mmio_hsotg_ops, s,
1381                          "dwc2-io", 4 * KiB);
1382    memory_region_add_subregion(&s->container, 0x0000, &s->hsotg);
1383
1384    memory_region_init_io(&s->fifos, obj, &dwc2_mmio_hreg2_ops, s,
1385                          "dwc2-fifo", 64 * KiB);
1386    memory_region_add_subregion(&s->container, 0x1000, &s->fifos);
1387}
1388
1389static const VMStateDescription vmstate_dwc2_state_packet = {
1390    .name = "dwc2/packet",
1391    .version_id = 1,
1392    .minimum_version_id = 1,
1393    .fields = (VMStateField[]) {
1394        VMSTATE_UINT32(devadr, DWC2Packet),
1395        VMSTATE_UINT32(epnum, DWC2Packet),
1396        VMSTATE_UINT32(epdir, DWC2Packet),
1397        VMSTATE_UINT32(mps, DWC2Packet),
1398        VMSTATE_UINT32(pid, DWC2Packet),
1399        VMSTATE_UINT32(index, DWC2Packet),
1400        VMSTATE_UINT32(pcnt, DWC2Packet),
1401        VMSTATE_UINT32(len, DWC2Packet),
1402        VMSTATE_INT32(async, DWC2Packet),
1403        VMSTATE_BOOL(small, DWC2Packet),
1404        VMSTATE_BOOL(needs_service, DWC2Packet),
1405        VMSTATE_END_OF_LIST()
1406    },
1407};
1408
1409const VMStateDescription vmstate_dwc2_state = {
1410    .name = "dwc2",
1411    .version_id = 1,
1412    .minimum_version_id = 1,
1413    .fields = (VMStateField[]) {
1414        VMSTATE_UINT32_ARRAY(glbreg, DWC2State,
1415                             DWC2_GLBREG_SIZE / sizeof(uint32_t)),
1416        VMSTATE_UINT32_ARRAY(fszreg, DWC2State,
1417                             DWC2_FSZREG_SIZE / sizeof(uint32_t)),
1418        VMSTATE_UINT32_ARRAY(hreg0, DWC2State,
1419                             DWC2_HREG0_SIZE / sizeof(uint32_t)),
1420        VMSTATE_UINT32_ARRAY(hreg1, DWC2State,
1421                             DWC2_HREG1_SIZE / sizeof(uint32_t)),
1422        VMSTATE_UINT32_ARRAY(pcgreg, DWC2State,
1423                             DWC2_PCGREG_SIZE / sizeof(uint32_t)),
1424
1425        VMSTATE_TIMER_PTR(eof_timer, DWC2State),
1426        VMSTATE_TIMER_PTR(frame_timer, DWC2State),
1427        VMSTATE_INT64(sof_time, DWC2State),
1428        VMSTATE_INT64(usb_frame_time, DWC2State),
1429        VMSTATE_INT64(usb_bit_time, DWC2State),
1430        VMSTATE_UINT32(usb_version, DWC2State),
1431        VMSTATE_UINT16(frame_number, DWC2State),
1432        VMSTATE_UINT16(fi, DWC2State),
1433        VMSTATE_UINT16(next_chan, DWC2State),
1434        VMSTATE_BOOL(working, DWC2State),
1435
1436        VMSTATE_STRUCT_ARRAY(packet, DWC2State, DWC2_NB_CHAN, 1,
1437                             vmstate_dwc2_state_packet, DWC2Packet),
1438        VMSTATE_UINT8_2DARRAY(usb_buf, DWC2State, DWC2_NB_CHAN,
1439                              DWC2_MAX_XFER_SIZE),
1440
1441        VMSTATE_END_OF_LIST()
1442    }
1443};
1444
1445static Property dwc2_usb_properties[] = {
1446    DEFINE_PROP_UINT32("usb_version", DWC2State, usb_version, 2),
1447    DEFINE_PROP_END_OF_LIST(),
1448};
1449
1450static void dwc2_class_init(ObjectClass *klass, void *data)
1451{
1452    DeviceClass *dc = DEVICE_CLASS(klass);
1453    DWC2Class *c = DWC2_USB_CLASS(klass);
1454    ResettableClass *rc = RESETTABLE_CLASS(klass);
1455
1456    dc->realize = dwc2_realize;
1457    dc->vmsd = &vmstate_dwc2_state;
1458    set_bit(DEVICE_CATEGORY_USB, dc->categories);
1459    device_class_set_props(dc, dwc2_usb_properties);
1460    resettable_class_set_parent_phases(rc, dwc2_reset_enter, dwc2_reset_hold,
1461                                       dwc2_reset_exit, &c->parent_phases);
1462}
1463
1464static const TypeInfo dwc2_usb_type_info = {
1465    .name          = TYPE_DWC2_USB,
1466    .parent        = TYPE_SYS_BUS_DEVICE,
1467    .instance_size = sizeof(DWC2State),
1468    .instance_init = dwc2_init,
1469    .class_size    = sizeof(DWC2Class),
1470    .class_init    = dwc2_class_init,
1471};
1472
1473static void dwc2_usb_register_types(void)
1474{
1475    type_register_static(&dwc2_usb_type_info);
1476}
1477
1478type_init(dwc2_usb_register_types)
1479