// Copyright lowRISC contributors.
// Licensed under the Apache License, Version 2.0, see LICENSE for details.
// SPDX-License-Identifier: Apache-2.0

#include "usbdpi.h"

#include <assert.h>
#include <errno.h>
#include <fcntl.h>
#include <limits.h>
#include <stdbool.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>

#include "usb_utils.h"
#include "usbdpi_test.h"

// Indexed directly by ctx->state (ST_)
static const char *st_states[] = {"ST_IDLE 0", "ST_SEND 1", "ST_GET 2",
                                  "ST_SYNC 3", "ST_EOP 4",  "ST_EOP0 5"};

// Indexed directly by ct-x>hostSt (HS_)
static const char *hs_states[] = {
    "HS_STARTFRAME 0", "HS_WAITACK 1",   "HS_SET_DATASTAGE 2", "HS_DS_RXDATA 3",
    "HS_DS_SENDACK 4", "HS_DONEDADR 5",  "HS_REQDATA 6",       "HS_WAITDATA 7",
    "HS_SENDACK 8",    "HS_WAIT_PKT 9",  "HS_ACKIFDATA 10",    "HS_SENDHI 11",
    "HS_EMPTYDATA 12", "HS_WAITACK2 13", "HS_STREAMOUT 14",    "HS_STREAMIN 15",
    "HS_NEXTFRAME 16"};

static const char *decode_usb[] = {"SE0", "0-K", "1-J", "SE1"};

// Optionally invert the signals the host is driving, according to bus
// configuration
static uint32_t inv_driving(usbdpi_ctx_t *ctx, uint32_t d2p);

// Request IN transfer. Get back NAK or DATA0/DATA1.
static void pollRX(usbdpi_ctx_t *ctx, uint8_t endpoint, bool send_hi,
                   bool nak_data);
// Get Baud (Vendor-specific)
static void readBaud(usbdpi_ctx_t *ctx, uint8_t endpoint);

// Get Test Configuration (Vendor-specific)
static void getTestConfig(usbdpi_ctx_t *ctx, uint16_t desc_len);

// Get Descriptor
static void getDescriptor(usbdpi_ctx_t *ctx, uint8_t desc_type,
                          uint8_t desc_idx, uint16_t desc_len);
// Set Baud (Vendor-specific)
static void setBaud(usbdpi_ctx_t *ctx, uint8_t endpoint);

// Set device address (with null data stage)
static void setDeviceAddress(usbdpi_ctx_t *ctx, uint8_t dev_addr);

// Set device configuration
static void setDeviceConfiguration(usbdpi_ctx_t *ctx, uint8_t config);

// Set test status, reporting progress/success/failure (Vendor-specific)
static void setTestStatus(usbdpi_ctx_t *ctx, uint32_t status, const char *msg);

// Change DP and DN outputs from host
static uint32_t set_driving(usbdpi_ctx_t *ctx, uint32_t d2p, uint32_t newval);

// Try to send OUT transfer. Optionally expect Status packet (eg. ACK|NAK) in
// response
static void tryTX(usbdpi_ctx_t *ctx, uint8_t endpoint, bool bExpectStatus);

// Test the ischronous transfers (without ACKs)
// static void testIso(usbdpi_ctx_t *ctx);
#define testIso(ctx) tryTX((ctx), ENDPOINT_ISOCHRONOUS, false)

// Callback for USB data detection
static void usbdpi_data_callback(void *ctx_v, usbmon_data_type_t type,
                                 uint8_t d);

/**
 * Create a USB DPI instance, returning a 'chandle' for later use
 */
void *usbdpi_create(const char *name, int loglevel) {
  // Use calloc for zero-initialisation
  usbdpi_ctx_t *ctx = (usbdpi_ctx_t *)calloc(1, sizeof(usbdpi_ctx_t));
  assert(ctx);

  // Note: calloc has initialized most of the fields for us
  // ctx->tick = 0;
  // ctx->tick_bits = 0;
  // ctx->frame = 0;
  // ctx->framepend = 0;
  // ctx->frame_start = 0;
  // ctx->last_pu = 0;
  // ctx->driving = 0;
  // ctx->baudrate_set_successfully = 0;

  // Initialize state for each endpoint and direction
  for (unsigned ep = 0U; ep < USBDPI_MAX_ENDPOINTS; ep++) {
    // First DATAx received shall be DATA0
    ctx->ep_in[ep].next_data = USB_PID_DATA0;

    // First DATAx transmitted shall be DATA0 because it must follow a SETUP
    // transaction
    ctx->ep_out[ep].next_data = USB_PID_DATA0;
  }

  ctx->state = ST_IDLE;
  ctx->hostSt = HS_NEXTFRAME;
  ctx->loglevel = loglevel;

  ctx->step = STEP_BUS_RESET;

  char cwd[FILENAME_MAX];
  char *cwd_rv;
  cwd_rv = getcwd(cwd, sizeof(cwd));
  assert(cwd_rv != NULL);

  // Monitor log file
  int rv = snprintf(ctx->mon_pathname, FILENAME_MAX, "%s/%s.log", cwd, name);
  assert(rv <= FILENAME_MAX && rv > 0);

  ctx->mon = usb_monitor_init(ctx->mon_pathname, usbdpi_data_callback, ctx);

  // Prepare the transfer descriptors for use
  usb_transfer_setup(ctx);

  return (void *)ctx;
}

void usbdpi_device_to_host(void *ctx_void, const svBitVecVal *usb_d2p) {
  usbdpi_ctx_t *ctx = (usbdpi_ctx_t *)ctx_void;
  assert(ctx);

  // Ascertain the state of the D+/D- signals from the device
  // TODO - migrate to a simple function
  uint32_t d2p = usb_d2p[0];
  unsigned dp, dn;
  if (d2p & D2P_TX_USE_D_SE0) {
    // Single-ended mode uses D and SE0
    if (d2p & D2P_D_EN) {
      if (d2p & D2P_DNPU) {
        // Pullup says swap i.e. D is inverted
        dp = (d2p & D2P_SE0) ? 0 : ((d2p & D2P_D) ? 0 : 1);
        dn = (d2p & D2P_SE0) ? 0 : ((d2p & D2P_D) ? 1 : 0);
      } else {
        dp = (d2p & D2P_SE0) ? 0 : ((d2p & D2P_D) ? 1 : 0);
        dn = (d2p & D2P_SE0) ? 0 : ((d2p & D2P_D) ? 0 : 1);
      }
    } else {
      dp = (d2p & D2P_PU) ? 1 : 0;
      dn = 0;
    }
  } else {
    // Normal D+/D- mode
    if (d2p & D2P_DNPU) {
      // Assertion of DN pullup suggests DP and DN are swapped
      dp = ((d2p & D2P_DN_EN) && (d2p & D2P_DN)) ||
           (!(d2p & D2P_DN_EN) && (d2p & D2P_DNPU));
      dn = (d2p & D2P_DP_EN) && (d2p & D2P_DP);
    } else {
      // No DN pullup so normal orientation
      dp = ((d2p & D2P_DP_EN) && (d2p & D2P_DP)) ||
           (!(d2p & D2P_DP_EN) && (d2p & D2P_DPPU));
      dn = (d2p & D2P_DN_EN) && (d2p & D2P_DN);
    }
  }

  // TODO - check the timing of the device responses to ensure compliance with
  // the specification; the response time of acknowledgements, for example, has
  // a hard real time requirement that is specified in terms of bit intervals
  if (d2p & (D2P_DP_EN | D2P_DN_EN | D2P_D_EN)) {
    switch (ctx->state) {
      // Host to device transmission
      case ST_SYNC:
      case ST_SEND:
      case ST_EOP:
      case ST_EOP0:
        printf(
            "[usbdpi] frame 0x%x tick_bits 0x%x error state %s hs %s and "
            "device "
            "drives\n",
            ctx->frame, ctx->tick_bits, st_states[ctx->state],
            hs_states[ctx->hostSt]);
        break;

      // Device to host transmission; collect the bits
      case ST_GET:
        // TODO - perform bit-level decoding and packet construction here rather
        // than relying upon usb_monitor to do that
        // TODO - synchronize with the device transmission and check that the
        // signals remain stable across all 4 cycles of the bit interval
        break;

      case ST_IDLE:
        // Nothing to do
        break;

      default:
        assert(!"Invalid/unknown state");
        break;
    }

    ctx->state = ST_GET;
  } else {
    if (ctx->state == ST_GET) {
      ctx->state = ST_IDLE;
    }
  }

  if ((d2p & D2P_DNPU) && (d2p & D2P_DPPU)) {
    printf("[usbdpi] frame 0x%x tick_bits 0x%x error both pullups are driven\n",
           ctx->frame, ctx->tick_bits);
  }
  if ((d2p & D2P_PU) != ctx->last_pu) {
    usb_monitor_log(ctx->mon, "0x%-3x 0x%-8x Pullup change to %s%s%s\n",
                    ctx->frame, ctx->tick_bits,
                    (d2p & D2P_DPPU) ? "DP Pulled up " : "",
                    (d2p & D2P_DNPU) ? "DN Pulled up " : "",
                    (d2p & D2P_TX_USE_D_SE0) ? "SingleEnded" : "Differential");

    ctx->last_pu = d2p & D2P_PU;
  }

  // TODO - prime candidate for a function
  if (ctx->loglevel & LOG_BIT) {
    char raw_str[D2P_BITS + 1];
    {
      int i;
      for (i = 0; i < D2P_BITS; i++) {
        raw_str[D2P_BITS - i - 1] = d2p & (1 << i) ? '1' : '0';
      }
    }
    raw_str[D2P_BITS] = 0;

    const char *pullup = (d2p & D2P_PU) ? "PU" : "  ";
    const char *state =
        (ctx->state == ST_GET) ? decode_usb[dp << 1 | dn] : "ZZ ";
    usb_monitor_log(ctx->mon, "0x%-3x 0x%-8x %s %s %s %x\n", ctx->frame,
                    ctx->tick_bits, raw_str, pullup, state, d2p);
  }

  // Device-to-Host EOP
  if (ctx->state == ST_GET && dp == 0 && dn == 0) {
    switch (ctx->bus_state) {
      // Control Transfers
      case kUsbControlSetup:
        ctx->bus_state = kUsbControlSetupAck;
        break;
      case kUsbControlDataOut:
        ctx->bus_state = kUsbControlDataOutAck;
        break;
      case kUsbControlStatusInToken:
        ctx->bus_state = kUsbControlStatusInData;
        break;
      case kUsbControlDataInToken:
        ctx->bus_state = kUsbControlDataInData;
        break;
      case kUsbControlStatusOut:
        ctx->bus_state = kUsbControlStatusOutAck;
        break;

      // Bulk Transfers
      case kUsbBulkOut:
        ctx->bus_state = kUsbBulkOutAck;
        break;
      case kUsbBulkInToken:
        ctx->bus_state = kUsbBulkInData;
        break;

      default:
        break;
    }
  }
}

// Callback for USB data detection
// - the DPI host model presently does not duplicate the bit-level decoding and
//   packet construction of the usb_monitor, so we piggyback on its decoding and
//   trust it to be neutral.
//
// Note: this is invoked for any byte transferred over the USB; both
// host-to-device and device-to-host traffic
void usbdpi_data_callback(void *ctx_v, usbmon_data_type_t type, uint8_t d) {
  usbdpi_ctx_t *ctx = (usbdpi_ctx_t *)ctx_v;
  assert(ctx);
  if (!ctx->recving) {
    ctx->recving = transfer_alloc(ctx);
  }

  // We are interested only in the packets from device to host
  if (ctx->state != ST_GET) {
    return;
  }

  usbdpi_transfer_t *tr = ctx->recving;
  // TODO - commute to run time error indicating buffer exhaustion
  assert(tr);
  if (tr) {
    if (false) {  // ctx->loglevel & LOG_MON) {
      printf("[usbdpi] data type %u d 0x%02x\n", type, d);
    }

    bool ok = false;
    switch (type) {
      case UsbMon_DataType_Sync:
        // Initialize/rewind the received transfer
        transfer_init(tr);
        ok = true;
        break;
      case UsbMon_DataType_EOP:
        ok = true;
        break;
      // Collect the PID and any subsequent data bytes
      case UsbMon_DataType_PID:
        switch (d) {
          case USB_PID_DATA0:
          case USB_PID_DATA1: {
            // TODO - this records the start of the data field with the
            // current transfer descriptors
            uint8_t *dp = transfer_data_start(tr, d, 0U);
            ok = (dp != NULL);
          } break;
          default:
            ok = transfer_append(tr, &d, 1);
            break;
        }
        break;
      // Collect data field
      case UsbMon_DataType_Byte:
        ok = transfer_append(tr, &d, 1);
        break;
      default:
        assert(!"Unknown/unhandled rx type from monitor");
        break;
    }

    // TODO - commute to run time error indicating excessive packet length
    assert(ok);
  }
}

// Set device address (with null data stage)
void setDeviceAddress(usbdpi_ctx_t *ctx, uint8_t dev_addr) {
  usbdpi_transfer_t *tr = ctx->sending;
  uint8_t *dp;
  switch (ctx->hostSt) {
    case HS_STARTFRAME:
      // Setting device address, uses address 0 initially
      transfer_token(tr, USB_PID_SETUP, 0, ENDPOINT_ZERO);

      dp = transfer_data_start(tr, USB_PID_DATA0, 8);
      if (INSERT_ERR_PID) {
        *(dp - 1) = 0xc4U;
      }
      dp[0] = 0;  // h2d, std, device
      dp[1] = USB_REQ_SET_ADDRESS;
      dp[2] = dev_addr;  // device address
      dp[3] = 0;
      // Trigger bitstuffing, technically the device
      // behavior is unspecified with wIndex != 0
      dp[4] = 0xFF;  // wIndex = 0xFF00
      dp[5] = 0;
      dp[6] = 0;  // wLength = 0
      dp[7] = 0;
      transfer_data_end(tr, dp + 8);
      if (INSERT_ERR_CRC) {
        // Flip the last CRC bit to emulate a CRC error
        dp[9] ^= 0x01u;
      }
      transfer_send(ctx, tr);
      ctx->bus_state = kUsbControlSetup;
      ctx->hostSt = HS_WAITACK;
      break;
    case HS_WAITACK:
      ctx->wait = ctx->tick_bits + 532;  // HACK
      ctx->hostSt = HS_SET_DATASTAGE;
      break;
    case HS_SET_DATASTAGE:
      if (ctx->bus_state == kUsbControlSetupAck &&
          ctx->tick_bits >= ctx->wait) {
        transfer_token(tr, USB_PID_IN, 0, 0);
        transfer_send(ctx, tr);
        ctx->bus_state = kUsbControlStatusInToken;
        ctx->hostSt = HS_DS_RXDATA;
      }
      break;
    case HS_DS_RXDATA:
      ctx->wait = ctx->tick_bits + 24;  // HACK -- 2 bytes
      ctx->hostSt = HS_DS_SENDACK;
      break;
    case HS_DS_SENDACK:
      if (ctx->bus_state == kUsbControlStatusInData ||
          ctx->tick_bits >= ctx->wait) {
        transfer_status(ctx, tr, USB_PID_ACK);
        ctx->bus_state = kUsbIdle;
        ctx->hostSt = HS_NEXTFRAME;

        // Remember the assigned device address
        ctx->dev_address = dev_addr;

        printf("[usbdpi] setDeviceAddress done\n");
      }
      break;
    default:
      break;
  }
}

// Set device configuration
void setDeviceConfiguration(usbdpi_ctx_t *ctx, uint8_t config) {
  usbdpi_transfer_t *tr = ctx->sending;
  uint8_t *dp;
  switch (ctx->hostSt) {
    case HS_STARTFRAME:
      transfer_token(tr, USB_PID_SETUP, ctx->dev_address, ENDPOINT_ZERO);

      dp = transfer_data_start(tr, USB_PID_DATA0, 8);
      dp[0] = 0;  // h2d, std, device
      dp[1] = USB_REQ_SET_CONFIGURATION;
      dp[2] = config;
      dp[3] = 0;
      dp[4] = 0;  // wIndex = 0
      dp[5] = 0;
      dp[6] = 0;  // wLength = 0
      dp[7] = 0;
      transfer_data_end(tr, dp + 8);

      transfer_send(ctx, tr);
      ctx->bus_state = kUsbControlSetup;
      ctx->hostSt = HS_WAITACK;
      break;
    case HS_WAITACK:
      ctx->wait = ctx->tick_bits + 532;  // HACK
      ctx->hostSt = HS_SET_DATASTAGE;
      break;
    case HS_SET_DATASTAGE:
      if (ctx->bus_state == kUsbControlSetupAck &&
          ctx->tick_bits >= ctx->wait) {
        transfer_token(tr, USB_PID_IN, ctx->dev_address, ENDPOINT_ZERO);
        transfer_send(ctx, tr);
        ctx->bus_state = kUsbControlStatusInToken;
        ctx->hostSt = HS_DS_RXDATA;
      }
      break;
    case HS_DS_RXDATA:
      ctx->wait = ctx->tick_bits + 24;  // HACK -- 2 bytes
      ctx->hostSt = HS_DS_SENDACK;
      break;
    case HS_DS_SENDACK:
      if (ctx->bus_state == kUsbControlStatusInData ||
          ctx->tick_bits >= ctx->wait) {
        transfer_status(ctx, tr, USB_PID_ACK);
        ctx->bus_state = kUsbIdle;
        ctx->hostSt = HS_NEXTFRAME;
        printf("[usbdpi] setDeviceConfiguration done\n");
      }
      break;
    default:
      break;
  }
}

// Get Descriptor
void getDescriptor(usbdpi_ctx_t *ctx, uint8_t desc_type, uint8_t desc_idx,
                   uint16_t desc_len) {
  usbdpi_transfer_t *tr = ctx->sending;
  uint8_t *dp;
  switch (ctx->hostSt) {
    case HS_STARTFRAME: {
      // TODO - build the bmRequestType by ORing values
      const uint8_t bmRequestType = 0x80;  // d2h, vendor, endpoint
      uint16_t wValue = (desc_type << 8) | (uint8_t)desc_idx;
      transfer_setup(ctx, tr, bmRequestType, USB_REQ_GET_DESCRIPTOR, wValue, 0U,
                     desc_len);
    } break;
    case HS_WAITACK:
      ctx->wait = ctx->tick_bits + 1164;  // HACK
      ctx->hostSt = HS_REQDATA;
      break;
    case HS_REQDATA:
      // TODO - we must wait before trying the IN because we currently
      // do not retry after a NAK response, but the CPU software can be tardy
      if (ctx->tick_bits >= ctx->wait &&
          ctx->bus_state == kUsbControlSetupAck) {
        transfer_token(tr, USB_PID_IN, ctx->dev_address, ENDPOINT_ZERO);

        transfer_send(ctx, tr);
        ctx->bus_state = kUsbControlDataInToken;
        ctx->hostSt = HS_WAITDATA;
      }
      break;
    case HS_WAITDATA:
      ctx->wait = ctx->tick_bits + 2000;  // HACK
      ctx->hostSt = HS_SENDACK;
      break;
    case HS_SENDACK:
      if (ctx->bus_state == kUsbControlDataInData) {
        if (ctx->step == STEP_GET_CONFIG_DESCRIPTOR) {
          // Check the GET_DESCRIPTOR response
          assert(ctx->recving);

          // TODO - detect when the returned data falls short of the requested
          // transfer length
          uint8_t *dp = transfer_data_field(ctx->recving);
          assert(dp);
          // Collect the returned values
          // uint8_t  bLength = dp[0];
          // uint8_t  bDescriptorType = dp[1];
          uint16_t wTotalLength = dp[2] | (dp[3] << 8);
          // uint8_t  bNumInterfaces = dp[4];

          ctx->cfg_desc_len = wTotalLength;
        }

        transfer_token(tr, USB_PID_ACK, ctx->dev_address, ENDPOINT_ZERO);

        transfer_send(ctx, tr);
        ctx->bus_state = kUsbControlDataInAck;
        ctx->hostSt = HS_WAIT_PKT;

        ctx->wait = ctx->tick_bits + 200;  // HACK
      } else if (ctx->tick_bits >= ctx->wait) {
        printf("[usbdpi] Timed out waiting for device\n");
        ctx->hostSt = HS_NEXTFRAME;
        ctx->bus_state = kUsbIdle;
      }
      break;
    case HS_WAIT_PKT:
      // TODO - introduce support for multiple packets when we've requested
      // longer transfers
      if (ctx->tick_bits >= ctx->wait) {
        ctx->hostSt = HS_EMPTYDATA;
      }
      break;
    case HS_EMPTYDATA:
      // Status stage of Control Read
      // Transmit zero-length data packet and await handshake
      transfer_token(tr, USB_PID_OUT, ctx->dev_address, ENDPOINT_ZERO);

      dp = transfer_data_start(tr, USB_PID_DATA1, 0);
      transfer_data_end(tr, dp);
      transfer_send(ctx, tr);
      ctx->bus_state = kUsbControlStatusOut;
      ctx->hostSt = HS_WAITACK2;
      ctx->wait = ctx->tick_bits + 200;  // HACK
      break;
    case HS_WAITACK2:
      if (ctx->bus_state == kUsbControlStatusOutAck) {
        switch (ctx->lastrxpid) {
          case USB_PID_ACK:
            ctx->ep_out[ENDPOINT_ZERO].next_data =
                DATA_TOGGLE_ADVANCE(ctx->ep_out[ENDPOINT_ZERO].next_data);
            ctx->hostSt = HS_NEXTFRAME;
            break;

          case USB_PID_NAK:
            // TODO - this means that the device is still busy
            ctx->hostSt = HS_WAITACK2;
            ctx->wait = ctx->tick_bits + 200;  // HACK
            break;

          // TODO - commute these other responses into test failures
          case USB_PID_STALL:
            printf("[usbdpi] Device stalled\n");
            ctx->hostSt = HS_NEXTFRAME;
            break;
          default:
            printf("[usbdpi] Unexpected handshake response 0x%02x\n",
                   ctx->lastrxpid);
            ctx->hostSt = HS_NEXTFRAME;
            break;
        }
      } else if (ctx->tick_bits >= ctx->wait) {
        printf(
            "[usbdpi] Time out waiting for device response in Status Stage\n");
        ctx->hostSt = HS_NEXTFRAME;
      }
      break;
    default:
      break;
  }
}

// Get Test Configuration (Vendor-specific)
void getTestConfig(usbdpi_ctx_t *ctx, uint16_t desc_len) {
  usbdpi_transfer_t *tr = ctx->sending;
  uint8_t *dp;
  assert(tr);
  switch (ctx->hostSt) {
    case HS_STARTFRAME: {
      const uint8_t bmRequestType = 0xc2;  // d2h, vendor, endpoint
      transfer_setup(ctx, tr, bmRequestType, USBDPI_VENDOR_TEST_CONFIG, 0U, 0U,
                     desc_len);
    } break;
    case HS_WAITACK:
      ctx->wait = ctx->tick_bits + 1164;  // HACK
      ctx->hostSt = HS_REQDATA;
      break;
    case HS_REQDATA:
      // TODO - we must wait before trying the IN because we currently
      // do not retry after a NAK response, but the CPU software can be tardy
      if (ctx->tick_bits >= ctx->wait &&
          ctx->bus_state == kUsbControlSetupAck) {
        transfer_token(tr, USB_PID_IN, ctx->dev_address, ENDPOINT_ZERO);

        transfer_send(ctx, tr);
        ctx->bus_state = kUsbControlDataInToken;
        ctx->hostSt = HS_WAITDATA;
      }
      break;
    case HS_WAITDATA:
      ctx->wait = ctx->tick_bits + 2000;  // HACK
      ctx->hostSt = HS_SENDACK;
      break;
    case HS_SENDACK:
      if (ctx->bus_state == kUsbControlDataInData) {
        switch (ctx->lastrxpid) {
          case USB_PID_DATA1: {
            usbdpi_transfer_t *rx = ctx->recving;
            assert(rx);
            // TODO - check the length of the received data field!
            uint8_t *dp = transfer_data_field(rx);
            assert(dp);
            // Validate the first part of the test descriptor
            printf("[usbdpi] Test descriptor 0x%.8X\n", get_le32(dp));

            transfer_dump(rx, stdout);

            // Check the header signature
            const uint8_t test_sig_head[] = {0x7eu, 0x57u, 0xc0u, 0xf1u};
            const uint8_t test_sig_tail[] = {0x1fu, 0x0cu, 0x75u, 0xe7u};
            if (!memcmp(dp, test_sig_head, 4) && 0x10 == get_le16(&dp[4]) &&
                !memcmp(&dp[12], test_sig_tail, 4)) {
              ctx->test_number = get_le16(&dp[6]);
              ctx->test_arg[0] = dp[8];
              ctx->test_arg[1] = dp[9];
              ctx->test_arg[2] = dp[10];
              ctx->test_arg[3] = dp[11];

              printf("[usbdpi] Test number 0x%04x args %02x %02x %02x %02x\n",
                     ctx->test_number, ctx->test_arg[0], ctx->test_arg[1],
                     ctx->test_arg[2], ctx->test_arg[3]);

              usbdpi_test_init(ctx);
            } else {
              printf(
                  "[usbdpi] Invalid/unrecognised test descriptor received\n");
              assert(!"Cannot proceed without test descriptor");
            }
          } break;

          case USB_PID_NAK:
            // TODO - we should retry the request in this case
            printf("[usbdpi] Unable to retrieve test config\n");
            assert(!"DPI is unable to retrieve test config");
            ctx->hostSt = HS_NEXTFRAME;
            break;

          case USB_PID_STALL:
            printf("[usbdpi] Device stalled\n");
            assert(!"Device is stalled");
            ctx->hostSt = HS_NEXTFRAME;
            break;
          default:
            printf("[usbdpi] Unexpected handshake response 0x%02x\n",
                   ctx->lastrxpid);
            assert(!"Unexpected handshake response");
            ctx->hostSt = HS_NEXTFRAME;
            break;
        }
        transfer_token(tr, USB_PID_ACK, ctx->dev_address, ENDPOINT_ZERO);

        transfer_send(ctx, tr);
        ctx->bus_state = kUsbControlDataInAck;
        ctx->hostSt = HS_WAIT_PKT;

        ctx->wait = ctx->tick_bits + 200;  // HACK
      } else if (ctx->tick_bits >= ctx->wait) {
        printf("[usbdpi] Timed out waiting for device\n");
        ctx->hostSt = HS_NEXTFRAME;
        ctx->bus_state = kUsbIdle;
      }
      break;
    case HS_WAIT_PKT:
      if (ctx->tick_bits >= ctx->wait) {
        ctx->hostSt = HS_EMPTYDATA;
      }
      break;
    case HS_EMPTYDATA:
      // Status stage of Control Read
      // Transmit zero-length data packet and await handshake
      transfer_token(tr, USB_PID_OUT, ctx->dev_address, ENDPOINT_ZERO);

      dp = transfer_data_start(tr, USB_PID_DATA1, 0);
      transfer_data_end(tr, dp);
      transfer_send(ctx, tr);
      ctx->bus_state = kUsbControlStatusOut;
      ctx->hostSt = HS_WAITACK2;
      ctx->wait = ctx->tick_bits + 200;  // HACK
      break;
    case HS_WAITACK2:
      if (ctx->bus_state == kUsbControlStatusOutAck) {
        switch (ctx->lastrxpid) {
          case USB_PID_ACK:
            ctx->ep_out[ENDPOINT_ZERO].next_data =
                DATA_TOGGLE_ADVANCE(ctx->ep_out[ENDPOINT_ZERO].next_data);
            ctx->hostSt = HS_NEXTFRAME;
            break;

          case USB_PID_NAK:
            // TODO - this means that the device is still busy
            ctx->hostSt = HS_WAITACK2;
            ctx->wait = ctx->tick_bits + 200;  // HACK
            break;

          // TODO - commute these other responses into test failures
          case USB_PID_STALL:
            printf("[usbdpi] Device stalled\n");
            ctx->hostSt = HS_NEXTFRAME;
            break;
          default:
            printf("[usbdpi] Unexpected handshake response 0x%02x\n",
                   ctx->lastrxpid);
            ctx->hostSt = HS_NEXTFRAME;
            break;
        }
      } else if (ctx->tick_bits >= ctx->wait) {
        printf(
            "[usbdpi] Time out waiting for device response in Status Stage\n");
        ctx->hostSt = HS_NEXTFRAME;
      }
      break;
    default:
      break;
  }
}

// Set Test Status, reporting progress/success/failure (Vendor-specific)
void setTestStatus(usbdpi_ctx_t *ctx, uint32_t status, const char *msg) {
  // TODO - placeholder for reporting of test status reporting and termination
}

// Get Baud (Vendor-specific)
void readBaud(usbdpi_ctx_t *ctx, uint8_t endpoint) {
  usbdpi_transfer_t *tr = ctx->sending;
  uint8_t *dp;
  switch (ctx->hostSt) {
    case HS_STARTFRAME:
      transfer_token(tr, USB_PID_SETUP, ctx->dev_address, endpoint);

      dp = transfer_data_start(tr, USB_PID_DATA0, 0);
      dp[0] = 0xc2;  // d2h, vendor, endpoint
      dp[1] = 2;     // get baud
      dp[2] = 0;     // index 0
      dp[3] = 0;     // type device
      dp[4] = 0;     // wIndex = 0
      dp[5] = 0;
      dp[6] = 0x2;  // wLength = 2
      dp[7] = 0;
      transfer_data_end(tr, dp + 8);

      transfer_send(ctx, tr);
      ctx->bus_state = kUsbControlSetup;
      ctx->hostSt = HS_WAITACK;
      break;
    case HS_WAITACK:
      ctx->wait = ctx->tick_bits + 32;  // HACK
      ctx->hostSt = HS_REQDATA;
      break;
    case HS_REQDATA:
      if (ctx->tick_bits >= ctx->wait) {
        // NOTE: This IN request produces a NAK from the device because there is
        //       nothing available, at which point a REAL host should surely
        //       retry the request at a later time!
        transfer_token(tr, USB_PID_IN, ctx->dev_address, endpoint);

        transfer_send(ctx, tr);
        ctx->hostSt = HS_WAITDATA;
      }
      break;
    case HS_WAITDATA:
      ctx->wait = ctx->tick_bits + 200;  // HACK
      ctx->hostSt = HS_SENDACK;
      break;
    case HS_SENDACK:
      // TODO - are we not ACKing the NAK at this point?
      if (ctx->tick_bits >= ctx->wait) {
        transfer_status(ctx, tr, USB_PID_ACK);
        ctx->hostSt = HS_EMPTYDATA;
      }
      break;
    case HS_EMPTYDATA:
      // Transmit OUT transaction with zero-length DATA packet
      transfer_token(tr, USB_PID_OUT, ctx->dev_address, endpoint);
      if (INSERT_ERR_DATA_TOGGLE) {
        // NOTE: This raises a LinkOutErr on the USBDEV because it is expecting
        //       DATA0
        uint8_t bad_pid = DATA_TOGGLE_ADVANCE(ctx->ep_out[endpoint].next_data);
        dp = transfer_data_start(tr, bad_pid, 0);
      } else {
        dp = transfer_data_start(tr, ctx->ep_out[endpoint].next_data, 0);
      }
      transfer_data_end(tr, dp);

      transfer_send(ctx, tr);
      ctx->bus_state = kUsbControlStatusOut;
      ctx->hostSt = HS_WAITACK2;

      ctx->wait = ctx->tick_bits + 200;  // HACK
      break;
    case HS_WAITACK2:
      if (ctx->tick_bits >= ctx->wait ||
          ctx->bus_state == kUsbControlStatusOutAck) {
        if (ctx->lastrxpid == USB_PID_ACK) {
          ctx->ep_out[endpoint].next_data =
              DATA_TOGGLE_ADVANCE(ctx->ep_out[endpoint].next_data);
        }
        ctx->hostSt = HS_NEXTFRAME;
        printf("[usbdpi] readBaud done\n");
      }
      break;
    default:
      break;
  }
}

// Set Baud (Vendor-specific)
void setBaud(usbdpi_ctx_t *ctx, uint8_t endpoint) {
  usbdpi_transfer_t *tr = ctx->sending;
  uint8_t *dp;
  switch (ctx->hostSt) {
    case HS_STARTFRAME:
      transfer_token(tr, USB_PID_SETUP, ctx->dev_address, endpoint);

      dp = transfer_data_start(tr, USB_PID_DATA0, 0);
      dp[0] = 0x42;  // h2d, vendor, endpoint
      dp[1] = 3;     // set baud
      dp[2] = 96;    // index 0
      dp[3] = 0;     // type device
      dp[4] = 0;     // wIndex = 0
      dp[5] = 0;
      dp[6] = 0;  // wLength = 0
      dp[7] = 0;
      transfer_data_end(tr, dp + 8);

      transfer_send(ctx, tr);
      ctx->bus_state = kUsbControlSetup;
      ctx->hostSt = HS_WAITACK;
      break;
    case HS_WAITACK:
      ctx->wait = ctx->tick_bits + 32;  // HACK
      ctx->hostSt = HS_REQDATA;
      break;
    case HS_REQDATA:
      if (ctx->tick_bits >= ctx->wait) {
        transfer_token(tr, USB_PID_IN, ctx->dev_address, endpoint);

        transfer_send(ctx, tr);
        ctx->hostSt = HS_WAITDATA;
      }
      break;
    case HS_WAITDATA:
      ctx->wait = ctx->tick_bits + 40;  // HACK
      ctx->hostSt = HS_SENDACK;
      break;
    case HS_SENDACK:
      if (ctx->tick_bits >= ctx->wait) {
        transfer_status(ctx, tr, USB_PID_ACK);
        ctx->hostSt = HS_NEXTFRAME;
        ctx->baudrate_set_successfully = 1;
        printf("[usbdpi] setBaud done\n");
      }
      break;
    default:
      break;
  }
}

// Try an OUT transfer to the device, optionally expecting a Status
//   packet (eg. ACK|NAK) in response; this is not expected for
//   Isochronous transfers
void tryTX(usbdpi_ctx_t *ctx, uint8_t endpoint, bool bExpectStatus) {
  const uint8_t pattern[] = {
      "AbCdEfGhIjKlMnOpQrStUvWxYz+0123456789-aBcDeFgHiJkLmNoPqRsTuVwXyZ"};
  usbdpi_transfer_t *tr = ctx->sending;
  uint8_t *dp;
  switch (ctx->hostSt) {
    case HS_STARTFRAME:
      transfer_token(tr, USB_PID_OUT, ctx->dev_address, endpoint);

      dp = transfer_data_start(tr, ctx->ep_out[endpoint].next_data, 0);
      memcpy(dp, pattern, sizeof(pattern));
      transfer_data_end(tr, dp + sizeof(pattern));

      transfer_send(ctx, tr);
      ctx->bus_state = kUsbBulkOut;
      ctx->hostSt = HS_WAITACK;
      break;
    case HS_WAITACK:  // no actual ACK if Isochronous transfer
      ctx->wait = ctx->tick_bits + 32;
      ctx->hostSt = HS_REQDATA;
      break;
    case HS_REQDATA:
      if (ctx->tick_bits >= ctx->wait) {
        // Note: Isochronous transfers are not acknowledged and do not employ
        //       Data Toggle Synchronization
        if (bExpectStatus && ctx->lastrxpid == USB_PID_ACK) {
          ctx->ep_out[endpoint].next_data =
              DATA_TOGGLE_ADVANCE(ctx->ep_out[endpoint].next_data);
        }

        transfer_token(tr, USB_PID_IN, ctx->dev_address, endpoint);
        transfer_send(ctx, tr);

        ctx->hostSt = HS_WAITDATA;
      }
      break;
    case HS_WAITDATA:
      ctx->wait = ctx->tick_bits + 40;  // HACK
      ctx->hostSt = HS_NEXTFRAME;
      printf("[usbdpi] testIso done\n");
    default:
      break;
  }
}

// Request IN. Get back DATA0/DATA1 or NAK.
//
// send_hi  -> also send OUT packet
// nak_data -> send NAK instead of ACK if there is data
void pollRX(usbdpi_ctx_t *ctx, uint8_t endpoint, bool send_hi, bool nak_data) {
  usbdpi_transfer_t *tr = ctx->sending;
  uint8_t *dp;
  switch (ctx->hostSt) {
    case HS_STARTFRAME:
      transfer_token(tr, USB_PID_IN, ctx->dev_address, endpoint);

      transfer_send(ctx, tr);
      ctx->bus_state = kUsbBulkInToken;
      ctx->hostSt = HS_WAIT_PKT;
      ctx->lastrxpid = 0;
      break;
    case HS_WAIT_PKT:
      // Wait max time for a response + packet
      ctx->wait = ctx->tick_bits + 18 + 8 + 8 + 64 * 8 + 16;
      ctx->hostSt = HS_ACKIFDATA;
      break;
    case HS_ACKIFDATA:
      if (ctx->bus_state == kUsbBulkInData) {
        // TODO - have we got a LFSR-generated data packet?
        if (ctx->lastrxpid != USB_PID_NAK) {
          transfer_status(ctx, tr, nak_data ? USB_PID_NAK : USB_PID_ACK);
        }
        ctx->hostSt = HS_SENDHI;
      } else if (ctx->tick_bits >= ctx->wait) {
        printf("[usbdpi] Timed out waiting for IN response\n");
        ctx->hostSt = HS_SENDHI;
      }
      break;
    case HS_SENDHI:
      if (send_hi) {
        transfer_token(tr, USB_PID_OUT, ctx->dev_address, endpoint);

        dp = transfer_data_start(tr, ctx->ep_out[endpoint].next_data, 0);
        dp[0] = 0x48;  // "H"
        dp[1] = 0x69;  // "i"
        dp[2] = 0x21;  // "!"
        transfer_data_end(tr, dp + 3);

        transfer_send(ctx, tr);
        ctx->wait = ctx->tick_bits + 532;  // HACK
        ctx->hostSt = HS_WAITACK;
      } else {
        ctx->hostSt = HS_NEXTFRAME;
      }
      break;
    case HS_WAITACK:
      if (ctx->tick_bits >= ctx->wait) {
        if (ctx->lastrxpid == USB_PID_ACK) {
          ctx->ep_out[endpoint].next_data =
              DATA_TOGGLE_ADVANCE(ctx->ep_out[endpoint].next_data);
        }
        ctx->hostSt = HS_NEXTFRAME;
      }
      break;
    default:
      break;
  }
}

// Test behavior in (non-)response to other device and unimplemented endpoints
void testUnimplEp(usbdpi_ctx_t *ctx, uint8_t pid, uint8_t device,
                  uint8_t endpoint) {
  usbdpi_transfer_t *tr = ctx->sending;
  uint8_t *dp;
  switch (ctx->hostSt) {
    case HS_STARTFRAME:
      if ((pid == USB_PID_SETUP) || (pid == USB_PID_OUT)) {
        transfer_token(tr, pid, device, endpoint);

        dp = transfer_data_start(tr, USB_PID_DATA0, 0);
        dp[0] = 0;  // h2d, std, device
        dp[1] = 5;  // set address
        dp[2] = 2;  // device address
        dp[3] = 0;
        // Trigger bitstuffing, technically the device
        // behavior is unspecified with wIndex != 0
        dp[4] = 0xFF;  // wIndex = 0xFF00
        dp[5] = 0;
        dp[6] = 0;  // wLength = 0
        dp[7] = 0;
        transfer_data_end(tr, dp + 8);

        transfer_send(ctx, tr);
        ctx->hostSt = HS_WAITACK;
        break;
      } else if (pid == USB_PID_IN) {
        transfer_token(tr, pid, device, endpoint);
        transfer_send(ctx, tr);

        // Since the endpoint is not implemented, the device should respond with
        // a STALL packet (not DATA0/1 or NAK).
        ctx->hostSt = HS_WAITACK;
        break;
      } else {
        ctx->hostSt = HS_NEXTFRAME;
        printf(
            "[usbdpi] testUnimplEp supports SETUP, OUT and IN transactions "
            "only\n");
        break;
      }
    case HS_WAITACK:
      // Note: We currently can't observe the responses sent by the device, but
      // usb_monitor() does log all transactions from host and device and does
      // some basic decoding.
      // Depending on the transaction type to unimplemented endpoints, we would
      // expect the following response:
      // - SETUP: no response (must be ignored by the device)
      // - OUT/IN: a STALL packet from the device
      ctx->wait = ctx->tick_bits + 32;  // HACK
      ctx->hostSt = HS_NEXTFRAME;
      printf("[usbdpi] testUnimplEp done\n");
      break;
    default:
      break;
  }
}

// Change DP and DN outputs from host
uint32_t set_driving(usbdpi_ctx_t *ctx, uint32_t d2p, uint32_t newval) {
  // Always maintain the current state of VBUS
  uint32_t driving = ctx->driving & P2D_SENSE;
  if (d2p & D2P_DNPU) {
    // Have dn pull-up, so must be flipping pins
    if (newval & P2D_DP) {
      driving |= P2D_DN | P2D_D;
    } else if (newval & P2D_DN) {
      driving |= P2D_DP;
    }
  } else {
    if (newval & P2D_DP) {
      driving |= P2D_DP | P2D_D;
    } else if (newval & P2D_DN) {
      driving |= P2D_DN;
    }
  }
  return driving;
}

// Optionally invert the signals the host is driving, according to bus
// configuration
uint32_t inv_driving(usbdpi_ctx_t *ctx, uint32_t d2p) {
  // works for either orientation
  return ctx->driving ^ (P2D_DP | P2D_DN | P2D_D);
}

uint8_t usbdpi_host_to_device(void *ctx_void, const svBitVecVal *usb_d2p) {
  usbdpi_ctx_t *ctx = (usbdpi_ctx_t *)ctx_void;
  assert(ctx);
  int d2p = usb_d2p[0];
  uint32_t last_driving = ctx->driving;
  int force_stat = 0;
  int dat;

  // The 48MHz clock runs at 4 times the bus clock for a full speed (12Mbps)
  // device
  //
  // TODO - vary the phase over the duration of the test to check device
  //        synchronization
  ctx->tick++;
  ctx->tick_bits = ctx->tick >> 2;
  if (ctx->tick & 3) {
    return ctx->driving;
  }

  // Monitor, analyse and record USB bus activity
  usb_monitor(ctx->mon, ctx->loglevel, ctx->tick_bits,
              (ctx->state != ST_IDLE) && (ctx->state != ST_GET), ctx->driving,
              d2p, &(ctx->lastrxpid));

  if (ctx->tick_bits == SENSE_AT) {
    ctx->driving |= P2D_SENSE;
  }

  if ((d2p & D2P_PU) == 0) {
    ctx->recovery_time = ctx->tick + 4 * 48;
    return ctx->driving;
  }

  if (ctx->tick < ctx->recovery_time) {
    ctx->frame_start = ctx->tick_bits;
    return ctx->driving;
  }

  // Time to commence a new bus frame?
  if ((ctx->tick_bits - ctx->frame_start) >= FRAME_INTERVAL) {
    if (ctx->state != ST_IDLE) {
      if (ctx->framepend == 0) {
        printf(
            "[usbdpi] frame 0x%x tick_bits 0x%x error state %d at frame 0x%x "
            "time\n",
            ctx->frame, ctx->tick, ctx->state, ctx->frame + 1);
      }
      ctx->framepend = 1;
    } else {
      if (ctx->framepend == 1) {
        printf("[usbdpi] frame 0x%x tick_bits 0x%x can send frame 0x%x SOF\n",
               ctx->frame, ctx->tick, ctx->frame + 1);
      }
      ctx->framepend = 0;
      ctx->frame++;
      ctx->frame_start = ctx->tick_bits;

      if (ctx->step >= STEP_IDLE_START && ctx->step < STEP_IDLE_END) {
        // Test suspend behavior by dropping the SOF signalling
        ctx->state = ST_IDLE;
        printf("[usbdpi] idle frame 0x%x\n", ctx->frame);
      } else {
        // Ensure that a buffer is available for constructing a transfer
        usbdpi_transfer_t *tr = ctx->sending;
        if (!tr) {
          tr = transfer_alloc(ctx);
          assert(tr);

          ctx->sending = tr;
        }

        transfer_frame_start(ctx, tr, ctx->frame);
        ctx->state = ST_SYNC;
      }
      printf("[usbdpi] frame 0x%x tick_bits 0x%x CRC5 0x%x\n", ctx->frame,
             ctx->tick, CRC5(ctx->frame, 11));

      if (ctx->hostSt == HS_NEXTFRAME) {
        ctx->step = usbdpi_test_seq_next(ctx, ctx->step);
        ctx->hostSt = HS_STARTFRAME;
      } else {
        // TODO - this surely means that something went wrong;
        // but what shall we do at this point?!
        assert(!"DPI Host not ready to start new frame");
      }
    }
  }

  switch (ctx->state) {
    // Host state machine advances when the bit-level activity is idle
    case ST_IDLE: {
      // Ensure that a buffer is available for constructing a transfer
      usbdpi_transfer_t *tr = ctx->sending;
      if (!tr) {
        tr = transfer_alloc(ctx);
        assert(tr);
        ctx->sending = tr;
      }

      switch (ctx->step) {
        case STEP_SET_DEVICE_ADDRESS:
          setDeviceAddress(ctx, USBDEV_ADDRESS);
          break;

          // TODO - an actual host issues a number of GET_DESCRIPTOR control/
          //        transfers to read descriptions of the configurations,
          //        interfaces and endpoints

        case STEP_GET_DEVICE_DESCRIPTOR:
          // Initially we fetch just the minimal descriptor length of 0x12U
          // bytes and the returned information will indicate the full length
          //
          // TODO - Set the descriptor length to the minimum because the DPI
          // model does not yet catch and report errors properly
          ctx->cfg_desc_len = 12U;
          getDescriptor(ctx, USB_DESC_TYPE_DEVICE, 0U, 0x12U);
          break;

        case STEP_GET_CONFIG_DESCRIPTOR:
          getDescriptor(ctx, USB_DESC_TYPE_CONFIGURATION, 0U, 0x9U);
          break;

        case STEP_GET_FULL_CONFIG_DESCRIPTOR: {
          uint16_t wLength = ctx->cfg_desc_len;
          if (wLength >= USBDEV_MAX_PACKET_SIZE) {
            // Note: getDescriptor cannot yet receive multiple packets
            wLength = USBDEV_MAX_PACKET_SIZE;
          }
          getDescriptor(ctx, USB_DESC_TYPE_CONFIGURATION, 0U, wLength);
        } break;

          // TODO - we must receive and respond to test configuration at some
          //        point; perhaps we can make the software advertise itself
          //        with different vendor/device combinations to indicate the
          //        testing we must do

        case STEP_SET_DEVICE_CONFIG:
          setDeviceConfiguration(ctx, 1);
          break;

        // Test configuration and status
        case STEP_GET_TEST_CONFIG:
          getTestConfig(ctx, 0x10U);
          break;

        case STEP_SET_TEST_STATUS:
          setTestStatus(ctx, ctx->test_status, ctx->test_msg);
          break;

          // These should be at 3 and 4 but the read needs the host
          // not to be sending (until skip fifo is implemented in in_pe engine)
          // so for now push later when things are quiet (could also adjust
          // hello_world to not use the uart until frame 4)

        case STEP_FIRST_READ:
          pollRX(ctx, ENDPOINT_SERIAL0, true, true);
          break;
        case STEP_READ_BAUD:
          readBaud(ctx, ENDPOINT_ZERO);
          break;
        case STEP_SECOND_READ:
          pollRX(ctx, ENDPOINT_SERIAL0, true, false);
          break;
        case STEP_SET_BAUD:
          setBaud(ctx, ENDPOINT_ZERO);
          break;
        case STEP_THIRD_READ:
          pollRX(ctx, ENDPOINT_SERIAL0, false, true);
          break;
        case STEP_TEST_ISO1:
          testIso(ctx);
          break;
        case STEP_TEST_ISO2:
          testIso(ctx);
          break;

        // Test each of SETUP, OUT and IN to an unimplemented endpoint
        case STEP_ENDPT_UNIMPL_SETUP:
          testUnimplEp(ctx, USB_PID_SETUP, ctx->dev_address,
                       ENDPOINT_UNIMPLEMENTED);
          break;
        case STEP_ENDPT_UNIMPL_OUT:
          testUnimplEp(ctx, USB_PID_OUT, ctx->dev_address,
                       ENDPOINT_UNIMPLEMENTED);
          break;
        case STEP_ENDPT_UNIMPL_IN:
          testUnimplEp(ctx, USB_PID_IN, ctx->dev_address,
                       ENDPOINT_UNIMPLEMENTED);
          break;
        case STEP_DEVICE_UK_SETUP:
          testUnimplEp(ctx, USB_PID_SETUP, UKDEV_ADDRESS, 1u);
          break;

        default:
          if (ctx->step < STEP_IDLE_START || ctx->step >= STEP_IDLE_END) {
            pollRX(ctx, ENDPOINT_SERIAL0, false, false);
          }
          break;
      }
    } break;

    case ST_SYNC:
      dat = ((USB_SYNC & ctx->bit)) ? P2D_DP : P2D_DN;
      ctx->driving = set_driving(ctx, d2p, dat);
      force_stat = 1;
      ctx->bit <<= 1;
      if (ctx->bit == 0x100) {
        ctx->bit = 1;
        ctx->linebits = 1;  // The KK at end of SYNC counts for bit stuffing!
        ctx->state = ST_SEND;
      }
      break;

    case ST_SEND: {
      usbdpi_transfer_t *sending = ctx->sending;
      assert(sending);
      if ((ctx->linebits & 0x3f) == 0x3f &&
          !INSERT_ERR_BITSTUFF) {  // sent 6 ones
        // bit stuff and force a transition
        ctx->driving = inv_driving(ctx, d2p);
        force_stat = 1;
        ctx->linebits = (ctx->linebits << 1);
      } else if (ctx->byte >= sending->num_bytes) {
        ctx->state = ST_EOP;
        ctx->driving = set_driving(ctx, d2p, 0);  // SE0
        ctx->bit = 1;
        force_stat = 1;
      } else {
        int nextbit = (sending->data[ctx->byte] & ctx->bit) ? 1 : 0;
        if (nextbit == 0) {
          ctx->driving = inv_driving(ctx, d2p);
        }
        ctx->linebits = (ctx->linebits << 1) | nextbit;
        force_stat = 1;
        ctx->bit <<= 1;
        if (ctx->bit == 0x100) {
          ctx->bit = 1;
          ctx->byte++;
          if (ctx->byte == sending->data_start) {
            ctx->state = ST_EOP0;
          }
        }
      }
    } break;

    case ST_EOP0:
      ctx->driving = set_driving(ctx, d2p, 0);  // SE0
      ctx->state = ST_EOP;
      break;

    case ST_EOP:  // SE0 SE0 J
      if (ctx->bit == 4) {
        ctx->driving = set_driving(ctx, d2p, P2D_DP);  // J
      }
      if (ctx->bit == 8) {
        usbdpi_transfer_t *sending = ctx->sending;
        assert(sending);
        // Stop driving: host pulldown to SE0 unless there is a pullup on DP
        ctx->driving = set_driving(ctx, d2p, (d2p & D2P_PU) ? P2D_DP : 0);
        if (ctx->byte == sending->data_start) {
          ctx->bit = 1;
          ctx->state = ST_SYNC;
        } else {
          ctx->state = ST_IDLE;
        }
      }
      ctx->bit <<= 1;
      break;

    case ST_GET:
      // Device is driving the bus; nothing to do here
      break;

    default:
      assert(!"Unknown/invalid USBDPI drive state");
      break;
  }

  if ((ctx->loglevel & LOG_BIT) &&
      (force_stat || (ctx->driving != last_driving))) {
    usb_monitor_log(
        ctx->mon, "0x%-3x 0x-%8x              %s %s %s\n", ctx->frame,
        ctx->tick_bits, ctx->driving & P2D_SENSE ? "VBUS" : "    ",
        (ctx->state != ST_IDLE) ? decode_usb[(ctx->driving >> 1) & 3] : "ZZ ",
        (ctx->driving & P2D_D) ? "1" : "0");
  }
  return ctx->driving;
}

// Export some internal diagnostic state for visibility in waveforms
void usbdpi_diags(void *ctx_void, svBitVecVal *diags) {
  usbdpi_ctx_t *ctx = (usbdpi_ctx_t *)ctx_void;

  // Check for overflow, which would cause confusion in waveform interpretation;
  // if an assertion fires, the mapping from fields to svBitVecVal will need
  // to be changed, both here and in usbdpi.sv
  assert(ctx->state <= 0xfU);
  assert(ctx->hostSt <= 0x1fU);
  assert(ctx->bus_state <= 0x3fU);
  assert(ctx->step <= 0x7fU);

  diags[2] = usb_monitor_diags(ctx->mon);
  diags[1] =
      (ctx->step << 25) | (ctx->bus_state << 20) | (ctx->tick_bits >> 12);
  diags[0] = (ctx->tick_bits << 20) | ((ctx->frame & 0x7ffU) << 9) |
             ((ctx->hostSt & 0x1fU) << 4) | (ctx->state & 0xfU);
}

// Close the USBDPI model and release resources
void usbdpi_close(void *ctx_void) {
  usbdpi_ctx_t *ctx = (usbdpi_ctx_t *)ctx_void;
  if (!ctx) {
    return;
  }
  usb_monitor_fin(ctx->mon);
  free(ctx);
}
