mirror of
https://github.com/hathach/tinyusb.git
synced 2025-03-14 04:18:56 +00:00
use musb_ep_csr_t for indexed CSR, also use indexed csr for TI access as well. Merge ep0 and epn together
This commit is contained in:
parent
7d8d364332
commit
6152adb17f
@ -41,10 +41,6 @@ _Pragma("GCC diagnostic ignored \"-Waddress-of-packed-member\"");
|
||||
// Following symbols must be defined by port header
|
||||
// - musb_dcd_int_enable/disable/clear/get_enable
|
||||
// - musb_dcd_int_handler_enter/exit
|
||||
// - musb_dcd_epn_regs: Get memory mapped struct of end point registers
|
||||
// - musb_dcd_ep0_regs: Get memory mapped struct of EP0 registers
|
||||
// - musb_dcd_ctl_regs: Get memory mapped struct of control registers
|
||||
// - musb_dcd_ep_get_fifo_ptr: Gets the address of the provided EP's FIFO
|
||||
// - musb_dcd_setup_fifo/reset_fifo: Configuration of the EP's FIFO
|
||||
#if TU_CHECK_MCU(OPT_MCU_MSP432E4, OPT_MCU_TM4C123, OPT_MCU_TM4C129)
|
||||
#include "musb_ti.h"
|
||||
@ -157,7 +153,7 @@ static void process_setup_packet(uint8_t rhport) {
|
||||
musb_regs_t* musb_regs = MUSB_REGS(rhport);
|
||||
uint32_t *p = (void*)&_dcd.setup_packet;
|
||||
volatile uint32_t *fifo_ptr = &musb_regs->fifo[0];
|
||||
volatile musb_ep0_regs_t* ep0_regs = musb_dcd_ep0_regs(rhport);
|
||||
|
||||
p[0] = *fifo_ptr;
|
||||
p[1] = *fifo_ptr;
|
||||
|
||||
@ -170,7 +166,10 @@ static void process_setup_packet(uint8_t rhport) {
|
||||
_dcd.remaining_ctrl = len;
|
||||
const unsigned dir_in = tu_edpt_dir(_dcd.setup_packet.bmRequestType);
|
||||
/* Clear RX FIFO and reverse the transaction direction */
|
||||
if (len && dir_in) ep0_regs->CSRL0 = USB_CSRL0_RXRDYC;
|
||||
if (len && dir_in) {
|
||||
musb_ep_csr_t* ep_csr = get_ep_csr(musb_regs, 0);
|
||||
ep_csr->csr0l = USB_CSRL0_RXRDYC;
|
||||
}
|
||||
}
|
||||
|
||||
static bool handle_xfer_in(uint8_t rhport, uint_fast8_t ep_addr)
|
||||
@ -186,8 +185,8 @@ static bool handle_xfer_in(uint8_t rhport, uint_fast8_t ep_addr)
|
||||
}
|
||||
|
||||
musb_regs_t* musb_regs = MUSB_REGS(rhport);
|
||||
volatile musb_epn_regs_t *regs = musb_dcd_epn_regs(rhport, epnum);
|
||||
const unsigned mps = regs->TXMAXP;
|
||||
musb_ep_csr_t* ep_csr = get_ep_csr(musb_regs, epnum);
|
||||
const unsigned mps = ep_csr->tx_maxp;
|
||||
const unsigned len = TU_MIN(mps, rem);
|
||||
void *buf = pipe->buf;
|
||||
volatile void *fifo_ptr = &musb_regs->fifo[epnum];
|
||||
@ -201,8 +200,8 @@ static bool handle_xfer_in(uint8_t rhport, uint_fast8_t ep_addr)
|
||||
}
|
||||
pipe->remaining = rem - len;
|
||||
}
|
||||
regs->TXCSRL = USB_TXCSRL1_TXRDY;
|
||||
// TU_LOG1(" TXCSRL%d = %x %d\r\n", epnum, regs->TXCSRL, rem - len);
|
||||
ep_csr->tx_csrl = USB_TXCSRL1_TXRDY;
|
||||
// TU_LOG1(" TXCSRL%d = %x %d\r\n", epnum, ep_csr->tx_csrl, rem - len);
|
||||
return false;
|
||||
}
|
||||
|
||||
@ -212,14 +211,14 @@ static bool handle_xfer_out(uint8_t rhport, uint_fast8_t ep_addr)
|
||||
unsigned epnum_minus1 = epnum - 1;
|
||||
pipe_state_t *pipe = &_dcd.pipe[tu_edpt_dir(ep_addr)][epnum_minus1];
|
||||
musb_regs_t* musb_regs = MUSB_REGS(rhport);
|
||||
volatile musb_epn_regs_t *regs = musb_dcd_epn_regs(rhport, epnum);
|
||||
// TU_LOG1(" RXCSRL%d = %x\r\n", epnum_minus1 + 1, regs->RXCSRL);
|
||||
musb_ep_csr_t* ep_csr = get_ep_csr(musb_regs, epnum);
|
||||
// TU_LOG1(" RXCSRL%d = %x\r\n", epnum_minus1 + 1, ep_csr->rx_csrl);
|
||||
|
||||
TU_ASSERT(regs->RXCSRL & USB_RXCSRL1_RXRDY);
|
||||
TU_ASSERT(ep_csr->rx_csrl & USB_RXCSRL1_RXRDY);
|
||||
|
||||
const unsigned mps = regs->RXMAXP;
|
||||
const unsigned mps = ep_csr->rx_maxp;
|
||||
const unsigned rem = pipe->remaining;
|
||||
const unsigned vld = regs->RXCOUNT;
|
||||
const unsigned vld = ep_csr->rx_count;
|
||||
const unsigned len = TU_MIN(TU_MIN(rem, mps), vld);
|
||||
void *buf = pipe->buf;
|
||||
volatile void *fifo_ptr = &musb_regs->fifo[epnum];
|
||||
@ -236,7 +235,7 @@ static bool handle_xfer_out(uint8_t rhport, uint_fast8_t ep_addr)
|
||||
pipe->buf = NULL;
|
||||
return NULL != buf;
|
||||
}
|
||||
regs->RXCSRL = 0; /* Clear RXRDY bit */
|
||||
ep_csr->rx_csrl = 0; /* Clear RXRDY bit */
|
||||
return false;
|
||||
}
|
||||
|
||||
@ -254,8 +253,9 @@ static bool edpt_n_xfer(uint8_t rhport, uint8_t ep_addr, uint8_t *buffer, uint16
|
||||
if (dir_in) {
|
||||
handle_xfer_in(rhport, ep_addr);
|
||||
} else {
|
||||
volatile musb_epn_regs_t *regs = musb_dcd_epn_regs(rhport, epnum);
|
||||
if (regs->RXCSRL & USB_RXCSRL1_RXRDY) regs->RXCSRL = 0;
|
||||
musb_regs_t* musb_regs = MUSB_REGS(rhport);
|
||||
musb_ep_csr_t* ep_csr = get_ep_csr(musb_regs, epnum);
|
||||
if (ep_csr->rx_csrl & USB_RXCSRL1_RXRDY) ep_csr->rx_csrl = 0;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
@ -265,7 +265,7 @@ static bool edpt0_xfer(uint8_t rhport, uint8_t ep_addr, uint8_t *buffer, uint16_
|
||||
(void)rhport;
|
||||
TU_ASSERT(total_bytes <= 64); /* Current implementation supports for only up to 64 bytes. */
|
||||
musb_regs_t* musb_regs = MUSB_REGS(rhport);
|
||||
volatile musb_ep0_regs_t* ep0_regs = musb_dcd_ep0_regs(rhport);
|
||||
musb_ep_csr_t* ep_csr = get_ep_csr(musb_regs, 0);
|
||||
const unsigned req = _dcd.setup_packet.bmRequestType;
|
||||
TU_ASSERT(req != REQUEST_TYPE_INVALID || total_bytes == 0);
|
||||
|
||||
@ -276,7 +276,7 @@ static bool edpt0_xfer(uint8_t rhport, uint8_t ep_addr, uint8_t *buffer, uint16_
|
||||
* may have already finished and received the next setup packet
|
||||
* without calling this function, so we have no choice but to
|
||||
* invoke the callback function of status packet here. */
|
||||
// TU_LOG1(" STATUS OUT ep0_regs->CSRL0 = %x\r\n", ep0_regs->CSRL0);
|
||||
// TU_LOG1(" STATUS OUT ep_csr->csr0l = %x\r\n", ep_csr->csr0l);
|
||||
_dcd.status_out = 0;
|
||||
if (req == REQUEST_TYPE_INVALID) {
|
||||
dcd_event_xfer_complete(rhport, ep_addr, total_bytes, XFER_RESULT_SUCCESS, false);
|
||||
@ -305,25 +305,25 @@ static bool edpt0_xfer(uint8_t rhport, uint8_t ep_addr, uint8_t *buffer, uint16_
|
||||
_dcd.setup_packet.bmRequestType = REQUEST_TYPE_INVALID; /* Change to STATUS/SETUP stage */
|
||||
_dcd.status_out = 1;
|
||||
/* Flush TX FIFO and reverse the transaction direction. */
|
||||
ep0_regs->CSRL0 = USB_CSRL0_TXRDY | USB_CSRL0_DATAEND;
|
||||
ep_csr->csr0l = USB_CSRL0_TXRDY | USB_CSRL0_DATAEND;
|
||||
} else {
|
||||
ep0_regs->CSRL0 = USB_CSRL0_TXRDY; /* Flush TX FIFO to return ACK. */
|
||||
ep_csr->csr0l = USB_CSRL0_TXRDY; /* Flush TX FIFO to return ACK. */
|
||||
}
|
||||
// TU_LOG1(" IN ep0_regs->CSRL0 = %x\r\n", ep0_regs->CSRL0);
|
||||
// TU_LOG1(" IN ep_csr->csr0l = %x\r\n", ep_csr->csr0l);
|
||||
} else {
|
||||
// TU_LOG1(" OUT ep0_regs->CSRL0 = %x\r\n", ep0_regs->CSRL0);
|
||||
// TU_LOG1(" OUT ep_csr->csr0l = %x\r\n", ep_csr->csr0l);
|
||||
_dcd.pipe0.buf = buffer;
|
||||
_dcd.pipe0.length = len;
|
||||
_dcd.pipe0.remaining = len;
|
||||
ep0_regs->CSRL0 = USB_CSRL0_RXRDYC; /* Clear RX FIFO to return ACK. */
|
||||
ep_csr->csr0l = USB_CSRL0_RXRDYC; /* Clear RX FIFO to return ACK. */
|
||||
}
|
||||
} else if (dir_in) {
|
||||
// TU_LOG1(" STATUS IN ep0_regs->CSRL0 = %x\r\n", ep0_regs->CSRL0);
|
||||
// TU_LOG1(" STATUS IN ep_csr->csr0l = %x\r\n", ep_csr->csr0l);
|
||||
_dcd.pipe0.buf = NULL;
|
||||
_dcd.pipe0.length = 0;
|
||||
_dcd.pipe0.remaining = 0;
|
||||
/* Clear RX FIFO and reverse the transaction direction */
|
||||
ep0_regs->CSRL0 = USB_CSRL0_RXRDYC | USB_CSRL0_DATAEND;
|
||||
ep_csr->csr0l = USB_CSRL0_RXRDYC | USB_CSRL0_DATAEND;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
@ -331,21 +331,21 @@ static bool edpt0_xfer(uint8_t rhport, uint8_t ep_addr, uint8_t *buffer, uint16_
|
||||
static void process_ep0(uint8_t rhport)
|
||||
{
|
||||
musb_regs_t* musb_regs = MUSB_REGS(rhport);
|
||||
volatile musb_ep0_regs_t* ep0_regs = musb_dcd_ep0_regs(rhport);
|
||||
uint_fast8_t csrl = ep0_regs->CSRL0;
|
||||
musb_ep_csr_t* ep_csr = get_ep_csr(musb_regs, 0);
|
||||
uint_fast8_t csrl = ep_csr->csr0l;
|
||||
|
||||
// TU_LOG1(" EP0 ep0_regs->CSRL0 = %x\r\n", csrl);
|
||||
// TU_LOG1(" EP0 ep_csr->csr0l = %x\r\n", csrl);
|
||||
|
||||
if (csrl & USB_CSRL0_STALLED) {
|
||||
/* Returned STALL packet to HOST. */
|
||||
ep0_regs->CSRL0 = 0; /* Clear STALL */
|
||||
ep_csr->csr0l = 0; /* Clear STALL */
|
||||
return;
|
||||
}
|
||||
|
||||
unsigned req = _dcd.setup_packet.bmRequestType;
|
||||
if (csrl & USB_CSRL0_SETEND) {
|
||||
TU_LOG1(" ABORT by the next packets\r\n");
|
||||
ep0_regs->CSRL0 = USB_CSRL0_SETENDC;
|
||||
ep_csr->csr0l = USB_CSRL0_SETENDC;
|
||||
if (req != REQUEST_TYPE_INVALID && _dcd.pipe0.buf) {
|
||||
/* DATA stage was aborted by receiving STATUS or SETUP packet. */
|
||||
_dcd.pipe0.buf = NULL;
|
||||
@ -363,13 +363,13 @@ static void process_ep0(uint8_t rhport)
|
||||
/* Received SETUP or DATA OUT packet */
|
||||
if (req == REQUEST_TYPE_INVALID) {
|
||||
/* SETUP */
|
||||
TU_ASSERT(sizeof(tusb_control_request_t) == ep0_regs->COUNT0,);
|
||||
TU_ASSERT(sizeof(tusb_control_request_t) == ep_csr->rx_count,);
|
||||
process_setup_packet(rhport);
|
||||
return;
|
||||
}
|
||||
if (_dcd.pipe0.buf) {
|
||||
/* DATA OUT */
|
||||
const unsigned vld = ep0_regs->COUNT0;
|
||||
const unsigned vld = ep_csr->rx_count;
|
||||
const unsigned rem = _dcd.pipe0.remaining;
|
||||
const unsigned len = TU_MIN(TU_MIN(rem, 64), vld);
|
||||
volatile void *fifo_ptr = &musb_regs->fifo[0];
|
||||
@ -415,22 +415,23 @@ static void process_ep0(uint8_t rhport)
|
||||
static void process_edpt_n(uint8_t rhport, uint_fast8_t ep_addr)
|
||||
{
|
||||
bool completed;
|
||||
const unsigned dir_in = tu_edpt_dir(ep_addr);
|
||||
const unsigned dir_in = tu_edpt_dir(ep_addr);
|
||||
const unsigned epn = tu_edpt_number(ep_addr);
|
||||
const unsigned epn_minus1 = epn - 1;
|
||||
|
||||
volatile musb_epn_regs_t *regs = musb_dcd_epn_regs(rhport, epn);
|
||||
musb_regs_t* musb_regs = MUSB_REGS(rhport);
|
||||
musb_ep_csr_t* ep_csr = get_ep_csr(musb_regs, epn);
|
||||
if (dir_in) {
|
||||
// TU_LOG1(" TXCSRL%d = %x\r\n", epn, regs->TXCSRL);
|
||||
if (regs->TXCSRL & USB_TXCSRL1_STALLED) {
|
||||
regs->TXCSRL &= ~(USB_TXCSRL1_STALLED | USB_TXCSRL1_UNDRN);
|
||||
// TU_LOG1(" TX CSRL%d = %x\r\n", epn, ep_csr->tx_csrl);
|
||||
if (ep_csr->tx_csrl & USB_TXCSRL1_STALLED) {
|
||||
ep_csr->tx_csrl &= ~(USB_TXCSRL1_STALLED | USB_TXCSRL1_UNDRN);
|
||||
return;
|
||||
}
|
||||
completed = handle_xfer_in(rhport, ep_addr);
|
||||
} else {
|
||||
// TU_LOG1(" RXCSRL%d = %x\r\n", epn, regs->RXCSRL);
|
||||
if (regs->RXCSRL & USB_RXCSRL1_STALLED) {
|
||||
regs->RXCSRL &= ~(USB_RXCSRL1_STALLED | USB_RXCSRL1_OVER);
|
||||
// TU_LOG1(" RX CSRL%d = %x\r\n", epn, ep_csr->rx_csrl);
|
||||
if (ep_csr->rx_csrl & USB_RXCSRL1_STALLED) {
|
||||
ep_csr->rx_csrl &= ~(USB_RXCSRL1_STALLED | USB_RXCSRL1_OVER);
|
||||
return;
|
||||
}
|
||||
completed = handle_xfer_out(rhport, ep_addr);
|
||||
@ -492,12 +493,14 @@ void dcd_int_disable(uint8_t rhport)
|
||||
void dcd_set_address(uint8_t rhport, uint8_t dev_addr)
|
||||
{
|
||||
(void)dev_addr;
|
||||
volatile musb_ep0_regs_t* ep0_regs = musb_dcd_ep0_regs(rhport);
|
||||
musb_regs_t* musb_regs = MUSB_REGS(rhport);
|
||||
musb_ep_csr_t* ep_csr = get_ep_csr(musb_regs, 0);
|
||||
|
||||
_dcd.pipe0.buf = NULL;
|
||||
_dcd.pipe0.length = 0;
|
||||
_dcd.pipe0.remaining = 0;
|
||||
/* Clear RX FIFO to return ACK. */
|
||||
ep0_regs->CSRL0 = USB_CSRL0_RXRDYC | USB_CSRL0_DATAEND;
|
||||
ep_csr->csr0l = USB_CSRL0_RXRDYC | USB_CSRL0_DATAEND;
|
||||
}
|
||||
|
||||
// Wake up host
|
||||
@ -554,24 +557,24 @@ bool dcd_edpt_open(uint8_t rhport, tusb_desc_endpoint_t const * ep_desc)
|
||||
pipe->length = 0;
|
||||
pipe->remaining = 0;
|
||||
|
||||
volatile musb_epn_regs_t *regs = musb_dcd_epn_regs(rhport, epn);
|
||||
musb_regs_t* musb_regs = MUSB_REGS(rhport);
|
||||
musb_ep_csr_t* ep_csr = get_ep_csr(musb_regs, epn);
|
||||
if (dir_in) {
|
||||
regs->TXMAXP = mps;
|
||||
regs->TXCSRH = (xfer == TUSB_XFER_ISOCHRONOUS) ? USB_TXCSRH1_ISO : 0;
|
||||
if (regs->TXCSRL & USB_TXCSRL1_TXRDY) {
|
||||
regs->TXCSRL = USB_TXCSRL1_CLRDT | USB_TXCSRL1_FLUSH;
|
||||
ep_csr->tx_maxp = mps;
|
||||
ep_csr->tx_csrh = (xfer == TUSB_XFER_ISOCHRONOUS) ? USB_TXCSRH1_ISO : 0;
|
||||
if (ep_csr->tx_csrl & USB_TXCSRL1_TXRDY) {
|
||||
ep_csr->tx_csrl = USB_TXCSRL1_CLRDT | USB_TXCSRL1_FLUSH;
|
||||
} else {
|
||||
regs->TXCSRL = USB_TXCSRL1_CLRDT;
|
||||
ep_csr->tx_csrl = USB_TXCSRL1_CLRDT;
|
||||
}
|
||||
musb_regs->intr_txen |= TU_BIT(epn);
|
||||
} else {
|
||||
regs->RXMAXP = mps;
|
||||
regs->RXCSRH = (xfer == TUSB_XFER_ISOCHRONOUS) ? USB_RXCSRH1_ISO : 0;
|
||||
if (regs->RXCSRL & USB_RXCSRL1_RXRDY) {
|
||||
regs->RXCSRL = USB_RXCSRL1_CLRDT | USB_RXCSRL1_FLUSH;
|
||||
ep_csr->rx_maxp = mps;
|
||||
ep_csr->rx_csrh = (xfer == TUSB_XFER_ISOCHRONOUS) ? USB_RXCSRH1_ISO : 0;
|
||||
if (ep_csr->rx_csrl & USB_RXCSRL1_RXRDY) {
|
||||
ep_csr->rx_csrl = USB_RXCSRL1_CLRDT | USB_RXCSRL1_FLUSH;
|
||||
} else {
|
||||
regs->RXCSRL = USB_RXCSRL1_CLRDT;
|
||||
ep_csr->rx_csrl = USB_RXCSRL1_CLRDT;
|
||||
}
|
||||
musb_regs->intr_rxen |= TU_BIT(epn);
|
||||
}
|
||||
@ -584,27 +587,26 @@ bool dcd_edpt_open(uint8_t rhport, tusb_desc_endpoint_t const * ep_desc)
|
||||
|
||||
void dcd_edpt_close_all(uint8_t rhport)
|
||||
{
|
||||
volatile musb_epn_regs_t *regs;
|
||||
musb_regs_t* musb_regs = MUSB_REGS(rhport);
|
||||
unsigned const ie = musb_dcd_get_int_enable(rhport);
|
||||
musb_dcd_int_disable(rhport);
|
||||
musb_regs->intr_txen = 1; /* Enable only EP0 */
|
||||
musb_regs->intr_rxen = 0;
|
||||
for (unsigned i = 1; i < TUP_DCD_ENDPOINT_MAX; ++i) {
|
||||
regs = musb_dcd_epn_regs(rhport, i);
|
||||
regs->TXMAXP = 0;
|
||||
regs->TXCSRH = 0;
|
||||
if (regs->TXCSRL & USB_TXCSRL1_TXRDY)
|
||||
regs->TXCSRL = USB_TXCSRL1_CLRDT | USB_TXCSRL1_FLUSH;
|
||||
musb_ep_csr_t* ep_csr = get_ep_csr(musb_regs, i);
|
||||
ep_csr->tx_maxp = 0;
|
||||
ep_csr->tx_csrh = 0;
|
||||
if (ep_csr->tx_csrl & USB_TXCSRL1_TXRDY)
|
||||
ep_csr->tx_csrl = USB_TXCSRL1_CLRDT | USB_TXCSRL1_FLUSH;
|
||||
else
|
||||
regs->TXCSRL = USB_TXCSRL1_CLRDT;
|
||||
ep_csr->tx_csrl = USB_TXCSRL1_CLRDT;
|
||||
|
||||
regs->RXMAXP = 0;
|
||||
regs->RXCSRH = 0;
|
||||
if (regs->RXCSRL & USB_RXCSRL1_RXRDY) {
|
||||
regs->RXCSRL = USB_RXCSRL1_CLRDT | USB_RXCSRL1_FLUSH;
|
||||
ep_csr->rx_maxp = 0;
|
||||
ep_csr->rx_csrh = 0;
|
||||
if (ep_csr->rx_csrl & USB_RXCSRL1_RXRDY) {
|
||||
ep_csr->rx_csrl = USB_RXCSRL1_CLRDT | USB_RXCSRL1_FLUSH;
|
||||
} else {
|
||||
regs->RXCSRL = USB_RXCSRL1_CLRDT;
|
||||
ep_csr->rx_csrl = USB_RXCSRL1_CLRDT;
|
||||
}
|
||||
|
||||
musb_dcd_reset_fifo(rhport, i, 0);
|
||||
@ -618,28 +620,27 @@ void dcd_edpt_close(uint8_t rhport, uint8_t ep_addr)
|
||||
{
|
||||
unsigned const epn = tu_edpt_number(ep_addr);
|
||||
unsigned const dir_in = tu_edpt_dir(ep_addr);
|
||||
|
||||
volatile musb_epn_regs_t *regs = musb_dcd_epn_regs(rhport, epn);
|
||||
musb_regs_t* musb_regs = MUSB_REGS(rhport);
|
||||
musb_ep_csr_t* ep_csr = get_ep_csr(musb_regs, epn);
|
||||
unsigned const ie = musb_dcd_get_int_enable(rhport);
|
||||
musb_dcd_int_disable(rhport);
|
||||
if (dir_in) {
|
||||
musb_regs->intr_txen &= ~TU_BIT(epn);
|
||||
regs->TXMAXP = 0;
|
||||
regs->TXCSRH = 0;
|
||||
if (regs->TXCSRL & USB_TXCSRL1_TXRDY) {
|
||||
regs->TXCSRL = USB_TXCSRL1_CLRDT | USB_TXCSRL1_FLUSH;
|
||||
ep_csr->tx_maxp = 0;
|
||||
ep_csr->tx_csrh = 0;
|
||||
if (ep_csr->tx_csrl & USB_TXCSRL1_TXRDY) {
|
||||
ep_csr->tx_csrl = USB_TXCSRL1_CLRDT | USB_TXCSRL1_FLUSH;
|
||||
} else {
|
||||
regs->TXCSRL = USB_TXCSRL1_CLRDT;
|
||||
ep_csr->tx_csrl = USB_TXCSRL1_CLRDT;
|
||||
}
|
||||
} else {
|
||||
musb_regs->intr_rxen &= ~TU_BIT(epn);
|
||||
regs->RXMAXP = 0;
|
||||
regs->RXCSRH = 0;
|
||||
if (regs->RXCSRL & USB_RXCSRL1_RXRDY) {
|
||||
regs->RXCSRL = USB_RXCSRL1_CLRDT | USB_RXCSRL1_FLUSH;
|
||||
ep_csr->rx_maxp = 0;
|
||||
ep_csr->rx_csrh = 0;
|
||||
if (ep_csr->rx_csrl & USB_RXCSRL1_RXRDY) {
|
||||
ep_csr->rx_csrl = USB_RXCSRL1_CLRDT | USB_RXCSRL1_FLUSH;
|
||||
} else {
|
||||
regs->RXCSRL = USB_RXCSRL1_CLRDT;
|
||||
ep_csr->rx_csrl = USB_RXCSRL1_CLRDT;
|
||||
}
|
||||
}
|
||||
musb_dcd_reset_fifo(rhport, epn, dir_in);
|
||||
@ -682,25 +683,24 @@ bool dcd_edpt_xfer_fifo(uint8_t rhport, uint8_t ep_addr, tu_fifo_t * ff, uint16_
|
||||
}
|
||||
|
||||
// Stall endpoint
|
||||
void dcd_edpt_stall(uint8_t rhport, uint8_t ep_addr)
|
||||
{
|
||||
void dcd_edpt_stall(uint8_t rhport, uint8_t ep_addr) {
|
||||
unsigned const epn = tu_edpt_number(ep_addr);
|
||||
unsigned const ie = musb_dcd_get_int_enable(rhport);
|
||||
musb_regs_t* musb_regs = MUSB_REGS(rhport);
|
||||
musb_ep_csr_t* ep_csr = get_ep_csr(musb_regs, epn);
|
||||
musb_dcd_int_disable(rhport);
|
||||
if (0 == epn) {
|
||||
volatile musb_ep0_regs_t* ep0_regs = musb_dcd_ep0_regs(rhport);
|
||||
if (!ep_addr) { /* Ignore EP80 */
|
||||
_dcd.setup_packet.bmRequestType = REQUEST_TYPE_INVALID;
|
||||
_dcd.pipe0.buf = NULL;
|
||||
ep0_regs->CSRL0 = USB_CSRL0_STALL;
|
||||
ep_csr->csr0l = USB_CSRL0_STALL;
|
||||
}
|
||||
} else {
|
||||
volatile musb_epn_regs_t *regs = musb_dcd_epn_regs(rhport, epn);
|
||||
if (tu_edpt_dir(ep_addr)) { /* IN */
|
||||
regs->TXCSRL = USB_TXCSRL1_STALL;
|
||||
ep_csr->tx_csrl = USB_TXCSRL1_STALL;
|
||||
} else { /* OUT */
|
||||
TU_ASSERT(!(regs->RXCSRL & USB_RXCSRL1_RXRDY),);
|
||||
regs->RXCSRL = USB_RXCSRL1_STALL;
|
||||
TU_ASSERT(!(ep_csr->rx_csrl & USB_RXCSRL1_RXRDY),);
|
||||
ep_csr->rx_csrl = USB_RXCSRL1_STALL;
|
||||
}
|
||||
}
|
||||
if (ie) musb_dcd_int_enable(rhport);
|
||||
@ -711,13 +711,14 @@ void dcd_edpt_clear_stall(uint8_t rhport, uint8_t ep_addr)
|
||||
{
|
||||
(void)rhport;
|
||||
unsigned const epn = tu_edpt_number(ep_addr);
|
||||
musb_epn_regs_t volatile *regs = musb_dcd_epn_regs(rhport, epn);
|
||||
musb_regs_t* musb_regs = MUSB_REGS(rhport);
|
||||
musb_ep_csr_t* ep_csr = get_ep_csr(musb_regs, epn);
|
||||
unsigned const ie = musb_dcd_get_int_enable(rhport);
|
||||
musb_dcd_int_disable(rhport);
|
||||
if (tu_edpt_dir(ep_addr)) { /* IN */
|
||||
regs->TXCSRL = USB_TXCSRL1_CLRDT;
|
||||
ep_csr->tx_csrl = USB_TXCSRL1_CLRDT;
|
||||
} else { /* OUT */
|
||||
regs->RXCSRL = USB_RXCSRL1_CLRDT;
|
||||
ep_csr->rx_csrl = USB_RXCSRL1_CLRDT;
|
||||
}
|
||||
if (ie) musb_dcd_int_enable(rhport);
|
||||
}
|
||||
|
@ -136,20 +136,6 @@ static inline void musb_dcd_phy_init(uint8_t rhport) {
|
||||
musb_periph_inst[rhport]->m31_phy_ponrst = 1;
|
||||
}
|
||||
|
||||
static inline volatile musb_epn_regs_t* musb_dcd_epn_regs(uint8_t rhport, unsigned epnum) {
|
||||
//Need to set index to map EP registers
|
||||
musb_periph_inst[rhport]->index = epnum;
|
||||
volatile musb_epn_regs_t* regs = (volatile musb_epn_regs_t*) ((uintptr_t) &(musb_periph_inst[rhport]->inmaxp));
|
||||
return regs;
|
||||
}
|
||||
|
||||
static inline volatile musb_ep0_regs_t* musb_dcd_ep0_regs(uint8_t rhport) {
|
||||
//Need to set index to map EP0 registers
|
||||
musb_periph_inst[rhport]->index = 0;
|
||||
volatile musb_ep0_regs_t* regs = (volatile musb_ep0_regs_t*) ((uintptr_t) &(musb_periph_inst[rhport]->csr0));
|
||||
return regs;
|
||||
}
|
||||
|
||||
static inline void musb_dcd_setup_fifo(uint8_t rhport, unsigned epnum, unsigned dir_in, unsigned mps) {
|
||||
(void) mps;
|
||||
|
||||
|
@ -97,22 +97,6 @@ static inline void musb_dcd_int_handler_exit(uint8_t rhport){
|
||||
//Nothing to do for this part
|
||||
}
|
||||
|
||||
static inline volatile musb_epn_regs_t* musb_dcd_epn_regs(uint8_t rhport, unsigned epnum)
|
||||
{
|
||||
uintptr_t baseptr = (uintptr_t)&(musb_periph_inst[rhport]->TXMAXP1);
|
||||
|
||||
//On the TI parts, the epn registers are 16-bytes apart. The core regs defined
|
||||
//by musb_dcd_epn_regs and 6 reserved/other use bytes
|
||||
volatile musb_epn_regs_t *regs = (volatile musb_epn_regs_t*)(baseptr + ((epnum - 1) * 16));
|
||||
return regs;
|
||||
}
|
||||
|
||||
static inline volatile musb_ep0_regs_t* musb_dcd_ep0_regs(uint8_t rhport)
|
||||
{
|
||||
volatile musb_ep0_regs_t *regs = (volatile musb_ep0_regs_t*)((uintptr_t)&(musb_periph_inst[rhport]->CSRL0));
|
||||
return regs;
|
||||
}
|
||||
|
||||
typedef struct {
|
||||
uint_fast16_t beg; /* offset of including first element */
|
||||
uint_fast16_t end; /* offset of excluding the last element */
|
||||
|
@ -1,3 +1,29 @@
|
||||
/*
|
||||
* The MIT License (MIT)
|
||||
*
|
||||
* Copyright (c) 2019 Ha Thach (tinyusb.org)
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
* of this software and associated documentation files (the "Software"), to deal
|
||||
* in the Software without restriction, including without limitation the rights
|
||||
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
* copies of the Software, and to permit persons to whom the Software is
|
||||
* furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included in
|
||||
* all copies or substantial portions of the Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
* THE SOFTWARE.
|
||||
*
|
||||
* This file is part of the TinyUSB stack.
|
||||
*/
|
||||
|
||||
/******************************************************************************
|
||||
*
|
||||
* Copyright (C) 2018 Texas Instruments Incorporated - http://www.ti.com/
|
||||
@ -57,24 +83,29 @@
|
||||
#define __R volatile const
|
||||
#endif
|
||||
|
||||
// Endpoint register mapping. Non-zero end points.
|
||||
typedef struct TU_ATTR_PACKED {
|
||||
uint16_t TXMAXP;
|
||||
uint8_t TXCSRL;
|
||||
uint8_t TXCSRH;
|
||||
uint16_t RXMAXP;
|
||||
uint8_t RXCSRL;
|
||||
uint8_t RXCSRH;
|
||||
uint16_t RXCOUNT;
|
||||
} musb_epn_regs_t;
|
||||
__IO uint16_t tx_maxp; // 0x00: TXMAXP
|
||||
union {
|
||||
__IO uint8_t csr0l; // 0x02: CSR0
|
||||
__IO uint8_t tx_csrl; // 0x02: TX CSRL
|
||||
};
|
||||
union {
|
||||
__IO uint8_t csr0h; // 0x03: CSR0H
|
||||
__IO uint8_t tx_csrh; // 0x03: TX CSRH
|
||||
};
|
||||
__IO uint16_t rx_maxp; // 0x04: RX MAXP
|
||||
__IO uint8_t rx_csrl; // 0x06: RX CSRL
|
||||
__IO uint8_t rx_csrh; // 0x07: RX CSRH
|
||||
__IO uint16_t rx_count; // 0x08: RX COUNT
|
||||
__IO uint8_t tx_type; // 0x0A: TX TYPE
|
||||
__IO uint8_t tx_interval; // 0x0B: TX INTERVAL
|
||||
__IO uint8_t rx_type; // 0x0C: RX TYPE
|
||||
__IO uint8_t rx_interval; // 0x0D: RX INTERVAL
|
||||
__IO uint8_t reserved_0x0e; // 0x0E: Reserved
|
||||
__IO uint8_t fifo_size; // 0x0F: FIFO_SIZE
|
||||
} musb_ep_csr_t;
|
||||
|
||||
// Endpoint 0 register mapping.
|
||||
typedef struct TU_ATTR_PACKED {
|
||||
uint8_t CSRL0;
|
||||
uint8_t CSRH0;
|
||||
uint32_t RESERVED;
|
||||
uint8_t COUNT0;
|
||||
} musb_ep0_regs_t;
|
||||
TU_VERIFY_STATIC(sizeof(musb_ep_csr_t) == 16, "size is not correct");
|
||||
|
||||
typedef struct {
|
||||
//------------- Common -------------//
|
||||
@ -93,21 +124,14 @@ typedef struct {
|
||||
__IO uint16_t frame; // 0x0C: FRAME
|
||||
__IO uint8_t index; // 0x0E: INDEX
|
||||
__IO uint8_t testmode; // 0x0F: TESTMODE
|
||||
__IO uint16_t inmaxp; // 0x10: INMAXP
|
||||
union {
|
||||
__IO uint8_t csr0; // 0x12: CSR0
|
||||
__IO uint8_t incsrl; // 0x12: INCSRL
|
||||
};
|
||||
__IO uint8_t incsru; // 0x13: INCSRU
|
||||
__IO uint16_t outmaxp; // 0x14: OUTMAXP
|
||||
__IO uint8_t outcsrl; // 0x16: OUTCSRL
|
||||
__IO uint8_t outcsru; // 0x17: OUTCSRU
|
||||
union {
|
||||
__IO uint16_t count0; // 0x18: COUNT0
|
||||
__IO uint16_t outcount; // 0x18: OUTCOUNT
|
||||
};
|
||||
__R uint16_t rsv_0x1a_0x1f[3];
|
||||
|
||||
//------------- Indexed CSR -------------//
|
||||
musb_ep_csr_t indexed_csr; // 0x10-0x1F: Indexed CSR 0-15
|
||||
|
||||
//------------- FIFOs -------------//
|
||||
__IO uint32_t fifo[16]; // 0x20-0x5C: FIFO 0-15
|
||||
|
||||
// Common (2)
|
||||
__IO uint8_t devctl; // 0x60: DEVCTL
|
||||
__IO uint8_t misc; // 0x61: MISC
|
||||
|
||||
@ -138,7 +162,13 @@ typedef struct {
|
||||
//------------- Extended -------------//
|
||||
__IO uint16_t ctuch; // 0x80: CTUCH
|
||||
__IO uint16_t cthsrtn; // 0x82: CTHSRTN
|
||||
__R uint32_t rsv_0x84_0x3ff[223];
|
||||
__R uint32_t rsv_0x84_0xff[31]; // 0x84-0xFF: Reserved
|
||||
|
||||
//------------- Absolute CSR (used index to remap to Indexed above) -------------//
|
||||
// TI tm4c can access this directly, but should use indexed_csr for portability
|
||||
musb_ep_csr_t ep_csr[16]; // 0x100-0x1FF: EP0-15 CSR
|
||||
|
||||
__R uint32_t rsv_0x200_0x3ff[128]; // 0x200-0x3FF: Reserved
|
||||
|
||||
//------------- Analog PHY -------------//
|
||||
__IO uint32_t mxm_usb_reg_00; // 0x400: MXM_USB_REG_00
|
||||
@ -187,6 +217,16 @@ typedef struct {
|
||||
|
||||
TU_VERIFY_STATIC(sizeof(musb_regs_t) == 0x4A8, "size is not correct");
|
||||
|
||||
//--------------------------------------------------------------------+
|
||||
// Helper
|
||||
//--------------------------------------------------------------------+
|
||||
|
||||
TU_ATTR_ALWAYS_INLINE static inline musb_ep_csr_t* get_ep_csr(musb_regs_t* musb_regs, unsigned epnum) {
|
||||
musb_regs->index = epnum;
|
||||
return &musb_regs->indexed_csr;
|
||||
}
|
||||
|
||||
|
||||
//*****************************************************************************
|
||||
//
|
||||
// The following are defines for the bit fields in the USB_O_FADDR register.
|
||||
|
Loading…
x
Reference in New Issue
Block a user