mirror of
https://github.com/torvalds/linux.git
synced 2026-05-22 22:22:08 +02:00
serial: 8250: dma: Allow driver operations before starting DMA transfers
One situation where this could be used is when configuring the UART controller to be the DMA flow controller. This is a typical case where the driver might need to program a few more registers before starting a DMA transfer. Provide the necessary infrastructure to support this case. Suggested-by: Andy Shevchenko <andriy.shevchenko@linux.intel.com> Reviewed-by: Andy Shevchenko <andriy.shevchenko@linux.intel.com> Signed-off-by: Miquel Raynal <miquel.raynal@bootlin.com> Link: https://lore.kernel.org/r/20220422180615.9098-6-miquel.raynal@bootlin.com Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
This commit is contained in:
parent
593dea000b
commit
e4fb03fe10
|
|
@ -17,6 +17,8 @@
|
|||
struct uart_8250_dma {
|
||||
int (*tx_dma)(struct uart_8250_port *p);
|
||||
int (*rx_dma)(struct uart_8250_port *p);
|
||||
void (*prepare_tx_dma)(struct uart_8250_port *p);
|
||||
void (*prepare_rx_dma)(struct uart_8250_port *p);
|
||||
|
||||
/* Filter function */
|
||||
dma_filter_fn fn;
|
||||
|
|
@ -302,6 +304,22 @@ extern int serial8250_rx_dma(struct uart_8250_port *);
|
|||
extern void serial8250_rx_dma_flush(struct uart_8250_port *);
|
||||
extern int serial8250_request_dma(struct uart_8250_port *);
|
||||
extern void serial8250_release_dma(struct uart_8250_port *);
|
||||
|
||||
static inline void serial8250_do_prepare_tx_dma(struct uart_8250_port *p)
|
||||
{
|
||||
struct uart_8250_dma *dma = p->dma;
|
||||
|
||||
if (dma->prepare_tx_dma)
|
||||
dma->prepare_tx_dma(p);
|
||||
}
|
||||
|
||||
static inline void serial8250_do_prepare_rx_dma(struct uart_8250_port *p)
|
||||
{
|
||||
struct uart_8250_dma *dma = p->dma;
|
||||
|
||||
if (dma->prepare_rx_dma)
|
||||
dma->prepare_rx_dma(p);
|
||||
}
|
||||
#else
|
||||
static inline int serial8250_tx_dma(struct uart_8250_port *p)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -86,6 +86,8 @@ int serial8250_tx_dma(struct uart_8250_port *p)
|
|||
|
||||
dma->tx_size = CIRC_CNT_TO_END(xmit->head, xmit->tail, UART_XMIT_SIZE);
|
||||
|
||||
serial8250_do_prepare_tx_dma(p);
|
||||
|
||||
desc = dmaengine_prep_slave_single(dma->txchan,
|
||||
dma->tx_addr + xmit->tail,
|
||||
dma->tx_size, DMA_MEM_TO_DEV,
|
||||
|
|
@ -123,6 +125,8 @@ int serial8250_rx_dma(struct uart_8250_port *p)
|
|||
if (dma->rx_running)
|
||||
return 0;
|
||||
|
||||
serial8250_do_prepare_rx_dma(p);
|
||||
|
||||
desc = dmaengine_prep_slave_single(dma->rxchan, dma->rx_addr,
|
||||
dma->rx_size, DMA_DEV_TO_MEM,
|
||||
DMA_PREP_INTERRUPT | DMA_CTRL_ACK);
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user