]>
Commit | Line | Data |
---|---|---|
4efb77d4 PW |
1 | /* |
2 | * (C) Copyright 2009 | |
3 | * Marvell Semiconductor <www.marvell.com> | |
4 | * Written-by: Prafulla Wadaskar <prafulla@marvell.com> | |
5 | * | |
1a459660 | 6 | * SPDX-License-Identifier: GPL-2.0+ |
4efb77d4 PW |
7 | */ |
8 | ||
9 | #include <config.h> | |
beeb2589 | 10 | #include <common.h> |
a7efd719 LW |
11 | #include <asm/io.h> |
12 | #include <asm/arch/cpu.h> | |
4efb77d4 PW |
13 | #include <asm/arch/kirkwood.h> |
14 | ||
beeb2589 PW |
15 | DECLARE_GLOBAL_DATA_PTR; |
16 | ||
cf37c5d9 HB |
17 | struct kw_sdram_bank { |
18 | u32 win_bar; | |
19 | u32 win_sz; | |
20 | }; | |
21 | ||
22 | struct kw_sdram_addr_dec { | |
23 | struct kw_sdram_bank sdram_bank[4]; | |
24 | }; | |
25 | ||
45515165 GF |
26 | #define KW_REG_CPUCS_WIN_ENABLE (1 << 0) |
27 | #define KW_REG_CPUCS_WIN_WR_PROTECT (1 << 1) | |
28 | #define KW_REG_CPUCS_WIN_WIN0_CS(x) (((x) & 0x3) << 2) | |
29 | #define KW_REG_CPUCS_WIN_SIZE(x) (((x) & 0xff) << 24) | |
30 | ||
4efb77d4 PW |
31 | /* |
32 | * kw_sdram_bar - reads SDRAM Base Address Register | |
33 | */ | |
34 | u32 kw_sdram_bar(enum memory_bank bank) | |
35 | { | |
cf37c5d9 HB |
36 | struct kw_sdram_addr_dec *base = |
37 | (struct kw_sdram_addr_dec *)KW_REGISTER(0x1500); | |
4efb77d4 | 38 | u32 result = 0; |
cf37c5d9 | 39 | u32 enable = 0x01 & readl(&base->sdram_bank[bank].win_sz); |
4efb77d4 PW |
40 | |
41 | if ((!enable) || (bank > BANK3)) | |
42 | return 0; | |
43 | ||
cf37c5d9 | 44 | result = readl(&base->sdram_bank[bank].win_bar); |
4efb77d4 PW |
45 | return result; |
46 | } | |
47 | ||
45515165 GF |
48 | /* |
49 | * kw_sdram_bs_set - writes SDRAM Bank size | |
50 | */ | |
51 | static void kw_sdram_bs_set(enum memory_bank bank, u32 size) | |
52 | { | |
53 | struct kw_sdram_addr_dec *base = | |
54 | (struct kw_sdram_addr_dec *)KW_REGISTER(0x1500); | |
55 | /* Read current register value */ | |
56 | u32 reg = readl(&base->sdram_bank[bank].win_sz); | |
57 | ||
58 | /* Clear window size */ | |
59 | reg &= ~KW_REG_CPUCS_WIN_SIZE(0xFF); | |
60 | ||
61 | /* Set new window size */ | |
62 | reg |= KW_REG_CPUCS_WIN_SIZE((size - 1) >> 24); | |
63 | ||
64 | writel(reg, &base->sdram_bank[bank].win_sz); | |
65 | } | |
66 | ||
4efb77d4 PW |
67 | /* |
68 | * kw_sdram_bs - reads SDRAM Bank size | |
69 | */ | |
70 | u32 kw_sdram_bs(enum memory_bank bank) | |
71 | { | |
cf37c5d9 HB |
72 | struct kw_sdram_addr_dec *base = |
73 | (struct kw_sdram_addr_dec *)KW_REGISTER(0x1500); | |
4efb77d4 | 74 | u32 result = 0; |
cf37c5d9 | 75 | u32 enable = 0x01 & readl(&base->sdram_bank[bank].win_sz); |
4efb77d4 PW |
76 | |
77 | if ((!enable) || (bank > BANK3)) | |
78 | return 0; | |
cf37c5d9 | 79 | result = 0xff000000 & readl(&base->sdram_bank[bank].win_sz); |
4efb77d4 PW |
80 | result += 0x01000000; |
81 | return result; | |
82 | } | |
beeb2589 | 83 | |
b3168f4b GF |
84 | void kw_sdram_size_adjust(enum memory_bank bank) |
85 | { | |
86 | u32 size; | |
87 | ||
88 | /* probe currently equipped RAM size */ | |
89 | size = get_ram_size((void *)kw_sdram_bar(bank), kw_sdram_bs(bank)); | |
90 | ||
91 | /* adjust SDRAM window size accordingly */ | |
92 | kw_sdram_bs_set(bank, size); | |
93 | } | |
94 | ||
beeb2589 PW |
95 | #ifndef CONFIG_SYS_BOARD_DRAM_INIT |
96 | int dram_init(void) | |
97 | { | |
98 | int i; | |
99 | ||
100 | gd->ram_size = 0; | |
101 | for (i = 0; i < CONFIG_NR_DRAM_BANKS; i++) { | |
102 | gd->bd->bi_dram[i].start = kw_sdram_bar(i); | |
103 | gd->bd->bi_dram[i].size = kw_sdram_bs(i); | |
104 | /* | |
105 | * It is assumed that all memory banks are consecutive | |
106 | * and without gaps. | |
107 | * If the gap is found, ram_size will be reported for | |
108 | * consecutive memory only | |
109 | */ | |
110 | if (gd->bd->bi_dram[i].start != gd->ram_size) | |
111 | break; | |
112 | ||
113 | gd->ram_size += gd->bd->bi_dram[i].size; | |
114 | ||
115 | } | |
28e57108 TU |
116 | |
117 | for (; i < CONFIG_NR_DRAM_BANKS; i++) { | |
118 | /* If above loop terminated prematurely, we need to set | |
119 | * remaining banks' start address & size as 0. Otherwise other | |
120 | * u-boot functions and Linux kernel gets wrong values which | |
121 | * could result in crash */ | |
122 | gd->bd->bi_dram[i].start = 0; | |
123 | gd->bd->bi_dram[i].size = 0; | |
124 | } | |
125 | ||
beeb2589 PW |
126 | return 0; |
127 | } | |
128 | ||
129 | /* | |
130 | * If this function is not defined here, | |
131 | * board.c alters dram bank zero configuration defined above. | |
132 | */ | |
133 | void dram_init_banksize(void) | |
134 | { | |
135 | dram_init(); | |
136 | } | |
137 | #endif /* CONFIG_SYS_BOARD_DRAM_INIT */ |