Commit | Line | Data |
---|---|---|
458eef2f LW |
1 | /* |
2 | * Copyright (C) ST-Ericsson SA 2011 | |
3 | * | |
4 | * License terms: GNU General Public License (GPL) version 2 | |
5 | */ | |
6 | ||
7 | #include <linux/io.h> | |
f1949ea0 LJ |
8 | #include <linux/of.h> |
9 | ||
458eef2f LW |
10 | #include <asm/cacheflush.h> |
11 | #include <asm/hardware/cache-l2x0.h> | |
7a4f2609 | 12 | |
174e7796 | 13 | #include "db8500-regs.h" |
7a4f2609 | 14 | #include "id.h" |
458eef2f LW |
15 | |
16 | static void __iomem *l2x0_base; | |
17 | ||
a3849a4c AB |
18 | static int __init ux500_l2x0_unlock(void) |
19 | { | |
20 | int i; | |
21 | ||
22 | /* | |
23 | * Unlock Data and Instruction Lock if locked. Ux500 U-Boot versions | |
24 | * apparently locks both caches before jumping to the kernel. The | |
25 | * l2x0 core will not touch the unlock registers if the l2x0 is | |
26 | * already enabled, so we do it right here instead. The PL310 has | |
27 | * 8 sets of registers, one per possible CPU. | |
28 | */ | |
29 | for (i = 0; i < 8; i++) { | |
30 | writel_relaxed(0x0, l2x0_base + L2X0_LOCKDOWN_WAY_D_BASE + | |
31 | i * L2X0_LOCKDOWN_STRIDE); | |
32 | writel_relaxed(0x0, l2x0_base + L2X0_LOCKDOWN_WAY_I_BASE + | |
33 | i * L2X0_LOCKDOWN_STRIDE); | |
34 | } | |
35 | return 0; | |
36 | } | |
37 | ||
38 | static int __init ux500_l2x0_init(void) | |
458eef2f | 39 | { |
bc71c096 LW |
40 | u32 aux_val = 0x3e000000; |
41 | ||
e1bbb55d | 42 | if (cpu_is_u8500_family() || cpu_is_ux540_family()) |
458eef2f LW |
43 | l2x0_base = __io_address(U8500_L2CC_BASE); |
44 | else | |
45 | ux500_unknown_soc(); | |
46 | ||
a3849a4c AB |
47 | /* Unlock before init */ |
48 | ux500_l2x0_unlock(); | |
49 | ||
0f2fa40e MC |
50 | /* DBx540's L2 has 128KB way size */ |
51 | if (cpu_is_ux540_family()) | |
bc71c096 LW |
52 | /* 128KB way size */ |
53 | aux_val |= (0x4 << L2X0_AUX_CTRL_WAY_SIZE_SHIFT); | |
54 | else | |
55 | /* 64KB way size */ | |
56 | aux_val |= (0x3 << L2X0_AUX_CTRL_WAY_SIZE_SHIFT); | |
57 | ||
458eef2f | 58 | /* 64KB way size, 8 way associativity, force WA */ |
f1949ea0 | 59 | if (of_have_populated_dt()) |
bc71c096 | 60 | l2x0_of_init(aux_val, 0xc0000fff); |
f1949ea0 | 61 | else |
bc71c096 | 62 | l2x0_init(l2x0_base, aux_val, 0xc0000fff); |
458eef2f | 63 | |
dd821823 | 64 | /* |
65 | * We can't disable l2 as we are in non secure mode, currently | |
66 | * this seems be called only during kexec path. So let's | |
67 | * override outer.disable with nasty assignment until we have | |
68 | * some SMI service available. | |
69 | */ | |
70 | outer_cache.disable = NULL; | |
458eef2f LW |
71 | |
72 | return 0; | |
73 | } | |
74 | ||
75 | early_initcall(ux500_l2x0_init); |