aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--arch/powerpc/mm/fsl_booke_mmu.c31
-rw-r--r--arch/powerpc/mm/mmu_decl.h2
-rw-r--r--arch/powerpc/mm/tlb_nohash.c21
3 files changed, 39 insertions, 15 deletions
diff --git a/arch/powerpc/mm/fsl_booke_mmu.c b/arch/powerpc/mm/fsl_booke_mmu.c
index f7802c8bba0a..6f593bd27174 100644
--- a/arch/powerpc/mm/fsl_booke_mmu.c
+++ b/arch/powerpc/mm/fsl_booke_mmu.c
@@ -146,29 +146,36 @@ static void settlbcam(int index, unsigned long virt, phys_addr_t phys,
146 loadcam_entry(index); 146 loadcam_entry(index);
147} 147}
148 148
149unsigned long calc_cam_sz(unsigned long ram, unsigned long virt,
150 phys_addr_t phys)
151{
152 unsigned int camsize = __ilog2(ram) & ~1U;
153 unsigned int align = __ffs(virt | phys) & ~1U;
154 unsigned long max_cam = (mfspr(SPRN_TLB1CFG) >> 16) & 0xf;
155
156 /* Convert (4^max) kB to (2^max) bytes */
157 max_cam = max_cam * 2 + 10;
158
159 if (camsize > align)
160 camsize = align;
161 if (camsize > max_cam)
162 camsize = max_cam;
163
164 return 1UL << camsize;
165}
166
149unsigned long map_mem_in_cams(unsigned long ram, int max_cam_idx) 167unsigned long map_mem_in_cams(unsigned long ram, int max_cam_idx)
150{ 168{
151 int i; 169 int i;
152 unsigned long virt = PAGE_OFFSET; 170 unsigned long virt = PAGE_OFFSET;
153 phys_addr_t phys = memstart_addr; 171 phys_addr_t phys = memstart_addr;
154 unsigned long amount_mapped = 0; 172 unsigned long amount_mapped = 0;
155 unsigned long max_cam = (mfspr(SPRN_TLB1CFG) >> 16) & 0xf;
156
157 /* Convert (4^max) kB to (2^max) bytes */
158 max_cam = max_cam * 2 + 10;
159 173
160 /* Calculate CAM values */ 174 /* Calculate CAM values */
161 for (i = 0; ram && i < max_cam_idx; i++) { 175 for (i = 0; ram && i < max_cam_idx; i++) {
162 unsigned int camsize = __ilog2(ram) & ~1U;
163 unsigned int align = __ffs(virt | phys) & ~1U;
164 unsigned long cam_sz; 176 unsigned long cam_sz;
165 177
166 if (camsize > align) 178 cam_sz = calc_cam_sz(ram, virt, phys);
167 camsize = align;
168 if (camsize > max_cam)
169 camsize = max_cam;
170
171 cam_sz = 1UL << camsize;
172 settlbcam(i, virt, phys, cam_sz, PAGE_KERNEL_X, 0); 179 settlbcam(i, virt, phys, cam_sz, PAGE_KERNEL_X, 0);
173 180
174 ram -= cam_sz; 181 ram -= cam_sz;
diff --git a/arch/powerpc/mm/mmu_decl.h b/arch/powerpc/mm/mmu_decl.h
index dd0a2589591d..83eb5d5f53d5 100644
--- a/arch/powerpc/mm/mmu_decl.h
+++ b/arch/powerpc/mm/mmu_decl.h
@@ -142,6 +142,8 @@ extern unsigned long mmu_mapin_ram(unsigned long top);
142 142
143#elif defined(CONFIG_PPC_FSL_BOOK3E) 143#elif defined(CONFIG_PPC_FSL_BOOK3E)
144extern unsigned long map_mem_in_cams(unsigned long ram, int max_cam_idx); 144extern unsigned long map_mem_in_cams(unsigned long ram, int max_cam_idx);
145extern unsigned long calc_cam_sz(unsigned long ram, unsigned long virt,
146 phys_addr_t phys);
145#ifdef CONFIG_PPC32 147#ifdef CONFIG_PPC32
146extern void MMU_init_hw(void); 148extern void MMU_init_hw(void);
147extern unsigned long mmu_mapin_ram(unsigned long top); 149extern unsigned long mmu_mapin_ram(unsigned long top);
diff --git a/arch/powerpc/mm/tlb_nohash.c b/arch/powerpc/mm/tlb_nohash.c
index afc95c7304ae..6c2eabf707b7 100644
--- a/arch/powerpc/mm/tlb_nohash.c
+++ b/arch/powerpc/mm/tlb_nohash.c
@@ -642,13 +642,28 @@ void __cpuinit early_init_mmu_secondary(void)
642void setup_initial_memory_limit(phys_addr_t first_memblock_base, 642void setup_initial_memory_limit(phys_addr_t first_memblock_base,
643 phys_addr_t first_memblock_size) 643 phys_addr_t first_memblock_size)
644{ 644{
645 /* On Embedded 64-bit, we adjust the RMA size to match 645 /* On non-FSL Embedded 64-bit, we adjust the RMA size to match
646 * the bolted TLB entry. We know for now that only 1G 646 * the bolted TLB entry. We know for now that only 1G
647 * entries are supported though that may eventually 647 * entries are supported though that may eventually
648 * change. We crop it to the size of the first MEMBLOCK to 648 * change.
649 *
650 * on FSL Embedded 64-bit, we adjust the RMA size to match the
651 * first bolted TLB entry size. We still limit max to 1G even if
652 * the TLB could cover more. This is due to what the early init
653 * code is setup to do.
654 *
655 * We crop it to the size of the first MEMBLOCK to
649 * avoid going over total available memory just in case... 656 * avoid going over total available memory just in case...
650 */ 657 */
651 ppc64_rma_size = min_t(u64, first_memblock_size, 0x40000000); 658#ifdef CONFIG_PPC_FSL_BOOK3E
659 if (mmu_has_feature(MMU_FTR_TYPE_FSL_E)) {
660 unsigned long linear_sz;
661 linear_sz = calc_cam_sz(first_memblock_size, PAGE_OFFSET,
662 first_memblock_base);
663 ppc64_rma_size = min_t(u64, linear_sz, 0x40000000);
664 } else
665#endif
666 ppc64_rma_size = min_t(u64, first_memblock_size, 0x40000000);
652 667
653 /* Finally limit subsequent allocations */ 668 /* Finally limit subsequent allocations */
654 memblock_set_current_limit(first_memblock_base + ppc64_rma_size); 669 memblock_set_current_limit(first_memblock_base + ppc64_rma_size);