diff options
Diffstat (limited to 'arch/mips/include')
-rw-r--r-- | arch/mips/include/asm/cpu-features.h | 3 | ||||
-rw-r--r-- | arch/mips/include/asm/pgtable-32.h | 4 | ||||
-rw-r--r-- | arch/mips/include/asm/pgtable-64.h | 4 | ||||
-rw-r--r-- | arch/mips/include/asm/pgtable-bits.h | 120 | ||||
-rw-r--r-- | arch/mips/include/asm/pgtable.h | 26 |
5 files changed, 128 insertions, 29 deletions
diff --git a/arch/mips/include/asm/cpu-features.h b/arch/mips/include/asm/cpu-features.h index 272c5ef35bb..ac73cede3a0 100644 --- a/arch/mips/include/asm/cpu-features.h +++ b/arch/mips/include/asm/cpu-features.h | |||
@@ -95,6 +95,9 @@ | |||
95 | #ifndef cpu_has_smartmips | 95 | #ifndef cpu_has_smartmips |
96 | #define cpu_has_smartmips (cpu_data[0].ases & MIPS_ASE_SMARTMIPS) | 96 | #define cpu_has_smartmips (cpu_data[0].ases & MIPS_ASE_SMARTMIPS) |
97 | #endif | 97 | #endif |
98 | #ifndef kernel_uses_smartmips_rixi | ||
99 | #define kernel_uses_smartmips_rixi 0 | ||
100 | #endif | ||
98 | #ifndef cpu_has_vtag_icache | 101 | #ifndef cpu_has_vtag_icache |
99 | #define cpu_has_vtag_icache (cpu_data[0].icache.flags & MIPS_CACHE_VTAG) | 102 | #define cpu_has_vtag_icache (cpu_data[0].icache.flags & MIPS_CACHE_VTAG) |
100 | #endif | 103 | #endif |
diff --git a/arch/mips/include/asm/pgtable-32.h b/arch/mips/include/asm/pgtable-32.h index 55813d6150c..ae90412556d 100644 --- a/arch/mips/include/asm/pgtable-32.h +++ b/arch/mips/include/asm/pgtable-32.h | |||
@@ -127,8 +127,8 @@ pfn_pte(unsigned long pfn, pgprot_t prot) | |||
127 | #define pte_pfn(x) ((unsigned long)((x).pte >> (PAGE_SHIFT + 2))) | 127 | #define pte_pfn(x) ((unsigned long)((x).pte >> (PAGE_SHIFT + 2))) |
128 | #define pfn_pte(pfn, prot) __pte(((pfn) << (PAGE_SHIFT + 2)) | pgprot_val(prot)) | 128 | #define pfn_pte(pfn, prot) __pte(((pfn) << (PAGE_SHIFT + 2)) | pgprot_val(prot)) |
129 | #else | 129 | #else |
130 | #define pte_pfn(x) ((unsigned long)((x).pte >> PAGE_SHIFT)) | 130 | #define pte_pfn(x) ((unsigned long)((x).pte >> _PFN_SHIFT)) |
131 | #define pfn_pte(pfn, prot) __pte(((unsigned long long)(pfn) << PAGE_SHIFT) | pgprot_val(prot)) | 131 | #define pfn_pte(pfn, prot) __pte(((unsigned long long)(pfn) << _PFN_SHIFT) | pgprot_val(prot)) |
132 | #endif | 132 | #endif |
133 | #endif /* defined(CONFIG_64BIT_PHYS_ADDR) && defined(CONFIG_CPU_MIPS32) */ | 133 | #endif /* defined(CONFIG_64BIT_PHYS_ADDR) && defined(CONFIG_CPU_MIPS32) */ |
134 | 134 | ||
diff --git a/arch/mips/include/asm/pgtable-64.h b/arch/mips/include/asm/pgtable-64.h index 24314d21a70..26dc69d792a 100644 --- a/arch/mips/include/asm/pgtable-64.h +++ b/arch/mips/include/asm/pgtable-64.h | |||
@@ -211,8 +211,8 @@ static inline void pud_clear(pud_t *pudp) | |||
211 | #define pte_pfn(x) ((unsigned long)((x).pte >> (PAGE_SHIFT + 2))) | 211 | #define pte_pfn(x) ((unsigned long)((x).pte >> (PAGE_SHIFT + 2))) |
212 | #define pfn_pte(pfn, prot) __pte(((pfn) << (PAGE_SHIFT + 2)) | pgprot_val(prot)) | 212 | #define pfn_pte(pfn, prot) __pte(((pfn) << (PAGE_SHIFT + 2)) | pgprot_val(prot)) |
213 | #else | 213 | #else |
214 | #define pte_pfn(x) ((unsigned long)((x).pte >> PAGE_SHIFT)) | 214 | #define pte_pfn(x) ((unsigned long)((x).pte >> _PFN_SHIFT)) |
215 | #define pfn_pte(pfn, prot) __pte(((pfn) << PAGE_SHIFT) | pgprot_val(prot)) | 215 | #define pfn_pte(pfn, prot) __pte(((pfn) << _PFN_SHIFT) | pgprot_val(prot)) |
216 | #endif | 216 | #endif |
217 | 217 | ||
218 | #define __pgd_offset(address) pgd_index(address) | 218 | #define __pgd_offset(address) pgd_index(address) |
diff --git a/arch/mips/include/asm/pgtable-bits.h b/arch/mips/include/asm/pgtable-bits.h index 1073e6df862..e9fe7e97ce4 100644 --- a/arch/mips/include/asm/pgtable-bits.h +++ b/arch/mips/include/asm/pgtable-bits.h | |||
@@ -50,7 +50,7 @@ | |||
50 | #define _CACHE_SHIFT 3 | 50 | #define _CACHE_SHIFT 3 |
51 | #define _CACHE_MASK (7<<3) | 51 | #define _CACHE_MASK (7<<3) |
52 | 52 | ||
53 | #else | 53 | #elif defined(CONFIG_CPU_R3000) || defined(CONFIG_CPU_TX39XX) |
54 | 54 | ||
55 | #define _PAGE_PRESENT (1<<0) /* implemented in software */ | 55 | #define _PAGE_PRESENT (1<<0) /* implemented in software */ |
56 | #define _PAGE_READ (1<<1) /* implemented in software */ | 56 | #define _PAGE_READ (1<<1) /* implemented in software */ |
@@ -59,8 +59,6 @@ | |||
59 | #define _PAGE_MODIFIED (1<<4) /* implemented in software */ | 59 | #define _PAGE_MODIFIED (1<<4) /* implemented in software */ |
60 | #define _PAGE_FILE (1<<4) /* set:pagecache unset:swap */ | 60 | #define _PAGE_FILE (1<<4) /* set:pagecache unset:swap */ |
61 | 61 | ||
62 | #if defined(CONFIG_CPU_R3000) || defined(CONFIG_CPU_TX39XX) | ||
63 | |||
64 | #define _PAGE_GLOBAL (1<<8) | 62 | #define _PAGE_GLOBAL (1<<8) |
65 | #define _PAGE_VALID (1<<9) | 63 | #define _PAGE_VALID (1<<9) |
66 | #define _PAGE_SILENT_READ (1<<9) /* synonym */ | 64 | #define _PAGE_SILENT_READ (1<<9) /* synonym */ |
@@ -69,21 +67,113 @@ | |||
69 | #define _CACHE_UNCACHED (1<<11) | 67 | #define _CACHE_UNCACHED (1<<11) |
70 | #define _CACHE_MASK (1<<11) | 68 | #define _CACHE_MASK (1<<11) |
71 | 69 | ||
70 | #else /* 'Normal' r4K case */ | ||
71 | /* | ||
72 | * When using the RI/XI bit support, we have 13 bits of flags below | ||
73 | * the physical address. The RI/XI bits are placed such that a SRL 5 | ||
74 | * can strip off the software bits, then a ROTR 2 can move the RI/XI | ||
75 | * into bits [63:62]. This also limits physical address to 56 bits, | ||
76 | * which is more than we need right now. | ||
77 | */ | ||
78 | |||
79 | /* implemented in software */ | ||
80 | #define _PAGE_PRESENT_SHIFT (0) | ||
81 | #define _PAGE_PRESENT (1 << _PAGE_PRESENT_SHIFT) | ||
82 | /* implemented in software, should be unused if kernel_uses_smartmips_rixi. */ | ||
83 | #define _PAGE_READ_SHIFT (kernel_uses_smartmips_rixi ? _PAGE_PRESENT_SHIFT : _PAGE_PRESENT_SHIFT + 1) | ||
84 | #define _PAGE_READ ({if (kernel_uses_smartmips_rixi) BUG(); 1 << _PAGE_READ_SHIFT; }) | ||
85 | /* implemented in software */ | ||
86 | #define _PAGE_WRITE_SHIFT (_PAGE_READ_SHIFT + 1) | ||
87 | #define _PAGE_WRITE (1 << _PAGE_WRITE_SHIFT) | ||
88 | /* implemented in software */ | ||
89 | #define _PAGE_ACCESSED_SHIFT (_PAGE_WRITE_SHIFT + 1) | ||
90 | #define _PAGE_ACCESSED (1 << _PAGE_ACCESSED_SHIFT) | ||
91 | /* implemented in software */ | ||
92 | #define _PAGE_MODIFIED_SHIFT (_PAGE_ACCESSED_SHIFT + 1) | ||
93 | #define _PAGE_MODIFIED (1 << _PAGE_MODIFIED_SHIFT) | ||
94 | /* set:pagecache unset:swap */ | ||
95 | #define _PAGE_FILE (_PAGE_MODIFIED) | ||
96 | |||
97 | #ifdef CONFIG_HUGETLB_PAGE | ||
98 | /* huge tlb page */ | ||
99 | #define _PAGE_HUGE_SHIFT (_PAGE_MODIFIED_SHIFT + 1) | ||
100 | #define _PAGE_HUGE (1 << _PAGE_HUGE_SHIFT) | ||
72 | #else | 101 | #else |
102 | #define _PAGE_HUGE_SHIFT (_PAGE_MODIFIED_SHIFT) | ||
103 | #define _PAGE_HUGE ({BUG(); 1; }) /* Dummy value */ | ||
104 | #endif | ||
73 | 105 | ||
74 | #define _PAGE_R4KBUG (1<<5) /* workaround for r4k bug */ | 106 | /* Page cannot be executed */ |
75 | #define _PAGE_HUGE (1<<5) /* huge tlb page */ | 107 | #define _PAGE_NO_EXEC_SHIFT (kernel_uses_smartmips_rixi ? _PAGE_HUGE_SHIFT + 1 : _PAGE_HUGE_SHIFT) |
76 | #define _PAGE_GLOBAL (1<<6) | 108 | #define _PAGE_NO_EXEC ({if (!kernel_uses_smartmips_rixi) BUG(); 1 << _PAGE_NO_EXEC_SHIFT; }) |
77 | #define _PAGE_VALID (1<<7) | 109 | |
78 | #define _PAGE_SILENT_READ (1<<7) /* synonym */ | 110 | /* Page cannot be read */ |
79 | #define _PAGE_DIRTY (1<<8) /* The MIPS dirty bit */ | 111 | #define _PAGE_NO_READ_SHIFT (kernel_uses_smartmips_rixi ? _PAGE_NO_EXEC_SHIFT + 1 : _PAGE_NO_EXEC_SHIFT) |
80 | #define _PAGE_SILENT_WRITE (1<<8) | 112 | #define _PAGE_NO_READ ({if (!kernel_uses_smartmips_rixi) BUG(); 1 << _PAGE_NO_READ_SHIFT; }) |
81 | #define _CACHE_SHIFT 9 | 113 | |
82 | #define _CACHE_MASK (7<<9) | 114 | #define _PAGE_GLOBAL_SHIFT (_PAGE_NO_READ_SHIFT + 1) |
115 | #define _PAGE_GLOBAL (1 << _PAGE_GLOBAL_SHIFT) | ||
116 | |||
117 | #define _PAGE_VALID_SHIFT (_PAGE_GLOBAL_SHIFT + 1) | ||
118 | #define _PAGE_VALID (1 << _PAGE_VALID_SHIFT) | ||
119 | /* synonym */ | ||
120 | #define _PAGE_SILENT_READ (_PAGE_VALID) | ||
121 | |||
122 | /* The MIPS dirty bit */ | ||
123 | #define _PAGE_DIRTY_SHIFT (_PAGE_VALID_SHIFT + 1) | ||
124 | #define _PAGE_DIRTY (1 << _PAGE_DIRTY_SHIFT) | ||
125 | #define _PAGE_SILENT_WRITE (_PAGE_DIRTY) | ||
126 | |||
127 | #define _CACHE_SHIFT (_PAGE_DIRTY_SHIFT + 1) | ||
128 | #define _CACHE_MASK (7 << _CACHE_SHIFT) | ||
129 | |||
130 | #define _PFN_SHIFT (PAGE_SHIFT - 12 + _CACHE_SHIFT + 3) | ||
83 | 131 | ||
84 | #endif | ||
85 | #endif /* defined(CONFIG_64BIT_PHYS_ADDR && defined(CONFIG_CPU_MIPS32) */ | 132 | #endif /* defined(CONFIG_64BIT_PHYS_ADDR && defined(CONFIG_CPU_MIPS32) */ |
86 | 133 | ||
134 | #ifndef _PFN_SHIFT | ||
135 | #define _PFN_SHIFT PAGE_SHIFT | ||
136 | #endif | ||
137 | #define _PFN_MASK (~((1 << (_PFN_SHIFT)) - 1)) | ||
138 | |||
139 | #ifndef _PAGE_NO_READ | ||
140 | #define _PAGE_NO_READ ({BUG(); 0; }) | ||
141 | #define _PAGE_NO_READ_SHIFT ({BUG(); 0; }) | ||
142 | #endif | ||
143 | #ifndef _PAGE_NO_EXEC | ||
144 | #define _PAGE_NO_EXEC ({BUG(); 0; }) | ||
145 | #endif | ||
146 | #ifndef _PAGE_GLOBAL_SHIFT | ||
147 | #define _PAGE_GLOBAL_SHIFT ilog2(_PAGE_GLOBAL) | ||
148 | #endif | ||
149 | |||
150 | |||
151 | #ifndef __ASSEMBLY__ | ||
152 | /* | ||
153 | * pte_to_entrylo converts a page table entry (PTE) into a Mips | ||
154 | * entrylo0/1 value. | ||
155 | */ | ||
156 | static inline uint64_t pte_to_entrylo(unsigned long pte_val) | ||
157 | { | ||
158 | if (kernel_uses_smartmips_rixi) { | ||
159 | int sa; | ||
160 | #ifdef CONFIG_32BIT | ||
161 | sa = 31 - _PAGE_NO_READ_SHIFT; | ||
162 | #else | ||
163 | sa = 63 - _PAGE_NO_READ_SHIFT; | ||
164 | #endif | ||
165 | /* | ||
166 | * C has no way to express that this is a DSRL | ||
167 | * _PAGE_NO_EXEC_SHIFT followed by a ROTR 2. Luckily | ||
168 | * in the fast path this is done in assembly | ||
169 | */ | ||
170 | return (pte_val >> _PAGE_GLOBAL_SHIFT) | | ||
171 | ((pte_val & (_PAGE_NO_EXEC | _PAGE_NO_READ)) << sa); | ||
172 | } | ||
173 | |||
174 | return pte_val >> _PAGE_GLOBAL_SHIFT; | ||
175 | } | ||
176 | #endif | ||
87 | 177 | ||
88 | /* | 178 | /* |
89 | * Cache attributes | 179 | * Cache attributes |
@@ -130,9 +220,9 @@ | |||
130 | 220 | ||
131 | #endif | 221 | #endif |
132 | 222 | ||
133 | #define __READABLE (_PAGE_READ | _PAGE_SILENT_READ | _PAGE_ACCESSED) | 223 | #define __READABLE (_PAGE_SILENT_READ | _PAGE_ACCESSED | (kernel_uses_smartmips_rixi ? 0 : _PAGE_READ)) |
134 | #define __WRITEABLE (_PAGE_WRITE | _PAGE_SILENT_WRITE | _PAGE_MODIFIED) | 224 | #define __WRITEABLE (_PAGE_WRITE | _PAGE_SILENT_WRITE | _PAGE_MODIFIED) |
135 | 225 | ||
136 | #define _PAGE_CHG_MASK (PAGE_MASK | _PAGE_ACCESSED | _PAGE_MODIFIED | _CACHE_MASK) | 226 | #define _PAGE_CHG_MASK (_PFN_MASK | _PAGE_ACCESSED | _PAGE_MODIFIED | _CACHE_MASK) |
137 | 227 | ||
138 | #endif /* _ASM_PGTABLE_BITS_H */ | 228 | #endif /* _ASM_PGTABLE_BITS_H */ |
diff --git a/arch/mips/include/asm/pgtable.h b/arch/mips/include/asm/pgtable.h index 02335fda9e7..93598ba0135 100644 --- a/arch/mips/include/asm/pgtable.h +++ b/arch/mips/include/asm/pgtable.h | |||
@@ -22,23 +22,24 @@ struct mm_struct; | |||
22 | struct vm_area_struct; | 22 | struct vm_area_struct; |
23 | 23 | ||
24 | #define PAGE_NONE __pgprot(_PAGE_PRESENT | _CACHE_CACHABLE_NONCOHERENT) | 24 | #define PAGE_NONE __pgprot(_PAGE_PRESENT | _CACHE_CACHABLE_NONCOHERENT) |
25 | #define PAGE_SHARED __pgprot(_PAGE_PRESENT | _PAGE_READ | _PAGE_WRITE | \ | 25 | #define PAGE_SHARED __pgprot(_PAGE_PRESENT | _PAGE_WRITE | (kernel_uses_smartmips_rixi ? 0 : _PAGE_READ) | \ |
26 | _page_cachable_default) | 26 | _page_cachable_default) |
27 | #define PAGE_COPY __pgprot(_PAGE_PRESENT | _PAGE_READ | \ | 27 | #define PAGE_COPY __pgprot(_PAGE_PRESENT | (kernel_uses_smartmips_rixi ? 0 : _PAGE_READ) | \ |
28 | _page_cachable_default) | 28 | (kernel_uses_smartmips_rixi ? _PAGE_NO_EXEC : 0) | _page_cachable_default) |
29 | #define PAGE_READONLY __pgprot(_PAGE_PRESENT | _PAGE_READ | \ | 29 | #define PAGE_READONLY __pgprot(_PAGE_PRESENT | (kernel_uses_smartmips_rixi ? 0 : _PAGE_READ) | \ |
30 | _page_cachable_default) | 30 | _page_cachable_default) |
31 | #define PAGE_KERNEL __pgprot(_PAGE_PRESENT | __READABLE | __WRITEABLE | \ | 31 | #define PAGE_KERNEL __pgprot(_PAGE_PRESENT | __READABLE | __WRITEABLE | \ |
32 | _PAGE_GLOBAL | _page_cachable_default) | 32 | _PAGE_GLOBAL | _page_cachable_default) |
33 | #define PAGE_USERIO __pgprot(_PAGE_PRESENT | _PAGE_READ | _PAGE_WRITE | \ | 33 | #define PAGE_USERIO __pgprot(_PAGE_PRESENT | (kernel_uses_smartmips_rixi ? 0 : _PAGE_READ) | _PAGE_WRITE | \ |
34 | _page_cachable_default) | 34 | _page_cachable_default) |
35 | #define PAGE_KERNEL_UNCACHED __pgprot(_PAGE_PRESENT | __READABLE | \ | 35 | #define PAGE_KERNEL_UNCACHED __pgprot(_PAGE_PRESENT | __READABLE | \ |
36 | __WRITEABLE | _PAGE_GLOBAL | _CACHE_UNCACHED) | 36 | __WRITEABLE | _PAGE_GLOBAL | _CACHE_UNCACHED) |
37 | 37 | ||
38 | /* | 38 | /* |
39 | * MIPS can't do page protection for execute, and considers that the same like | 39 | * If _PAGE_NO_EXEC is not defined, we can't do page protection for |
40 | * read. Also, write permissions imply read permissions. This is the closest | 40 | * execute, and consider it to be the same as read. Also, write |
41 | * we can get by reasonable means.. | 41 | * permissions imply read permissions. This is the closest we can get |
42 | * by reasonable means.. | ||
42 | */ | 43 | */ |
43 | 44 | ||
44 | /* | 45 | /* |
@@ -298,8 +299,13 @@ static inline pte_t pte_mkdirty(pte_t pte) | |||
298 | static inline pte_t pte_mkyoung(pte_t pte) | 299 | static inline pte_t pte_mkyoung(pte_t pte) |
299 | { | 300 | { |
300 | pte_val(pte) |= _PAGE_ACCESSED; | 301 | pte_val(pte) |= _PAGE_ACCESSED; |
301 | if (pte_val(pte) & _PAGE_READ) | 302 | if (kernel_uses_smartmips_rixi) { |
302 | pte_val(pte) |= _PAGE_SILENT_READ; | 303 | if (!(pte_val(pte) & _PAGE_NO_READ)) |
304 | pte_val(pte) |= _PAGE_SILENT_READ; | ||
305 | } else { | ||
306 | if (pte_val(pte) & _PAGE_READ) | ||
307 | pte_val(pte) |= _PAGE_SILENT_READ; | ||
308 | } | ||
303 | return pte; | 309 | return pte; |
304 | } | 310 | } |
305 | 311 | ||