2022-09-04 12:22 PM
The Cube IDE code flow is
CDC_Transmit_FS
USBD_CDC_TransmitPacket
USBD_LL_Transmit
HAL_PCD_EP_Transmit
USB_WritePacket
and the last one does 16 32 bit word transfers to the USB FIFO
HAL_StatusTypeDef USB_WritePacket(USB_OTG_GlobalTypeDef *USBx, uint8_t *src, uint8_t ch_ep_num, uint16_t len, uint8_t dma)
{
uint32_t USBx_BASE = (uint32_t)USBx;
uint32_t *pSrc = (uint32_t *)src;
uint32_t count32b, i;
if (dma == 0U)
{
count32b = ((uint32_t)len + 3U) / 4U;
for (i = 0U; i < count32b; i++)
{
USBx_DFIFO((uint32_t)ch_ep_num) = *((__packed uint32_t *)pSrc);
pSrc++;
}
}
return HAL_OK;
}
My Q is whether there is any way to tell when that data has been consumed.
I have been doing tests and found
I am sure these are both system dependent, so I am rate limiting to 1kHz and size limiting to 256 bytes.
There are various return codes from various functions but none of these appear to relate to whether you can shove more data out.
Is USB really "open loop" like that? I know it is all polled by the PC, seemingly at ~10kHz
2022-09-06 03:42 PM
That depends on what the box is doing, how much buffering there is, what response time is needed, etc.
Much of my work is in comms and mostly one has buffers, so the whole box can run in IDLE. If one was doing 3 phase motor control at 10000rpm that would be different.
I have ETH RX as highest priority, then 2-3 lower ones, and all the rest is at IDLE. Timer tick is a 1kHz ISR, not an RTOS task.
Is TxState an int or a boolean?
2022-11-05 04:47 PM
A system tick (hardware with ISR) and the timer thread are related but different things. The timer thread manages all software timers. If the IDLE thread is not the only one at the lowest priority, it cannot be used to put the CPU into sleep mode, which is an unnecessary waste of energy and heating of the MCU without any gain. The ETH Rx thread typically doesn't need to be set at the highest priorities because typically it has several Rx buffers for packets and it's DMA can fill those completely autonomously. It could be that some thread processing UART or similar data has to be at a higher priority because that communication is more timing sensitive. But, of course, it depends on protocols, hardware buffers and the project specifics.
Running (almost) everything at a single priority is not an achievement. It's a deliberate crippling of the system for no reason. Except for a few bytes of RAM, you don't gain anything from that. That's true for up to 32 priority levels, which is plenty for almost anything. Going for more is indeed not recommended as it will loose more resources.
> Is TxState an int or a boolean?
It doesn't matter. What I mean is that this is enough:
while (hcdc->TxState)