Commit aec9222551353890190af810a4c93ed7050bfa19

Authored by Hauke Mehrtens
Committed by Ralf Baechle
1 parent 5c8974538a

MIPS: BCM47xx: Really fix 128MB RAM problem

The previous patch 4a86f2d27733f610e642649aca3e82e86fca9e22 (lmo) rsp.
84a6fcb368a080620d12fc4d79e07902dbee7335 (kernel.org) was wrong.

The BCM47xx architecture maps the ram into a 128MB address space. It
will be spaced there as often as goes into the 128MB. Detection tries to
find the position where the same memory is found. When reading beyond
128MB the processor will throw an exception. If 128MB RAM is installed,
it will not find a memory alias because it tries to read beyond the 128MB
border. Now it just assumes 128MB installed ram if it can not find an
alias.

Signed-off-by: Hauke Mehrtens <hauke@hauke-m.de>
To: linux-mips@linux-mips.org
Patchwork: https://patchwork.linux-mips.org/patch/1508/
Acked-by: Florian Fainelli <florian@openwrt.org>
Signed-off-by: Ralf Baechle <ralf@linux-mips.org>

Showing 1 changed file with 14 additions and 8 deletions Side-by-side Diff

arch/mips/bcm47xx/prom.c
... ... @@ -126,6 +126,7 @@
126 126 static __init void prom_init_mem(void)
127 127 {
128 128 unsigned long mem;
  129 + unsigned long max;
129 130  
130 131 /* Figure out memory size by finding aliases.
131 132 *
132 133  
133 134  
134 135  
... ... @@ -134,20 +135,25 @@
134 135 * want to reuse the memory used by CFE (around 4MB). That means cfe_*
135 136 * functions stop to work at some point during the boot, we should only
136 137 * call them at the beginning of the boot.
  138 + *
  139 + * BCM47XX uses 128MB for addressing the ram, if the system contains
  140 + * less that that amount of ram it remaps the ram more often into the
  141 + * available space.
  142 + * Accessing memory after 128MB will cause an exception.
  143 + * max contains the biggest possible address supported by the platform.
  144 + * If the method wants to try something above we assume 128MB ram.
137 145 */
  146 + max = ((unsigned long)(prom_init) | ((128 << 20) - 1));
138 147 for (mem = (1 << 20); mem < (128 << 20); mem += (1 << 20)) {
  148 + if (((unsigned long)(prom_init) + mem) > max) {
  149 + mem = (128 << 20);
  150 + printk(KERN_DEBUG "assume 128MB RAM\n");
  151 + break;
  152 + }
139 153 if (*(unsigned long *)((unsigned long)(prom_init) + mem) ==
140 154 *(unsigned long *)(prom_init))
141 155 break;
142 156 }
143   -
144   - /* Ignoring the last page when ddr size is 128M. Cached
145   - * accesses to last page is causing the processor to prefetch
146   - * using address above 128M stepping out of the ddr address
147   - * space.
148   - */
149   - if (mem == 0x8000000)
150   - mem -= 0x1000;
151 157  
152 158 add_memory_region(0, mem, BOOT_MEM_RAM);
153 159 }