xref: /rk3399_rockchip-uboot/arch/arm/cpu/armv7/ls102xa/cpu.c (revision 636ef95605560a45cd9be21c6340d2bca33352ed)
1 /*
2  * Copyright 2014 Freescale Semiconductor, Inc.
3  *
4  * SPDX-License-Identifier:	GPL-2.0+
5  */
6 
7 #include <common.h>
8 #include <asm/arch/clock.h>
9 #include <asm/io.h>
10 #include <asm/arch/immap_ls102xa.h>
11 #include <asm/cache.h>
12 #include <asm/system.h>
13 #include <tsec.h>
14 #include <netdev.h>
15 #include <fsl_esdhc.h>
16 
17 #include "fsl_epu.h"
18 
19 DECLARE_GLOBAL_DATA_PTR;
20 
21 #ifndef CONFIG_SYS_DCACHE_OFF
22 
23 /*
24  * Bit[1] of the descriptor indicates the descriptor type,
25  * and bit[0] indicates whether the descriptor is valid.
26  */
27 #define PMD_TYPE_TABLE		0x3
28 #define PMD_TYPE_SECT		0x1
29 
30 /* AttrIndx[2:0] */
31 #define PMD_ATTRINDX(t)		((t) << 2)
32 
33 /* Section */
34 #define PMD_SECT_AF		(1 << 10)
35 
36 #define BLOCK_SIZE_L1		(1UL << 30)
37 #define BLOCK_SIZE_L2		(1UL << 21)
38 
39 /* TTBCR flags */
40 #define TTBCR_EAE		(1 << 31)
41 #define TTBCR_T0SZ(x)		((x) << 0)
42 #define TTBCR_T1SZ(x)		((x) << 16)
43 #define TTBCR_USING_TTBR0	(TTBCR_T0SZ(0) | TTBCR_T1SZ(0))
44 #define TTBCR_IRGN0_NC		(0 << 8)
45 #define TTBCR_IRGN0_WBWA	(1 << 8)
46 #define TTBCR_IRGN0_WT		(2 << 8)
47 #define TTBCR_IRGN0_WBNWA	(3 << 8)
48 #define TTBCR_IRGN0_MASK	(3 << 8)
49 #define TTBCR_ORGN0_NC		(0 << 10)
50 #define TTBCR_ORGN0_WBWA	(1 << 10)
51 #define TTBCR_ORGN0_WT		(2 << 10)
52 #define TTBCR_ORGN0_WBNWA	(3 << 10)
53 #define TTBCR_ORGN0_MASK	(3 << 10)
54 #define TTBCR_SHARED_NON	(0 << 12)
55 #define TTBCR_SHARED_OUTER	(2 << 12)
56 #define TTBCR_SHARED_INNER	(3 << 12)
57 #define TTBCR_EPD0		(0 << 7)
58 #define TTBCR			(TTBCR_SHARED_NON | \
59 				 TTBCR_ORGN0_NC	| \
60 				 TTBCR_IRGN0_NC	| \
61 				 TTBCR_USING_TTBR0 | \
62 				 TTBCR_EAE)
63 
64 /*
65  * Memory region attributes for LPAE (defined in pgtable):
66  *
67  * n = AttrIndx[2:0]
68  *
69  *		              n       MAIR
70  *	UNCACHED              000     00000000
71  *	BUFFERABLE            001     01000100
72  *	DEV_WC                001     01000100
73  *	WRITETHROUGH          010     10101010
74  *	WRITEBACK             011     11101110
75  *	DEV_CACHED            011     11101110
76  *	DEV_SHARED            100     00000100
77  *	DEV_NONSHARED         100     00000100
78  *	unused                101
79  *	unused                110
80  *	WRITEALLOC            111     11111111
81  */
82 #define MT_MAIR0		0xeeaa4400
83 #define MT_MAIR1		0xff000004
84 #define MT_STRONLY_ORDER	0
85 #define MT_NORMAL_NC		1
86 #define MT_DEVICE_MEM		4
87 #define MT_NORMAL		7
88 
89 /* The phy_addr must be aligned to 4KB */
90 static inline void set_pgtable(u32 *page_table, u32 index, u32 phy_addr)
91 {
92 	u32 value = phy_addr | PMD_TYPE_TABLE;
93 
94 	page_table[2 * index] = value;
95 	page_table[2 * index + 1] = 0;
96 }
97 
98 /* The phy_addr must be aligned to 4KB */
99 static inline void set_pgsection(u32 *page_table, u32 index, u64 phy_addr,
100 				 u32 memory_type)
101 {
102 	u64 value;
103 
104 	value = phy_addr | PMD_TYPE_SECT | PMD_SECT_AF;
105 	value |= PMD_ATTRINDX(memory_type);
106 	page_table[2 * index] = value & 0xFFFFFFFF;
107 	page_table[2 * index + 1] = (value >> 32) & 0xFFFFFFFF;
108 }
109 
110 /*
111  * Start MMU after DDR is available, we create MMU table in DRAM.
112  * The base address of TTLB is gd->arch.tlb_addr. We use two
113  * levels of translation tables here to cover 40-bit address space.
114  *
115  * The TTLBs are located at PHY 2G~4G.
116  *
117  * VA mapping:
118  *
119  *  -------  <---- 0GB
120  * |       |
121  * |       |
122  * |-------| <---- 0x24000000
123  * |///////|  ===> 192MB VA map for PCIe1 with offset 0x40_0000_0000
124  * |-------| <---- 0x300000000
125  * |       |
126  * |-------| <---- 0x34000000
127  * |///////|  ===> 192MB VA map for PCIe2 with offset 0x48_0000_0000
128  * |-------| <---- 0x40000000
129  * |       |
130  * |-------| <---- 0x80000000 DDR0 space start
131  * |\\\\\\\|
132  *.|\\\\\\\|  ===> 2GB VA map for 2GB DDR0 Memory space
133  * |\\\\\\\|
134  *  -------  <---- 4GB DDR0 space end
135  */
136 static void mmu_setup(void)
137 {
138 	u32 *level0_table = (u32 *)gd->arch.tlb_addr;
139 	u32 *level1_table = (u32 *)(gd->arch.tlb_addr + 0x1000);
140 	u64 va_start = 0;
141 	u32 reg;
142 	int i;
143 
144 	/* Level 0 Table 2-3 are used to map DDR */
145 	set_pgsection(level0_table, 3, 3 * BLOCK_SIZE_L1, MT_NORMAL);
146 	set_pgsection(level0_table, 2, 2 * BLOCK_SIZE_L1, MT_NORMAL);
147 	/* Level 0 Table 1 is used to map device */
148 	set_pgsection(level0_table, 1, 1 * BLOCK_SIZE_L1, MT_DEVICE_MEM);
149 	/* Level 0 Table 0 is used to map device including PCIe MEM */
150 	set_pgtable(level0_table, 0, (u32)level1_table);
151 
152 	/* Level 1 has 512 entries */
153 	for (i = 0; i < 512; i++) {
154 		/* Mapping for PCIe 1 */
155 		if (va_start >= CONFIG_SYS_PCIE1_VIRT_ADDR &&
156 		    va_start < (CONFIG_SYS_PCIE1_VIRT_ADDR +
157 				 CONFIG_SYS_PCIE_MMAP_SIZE))
158 			set_pgsection(level1_table, i,
159 				      CONFIG_SYS_PCIE1_PHYS_BASE + va_start,
160 				      MT_DEVICE_MEM);
161 		/* Mapping for PCIe 2 */
162 		else if (va_start >= CONFIG_SYS_PCIE2_VIRT_ADDR &&
163 			 va_start < (CONFIG_SYS_PCIE2_VIRT_ADDR +
164 				     CONFIG_SYS_PCIE_MMAP_SIZE))
165 			set_pgsection(level1_table, i,
166 				      CONFIG_SYS_PCIE2_PHYS_BASE + va_start,
167 				      MT_DEVICE_MEM);
168 		else
169 			set_pgsection(level1_table, i,
170 				      va_start,
171 				      MT_DEVICE_MEM);
172 		va_start += BLOCK_SIZE_L2;
173 	}
174 
175 	asm volatile("dsb sy;isb");
176 	asm volatile("mcr p15, 0, %0, c2, c0, 2" /* Write RT to TTBCR */
177 			: : "r" (TTBCR) : "memory");
178 	asm volatile("mcrr p15, 0, %0, %1, c2" /* TTBR 0 */
179 			: : "r" ((u32)level0_table), "r" (0) : "memory");
180 	asm volatile("mcr p15, 0, %0, c10, c2, 0" /* write MAIR 0 */
181 			: : "r" (MT_MAIR0) : "memory");
182 	asm volatile("mcr p15, 0, %0, c10, c2, 1" /* write MAIR 1 */
183 			: : "r" (MT_MAIR1) : "memory");
184 
185 	/* Set the access control to all-supervisor */
186 	asm volatile("mcr p15, 0, %0, c3, c0, 0"
187 		     : : "r" (~0));
188 
189 	/* Enable the mmu */
190 	reg = get_cr();
191 	set_cr(reg | CR_M);
192 }
193 
194 /*
195  * This function is called from lib/board.c. It recreates MMU
196  * table in main memory. MMU and i/d-cache are enabled here.
197  */
198 void enable_caches(void)
199 {
200 	/* Invalidate all TLB */
201 	mmu_page_table_flush(gd->arch.tlb_addr,
202 			     gd->arch.tlb_addr +  gd->arch.tlb_size);
203 	/* Set up and enable mmu */
204 	mmu_setup();
205 
206 	/* Invalidate & Enable d-cache */
207 	invalidate_dcache_all();
208 	set_cr(get_cr() | CR_C);
209 }
210 #endif /* #ifndef CONFIG_SYS_DCACHE_OFF */
211 
212 #if defined(CONFIG_DISPLAY_CPUINFO)
213 int print_cpuinfo(void)
214 {
215 	char buf1[32], buf2[32];
216 	struct ccsr_gur __iomem *gur = (void *)(CONFIG_SYS_FSL_GUTS_ADDR);
217 	unsigned int svr, major, minor, ver, i;
218 
219 	svr = in_be32(&gur->svr);
220 	major = SVR_MAJ(svr);
221 	minor = SVR_MIN(svr);
222 
223 	puts("CPU:   Freescale LayerScape ");
224 
225 	ver = SVR_SOC_VER(svr);
226 	switch (ver) {
227 	case SOC_VER_SLS1020:
228 		puts("SLS1020");
229 		break;
230 	case SOC_VER_LS1020:
231 		puts("LS1020");
232 		break;
233 	case SOC_VER_LS1021:
234 		puts("LS1021");
235 		break;
236 	case SOC_VER_LS1022:
237 		puts("LS1022");
238 		break;
239 	default:
240 		puts("Unknown");
241 		break;
242 	}
243 
244 	if (IS_E_PROCESSOR(svr) && (ver != SOC_VER_SLS1020))
245 		puts("E");
246 
247 	printf(", Version: %d.%d, (0x%08x)\n", major, minor, svr);
248 
249 	puts("Clock Configuration:");
250 
251 	printf("\n       CPU0(ARMV7):%-4s MHz, ", strmhz(buf1, gd->cpu_clk));
252 	printf("\n       Bus:%-4s MHz, ", strmhz(buf1, gd->bus_clk));
253 	printf("DDR:%-4s MHz (%s MT/s data rate), ",
254 	       strmhz(buf1, gd->mem_clk/2), strmhz(buf2, gd->mem_clk));
255 	puts("\n");
256 
257 	/* Display the RCW, so that no one gets confused as to what RCW
258 	 * we're actually using for this boot.
259 	 */
260 	puts("Reset Configuration Word (RCW):");
261 	for (i = 0; i < ARRAY_SIZE(gur->rcwsr); i++) {
262 		u32 rcw = in_be32(&gur->rcwsr[i]);
263 
264 		if ((i % 4) == 0)
265 			printf("\n       %08x:", i * 4);
266 		printf(" %08x", rcw);
267 	}
268 	puts("\n");
269 
270 	return 0;
271 }
272 #endif
273 
274 #ifdef CONFIG_FSL_ESDHC
275 int cpu_mmc_init(bd_t *bis)
276 {
277 	return fsl_esdhc_mmc_init(bis);
278 }
279 #endif
280 
281 int cpu_eth_init(bd_t *bis)
282 {
283 #ifdef CONFIG_TSEC_ENET
284 	tsec_standard_init(bis);
285 #endif
286 
287 	return 0;
288 }
289 
290 int arch_cpu_init(void)
291 {
292 	void *epu_base = (void *)(CONFIG_SYS_DCSRBAR + EPU_BLOCK_OFFSET);
293 
294 	/*
295 	 * After wakeup from deep sleep, Clear EPU registers
296 	 * as early as possible to prevent from possible issue.
297 	 * It's also safe to clear at normal boot.
298 	 */
299 	fsl_epu_clean(epu_base);
300 
301 	return 0;
302 }
303 
304 #if defined(CONFIG_ARMV7_NONSEC) || defined(CONFIG_ARMV7_VIRT)
305 /* Set the address at which the secondary core starts from.*/
306 void smp_set_core_boot_addr(unsigned long addr, int corenr)
307 {
308 	struct ccsr_gur __iomem *gur = (void *)(CONFIG_SYS_FSL_GUTS_ADDR);
309 
310 	out_be32(&gur->scratchrw[0], addr);
311 }
312 
313 /* Release the secondary core from holdoff state and kick it */
314 void smp_kick_all_cpus(void)
315 {
316 	struct ccsr_gur __iomem *gur = (void *)(CONFIG_SYS_FSL_GUTS_ADDR);
317 
318 	out_be32(&gur->brrl, 0x2);
319 }
320 #endif
321