xref: /rk3399_ARM-atf/drivers/renesas/common/scif/scif.c (revision 656a8564ec06a4f737c2eeb9fd6e580e8f002c14)
1*656a8564SMarek Vasut /*
2*656a8564SMarek Vasut  * Copyright (c) 2026, Renesas Electronics Corporation. All rights reserved.
3*656a8564SMarek Vasut  *
4*656a8564SMarek Vasut  * SPDX-License-Identifier: BSD-3-Clause
5*656a8564SMarek Vasut  */
6*656a8564SMarek Vasut 
7*656a8564SMarek Vasut #include <stddef.h>
8*656a8564SMarek Vasut #include <stdint.h>
9*656a8564SMarek Vasut 
10*656a8564SMarek Vasut #include <drivers/console.h>
11*656a8564SMarek Vasut #include <lib/mmio.h>
12*656a8564SMarek Vasut #include <lib/utils_def.h>
13*656a8564SMarek Vasut #include "scif.h"
14*656a8564SMarek Vasut 
15*656a8564SMarek Vasut #include "cpg_registers.h"
16*656a8564SMarek Vasut #include "rcar_def.h"
17*656a8564SMarek Vasut #include "rcar_private.h"
18*656a8564SMarek Vasut 
19*656a8564SMarek Vasut /* CPG */
20*656a8564SMarek Vasut #define CPG_MSTPSR2_SCIF0	BIT(7)
21*656a8564SMarek Vasut #define CPG_MSTPSR3_SCIF2	BIT(10)
22*656a8564SMarek Vasut 
23*656a8564SMarek Vasut /* SCIF */
24*656a8564SMarek Vasut #define SCIF0_BASE		0xE6E60000UL
25*656a8564SMarek Vasut #define SCIF2_BASE		0xE6E88000UL
26*656a8564SMarek Vasut 
27*656a8564SMarek Vasut /* SCIF */
28*656a8564SMarek Vasut #define SCIF_SCSMR		0x00
29*656a8564SMarek Vasut #define SCIF_SCBRR		0x04
30*656a8564SMarek Vasut #define SCIF_SCSCR		0x08
31*656a8564SMarek Vasut #define SCIF_SCFTDR		0x0C
32*656a8564SMarek Vasut #define SCIF_SCFSR		0x10
33*656a8564SMarek Vasut #define SCIF_SCFCR		0x18
34*656a8564SMarek Vasut #define SCIF_SCLSR		0x24
35*656a8564SMarek Vasut #define SCIF_DL			0x30
36*656a8564SMarek Vasut #define SCIF_CKS		0x34
37*656a8564SMarek Vasut 
38*656a8564SMarek Vasut /* MODE pin */
39*656a8564SMarek Vasut #define MODEMR_MD12		BIT(12)
40*656a8564SMarek Vasut 
41*656a8564SMarek Vasut #define SCBRR_115200BPS		17
42*656a8564SMarek Vasut #define SCBRR_115200BPS_D3_SSCG	16
43*656a8564SMarek Vasut #define SCBRR_115200BPS_E3_SSCG	15
44*656a8564SMarek Vasut #define SCBRR_230400BPS		8
45*656a8564SMarek Vasut 
46*656a8564SMarek Vasut #define SCSCR_TE_EN		BIT(5)
47*656a8564SMarek Vasut #define SCSCR_RE_EN		BIT(4)
48*656a8564SMarek Vasut #define SCSCR_CKE_MASK		3
49*656a8564SMarek Vasut #define SCFSR_TEND_MASK		BIT(6)
50*656a8564SMarek Vasut #define SCFSR_TEND_TRANS_END	BIT(6)
51*656a8564SMarek Vasut #define SCSCR_CKE_INT_CLK	0
52*656a8564SMarek Vasut #define SCFCR_TFRST_EN		BIT(2)
53*656a8564SMarek Vasut #define SCFCR_RFRS_EN		BIT(1)
54*656a8564SMarek Vasut 
55*656a8564SMarek Vasut int console_rcar_init(uintptr_t base_addr, uint32_t uart_clk,
56*656a8564SMarek Vasut 		      uint32_t baud_rate)
57*656a8564SMarek Vasut {
58*656a8564SMarek Vasut 	uint32_t prr = mmio_read_32(PRR);
59*656a8564SMarek Vasut 	uint32_t base;
60*656a8564SMarek Vasut 	int i;
61*656a8564SMarek Vasut 
62*656a8564SMarek Vasut 	if ((prr & PRR_PRODUCT_MASK) == PRR_PRODUCT_V3M) { /* V3M */
63*656a8564SMarek Vasut 		base = SCIF0_BASE;
64*656a8564SMarek Vasut 		/* Enable SCIF clock */
65*656a8564SMarek Vasut 		mstpcr_write(CPG_SMSTPCR2, CPG_MSTPSR2, CPG_MSTPSR2_SCIF0);
66*656a8564SMarek Vasut 	} else {
67*656a8564SMarek Vasut 		base = SCIF2_BASE;
68*656a8564SMarek Vasut 		/* Enable SCIF clock */
69*656a8564SMarek Vasut 		mstpcr_write(CPG_SMSTPCR3, CPG_MSTPSR3, CPG_MSTPSR3_SCIF2);
70*656a8564SMarek Vasut 	}
71*656a8564SMarek Vasut 
72*656a8564SMarek Vasut 	scif_console_set_regs(base + SCIF_SCFSR, base + SCIF_SCFTDR);
73*656a8564SMarek Vasut 
74*656a8564SMarek Vasut 	/* Clear bits TE and RE in SCSCR to 0 */
75*656a8564SMarek Vasut 	mmio_write_16(base + SCIF_SCSCR, 0);
76*656a8564SMarek Vasut 
77*656a8564SMarek Vasut 	/* Set bits TFRST and RFRST in SCFCR to 1 */
78*656a8564SMarek Vasut 	mmio_clrsetbits_16(base + SCIF_SCFCR,
79*656a8564SMarek Vasut 			   SCFCR_TFRST_EN | SCFCR_RFRS_EN,
80*656a8564SMarek Vasut 			   SCFCR_TFRST_EN | SCFCR_RFRS_EN);
81*656a8564SMarek Vasut 
82*656a8564SMarek Vasut 	/*
83*656a8564SMarek Vasut 	 * Read flags of ER, DR, BRK, and RDF in SCFSR and those
84*656a8564SMarek Vasut 	 * of TO and ORER in SCLSR, then clear them to 0.
85*656a8564SMarek Vasut 	 */
86*656a8564SMarek Vasut 	mmio_write_16(base + SCIF_SCFSR, 0);
87*656a8564SMarek Vasut 	mmio_write_16(base + SCIF_SCLSR, 0);
88*656a8564SMarek Vasut 
89*656a8564SMarek Vasut 	/* Set bits CKE[1:0] in SCSCR */
90*656a8564SMarek Vasut 	mmio_clrsetbits_16(base + SCIF_SCSCR, SCSCR_CKE_MASK,
91*656a8564SMarek Vasut 			   SCSCR_CKE_INT_CLK);
92*656a8564SMarek Vasut 
93*656a8564SMarek Vasut 	/* Set data transfer format in SCSMR */
94*656a8564SMarek Vasut 	mmio_write_16(base + SCIF_SCSMR, 0);
95*656a8564SMarek Vasut 
96*656a8564SMarek Vasut 	/* Set value in SCBRR */
97*656a8564SMarek Vasut 	if ((prr & (PRR_PRODUCT_MASK | PRR_CUT_MASK)) == PRR_PRODUCT_H3_CUT10) {
98*656a8564SMarek Vasut 		/* H3 ES 1.0 */
99*656a8564SMarek Vasut 		mmio_write_8(base + SCIF_SCBRR, SCBRR_230400BPS);
100*656a8564SMarek Vasut 	} else if (((prr & PRR_PRODUCT_MASK) == PRR_PRODUCT_D3) &&
101*656a8564SMarek Vasut 		   (mmio_read_32(RST_MODEMR) & MODEMR_MD12)) {
102*656a8564SMarek Vasut 		/* D3 with SSCG(MD12) ON */
103*656a8564SMarek Vasut 		mmio_write_8(base + SCIF_SCBRR, SCBRR_115200BPS_D3_SSCG);
104*656a8564SMarek Vasut 	} else if (((prr & PRR_PRODUCT_MASK) == PRR_PRODUCT_E3) &&
105*656a8564SMarek Vasut 		   (mmio_read_32(RST_MODEMR) & MODEMR_MD12)) {
106*656a8564SMarek Vasut 		/* E3 with SSCG(MD12) ON */
107*656a8564SMarek Vasut 		mmio_write_8(base + SCIF_SCBRR, SCBRR_115200BPS_E3_SSCG);
108*656a8564SMarek Vasut 	} else {
109*656a8564SMarek Vasut 		/* H3/M3/M3N or when SSCG(MD12) is off in E3/D3 */
110*656a8564SMarek Vasut 		mmio_write_8(base + SCIF_SCBRR, SCBRR_115200BPS);
111*656a8564SMarek Vasut 	}
112*656a8564SMarek Vasut 
113*656a8564SMarek Vasut 	/* 1-bit interval elapsed */
114*656a8564SMarek Vasut 	for (i = 0; i < 100; i++)
115*656a8564SMarek Vasut 		asm volatile("nop");
116*656a8564SMarek Vasut 
117*656a8564SMarek Vasut 	/*
118*656a8564SMarek Vasut 	 * Set bits RTRG[1:0], TTRG[1:0], and MCE in SCFCR
119*656a8564SMarek Vasut 	 * Clear bits FRST and RFRST to 0
120*656a8564SMarek Vasut 	 */
121*656a8564SMarek Vasut 	mmio_write_16(base + SCIF_SCFCR, 0);
122*656a8564SMarek Vasut 
123*656a8564SMarek Vasut 	/* Set bits TE and RE in SCSCR to 1 */
124*656a8564SMarek Vasut 	mmio_clrsetbits_16(base + SCIF_SCSCR, SCSCR_TE_EN | SCSCR_RE_EN,
125*656a8564SMarek Vasut 			   SCSCR_TE_EN | SCSCR_RE_EN);
126*656a8564SMarek Vasut 
127*656a8564SMarek Vasut 	return 1;
128*656a8564SMarek Vasut }
129