blob: 09dc90b8d100ff06f3ee44131adc4908079c57fc [file] [log] [blame]
Jorge Ramirez-Ortiz1d753672018-09-23 09:41:53 +02001/*
2 * Copyright (c) 2015-2018, Renesas Electronics Corporation. All rights reserved.
3 *
4 * SPDX-License-Identifier: BSD-3-Clause
5 */
6
7#include <arch.h>
8#include <asm_macros.S>
9
10#define SCIF_INTERNAL_CLK 0
11#define SCIF_EXTARNAL_CLK 1
12#define SCIF_CLK SCIF_INTERNAL_CLK
13
14/* product register */
15#define PRR (0xFFF00044)
16#define PRR_PRODUCT_MASK (0x00007F00)
17#define PRR_CUT_MASK (0x000000FF)
18#define PRR_PRODUCT_H3_VER_10 (0x00004F00)
19#define PRR_PRODUCT_E3 (0x00005700)
20
21/* module stop */
22#define CPG_BASE (0xE6150000)
23#define CPG_SMSTPCR3 (0x013C)
24#define CPG_MSTPSR3 (0x0048)
25#define MSTP310 (1 << 10)
26#define CPG_CPGWPR (0x0900)
27
28/* scif */
29#define SCIF2_BASE (0xE6E88000)
30#define SCIF_SCSMR (0x00)
31#define SCIF_SCBRR (0x04)
32#define SCIF_SCSCR (0x08)
33#define SCIF_SCFTDR (0x0C)
34#define SCIF_SCFSR (0x10)
35#define SCIF_SCFRDR (0x14)
36#define SCIF_SCFCR (0x18)
37#define SCIF_SCFDR (0x1C)
38#define SCIF_SCSPTR (0x20)
39#define SCIF_SCLSR (0x24)
40#define SCIF_DL (0x30)
41#define SCIF_CKS (0x34)
42
43/* mode pin */
44#define RST_MODEMR (0xE6160060)
45#define MODEMR_MD12 (0x00001000)
46
47#define SCSMR_CA_MASK (1 << 7)
48#define SCSMR_CA_ASYNC (0x0000)
49#define SCSMR_CHR_MASK (1 << 6)
50#define SCSMR_CHR_8 (0x0000)
51#define SCSMR_PE_MASK (1 << 5)
52#define SCSMR_PE_DIS (0x0000)
53#define SCSMR_STOP_MASK (1 << 3)
54#define SCSMR_STOP_1 (0x0000)
55#define SCSMR_CKS_MASK (3 << 0)
56#define SCSMR_CKS_DIV1 (0x0000)
57#define SCSMR_INIT_DATA (SCSMR_CA_ASYNC + \
58 SCSMR_CHR_8 + \
59 SCSMR_PE_DIS + \
60 SCSMR_STOP_1 + \
61 SCSMR_CKS_DIV1)
62#define SCBRR_115200BPS (17)
63#define SCBRR_115200BPS_E3_SSCG (15)
64#define SCBRR_230400BPS (8)
65
66#define SCSCR_TE_MASK (1 << 5)
67#define SCSCR_TE_DIS (0x0000)
68#define SCSCR_TE_EN (0x0020)
69#define SCSCR_RE_MASK (1 << 4)
70#define SCSCR_RE_DIS (0x0000)
71#define SCSCR_RE_EN (0x0010)
72#define SCSCR_CKE_MASK (3 << 0)
73#define SCSCR_CKE_INT (0x0000)
74#define SCSCR_CKE_BRG (0x0002)
75#if SCIF_CLK == SCIF_EXTARNAL_CLK
76#define SCSCR_CKE_INT_CLK (SCSCR_CKE_BRG)
77#else
Marek Vasutaae2c722018-12-27 20:31:22 +010078#define SCFSR_TEND_MASK (1 << 6)
79#define SCFSR_TEND_TRANS_END (0x0040)
Jorge Ramirez-Ortiz1d753672018-09-23 09:41:53 +020080#define SCSCR_CKE_INT_CLK (SCSCR_CKE_INT)
81#endif
82#define SCFSR_INIT_DATA (0x0000)
83#define SCFCR_TTRG_MASK (3 << 4)
84#define SCFCR_TTRG_8 (0x0000)
85#define SCFCR_TTRG_0 (0x0030)
86#define SCFCR_TFRST_MASK (1 << 2)
87#define SCFCR_TFRST_DIS (0x0000)
88#define SCFCR_TFRST_EN (0x0004)
89#define SCFCR_RFRS_MASK (1 << 1)
90#define SCFCR_RFRS_DIS (0x0000)
91#define SCFCR_RFRS_EN (0x0002)
92#define SCFCR_INIT_DATA (SCFCR_TTRG_8)
93#define SCFDR_T_MASK (0x1f << 8)
94#define DL_INIT_DATA (8)
95#define CKS_CKS_DIV_MASK (1 << 15)
96#define CKS_CKS_DIV_CLK (0x0000)
97#define CKS_XIN_MASK (1 << 14)
98#define CKS_XIN_SCIF_CLK (0x0000)
99#define CKS_INIT_DATA (CKS_CKS_DIV_CLK + CKS_XIN_SCIF_CLK)
100
101 .globl console_init
102 .globl console_uninit
103 .globl console_putc
104 .globl console_core_init
105 .globl console_core_putc
106 .globl console_getc
107 .globl console_flush
108
109 /*
110 * The console base is in the data section and not in .bss
111 * even though it is zero-init. In particular, this allows
112 * the console functions to start using this variable before
113 * the runtime memory is initialized for images which do not
114 * need to copy the .data section from ROM to RAM.
115 */
116 /* -----------------------------------------------
117 * int console_init(unsigned long base_addr,
118 * unsigned int uart_clk, unsigned int baud_rate)
119 * Function to initialize the console without a
120 * C Runtime to print debug information. It saves
121 * the console base to the data section.
122 * In: x0 - console base address
123 * w1 - Uart clock in Hz
124 * w2 - Baud rate
125 * out: return 1 on success.
126 * Clobber list : x1 - x3
127 * -----------------------------------------------
128 */
129func console_init
130 b console_core_init
131endfunc console_init
132
133func console_uninit
134 ret
135endfunc console_uninit
136
137 /* -----------------------------------------------
138 * int console_core_init(unsigned long base_addr,
139 * unsigned int uart_clk, unsigned int baud_rate)
140 * Function to initialize the console without a
141 * C Runtime to print debug information. This
142 * function will be accessed by console_init and
143 * crash reporting.
144 * In: x0 - console base address
145 * w1 - Uart clock in Hz
146 * w2 - Baud rate
147 * Out: return 1 on success
148 * Clobber list : x1, x2
149 * -----------------------------------------------
150 */
151func console_core_init
152 ldr x0, =CPG_BASE
153 ldr w1, [x0, #CPG_SMSTPCR3]
154 and w1, w1, #~MSTP310 /* MSTP310=0 */
155 mvn w2, w1
156 str w2, [x0, #CPG_CPGWPR]
157 str w1, [x0, #CPG_SMSTPCR3]
1585:
159 ldr w1, [x0, #CPG_MSTPSR3]
160 and w1, w1, #MSTP310
161 cbnz w1, 5b
162
163 ldr x0, =SCIF2_BASE
164 /* Clear bits TE and RE in SCSCR to 0 */
165 mov w1, #(SCSCR_TE_DIS + SCSCR_RE_DIS)
166 strh w1, [x0, #SCIF_SCSCR]
167 /* Set bits TFRST and RFRST in SCFCR to 1 */
168 ldrh w1, [x0, #SCIF_SCFCR]
169 orr w1, w1, #(SCFCR_TFRST_EN + SCFCR_RFRS_EN)
170 strh w1, [x0, #SCIF_SCFCR]
171 /* Read flags of ER, DR, BRK, and RDF in SCFSR and those of TO and ORER
172 in SCLSR, then clear them to 0 */
173 mov w1, #SCFSR_INIT_DATA
174 strh w1, [x0, #SCIF_SCFSR]
175 mov w1, #0
176 strh w1, [x0, #SCIF_SCLSR]
177 /* Set bits CKE[1:0] in SCSCR */
178 ldrh w1, [x0, #SCIF_SCSCR]
179 and w1, w1, #~SCSCR_CKE_MASK
180 mov w2, #SCSCR_CKE_INT_CLK
181 orr w1, w1, w2
182 strh w1, [x0, #SCIF_SCSCR]
183 /* Set data transfer format in SCSMR */
184 mov w1, #SCSMR_INIT_DATA
185 strh w1, [x0, #SCIF_SCSMR]
186 /* Set value in SCBRR */
187#if SCIF_CLK == SCIF_INTERNAL_CLK
188 ldr x1, =PRR
189 ldr w1, [x1]
190 and w1, w1, #(PRR_PRODUCT_MASK | PRR_CUT_MASK)
191 mov w2, #PRR_PRODUCT_H3_VER_10
192 cmp w1, w2
193 beq 3f
194 and w1, w1, #PRR_PRODUCT_MASK
195 mov w2, #PRR_PRODUCT_E3
196 cmp w1, w2
197 bne 4f
198
199 ldr x1, =RST_MODEMR
200 ldr w1, [x1]
201 and w1, w1, #MODEMR_MD12
202 mov w2, #MODEMR_MD12
203 cmp w1, w2
204 bne 4f
205
206 mov w1, #SCBRR_115200BPS_E3_SSCG
207 b 2f
2084:
209 mov w1, #SCBRR_115200BPS
210 b 2f
2113:
212 mov w1, #SCBRR_230400BPS
2132:
214 strb w1, [x0, SCIF_SCBRR]
215#else
216 mov w1, #DL_INIT_DATA
217 strh w1, [x0, #SCIF_DL]
218 mov w1, #CKS_INIT_DATA
219 strh w1, [x0, #SCIF_CKS]
220#endif
221 /* 1-bit interval elapsed */
222 mov w1, #100
2231:
224 subs w1, w1, #1
225 cbnz w1, 1b
226 /*
227 * Set bits RTRG[1:0], TTRG[1:0], and MCE in SCFCR
228 * Clear bits FRST and RFRST to 0
229 */
230 mov w1, #SCFCR_INIT_DATA
231 strh w1, [x0, #SCIF_SCFCR]
232 /* Set bits TE and RE in SCSCR to 1 */
233 ldrh w1, [x0, #SCIF_SCSCR]
234 orr w1, w1, #(SCSCR_TE_EN + SCSCR_RE_EN)
235 strh w1, [x0, #SCIF_SCSCR]
236 mov x0, #1
237
238 ret
239endfunc console_core_init
240
241 /* ---------------------------------------------
242 * int console_putc(int c)
243 * Function to output a character over the
244 * console. It returns the character printed on
245 * success or -1 on error.
246 * In : x0 - character to be printed
247 * Out : return -1 on error else return character.
248 * Clobber list : x1, x2
249 * ---------------------------------------------
250 */
251func console_putc
252 b console_core_putc
253endfunc console_putc
254
255 /* --------------------------------------------------------
256 * int console_core_putc(int c, unsigned int base_addr)
257 * Function to output a character over the console. It
258 * returns the character printed on success or -1 on error.
259 * In : w0 - character to be printed
260 * x1 - console base address
261 * Out : return -1 on error else return character.
262 * Clobber list : x2
263 * --------------------------------------------------------
264 */
265func console_core_putc
266 ldr x1, =SCIF2_BASE
267 cmp w0, #0xA
268 /* Prepend '\r' to '\n' */
269 bne 2f
2701:
271 /* Check if the transmit FIFO is full */
272 ldrh w2, [x1, #SCIF_SCFDR]
273 ubfx w2, w2, #8, #5
274 cmp w2, #16
275 bcs 1b
276 mov w2, #0x0D
277 strb w2, [x1, #SCIF_SCFTDR]
2782:
279 /* Check if the transmit FIFO is full */
280 ldrh w2, [x1, #SCIF_SCFDR]
281 ubfx w2, w2, #8, #5
282 cmp w2, #16
283 bcs 2b
284 strb w0, [x1, #SCIF_SCFTDR]
285
Marek Vasutaae2c722018-12-27 20:31:22 +0100286 /* Clear TEND flag */
287 ldrh w2, [x1, #SCIF_SCFSR]
288 and w2, w2, #~SCFSR_TEND_MASK
289 strh w2, [x1, #SCIF_SCFSR]
290
Jorge Ramirez-Ortiz1d753672018-09-23 09:41:53 +0200291 ret
292endfunc console_core_putc
293
294 /* ---------------------------------------------
295 * int console_getc(void)
296 * Function to get a character from the console.
297 * It returns the character grabbed on success
298 * or -1 on error.
299 * Clobber list : x0, x1
300 * ---------------------------------------------
301 */
302func console_getc
303 mov w0, #-1
304 ret
305endfunc console_getc
306
307 /* ---------------------------------------------
308 * int console_flush(void)
309 * Function to force a write of all buffered
310 * data that hasn't been output. It returns 0
311 * upon successful completion, otherwise it
312 * returns -1.
313 * Clobber list : x0, x1
314 * ---------------------------------------------
315 */
316func console_flush
317 ldr x0, =SCIF2_BASE
3181:
Marek Vasutaae2c722018-12-27 20:31:22 +0100319 /* Check TEND flag */
320 ldrh w1, [x0, #SCIF_SCFSR]
321 and w1, w1, #SCFSR_TEND_MASK
322 cmp w1, #SCFSR_TEND_TRANS_END
Jorge Ramirez-Ortiz1d753672018-09-23 09:41:53 +0200323 bne 1b
324
Jorge Ramirez-Ortiz1d753672018-09-23 09:41:53 +0200325 ldr x0, =SCIF2_BASE
326 ldrh w1, [x0, #SCIF_SCSCR]
327 and w1, w1, #~(SCSCR_TE_EN + SCSCR_RE_EN)
328 strh w1, [x0, #SCIF_SCSCR]
329
330 mov w0, #0
331 ret
332endfunc console_flush