xref: /rk3399_ARM-atf/drivers/cadence/uart/aarch64/cdns_console.S (revision 1dcc28cfbac5dae3992ad9581f9ea68f6cb339c1)
1/*
2 * Copyright (c) 2016-2017, ARM Limited and Contributors. All rights reserved.
3 *
4 * SPDX-License-Identifier: BSD-3-Clause
5 */
6#include <arch.h>
7#include <asm_macros.S>
8#include <assert_macros.S>
9#include <cadence/cdns_uart.h>
10
11	/*
12	 * "core" functions are low-level implementations that don't require
13	 * writable memory and are thus safe to call in BL1 crash context.
14	 */
15	.globl console_cdns_core_init
16	.globl console_cdns_core_putc
17	.globl console_cdns_core_getc
18	.globl console_cdns_core_flush
19
20	.globl  console_cdns_putc
21	.globl  console_cdns_getc
22	.globl  console_cdns_flush
23
24	/* -----------------------------------------------
25	 * int console_cdns_core_init(uintptr_t base_addr)
26	 * Function to initialize the console without a
27	 * C Runtime to print debug information. This
28	 * function will be accessed by console_init and
29	 * crash reporting.
30	 * We assume that the bootloader already set up
31	 * the HW (baud, ...) and only enable the trans-
32	 * mitter and receiver here.
33	 * In: x0 - console base address
34	 * Out: return 1 on success else 0 on error
35	 * Clobber list : x1, x2, x3
36	 * -----------------------------------------------
37	 */
38func console_cdns_core_init
39	/* Check the input base address */
40	cbz	x0, core_init_fail
41
42	/* RX/TX enabled & reset */
43	mov	w3, #(R_UART_CR_TX_EN | R_UART_CR_RX_EN | R_UART_CR_TXRST | R_UART_CR_RXRST)
44	str	w3, [x0, #R_UART_CR]
45
46	mov	w0, #1
47	ret
48core_init_fail:
49	mov	w0, wzr
50	ret
51endfunc console_cdns_core_init
52
53#if MULTI_CONSOLE_API
54	.globl console_cdns_register
55
56	/* -----------------------------------------------
57	 * int console_cdns_register(console_cdns_t *console,
58		uintptr_t base, uint32_t clk, uint32_t baud)
59	 * Function to initialize and register a new CDNS
60	 * console. Storage passed in for the console struct
61	 * *must* be persistent (i.e. not from the stack).
62	 * In: x0 - UART register base address
63	 *     x1 - pointer to empty console_cdns_t struct
64	 * Out: return 1 on success, 0 on error
65	 * Clobber list : x0, x1, x2, x6, x7, x14
66	 * -----------------------------------------------
67	 */
68func console_cdns_register
69	mov	x7, x30
70	mov	x6, x1
71	cbz	x6, register_fail
72	str	x0, [x6, #CONSOLE_T_CDNS_BASE]
73
74	bl	console_cdns_core_init
75	cbz	x0, register_fail
76
77	mov	x0, x6
78	mov	x30, v7
79	finish_console_register cdns
80
81register_fail:
82	ret	x7
83endfunc console_cdns_register
84#else
85	.globl console_core_init
86	.globl console_core_putc
87	.globl console_core_getc
88	.globl console_core_flush
89	.equ console_core_init,console_cdns_core_init
90	.equ console_core_putc,console_cdns_core_putc
91	.equ console_core_getc,console_cdns_core_getc
92	.equ console_core_flush,console_cdns_core_flush
93#endif
94
95	/* --------------------------------------------------------
96	 * int console_cdns_core_putc(int c, uintptr_t base_addr)
97	 * Function to output a character over the console. It
98	 * returns the character printed on success or -1 on error.
99	 * In : w0 - character to be printed
100	 *      x1 - console base address
101	 * Out : return -1 on error else return character.
102	 * Clobber list : x2
103	 * --------------------------------------------------------
104	 */
105func console_cdns_core_putc
106#if ENABLE_ASSERTIONS
107	cmp	x1, #0
108	ASM_ASSERT(ne)
109#endif /* ENABLE_ASSERTIONS */
110
111	/* Prepend '\r' to '\n' */
112	cmp	w0, #0xA
113	b.ne	2f
1141:
115	/* Check if the transmit FIFO is full */
116	ldr	w2, [x1, #R_UART_SR]
117	tbnz	w2, #UART_SR_INTR_TFUL_BIT, 1b
118	mov	w2, #0xD
119	str	w2, [x1, #R_UART_TX]
1202:
121	/* Check if the transmit FIFO is full */
122	ldr	w2, [x1, #R_UART_SR]
123	tbnz	w2, #UART_SR_INTR_TFUL_BIT, 2b
124	str	w0, [x1, #R_UART_TX]
125	ret
126endfunc console_cdns_core_putc
127
128	/* --------------------------------------------------------
129	 * int console_cdns_putc(int c, console_cdns_t *cdns)
130	 * Function to output a character over the console. It
131	 * returns the character printed on success or -1 on error.
132	 * In : w0 - character to be printed
133	 *      x1 - pointer to console_t structure
134	 * Out : return -1 on error else return character.
135	 * Clobber list : x2
136	 * --------------------------------------------------------
137	 */
138func console_cdns_putc
139#if ENABLE_ASSERTIONS
140	cmp	x1, #0
141	ASM_ASSERT(ne)
142#endif /* ENABLE_ASSERTIONS */
143	ldr	x1, [x1, #CONSOLE_T_CDNS_BASE]
144	b	console_cdns_core_putc
145endfunc console_cdns_putc
146
147	/* ---------------------------------------------
148	 * int console_cdns_core_getc(uintptr_t base_addr)
149	 * Function to get a character from the console.
150	 * It returns the character grabbed on success
151	 * or -1 if no character is available.
152	 * In : x0 - console base address
153	 * Out: w0 - character if available, else -1
154	 * Clobber list : x0, x1
155	 * ---------------------------------------------
156	 */
157func console_cdns_core_getc
158#if ENABLE_ASSERTIONS
159	cmp	x0, #0
160	ASM_ASSERT(ne)
161#endif /* ENABLE_ASSERTIONS */
162
163	/* Check if the receive FIFO is empty */
164	ldr	w1, [x0, #R_UART_SR]
165	tbnz	w1, #UART_SR_INTR_REMPTY_BIT, no_char
166	ldr	w1, [x0, #R_UART_RX]
167	mov	w0, w1
168	ret
169no_char:
170	mov	w0, #ERROR_NO_PENDING_CHAR
171	ret
172endfunc console_cdns_core_getc
173
174	/* ---------------------------------------------
175	 * int console_cdns_getc(console_cdns_t *console)
176	 * Function to get a character from the console.
177	 * It returns the character grabbed on success
178	 * or -1 if no character is available.
179	 * In : x0 - pointer to console_t structure
180	 * Out: w0 - character if available, else -1
181	 * Clobber list : x0, x1
182	 * ---------------------------------------------
183	 */
184func console_cdns_getc
185#if ENABLE_ASSERTIONS
186	cmp	x0, #0
187	ASM_ASSERT(ne)
188#endif /* ENABLE_ASSERTIONS */
189	ldr	x0, [x0, #CONSOLE_T_CDNS_BASE]
190	b	console_cdns_core_getc
191endfunc console_cdns_getc
192
193	/* ---------------------------------------------
194	 * int console_cdns_core_flush(uintptr_t base_addr)
195	 * Function to force a write of all buffered
196	 * data that hasn't been output.
197	 * In : x0 - console base address
198	 * Out : return -1 on error else return 0.
199	 * Clobber list : x0, x1
200	 * ---------------------------------------------
201	 */
202func console_cdns_core_flush
203#if ENABLE_ASSERTIONS
204	cmp	x0, #0
205	ASM_ASSERT(ne)
206#endif /* ENABLE_ASSERTIONS */
207	/* Placeholder */
208	mov	w0, #0
209	ret
210endfunc console_cdns_core_flush
211
212	/* ---------------------------------------------
213	 * int console_cdns_flush(console_pl011_t *console)
214	 * Function to force a write of all buffered
215	 * data that hasn't been output.
216	 * In : x0 - pointer to console_t structure
217	 * Out : return -1 on error else return 0.
218	 * Clobber list : x0, x1
219	 * ---------------------------------------------
220	 */
221func console_cdns_flush
222#if ENABLE_ASSERTIONS
223	cmp	x0, #0
224	ASM_ASSERT(ne)
225#endif /* ENABLE_ASSERTIONS */
226	ldr	x0, [x0, #CONSOLE_T_CDNS_BASE]
227	b	console_cdns_core_flush
228endfunc console_cdns_flush
229