zhang-2019 commented on code in PR #9057:
URL: https://github.com/apache/nuttx/pull/9057#discussion_r1194741598
##########
drivers/serial/uart_16550.c:
##########
@@ -1157,25 +1317,198 @@ static bool u16550_rxflowcontrol(struct uart_dev_s
*dev,
*
****************************************************************************/
-#ifdef CONFIG_SERIAL_TXDMA
+#ifdef HAVE_16550_UART_DMA
+static void u16550_dmasend_done(FAR struct dma_chan_s *chan,
+ FAR void *arg, ssize_t len)
+{
+ FAR struct uart_dev_s *dev = arg;
+
+ if (len > 0)
+ {
+ dev->dmatx.nbytes = len;
+ uart_xmitchars_done(dev);
+ uart_xmitchars_dma(dev);
+ }
+ else /* Fail, resend */
+ {
+ u16550_dmasend(dev);
+ }
+}
+
static void u16550_dmasend(FAR struct uart_dev_s *dev)
{
+ FAR struct u16550_s *priv = dev->priv;
+ FAR void *buffer = dev->dmatx.buffer;
+ size_t length = dev->dmatx.length;
+
+ up_clean_dcache((uintptr_t)buffer, (uintptr_t)buffer + length);
+ DMA_START(priv->chantx, u16550_dmasend_done, dev,
+ up_addrenv_va_to_pa((void *)priv->uartbase),
+ up_addrenv_va_to_pa(buffer), length);
+}
+
+static void u16550_dmareceive_done(FAR struct dma_chan_s *chan,
+ FAR void *arg, ssize_t len)
+{
+ FAR struct uart_dev_s *dev = arg;
+ FAR struct u16550_s *priv = dev->priv;
+
+ if (len >= 0)
+ {
+ size_t slot = priv->dmarxhead / priv->dmarxsize;
+ size_t offset = priv->dmarxhead - slot * priv->dmarxsize;
+
+ if (len >= priv->dmarxsize)
+ {
+ len = 0;
+ }
+ if (len < offset)
+ {
+ slot++; /* Wrap, move to the next slot */
+ }
+
+ priv->dmarxhead = slot * priv->dmarxsize + len;
+ if (priv->dmarxhead - priv->dmarxtail >= priv->dmarxsize)
+ {
+ serr("The receive dma buffer is overrun\n");
+ priv->dmarxtail = priv->dmarxhead - priv->dmarxsize / 2;
+ }
+
+ /* The receive isn't in the process? */
+ if (dev->dmarx.length == 0)
+ {
+ /* Trigger the receive process */
+ uart_recvchars_dma(dev);
+ }
+ else
+ {
+ /* Copy the received data */
+ u16550_dmareceive(dev);
+ }
+ }
}
-#endif
-#ifdef CONFIG_SERIAL_RXDMA
static void u16550_dmareceive(FAR struct uart_dev_s *dev)
{
+ FAR struct u16550_s *priv = dev->priv;
+
+ if (priv->dmarxhead != priv->dmarxtail)
+ {
+ size_t length = priv->dmarxhead - priv->dmarxtail;
+ size_t offset = priv->dmarxtail % priv->dmarxsize;
+ FAR void *buffer = priv->dmarxbuf + offset;
Review Comment:
change the type of dmarxbuf from void * to char * would be ok
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: [email protected]
For queries about this service, please contact Infrastructure at:
[email protected]