From 6c5704361af06ba9b5504f707365b0cb558e225d Mon Sep 17 00:00:00 2001 From: lupeng Date: Tue, 18 Dec 2018 17:03:05 +0800 Subject: [PATCH] merge v306 drivers sunxi_uart.c code --- .../linux-4.9/drivers/tty/serial/sunxi-uart.c | 46 +++++++++++-------- 1 file changed, 26 insertions(+), 20 deletions(-) diff --git a/lichee/linux-4.9/drivers/tty/serial/sunxi-uart.c b/lichee/linux-4.9/drivers/tty/serial/sunxi-uart.c index fbb529ad6..360b03ac2 100755 --- a/lichee/linux-4.9/drivers/tty/serial/sunxi-uart.c +++ b/lichee/linux-4.9/drivers/tty/serial/sunxi-uart.c @@ -88,7 +88,7 @@ static void sw_uart_release_dma_rx(struct sw_uart_port *sw_uport); static int sw_uart_init_dma_rx(struct sw_uart_port *sw_uport); static int sw_uart_start_dma_rx(struct sw_uart_port *sw_uport); static void sw_uart_update_rb_addr(struct sw_uart_port *sw_uport); -static void sw_uart_report_dma_rx(unsigned long uart); +static enum hrtimer_restart sw_uart_report_dma_rx(struct hrtimer *rx_hrtimer); #endif #ifdef CONFIG_SW_UART_DUMP_DATA @@ -575,7 +575,7 @@ static void sw_uart_stop_dma_rx(struct sw_uart_port *sw_uport) struct sw_uart_dma *uart_dma = sw_uport->dma; if (uart_dma && uart_dma->rx_dma_used) { - del_timer(&uart_dma->rx_timer); + hrtimer_cancel(&sw_uport->rx_hrtimer); dmaengine_terminate_all(uart_dma->dma_chan_rx); uart_dma->rb_tail = 0; uart_dma->rx_dma_used = 0; @@ -671,8 +671,8 @@ static int sw_uart_start_dma_rx(struct sw_uart_port *sw_uport) uart_dma->rx_dma_used = 1; if (uart_dma->use_timer == 1) { - mod_timer(&uart_dma->rx_timer, - jiffies + msecs_to_jiffies(uart_dma->rx_timeout)); + hrtimer_start(&sw_uport->rx_hrtimer, + ns_to_ktime(uart_dma->rx_timeout), HRTIMER_MODE_REL); } return 1; } @@ -693,15 +693,16 @@ static void sw_uart_update_rb_addr(struct sw_uart_port *sw_uport) } } -static void sw_uart_report_dma_rx(unsigned long uart) +static enum hrtimer_restart sw_uart_report_dma_rx(struct hrtimer *rx_hrtimer) { int count, flip = 0; - struct sw_uart_port *sw_uport = (struct sw_uart_port *)uart; + struct sw_uart_port *sw_uport = container_of(rx_hrtimer, + struct sw_uart_port, rx_hrtimer); struct uart_port *port = &sw_uport->port; struct sw_uart_dma *uart_dma = sw_uport->dma; if (!uart_dma->rx_dma_used || !port->state->port.tty) - return; + return HRTIMER_NORESTART; sw_uart_update_rb_addr(sw_uport); while (1) { @@ -717,9 +718,12 @@ static void sw_uart_report_dma_rx(unsigned long uart) (uart_dma->rb_tail + count) & (uart_dma->rb_size - 1); } - if (uart_dma->use_timer == 1) - mod_timer(&uart_dma->rx_timer, - jiffies + msecs_to_jiffies(uart_dma->rx_timeout)); + if (uart_dma->use_timer == 1) { + hrtimer_forward_now(&sw_uport->rx_hrtimer, + ns_to_ktime(uart_dma->rx_timeout)); + } + + return HRTIMER_RESTART; } #endif @@ -1183,8 +1187,11 @@ static void sw_uart_set_termios(struct uart_port *port, struct ktermios *termios #endif /* flow control */ sw_uport->mcr &= ~SUNXI_UART_MCR_AFE; - if (termios->c_cflag & CRTSCTS) + port->status &= ~(UPSTAT_AUTOCTS | UPSTAT_AUTORTS); + if (termios->c_cflag & CRTSCTS) { + port->status |= UPSTAT_AUTOCTS | UPSTAT_AUTORTS; sw_uport->mcr |= SUNXI_UART_MCR_AFE; + } serial_out(port, sw_uport->mcr, SUNXI_UART_MCR); /* @@ -1831,6 +1838,7 @@ static int sw_uart_probe(struct platform_device *pdev) pdev->dev.init_name = sw_uport->name; pdev->dev.platform_data = sw_uport->pdata; +#if 0 snprintf(uart_para, sizeof(uart_para), "uart%d_regulator", pdev->id); ret = of_property_read_string(np, uart_para, &uart_string); if (ret) @@ -1844,7 +1852,7 @@ static int sw_uart_probe(struct platform_device *pdev) SERIAL_MSG("uart%d error to get resource\n", pdev->id); return -ENXIO; } - +#endif #ifdef CONFIG_EVB_PLATFORM sw_uport->mclk = of_clk_get(np, 0); @@ -1942,23 +1950,21 @@ static int sw_uart_probe(struct platform_device *pdev) if (sw_uport->dma->use_dma & RX_DMA) { /* timer */ sw_uport->dma->use_timer = UART_USE_TIMER; - sw_uport->dma->rx_timer.function = sw_uart_report_dma_rx; - sw_uport->dma->rx_timer.data = (unsigned long)sw_uport; - sw_uport->dma->rx_timeout = 5; - sw_uport->dma->rx_timer.expires = - jiffies + msecs_to_jiffies(sw_uport->dma->rx_timeout); - init_timer(&sw_uport->dma->rx_timer); + sw_uport->dma->rx_timeout = 2000000; + hrtimer_init(&sw_uport->rx_hrtimer, CLOCK_MONOTONIC, HRTIMER_MODE_REL); + sw_uport->rx_hrtimer.function = sw_uart_report_dma_rx; /* rx buffer */ sw_uport->dma->rb_size = DMA_SERIAL_BUFFER_SIZE; sw_uport->dma->rx_buffer = dma_alloc_coherent( sw_uport->port.dev, sw_uport->dma->rb_size, - &sw_uport->dma->rx_phy_addr, DMA_MEMORY_MAP); + &sw_uport->dma->rx_phy_addr, GFP_KERNEL); sw_uport->dma->rb_tail = 0; if (!sw_uport->dma->rx_buffer) { - dev_info(sw_uport->port.dev, + dev_err(sw_uport->port.dev, "dmam_alloc_coherent dma_rx_buffer fail\n"); + return -ENOMEM; } else { dev_info(sw_uport->port.dev, "dma_rx_buffer %p\n", sw_uport->dma->rx_buffer);