xref: /rk3399_ARM-atf/drivers/cadence/uart/aarch64/cdns_console.S (revision 61d2b40d287f2007737498348ad2768bf7cd74d7)
19c94d3b3SSoby Mathew/*
2ad4c2ec6SAntonio Nino Diaz * Copyright (c) 2016-2017, ARM Limited and Contributors. All rights reserved.
39c94d3b3SSoby Mathew *
482cb2c1aSdp-arm * SPDX-License-Identifier: BSD-3-Clause
59c94d3b3SSoby Mathew */
69c94d3b3SSoby Mathew#include <arch.h>
79c94d3b3SSoby Mathew#include <asm_macros.S>
838ba8e93SJulius Werner#include <assert_macros.S>
99c94d3b3SSoby Mathew#include <cadence/cdns_uart.h>
109c94d3b3SSoby Mathew
1138ba8e93SJulius Werner	/*
1238ba8e93SJulius Werner	 * "core" functions are low-level implementations that don't require
1338ba8e93SJulius Werner	 * writable memory and are thus safe to call in BL1 crash context.
1438ba8e93SJulius Werner	 */
1538ba8e93SJulius Werner	.globl console_cdns_core_init
1638ba8e93SJulius Werner	.globl console_cdns_core_putc
1738ba8e93SJulius Werner	.globl console_cdns_core_getc
18*61d2b40dSAntonio Nino Diaz	.globl console_cdns_core_flush
1938ba8e93SJulius Werner
2038ba8e93SJulius Werner	.globl  console_cdns_putc
2138ba8e93SJulius Werner	.globl  console_cdns_getc
22*61d2b40dSAntonio Nino Diaz	.globl  console_cdns_flush
239c94d3b3SSoby Mathew
249c94d3b3SSoby Mathew	/* -----------------------------------------------
2538ba8e93SJulius Werner	 * int console_cdns_core_init(uintptr_t base_addr)
269c94d3b3SSoby Mathew	 * Function to initialize the console without a
279c94d3b3SSoby Mathew	 * C Runtime to print debug information. This
289c94d3b3SSoby Mathew	 * function will be accessed by console_init and
299c94d3b3SSoby Mathew	 * crash reporting.
309c94d3b3SSoby Mathew	 * We assume that the bootloader already set up
319c94d3b3SSoby Mathew	 * the HW (baud, ...) and only enable the trans-
329c94d3b3SSoby Mathew	 * mitter and receiver here.
339c94d3b3SSoby Mathew	 * In: x0 - console base address
349c94d3b3SSoby Mathew	 * Out: return 1 on success else 0 on error
359c94d3b3SSoby Mathew	 * Clobber list : x1, x2, x3
369c94d3b3SSoby Mathew	 * -----------------------------------------------
379c94d3b3SSoby Mathew	 */
3838ba8e93SJulius Wernerfunc console_cdns_core_init
399c94d3b3SSoby Mathew	/* Check the input base address */
409c94d3b3SSoby Mathew	cbz	x0, core_init_fail
419c94d3b3SSoby Mathew
429c94d3b3SSoby Mathew	/* RX/TX enabled & reset */
439c94d3b3SSoby Mathew	mov	w3, #(R_UART_CR_TX_EN | R_UART_CR_RX_EN | R_UART_CR_TXRST | R_UART_CR_RXRST)
449c94d3b3SSoby Mathew	str	w3, [x0, #R_UART_CR]
459c94d3b3SSoby Mathew
469c94d3b3SSoby Mathew	mov	w0, #1
479c94d3b3SSoby Mathew	ret
489c94d3b3SSoby Mathewcore_init_fail:
499c94d3b3SSoby Mathew	mov	w0, wzr
509c94d3b3SSoby Mathew	ret
5138ba8e93SJulius Wernerendfunc console_cdns_core_init
5238ba8e93SJulius Werner
5338ba8e93SJulius Werner#if MULTI_CONSOLE_API
5438ba8e93SJulius Werner	.globl console_cdns_register
5538ba8e93SJulius Werner
5638ba8e93SJulius Werner	/* -----------------------------------------------
5738ba8e93SJulius Werner	 * int console_cdns_register(console_cdns_t *console,
5838ba8e93SJulius Werner		uintptr_t base, uint32_t clk, uint32_t baud)
5938ba8e93SJulius Werner	 * Function to initialize and register a new CDNS
6038ba8e93SJulius Werner	 * console. Storage passed in for the console struct
6138ba8e93SJulius Werner	 * *must* be persistent (i.e. not from the stack).
6238ba8e93SJulius Werner	 * In: x0 - UART register base address
6338ba8e93SJulius Werner	 *     x1 - pointer to empty console_cdns_t struct
6438ba8e93SJulius Werner	 * Out: return 1 on success, 0 on error
6538ba8e93SJulius Werner	 * Clobber list : x0, x1, x2, x6, x7, x14
6638ba8e93SJulius Werner	 * -----------------------------------------------
6738ba8e93SJulius Werner	 */
6838ba8e93SJulius Wernerfunc console_cdns_register
6938ba8e93SJulius Werner	mov	x7, x30
7038ba8e93SJulius Werner	mov	x6, x1
7138ba8e93SJulius Werner	cbz	x6, register_fail
7238ba8e93SJulius Werner	str	x0, [x6, #CONSOLE_T_CDNS_BASE]
7338ba8e93SJulius Werner
7438ba8e93SJulius Werner	bl	console_cdns_core_init
7538ba8e93SJulius Werner	cbz	x0, register_fail
7638ba8e93SJulius Werner
7738ba8e93SJulius Werner	mov	x0, x6
7838ba8e93SJulius Werner	mov	x30, v7
7938ba8e93SJulius Werner	finish_console_register cdns
8038ba8e93SJulius Werner
8138ba8e93SJulius Wernerregister_fail:
8238ba8e93SJulius Werner	ret	x7
8338ba8e93SJulius Wernerendfunc console_cdns_register
8438ba8e93SJulius Werner#else
8538ba8e93SJulius Werner	.globl console_core_init
8638ba8e93SJulius Werner	.globl console_core_putc
8738ba8e93SJulius Werner	.globl console_core_getc
8838ba8e93SJulius Werner	.globl console_core_flush
8938ba8e93SJulius Werner	.equ console_core_init,console_cdns_core_init
9038ba8e93SJulius Werner	.equ console_core_putc,console_cdns_core_putc
9138ba8e93SJulius Werner	.equ console_core_getc,console_cdns_core_getc
92*61d2b40dSAntonio Nino Diaz	.equ console_core_flush,console_cdns_core_flush
9338ba8e93SJulius Werner#endif
949c94d3b3SSoby Mathew
959c94d3b3SSoby Mathew	/* --------------------------------------------------------
9638ba8e93SJulius Werner	 * int console_cdns_core_putc(int c, uintptr_t base_addr)
979c94d3b3SSoby Mathew	 * Function to output a character over the console. It
989c94d3b3SSoby Mathew	 * returns the character printed on success or -1 on error.
999c94d3b3SSoby Mathew	 * In : w0 - character to be printed
1009c94d3b3SSoby Mathew	 *      x1 - console base address
1019c94d3b3SSoby Mathew	 * Out : return -1 on error else return character.
1029c94d3b3SSoby Mathew	 * Clobber list : x2
1039c94d3b3SSoby Mathew	 * --------------------------------------------------------
1049c94d3b3SSoby Mathew	 */
10538ba8e93SJulius Wernerfunc console_cdns_core_putc
10638ba8e93SJulius Werner#if ENABLE_ASSERTIONS
10738ba8e93SJulius Werner	cmp	x1, #0
10838ba8e93SJulius Werner	ASM_ASSERT(ne)
10938ba8e93SJulius Werner#endif /* ENABLE_ASSERTIONS */
11038ba8e93SJulius Werner
1119c94d3b3SSoby Mathew	/* Prepend '\r' to '\n' */
1129c94d3b3SSoby Mathew	cmp	w0, #0xA
1139c94d3b3SSoby Mathew	b.ne	2f
1149c94d3b3SSoby Mathew1:
1159c94d3b3SSoby Mathew	/* Check if the transmit FIFO is full */
1169c94d3b3SSoby Mathew	ldr	w2, [x1, #R_UART_SR]
1179c94d3b3SSoby Mathew	tbnz	w2, #UART_SR_INTR_TFUL_BIT, 1b
1189c94d3b3SSoby Mathew	mov	w2, #0xD
1199c94d3b3SSoby Mathew	str	w2, [x1, #R_UART_TX]
1209c94d3b3SSoby Mathew2:
1219c94d3b3SSoby Mathew	/* Check if the transmit FIFO is full */
1229c94d3b3SSoby Mathew	ldr	w2, [x1, #R_UART_SR]
1239c94d3b3SSoby Mathew	tbnz	w2, #UART_SR_INTR_TFUL_BIT, 2b
1249c94d3b3SSoby Mathew	str	w0, [x1, #R_UART_TX]
1259c94d3b3SSoby Mathew	ret
12638ba8e93SJulius Wernerendfunc console_cdns_core_putc
12738ba8e93SJulius Werner
12838ba8e93SJulius Werner	/* --------------------------------------------------------
12938ba8e93SJulius Werner	 * int console_cdns_putc(int c, console_cdns_t *cdns)
13038ba8e93SJulius Werner	 * Function to output a character over the console. It
13138ba8e93SJulius Werner	 * returns the character printed on success or -1 on error.
13238ba8e93SJulius Werner	 * In : w0 - character to be printed
13338ba8e93SJulius Werner	 *      x1 - pointer to console_t structure
13438ba8e93SJulius Werner	 * Out : return -1 on error else return character.
13538ba8e93SJulius Werner	 * Clobber list : x2
13638ba8e93SJulius Werner	 * --------------------------------------------------------
13738ba8e93SJulius Werner	 */
13838ba8e93SJulius Wernerfunc console_cdns_putc
13938ba8e93SJulius Werner#if ENABLE_ASSERTIONS
14038ba8e93SJulius Werner	cmp	x1, #0
14138ba8e93SJulius Werner	ASM_ASSERT(ne)
14238ba8e93SJulius Werner#endif /* ENABLE_ASSERTIONS */
14338ba8e93SJulius Werner	ldr	x1, [x1, #CONSOLE_T_CDNS_BASE]
14438ba8e93SJulius Werner	b	console_cdns_core_putc
14538ba8e93SJulius Wernerendfunc console_cdns_putc
1469c94d3b3SSoby Mathew
1479c94d3b3SSoby Mathew	/* ---------------------------------------------
14838ba8e93SJulius Werner	 * int console_cdns_core_getc(uintptr_t base_addr)
1499c94d3b3SSoby Mathew	 * Function to get a character from the console.
1509c94d3b3SSoby Mathew	 * It returns the character grabbed on success
15138ba8e93SJulius Werner	 * or -1 if no character is available.
1529c94d3b3SSoby Mathew	 * In : x0 - console base address
15338ba8e93SJulius Werner	 * Out: w0 - character if available, else -1
1549c94d3b3SSoby Mathew	 * Clobber list : x0, x1
1559c94d3b3SSoby Mathew	 * ---------------------------------------------
1569c94d3b3SSoby Mathew	 */
15738ba8e93SJulius Wernerfunc console_cdns_core_getc
15838ba8e93SJulius Werner#if ENABLE_ASSERTIONS
15938ba8e93SJulius Werner	cmp	x0, #0
16038ba8e93SJulius Werner	ASM_ASSERT(ne)
16138ba8e93SJulius Werner#endif /* ENABLE_ASSERTIONS */
16238ba8e93SJulius Werner
1639c94d3b3SSoby Mathew	/* Check if the receive FIFO is empty */
1649c94d3b3SSoby Mathew	ldr	w1, [x0, #R_UART_SR]
16538ba8e93SJulius Werner	tbnz	w1, #UART_SR_INTR_REMPTY_BIT, no_char
1669c94d3b3SSoby Mathew	ldr	w1, [x0, #R_UART_RX]
1679c94d3b3SSoby Mathew	mov	w0, w1
1689c94d3b3SSoby Mathew	ret
16938ba8e93SJulius Wernerno_char:
17038ba8e93SJulius Werner	mov	w0, #ERROR_NO_PENDING_CHAR
1719c94d3b3SSoby Mathew	ret
17238ba8e93SJulius Wernerendfunc console_cdns_core_getc
17338ba8e93SJulius Werner
17438ba8e93SJulius Werner	/* ---------------------------------------------
17538ba8e93SJulius Werner	 * int console_cdns_getc(console_cdns_t *console)
17638ba8e93SJulius Werner	 * Function to get a character from the console.
17738ba8e93SJulius Werner	 * It returns the character grabbed on success
17838ba8e93SJulius Werner	 * or -1 if no character is available.
17938ba8e93SJulius Werner	 * In : x0 - pointer to console_t structure
18038ba8e93SJulius Werner	 * Out: w0 - character if available, else -1
18138ba8e93SJulius Werner	 * Clobber list : x0, x1
18238ba8e93SJulius Werner	 * ---------------------------------------------
18338ba8e93SJulius Werner	 */
18438ba8e93SJulius Wernerfunc console_cdns_getc
18538ba8e93SJulius Werner#if ENABLE_ASSERTIONS
18638ba8e93SJulius Werner	cmp	x0, #0
18738ba8e93SJulius Werner	ASM_ASSERT(ne)
18838ba8e93SJulius Werner#endif /* ENABLE_ASSERTIONS */
18938ba8e93SJulius Werner	ldr	x0, [x0, #CONSOLE_T_CDNS_BASE]
19038ba8e93SJulius Werner	b	console_cdns_core_getc
19138ba8e93SJulius Wernerendfunc console_cdns_getc
192ad4c2ec6SAntonio Nino Diaz
193ad4c2ec6SAntonio Nino Diaz	/* ---------------------------------------------
194*61d2b40dSAntonio Nino Diaz	 * int console_cdns_core_flush(uintptr_t base_addr)
195ad4c2ec6SAntonio Nino Diaz	 * Function to force a write of all buffered
196ad4c2ec6SAntonio Nino Diaz	 * data that hasn't been output.
197ad4c2ec6SAntonio Nino Diaz	 * In : x0 - console base address
198ad4c2ec6SAntonio Nino Diaz	 * Out : return -1 on error else return 0.
199ad4c2ec6SAntonio Nino Diaz	 * Clobber list : x0, x1
200ad4c2ec6SAntonio Nino Diaz	 * ---------------------------------------------
201ad4c2ec6SAntonio Nino Diaz	 */
202*61d2b40dSAntonio Nino Diazfunc console_cdns_core_flush
203*61d2b40dSAntonio Nino Diaz#if ENABLE_ASSERTIONS
204*61d2b40dSAntonio Nino Diaz	cmp	x0, #0
205*61d2b40dSAntonio Nino Diaz	ASM_ASSERT(ne)
206*61d2b40dSAntonio Nino Diaz#endif /* ENABLE_ASSERTIONS */
207ad4c2ec6SAntonio Nino Diaz	/* Placeholder */
208ad4c2ec6SAntonio Nino Diaz	mov	w0, #0
209ad4c2ec6SAntonio Nino Diaz	ret
210*61d2b40dSAntonio Nino Diazendfunc console_cdns_core_flush
211*61d2b40dSAntonio Nino Diaz
212*61d2b40dSAntonio Nino Diaz	/* ---------------------------------------------
213*61d2b40dSAntonio Nino Diaz	 * int console_cdns_flush(console_pl011_t *console)
214*61d2b40dSAntonio Nino Diaz	 * Function to force a write of all buffered
215*61d2b40dSAntonio Nino Diaz	 * data that hasn't been output.
216*61d2b40dSAntonio Nino Diaz	 * In : x0 - pointer to console_t structure
217*61d2b40dSAntonio Nino Diaz	 * Out : return -1 on error else return 0.
218*61d2b40dSAntonio Nino Diaz	 * Clobber list : x0, x1
219*61d2b40dSAntonio Nino Diaz	 * ---------------------------------------------
220*61d2b40dSAntonio Nino Diaz	 */
221*61d2b40dSAntonio Nino Diazfunc console_cdns_flush
222*61d2b40dSAntonio Nino Diaz#if ENABLE_ASSERTIONS
223*61d2b40dSAntonio Nino Diaz	cmp	x0, #0
224*61d2b40dSAntonio Nino Diaz	ASM_ASSERT(ne)
225*61d2b40dSAntonio Nino Diaz#endif /* ENABLE_ASSERTIONS */
226*61d2b40dSAntonio Nino Diaz	ldr	x0, [x0, #CONSOLE_T_CDNS_BASE]
227*61d2b40dSAntonio Nino Diaz	b	console_cdns_core_flush
228*61d2b40dSAntonio Nino Diazendfunc console_cdns_flush
229