forked from mirrors/linux
		
	ARM: 8031/2: change fixmap mapping region to support 32 CPUs
In 32-bit ARM systems, the fixmap mapping region can support no more than 14 CPUs(total: 896k; one CPU: 64K). And we can configure NR_CPUS up to 32. So there is a mismatch. This patch moves fixmapping region downwards to region 0xffc00000- 0xffe00000. Then the fixmap mapping region can support up to 32 CPUs. Reviewed-by: Nicolas Pitre <nico@linaro.org> Signed-off-by: Liu Hua <sdu.liu@huawei.com> Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
This commit is contained in:
		
							parent
							
								
									4221e2e6b3
								
							
						
					
					
						commit
						a05e54c103
					
				
					 5 changed files with 29 additions and 21 deletions
				
			
		| 
						 | 
					@ -41,7 +41,7 @@ fffe8000	fffeffff	DTCM mapping area for platforms with
 | 
				
			||||||
fffe0000	fffe7fff	ITCM mapping area for platforms with
 | 
					fffe0000	fffe7fff	ITCM mapping area for platforms with
 | 
				
			||||||
				ITCM mounted inside the CPU.
 | 
									ITCM mounted inside the CPU.
 | 
				
			||||||
 | 
					
 | 
				
			||||||
fff00000	fffdffff	Fixmap mapping region.  Addresses provided
 | 
					fffc0000	ffdfffff	Fixmap mapping region.  Addresses provided
 | 
				
			||||||
				by fix_to_virt() will be located here.
 | 
									by fix_to_virt() will be located here.
 | 
				
			||||||
 | 
					
 | 
				
			||||||
fee00000	feffffff	Mapping of PCI I/O space. This is a static
 | 
					fee00000	feffffff	Mapping of PCI I/O space. This is a static
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -1,20 +1,8 @@
 | 
				
			||||||
#ifndef _ASM_FIXMAP_H
 | 
					#ifndef _ASM_FIXMAP_H
 | 
				
			||||||
#define _ASM_FIXMAP_H
 | 
					#define _ASM_FIXMAP_H
 | 
				
			||||||
 | 
					
 | 
				
			||||||
/*
 | 
					#define FIXADDR_START		0xffc00000UL
 | 
				
			||||||
 * Nothing too fancy for now.
 | 
					#define FIXADDR_TOP		0xffe00000UL
 | 
				
			||||||
 *
 | 
					 | 
				
			||||||
 * On ARM we already have well known fixed virtual addresses imposed by
 | 
					 | 
				
			||||||
 * the architecture such as the vector page which is located at 0xffff0000,
 | 
					 | 
				
			||||||
 * therefore a second level page table is already allocated covering
 | 
					 | 
				
			||||||
 * 0xfff00000 upwards.
 | 
					 | 
				
			||||||
 *
 | 
					 | 
				
			||||||
 * The cache flushing code in proc-xscale.S uses the virtual area between
 | 
					 | 
				
			||||||
 * 0xfffe0000 and 0xfffeffff.
 | 
					 | 
				
			||||||
 */
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
#define FIXADDR_START		0xfff00000UL
 | 
					 | 
				
			||||||
#define FIXADDR_TOP		0xfffe0000UL
 | 
					 | 
				
			||||||
#define FIXADDR_SIZE		(FIXADDR_TOP - FIXADDR_START)
 | 
					#define FIXADDR_SIZE		(FIXADDR_TOP - FIXADDR_START)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#define FIX_KMAP_NR_PTES	(FIXADDR_SIZE >> PAGE_SHIFT)
 | 
					#define FIX_KMAP_NR_PTES	(FIXADDR_SIZE >> PAGE_SHIFT)
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -18,6 +18,7 @@
 | 
				
			||||||
	} while (0)
 | 
						} while (0)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
extern pte_t *pkmap_page_table;
 | 
					extern pte_t *pkmap_page_table;
 | 
				
			||||||
 | 
					extern pte_t *fixmap_page_table;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
extern void *kmap_high(struct page *page);
 | 
					extern void *kmap_high(struct page *page);
 | 
				
			||||||
extern void kunmap_high(struct page *page);
 | 
					extern void kunmap_high(struct page *page);
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -18,6 +18,21 @@
 | 
				
			||||||
#include <asm/tlbflush.h>
 | 
					#include <asm/tlbflush.h>
 | 
				
			||||||
#include "mm.h"
 | 
					#include "mm.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					pte_t *fixmap_page_table;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static inline void set_fixmap_pte(int idx, pte_t pte)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
						unsigned long vaddr = __fix_to_virt(idx);
 | 
				
			||||||
 | 
						set_pte_ext(fixmap_page_table + idx, pte, 0);
 | 
				
			||||||
 | 
						local_flush_tlb_kernel_page(vaddr);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static inline pte_t get_fixmap_pte(unsigned long vaddr)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
						unsigned long idx = __virt_to_fix(vaddr);
 | 
				
			||||||
 | 
						return *(fixmap_page_table + idx);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void *kmap(struct page *page)
 | 
					void *kmap(struct page *page)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	might_sleep();
 | 
						might_sleep();
 | 
				
			||||||
| 
						 | 
					@ -69,14 +84,14 @@ void *kmap_atomic(struct page *page)
 | 
				
			||||||
	 * With debugging enabled, kunmap_atomic forces that entry to 0.
 | 
						 * With debugging enabled, kunmap_atomic forces that entry to 0.
 | 
				
			||||||
	 * Make sure it was indeed properly unmapped.
 | 
						 * Make sure it was indeed properly unmapped.
 | 
				
			||||||
	 */
 | 
						 */
 | 
				
			||||||
	BUG_ON(!pte_none(get_top_pte(vaddr)));
 | 
						BUG_ON(!pte_none(*(fixmap_page_table + idx)));
 | 
				
			||||||
#endif
 | 
					#endif
 | 
				
			||||||
	/*
 | 
						/*
 | 
				
			||||||
	 * When debugging is off, kunmap_atomic leaves the previous mapping
 | 
						 * When debugging is off, kunmap_atomic leaves the previous mapping
 | 
				
			||||||
	 * in place, so the contained TLB flush ensures the TLB is updated
 | 
						 * in place, so the contained TLB flush ensures the TLB is updated
 | 
				
			||||||
	 * with the new mapping.
 | 
						 * with the new mapping.
 | 
				
			||||||
	 */
 | 
						 */
 | 
				
			||||||
	set_top_pte(vaddr, mk_pte(page, kmap_prot));
 | 
						set_fixmap_pte(idx, mk_pte(page, kmap_prot));
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	return (void *)vaddr;
 | 
						return (void *)vaddr;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
| 
						 | 
					@ -95,7 +110,7 @@ void __kunmap_atomic(void *kvaddr)
 | 
				
			||||||
			__cpuc_flush_dcache_area((void *)vaddr, PAGE_SIZE);
 | 
								__cpuc_flush_dcache_area((void *)vaddr, PAGE_SIZE);
 | 
				
			||||||
#ifdef CONFIG_DEBUG_HIGHMEM
 | 
					#ifdef CONFIG_DEBUG_HIGHMEM
 | 
				
			||||||
		BUG_ON(vaddr != __fix_to_virt(idx));
 | 
							BUG_ON(vaddr != __fix_to_virt(idx));
 | 
				
			||||||
		set_top_pte(vaddr, __pte(0));
 | 
							set_fixmap_pte(idx, __pte(0));
 | 
				
			||||||
#else
 | 
					#else
 | 
				
			||||||
		(void) idx;  /* to kill a warning */
 | 
							(void) idx;  /* to kill a warning */
 | 
				
			||||||
#endif
 | 
					#endif
 | 
				
			||||||
| 
						 | 
					@ -119,9 +134,9 @@ void *kmap_atomic_pfn(unsigned long pfn)
 | 
				
			||||||
	idx = type + KM_TYPE_NR * smp_processor_id();
 | 
						idx = type + KM_TYPE_NR * smp_processor_id();
 | 
				
			||||||
	vaddr = __fix_to_virt(idx);
 | 
						vaddr = __fix_to_virt(idx);
 | 
				
			||||||
#ifdef CONFIG_DEBUG_HIGHMEM
 | 
					#ifdef CONFIG_DEBUG_HIGHMEM
 | 
				
			||||||
	BUG_ON(!pte_none(get_top_pte(vaddr)));
 | 
						BUG_ON(!pte_none(*(fixmap_page_table + idx)));
 | 
				
			||||||
#endif
 | 
					#endif
 | 
				
			||||||
	set_top_pte(vaddr, pfn_pte(pfn, kmap_prot));
 | 
						set_fixmap_pte(idx, pfn_pte(pfn, kmap_prot));
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	return (void *)vaddr;
 | 
						return (void *)vaddr;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
| 
						 | 
					@ -133,5 +148,5 @@ struct page *kmap_atomic_to_page(const void *ptr)
 | 
				
			||||||
	if (vaddr < FIXADDR_START)
 | 
						if (vaddr < FIXADDR_START)
 | 
				
			||||||
		return virt_to_page(ptr);
 | 
							return virt_to_page(ptr);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	return pte_page(get_top_pte(vaddr));
 | 
						return pte_page(get_fixmap_pte(vaddr));
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -35,6 +35,7 @@
 | 
				
			||||||
#include <asm/mach/arch.h>
 | 
					#include <asm/mach/arch.h>
 | 
				
			||||||
#include <asm/mach/map.h>
 | 
					#include <asm/mach/map.h>
 | 
				
			||||||
#include <asm/mach/pci.h>
 | 
					#include <asm/mach/pci.h>
 | 
				
			||||||
 | 
					#include <asm/fixmap.h>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#include "mm.h"
 | 
					#include "mm.h"
 | 
				
			||||||
#include "tcm.h"
 | 
					#include "tcm.h"
 | 
				
			||||||
| 
						 | 
					@ -1359,6 +1360,9 @@ static void __init kmap_init(void)
 | 
				
			||||||
#ifdef CONFIG_HIGHMEM
 | 
					#ifdef CONFIG_HIGHMEM
 | 
				
			||||||
	pkmap_page_table = early_pte_alloc(pmd_off_k(PKMAP_BASE),
 | 
						pkmap_page_table = early_pte_alloc(pmd_off_k(PKMAP_BASE),
 | 
				
			||||||
		PKMAP_BASE, _PAGE_KERNEL_TABLE);
 | 
							PKMAP_BASE, _PAGE_KERNEL_TABLE);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						fixmap_page_table = early_pte_alloc(pmd_off_k(FIXADDR_START),
 | 
				
			||||||
 | 
							FIXADDR_START, _PAGE_KERNEL_TABLE);
 | 
				
			||||||
#endif
 | 
					#endif
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
		Loading…
	
		Reference in a new issue