
On 01/21/2011 08:42 AM, Tom Warren wrote:
+enum {
- UART_A = 1,
- UART_B,
- UART_C,
- UART_D,
- UART_E
+};
+#endif /* _BOARD_H_ */
diff --git a/arch/arm/cpu/armv7/tegra2/uart.c b/arch/arm/cpu/armv7/tegra2/uart.c new file mode 100644 index 0000000..5e60bd8 --- /dev/null +++ b/arch/arm/cpu/armv7/tegra2/uart.c @@ -0,0 +1,216 @@ +/*
- (C) Copyright 2010,2011
- NVIDIA Corporation<www.nvidia.com>
- See file CREDITS for list of people who contributed to this
- project.
- This program is free software; you can redistribute it and/or
- modify it under the terms of the GNU General Public License as
- published by the Free Software Foundation; either version 2 of
- the License, or (at your option) any later version.
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
- You should have received a copy of the GNU General Public License
- along with this program; if not, write to the Free Software
- Foundation, Inc., 59 Temple Place, Suite 330, Boston,
- MA 02111-1307 USA
- */
+#include<common.h> +#include<ns16550.h> +#include<asm/io.h> +#include<asm/arch/tegra2.h> +#include "board.h"
+/*
- Routine: uart_clock_init
- Description: init the PLL and clock for the UART in uart_num
- */
+static void uart_clock_init(int uart_num) +{
- clk_rst_ctlr *const clkrst = (clk_rst_ctlr *)NV_PA_CLK_RST_BASE;
- static int pllp_init_done;
- u32 reg;
- if (!pllp_init_done) {
/* Override pllp setup for 216MHz operation. */
reg = (PLL_BYPASS | PLL_BASE_OVRRIDE | PLL_DIVP);
reg |= (((NVRM_PLLP_FIXED_FREQ_KHZ/500)<< 8) | PLL_DIVM);
writel(reg,&clkrst->crc_pllp_base);
reg |= PLL_ENABLE;
writel(reg,&clkrst->crc_pllp_base);
reg&= ~PLL_BYPASS;
writel(reg,&clkrst->crc_pllp_base);
pllp_init_done++;
- }
- /* Now do the UART reset/clock enable based on uart_num */
+#if CONFIG_TEGRA2_ENABLE_UARTA
- if (uart_num == UART_A) {
/* Assert Reset to UART */
reg = readl(&clkrst->crc_rst_dev_l);
reg |= SWR_UARTA_RST; /* SWR_UARTA_RST = 1 */
writel(reg,&clkrst->crc_rst_dev_l);
/* Enable clk to UART */
reg = readl(&clkrst->crc_clk_out_enb_l);
reg |= CLK_ENB_UARTA; /* CLK_ENB_UARTA = 1 */
writel(reg,&clkrst->crc_clk_out_enb_l);
/* Enable pllp_out0 to UART */
reg = readl(&clkrst->crc_clk_src_uarta);
reg&= 0x3FFFFFFF; /* UARTA_CLK_SRC = 00, PLLP_OUT0 */
writel(reg,&clkrst->crc_clk_src_uarta);
/* wait for 2us */
udelay(2);
/* De-assert reset to UART */
reg = readl(&clkrst->crc_rst_dev_l);
reg&= ~SWR_UARTA_RST; /* SWR_UARTA_RST = 0 */
writel(reg,&clkrst->crc_rst_dev_l);
- }
+#endif /* CONFIG_TEGRA2_ENABLE_UARTA */ +#if CONFIG_TEGRA2_ENABLE_UARTD
- if (uart_num == UART_D) {
/* Assert Reset to UART */
reg = readl(&clkrst->crc_rst_dev_u);
reg |= SWR_UARTD_RST; /* SWR_UARTD_RST = 1 */
writel(reg,&clkrst->crc_rst_dev_u);
/* Enable clk to UART */
reg = readl(&clkrst->crc_clk_out_enb_u);
reg |= CLK_ENB_UARTD; /* CLK_ENB_UARTD = 1 */
writel(reg,&clkrst->crc_clk_out_enb_u);
/* Enable pllp_out0 to UART */
reg = readl(&clkrst->crc_clk_src_uartd);
reg&= 0x3FFFFFFF; /* UARTD_CLK_SRC = 00, PLLP_OUT0 */
writel(reg,&clkrst->crc_clk_src_uartd);
/* wait for 2us */
udelay(2);
/* De-assert reset to UART */
reg = readl(&clkrst->crc_rst_dev_u);
reg&= ~SWR_UARTD_RST; /* SWR_UARTD_RST = 0 */
writel(reg,&clkrst->crc_rst_dev_u);
- }
+#endif /* CONFIG_TEGRA2_ENABLE_UARTD */ +}
+/*
- Routine: pin_mux_uart
- Description: setup the pin muxes/tristate values for UART based on uart_num
- */
+static void pin_mux_uart(int uart_num) +{
- pinmux_tri_ctlr *const pmt = (pinmux_tri_ctlr *)NV_PA_APB_MISC_BASE;
- u32 reg;
+#if CONFIG_TEGRA2_ENABLE_UARTA
- if (uart_num == UART_A) {
Why you need get the parameters uart_num, I think if you want to use CONFIG_TEGRA2_ENABLE_UARTA, You only defined CONFIG_TEGRA2_ENABLE_UARTA in include/configs/seaboard.h or include/configs/tegra2-common.h.
Here, The code formats may be as following:
#ifdef CONFIG_SERIAL1 ...... #elif defined(CONFIG_SERIAL2) ...... #else ...... #endif
reg = readl(&pmt->pmt_ctl_c);
reg&= 0xFFF0FFFF; /* IRRX_/IRTX_SEL [19:16] = 00 UARTA */
writel(reg,&pmt->pmt_ctl_c);
reg = readl(&pmt->pmt_tri_a);
reg&= ~Z_IRRX; /* Z_IRRX = normal (0) */
reg&= ~Z_IRTX; /* Z_IRTX = normal (0) */
writel(reg,&pmt->pmt_tri_a);
- }
+#endif /* CONFIG_TEGRA2_ENABLE_UARTA */ +#if CONFIG_TEGRA2_ENABLE_UARTD
- if (uart_num == UART_D) {
reg = readl(&pmt->pmt_ctl_b);
reg&= 0xFFFFFFF3; /* GMC_SEL [3:2] = 00, UARTD */
writel(reg,&pmt->pmt_ctl_b);
reg = readl(&pmt->pmt_tri_a);
reg&= ~Z_GMC; /* Z_GMC = normal (0) */
writel(reg,&pmt->pmt_tri_a);
- }
+#endif /* CONFIG_TEGRA2_ENABLE_UARTD */ +}
+static void setup_uart(uart_ctlr *u) +{
- u32 reg;
- /* Prepare the divisor value */
- reg = NVRM_PLLP_FIXED_FREQ_KHZ * 1000 / NV_DEFAULT_DEBUG_BAUD / 16;
- /* Set up UART parameters */
- writel(UART_LCR_DLAB,&u->uart_lcr);
- writel(reg,&u->uart_thr_dlab_0);
- writel(0,&u->uart_ier_dlab_0);
- writel(0,&u->uart_lcr); /* clear DLAB */
- writel((UART_FCR_TRIGGER_3 | UART_FCR_FIFO_EN | \
UART_FCR_CLEAR_XMIT | UART_FCR_CLEAR_RCVR),&u->uart_iir_fcr);
- writel(0,&u->uart_ier_dlab_0);
- writel(UART_LCR_WLS_8,&u->uart_lcr); /* 8N1 */
- writel(UART_MCR_RTS,&u->uart_mcr);
- writel(0,&u->uart_msr);
- writel(0,&u->uart_spr);
- writel(0,&u->uart_irda_csr);
- writel(0,&u->uart_asr);
- writel((UART_FCR_TRIGGER_3 | UART_FCR_FIFO_EN),&u->uart_iir_fcr);
- /* Flush any old characters out of the RX FIFO */
- reg = readl(&u->uart_lsr);
- while (reg& UART_LSR_DR) {
reg = readl(&u->uart_thr_dlab_0);
reg = readl(&u->uart_lsr);
- }
+}
+/*
- Routine: init_uart
- Description: init the UART clocks, muxes, and baudrate/parity/etc.
- */
+static void init_uart(int uart_num) +{ +#if CONFIG_TEGRA2_ENABLE_UARTA
- if (uart_num == UART_A) {
above.
Thanks seedshope
uart_ctlr *const uart = (uart_ctlr *)NV_PA_APB_UARTA_BASE;
uart_clock_init(UART_A);
/* Enable UARTA - uses config 0 */
pin_mux_uart(UART_A);
setup_uart(uart);
- }
+#endif /* CONFIG_TEGRA2_ENABLE_UARTD */ +#if CONFIG_TEGRA2_ENABLE_UARTD
- if (uart_num == UART_D) {
uart_ctlr *const uart = (uart_ctlr *)NV_PA_APB_UARTD_BASE;
uart_clock_init(UART_D);
/* Enable UARTD - uses config 0 */
pin_mux_uart(UART_D);
setup_uart(uart);
- }
+#endif /* CONFIG_TEGRA2_ENABLE_UARTD */ +}
+void uart_init(void) +{ +#if (CONFIG_TEGRA2_ENABLE_UARTA)
- init_uart(UART_A);
+#endif +#if (CONFIG_TEGRA2_ENABLE_UARTD)
- init_uart(UART_D);
+#endif +}