1 /*************************************************************************/ /*!
3 @Title Device specific initialisation routines
4 @Copyright Copyright (c) Imagination Technologies Ltd. All Rights Reserved
5 @Description Device specific MMU initialisation
6 @License Dual MIT/GPLv2
8 The contents of this file are subject to the MIT license as set out below.
10 Permission is hereby granted, free of charge, to any person obtaining a copy
11 of this software and associated documentation files (the "Software"), to deal
12 in the Software without restriction, including without limitation the rights
13 to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
14 copies of the Software, and to permit persons to whom the Software is
15 furnished to do so, subject to the following conditions:
17 The above copyright notice and this permission notice shall be included in
18 all copies or substantial portions of the Software.
20 Alternatively, the contents of this file may be used under the terms of
21 the GNU General Public License Version 2 ("GPL") in which case the provisions
22 of GPL are applicable instead of those above.
24 If you wish to allow use of your version of this file only under the terms of
25 GPL, and not to allow others to use your version of this file under the terms
26 of the MIT license, indicate your decision by deleting the provisions above
27 and replace them with the notice and other provisions required by GPL as set
28 out in the file called "GPL-COPYING" included in this distribution. If you do
29 not delete the provisions above, a recipient may use your version of this file
30 under the terms of either the MIT license or GPL.
32 This License is also included in this distribution in the file called
35 EXCEPT AS OTHERWISE STATED IN A NEGOTIATED AGREEMENT: (A) THE SOFTWARE IS
36 PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
37 BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
38 PURPOSE AND NONINFRINGEMENT; AND (B) IN NO EVENT SHALL THE AUTHORS OR
39 COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
40 IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
41 CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
42 */ /**************************************************************************/
43 #include "rgxmipsmmuinit.h"
46 #include "img_types.h"
47 #include "mmu_common.h"
48 #include "pdump_mmu.h"
49 #include "rgxheapconfig.h"
50 #include "pvr_debug.h"
51 #include "pvrsrv_error.h"
52 #include "rgx_memallocflags.h"
57 * Bits of PT, PD and PC not involving addresses
60 /* Position of the MIPS PT entry indicating entry validity */
61 #define RGX_MIPS_MMUCTRL_PTE_PROTMASK (RGX_MIPS_MMUCTRL_PT_DATA_VALID_EN | \
62 RGX_MIPS_MMUCTRL_PT_DATA_GLOBAL_EN | \
63 RGX_MIPS_MMUCTRL_PT_DATA_WRITABLE_EN | \
64 ~RGX_MIPS_MMUCTRL_PT_CACHE_POLICY_CLRMSK);
65 /* Currently there is no page directory for MIPS MMU */
66 #define RGX_MIPS_MMUCTRL_PDE_PROTMASK 0
67 /* Currently there is no page catalog for MIPS MMU */
68 #define RGX_MIPS_MMUCTRL_PCE_PROTMASK 0
71 static MMU_PxE_CONFIG sRGXMMUPCEConfig;
72 static MMU_DEVVADDR_CONFIG sRGXMMUTopLevelDevVAddrConfig;
77 * Configuration for heaps with 4kB Data-Page size
81 static MMU_PxE_CONFIG sRGXMMUPDEConfig_4KBDP;
82 static MMU_PxE_CONFIG sRGXMMUPTEConfig_4KBDP;
83 static MMU_DEVVADDR_CONFIG sRGXMMUDevVAddrConfig_4KBDP;
84 static MMU_PAGESIZECONFIG gsPageSizeConfig4KB;
89 * Configuration for heaps with 16kB Data-Page size
93 static MMU_PxE_CONFIG sRGXMMUPDEConfig_16KBDP;
94 static MMU_PxE_CONFIG sRGXMMUPTEConfig_16KBDP;
95 static MMU_DEVVADDR_CONFIG sRGXMMUDevVAddrConfig_16KBDP;
96 static MMU_PAGESIZECONFIG gsPageSizeConfig16KB;
101 * Configuration for heaps with 64kB Data-Page size
105 static MMU_PxE_CONFIG sRGXMMUPDEConfig_64KBDP;
106 static MMU_PxE_CONFIG sRGXMMUPTEConfig_64KBDP;
107 static MMU_DEVVADDR_CONFIG sRGXMMUDevVAddrConfig_64KBDP;
108 static MMU_PAGESIZECONFIG gsPageSizeConfig64KB;
113 * Configuration for heaps with 256kB Data-Page size
117 static MMU_PxE_CONFIG sRGXMMUPDEConfig_256KBDP;
118 static MMU_PxE_CONFIG sRGXMMUPTEConfig_256KBDP;
119 static MMU_DEVVADDR_CONFIG sRGXMMUDevVAddrConfig_256KBDP;
120 static MMU_PAGESIZECONFIG gsPageSizeConfig256KB;
125 * Configuration for heaps with 1MB Data-Page size
129 static MMU_PxE_CONFIG sRGXMMUPDEConfig_1MBDP;
130 static MMU_PxE_CONFIG sRGXMMUPTEConfig_1MBDP;
131 static MMU_DEVVADDR_CONFIG sRGXMMUDevVAddrConfig_1MBDP;
132 static MMU_PAGESIZECONFIG gsPageSizeConfig1MB;
137 * Configuration for heaps with 2MB Data-Page size
141 static MMU_PxE_CONFIG sRGXMMUPDEConfig_2MBDP;
142 static MMU_PxE_CONFIG sRGXMMUPTEConfig_2MBDP;
143 static MMU_DEVVADDR_CONFIG sRGXMMUDevVAddrConfig_2MBDP;
144 static MMU_PAGESIZECONFIG gsPageSizeConfig2MB;
147 /* Forward declaration of protection bits derivation functions, for
148 the following structure */
149 static IMG_UINT64 RGXDerivePCEProt8(IMG_UINT32 uiProtFlags, IMG_UINT32 uiLog2DataPageSize);
150 static IMG_UINT32 RGXDerivePCEProt4(IMG_UINT32 uiProtFlags);
151 static IMG_UINT64 RGXDerivePDEProt8(IMG_UINT32 uiProtFlags, IMG_UINT32 uiLog2DataPageSize);
152 static IMG_UINT32 RGXDerivePDEProt4(IMG_UINT32 uiProtFlags);
153 static IMG_UINT64 RGXDerivePTEProt8(IMG_UINT32 uiProtFlags, IMG_UINT32 uiLog2DataPageSize);
154 static IMG_UINT32 RGXDerivePTEProt4(IMG_UINT32 uiProtFlags);
156 static PVRSRV_ERROR RGXGetPageSizeConfigCB(IMG_UINT32 uiLog2DataPageSize,
157 const MMU_PxE_CONFIG **ppsMMUPDEConfig,
158 const MMU_PxE_CONFIG **ppsMMUPTEConfig,
159 const MMU_DEVVADDR_CONFIG **ppsMMUDevVAddrConfig,
162 static PVRSRV_ERROR RGXPutPageSizeConfigCB(IMG_HANDLE hPriv);
164 static PVRSRV_ERROR RGXGetPageSizeFromPDE4(IMG_UINT32 ui32PDE, IMG_UINT32 *pui32Log2PageSize);
165 static PVRSRV_ERROR RGXGetPageSizeFromPDE8(IMG_UINT64 ui64PDE, IMG_UINT32 *pui32Log2PageSize);
167 static MMU_DEVICEATTRIBS sRGXMMUDeviceAttributes;
169 PVRSRV_ERROR RGXMipsMMUInit_Register(PVRSRV_DEVICE_NODE *psDeviceNode)
171 sRGXMMUDeviceAttributes.pszMMUPxPDumpMemSpaceName =
172 PhysHeapPDumpMemspaceName(psDeviceNode->apsPhysHeap[PVRSRV_DEVICE_PHYS_HEAP_FW_LOCAL]);
175 * Setup sRGXMMUPCEConfig, no PC in MIPS MMU currently
177 sRGXMMUPCEConfig.uiBytesPerEntry = 0; /* 32 bit entries */
178 sRGXMMUPCEConfig.uiAddrMask = 0; /* Mask to get significant address bits of PC entry */
180 sRGXMMUPCEConfig.uiAddrShift = 0; /* Shift this many bits to get PD address in PC entry */
181 sRGXMMUPCEConfig.uiAddrLog2Align = (IMG_UINT32)RGXMIPSFW_LOG2_PAGE_SIZE; /* Alignment of PD AND PC */
183 sRGXMMUPCEConfig.uiProtMask = RGX_MIPS_MMUCTRL_PCE_PROTMASK; //Mask to get the status bits of the PC */
184 sRGXMMUPCEConfig.uiProtShift = 0; /* Shift this many bits to have status bits starting with bit 0 */
186 sRGXMMUPCEConfig.uiValidEnMask = RGX_MIPS_MMUCTRL_PC_DATA_VALID_EN; /* Mask to get entry valid bit of the PC */
187 sRGXMMUPCEConfig.uiValidEnShift = RGX_MIPS_MMUCTRL_PC_DATA_VALID_SHIFT; /* Shift this many bits to have entry valid bit starting with bit 0 */
190 * Setup sRGXMMUTopLevelDevVAddrConfig
192 sRGXMMUTopLevelDevVAddrConfig.uiPCIndexMask = 0; /* Get the PC address bits from a 40 bit virt. address (in a 64bit UINT) */
193 sRGXMMUTopLevelDevVAddrConfig.uiPCIndexShift = 0;
194 sRGXMMUTopLevelDevVAddrConfig.uiNumEntriesPC = 0;
196 sRGXMMUTopLevelDevVAddrConfig.uiPDIndexMask = 0; /* Get the PD address bits from a 40 bit virt. address (in a 64bit UINT) */
197 sRGXMMUTopLevelDevVAddrConfig.uiPDIndexShift = 0;
198 sRGXMMUTopLevelDevVAddrConfig.uiNumEntriesPD = 0;
200 sRGXMMUTopLevelDevVAddrConfig.uiPTIndexMask = IMG_UINT64_C(0xfffffff000); /* Get the PT address bits from a 40 bit virt. address (in a 64bit UINT) */
201 sRGXMMUTopLevelDevVAddrConfig.uiPTIndexShift = (IMG_UINT32)RGXMIPSFW_LOG2_PAGE_SIZE;
202 sRGXMMUTopLevelDevVAddrConfig.uiNumEntriesPT = RGX_FIRMWARE_HEAP_SIZE >> sRGXMMUTopLevelDevVAddrConfig.uiPTIndexShift;
206 * Configuration for heaps with 4kB Data-Page size
211 * Setup sRGXMMUPDEConfig_4KBDP. No PD in MIPS MMU currently
213 sRGXMMUPDEConfig_4KBDP.uiBytesPerEntry = 0;
215 /* No PD used for MIPS */
216 sRGXMMUPDEConfig_4KBDP.uiAddrMask = 0;
217 sRGXMMUPDEConfig_4KBDP.uiAddrShift = 0;
218 sRGXMMUPDEConfig_4KBDP.uiAddrLog2Align = (IMG_UINT32)RGXMIPSFW_LOG2_PAGE_SIZE;
220 sRGXMMUPDEConfig_4KBDP.uiVarCtrlMask = IMG_UINT64_C(0x0);
221 sRGXMMUPDEConfig_4KBDP.uiVarCtrlShift = 0;
223 sRGXMMUPDEConfig_4KBDP.uiProtMask = RGX_MIPS_MMUCTRL_PDE_PROTMASK;
224 sRGXMMUPDEConfig_4KBDP.uiProtShift = 0;
226 sRGXMMUPDEConfig_4KBDP.uiValidEnMask = RGX_MIPS_MMUCTRL_PD_DATA_VALID_EN;
227 sRGXMMUPDEConfig_4KBDP.uiValidEnShift = RGX_MIPS_MMUCTRL_PD_DATA_VALID_SHIFT;
230 * Setup sRGXMMUPTEConfig_4KBDP.
232 sRGXMMUPTEConfig_4KBDP.uiBytesPerEntry = 1 << RGXMIPSFW_LOG2_PTE_ENTRY_SIZE;
234 sRGXMMUPTEConfig_4KBDP.uiAddrMask = IMG_UINT64_C(0xffffffffc0);
235 sRGXMMUPTEConfig_4KBDP.uiAddrShift = RGX_MIPS_MMUCTRL_PT_PFN_SHIFT;
236 sRGXMMUPTEConfig_4KBDP.uiAddrLog2Align = (IMG_UINT32)RGXMIPSFW_LOG2_PAGE_SIZE;
238 sRGXMMUPTEConfig_4KBDP.uiProtMask = RGX_MIPS_MMUCTRL_PTE_PROTMASK;
239 sRGXMMUPTEConfig_4KBDP.uiProtShift = 0;
241 sRGXMMUPTEConfig_4KBDP.uiValidEnMask = RGX_MIPS_MMUCTRL_PT_DATA_VALID_EN;
242 sRGXMMUPTEConfig_4KBDP.uiValidEnShift = RGX_MIPS_MMUCTRL_PT_DATA_VALID_SHIFT;
245 * Setup sRGXMMUDevVAddrConfig_4KBDP
247 sRGXMMUDevVAddrConfig_4KBDP.uiPCIndexMask = 0;
248 sRGXMMUDevVAddrConfig_4KBDP.uiPCIndexShift = 0;
249 sRGXMMUDevVAddrConfig_4KBDP.uiNumEntriesPC = 0;
252 sRGXMMUDevVAddrConfig_4KBDP.uiPDIndexMask = 0;
253 sRGXMMUDevVAddrConfig_4KBDP.uiPDIndexShift = 0;
254 sRGXMMUDevVAddrConfig_4KBDP.uiNumEntriesPD = 0;
256 sRGXMMUDevVAddrConfig_4KBDP.uiPTIndexMask = ~RGX_MIPS_MMUCTRL_VADDR_PT_INDEX_CLRMSK;
257 sRGXMMUDevVAddrConfig_4KBDP.uiPTIndexShift = RGX_MIPS_MMUCTRL_VADDR_PT_INDEX_SHIFT;
258 sRGXMMUDevVAddrConfig_4KBDP.uiNumEntriesPT = RGX_FIRMWARE_HEAP_SIZE >> sRGXMMUDevVAddrConfig_4KBDP.uiPTIndexShift;
261 sRGXMMUDevVAddrConfig_4KBDP.uiPageOffsetMask = IMG_UINT64_C(0x0000000fff);
262 sRGXMMUDevVAddrConfig_4KBDP.uiPageOffsetShift = 0;
263 sRGXMMUDevVAddrConfig_4KBDP.uiOffsetInBytes = RGX_FIRMWARE_HEAP_BASE & IMG_UINT64_C(0x00ffffffff);
266 * Setup gsPageSizeConfig4KB
268 gsPageSizeConfig4KB.psPDEConfig = &sRGXMMUPDEConfig_4KBDP;
269 gsPageSizeConfig4KB.psPTEConfig = &sRGXMMUPTEConfig_4KBDP;
270 gsPageSizeConfig4KB.psDevVAddrConfig = &sRGXMMUDevVAddrConfig_4KBDP;
271 gsPageSizeConfig4KB.uiRefCount = 0;
272 gsPageSizeConfig4KB.uiMaxRefCount = 0;
277 * Configuration for heaps with 16kB Data-Page size
282 * Setup sRGXMMUPDEConfig_16KBDP
284 sRGXMMUPDEConfig_16KBDP.uiBytesPerEntry = 0;
286 sRGXMMUPDEConfig_16KBDP.uiAddrMask = 0;
287 sRGXMMUPDEConfig_16KBDP.uiAddrShift = 0; /* These are for a page directory ENTRY, meaning the address of a PT cropped to suit the PD */
288 sRGXMMUPDEConfig_16KBDP.uiAddrLog2Align = 0; /* Alignment of the page tables NOT directories */
290 sRGXMMUPDEConfig_16KBDP.uiVarCtrlMask = 0;
291 sRGXMMUPDEConfig_16KBDP.uiVarCtrlShift = 0;
293 sRGXMMUPDEConfig_16KBDP.uiProtMask = 0;
294 sRGXMMUPDEConfig_16KBDP.uiProtShift = 0;
296 sRGXMMUPDEConfig_16KBDP.uiValidEnMask = 0;
297 sRGXMMUPDEConfig_16KBDP.uiValidEnShift = 0;
300 * Setup sRGXMMUPTEConfig_16KBDP. Not supported yet
302 sRGXMMUPTEConfig_16KBDP.uiBytesPerEntry = 0;
304 sRGXMMUPTEConfig_16KBDP.uiAddrMask = 0;
305 sRGXMMUPTEConfig_16KBDP.uiAddrShift = 0; /* These are for a page table ENTRY, meaning the address of a PAGE cropped to suit the PD */
306 sRGXMMUPTEConfig_16KBDP.uiAddrLog2Align = 0; /* Alignment of the pages NOT tables */
308 sRGXMMUPTEConfig_16KBDP.uiProtMask = 0;
309 sRGXMMUPTEConfig_16KBDP.uiProtShift = 0;
311 sRGXMMUPTEConfig_16KBDP.uiValidEnMask = 0;
312 sRGXMMUPTEConfig_16KBDP.uiValidEnShift = 0;
315 * Setup sRGXMMUDevVAddrConfig_16KBDP
317 sRGXMMUDevVAddrConfig_16KBDP.uiPCIndexMask = 0;
318 sRGXMMUDevVAddrConfig_16KBDP.uiPCIndexShift = 0;
319 sRGXMMUDevVAddrConfig_16KBDP.uiNumEntriesPC = 0;
321 sRGXMMUDevVAddrConfig_16KBDP.uiPDIndexMask = 0;
322 sRGXMMUDevVAddrConfig_16KBDP.uiPDIndexShift = 0;
323 sRGXMMUDevVAddrConfig_16KBDP.uiNumEntriesPD= 0;
325 sRGXMMUDevVAddrConfig_16KBDP.uiPTIndexMask = 0;
326 sRGXMMUDevVAddrConfig_16KBDP.uiPTIndexShift = 0;
327 sRGXMMUDevVAddrConfig_16KBDP.uiNumEntriesPT = 0;
329 sRGXMMUDevVAddrConfig_16KBDP.uiPageOffsetMask = 0;
330 sRGXMMUDevVAddrConfig_16KBDP.uiPageOffsetShift = 0;
331 sRGXMMUDevVAddrConfig_16KBDP.uiOffsetInBytes = 0;
334 * Setup gsPageSizeConfig16KB
336 gsPageSizeConfig16KB.psPDEConfig = &sRGXMMUPDEConfig_16KBDP;
337 gsPageSizeConfig16KB.psPTEConfig = &sRGXMMUPTEConfig_16KBDP;
338 gsPageSizeConfig16KB.psDevVAddrConfig = &sRGXMMUDevVAddrConfig_16KBDP;
339 gsPageSizeConfig16KB.uiRefCount = 0;
340 gsPageSizeConfig16KB.uiMaxRefCount = 0;
345 * Configuration for heaps with 64kB Data-Page size. Not supported yet
350 * Setup sRGXMMUPDEConfig_64KBDP
352 sRGXMMUPDEConfig_64KBDP.uiBytesPerEntry = 0;
354 sRGXMMUPDEConfig_64KBDP.uiAddrMask = 0;
355 sRGXMMUPDEConfig_64KBDP.uiAddrShift = 0;
356 sRGXMMUPDEConfig_64KBDP.uiAddrLog2Align = 0;
358 sRGXMMUPDEConfig_64KBDP.uiVarCtrlMask = 0;
359 sRGXMMUPDEConfig_64KBDP.uiVarCtrlShift = 0;
361 sRGXMMUPDEConfig_64KBDP.uiProtMask = 0;
362 sRGXMMUPDEConfig_64KBDP.uiProtShift = 0;
364 sRGXMMUPDEConfig_64KBDP.uiValidEnMask = 0;
365 sRGXMMUPDEConfig_64KBDP.uiValidEnShift = 0;
368 * Setup sRGXMMUPTEConfig_64KBDP.
371 sRGXMMUPTEConfig_64KBDP.uiBytesPerEntry = 0;
373 sRGXMMUPTEConfig_64KBDP.uiAddrMask = 0;
374 sRGXMMUPTEConfig_64KBDP.uiAddrShift = 0;
375 sRGXMMUPTEConfig_64KBDP.uiAddrLog2Align = 0;
377 sRGXMMUPTEConfig_64KBDP.uiProtMask = 0;
378 sRGXMMUPTEConfig_64KBDP.uiProtShift = 0;
380 sRGXMMUPTEConfig_64KBDP.uiValidEnMask = 0;
381 sRGXMMUPTEConfig_64KBDP.uiValidEnShift = 0;
384 * Setup sRGXMMUDevVAddrConfig_64KBDP.
386 sRGXMMUDevVAddrConfig_64KBDP.uiPCIndexMask = 0;
387 sRGXMMUDevVAddrConfig_64KBDP.uiPCIndexShift = 0;
388 sRGXMMUDevVAddrConfig_64KBDP.uiNumEntriesPC = 0;
390 sRGXMMUDevVAddrConfig_64KBDP.uiPDIndexMask = 0;
391 sRGXMMUDevVAddrConfig_64KBDP.uiPDIndexShift = 0;
392 sRGXMMUDevVAddrConfig_64KBDP.uiNumEntriesPD = 0;
394 sRGXMMUDevVAddrConfig_64KBDP.uiPTIndexMask = 0;
395 sRGXMMUDevVAddrConfig_64KBDP.uiPTIndexShift = 0;
396 sRGXMMUDevVAddrConfig_64KBDP.uiNumEntriesPT = 0;
398 sRGXMMUDevVAddrConfig_64KBDP.uiPageOffsetMask = 0;
399 sRGXMMUDevVAddrConfig_64KBDP.uiPageOffsetShift = 0;
400 sRGXMMUDevVAddrConfig_64KBDP.uiOffsetInBytes = 0;
403 * Setup gsPageSizeConfig64KB.
405 gsPageSizeConfig64KB.psPDEConfig = &sRGXMMUPDEConfig_64KBDP;
406 gsPageSizeConfig64KB.psPTEConfig = &sRGXMMUPTEConfig_64KBDP;
407 gsPageSizeConfig64KB.psDevVAddrConfig = &sRGXMMUDevVAddrConfig_64KBDP;
408 gsPageSizeConfig64KB.uiRefCount = 0;
409 gsPageSizeConfig64KB.uiMaxRefCount = 0;
414 * Configuration for heaps with 256kB Data-Page size. Not supported yet
419 * Setup sRGXMMUPDEConfig_256KBDP
421 sRGXMMUPDEConfig_256KBDP.uiBytesPerEntry = 0;
423 sRGXMMUPDEConfig_256KBDP.uiAddrMask = 0;
424 sRGXMMUPDEConfig_256KBDP.uiAddrShift = 0;
425 sRGXMMUPDEConfig_256KBDP.uiAddrLog2Align = 0;
427 sRGXMMUPDEConfig_256KBDP.uiVarCtrlMask = 0;
428 sRGXMMUPDEConfig_256KBDP.uiVarCtrlShift = 0;
430 sRGXMMUPDEConfig_256KBDP.uiProtMask = 0;
431 sRGXMMUPDEConfig_256KBDP.uiProtShift = 0;
433 sRGXMMUPDEConfig_256KBDP.uiValidEnMask = 0;
434 sRGXMMUPDEConfig_256KBDP.uiValidEnShift = 0;
437 * Setup MMU_PxE_CONFIG sRGXMMUPTEConfig_256KBDP
439 sRGXMMUPTEConfig_256KBDP.uiBytesPerEntry = 0;
441 sRGXMMUPTEConfig_256KBDP.uiAddrMask = 0;
442 sRGXMMUPTEConfig_256KBDP.uiAddrShift = 0;
443 sRGXMMUPTEConfig_256KBDP.uiAddrLog2Align = 0;
445 sRGXMMUPTEConfig_256KBDP.uiProtMask = 0;
446 sRGXMMUPTEConfig_256KBDP.uiProtShift = 0;
448 sRGXMMUPTEConfig_256KBDP.uiValidEnMask = 0;
449 sRGXMMUPTEConfig_256KBDP.uiValidEnShift = 0;
452 * Setup sRGXMMUDevVAddrConfig_256KBDP
454 sRGXMMUDevVAddrConfig_256KBDP.uiPCIndexMask = 0;
455 sRGXMMUDevVAddrConfig_256KBDP.uiPCIndexShift = 0;
456 sRGXMMUDevVAddrConfig_256KBDP.uiNumEntriesPC = 0;
458 sRGXMMUDevVAddrConfig_256KBDP.uiPDIndexMask = 0;
459 sRGXMMUDevVAddrConfig_256KBDP.uiPDIndexShift = 0;
460 sRGXMMUDevVAddrConfig_256KBDP.uiNumEntriesPD = 0;
462 sRGXMMUDevVAddrConfig_256KBDP.uiPTIndexMask = 0;
463 sRGXMMUDevVAddrConfig_256KBDP.uiPTIndexShift = 0;
464 sRGXMMUDevVAddrConfig_256KBDP.uiNumEntriesPT = 0;
466 sRGXMMUDevVAddrConfig_256KBDP.uiPageOffsetMask = 0;
467 sRGXMMUDevVAddrConfig_256KBDP.uiPageOffsetShift = 0;
468 sRGXMMUDevVAddrConfig_256KBDP.uiOffsetInBytes = 0;
471 * Setup gsPageSizeConfig256KB
473 gsPageSizeConfig256KB.psPDEConfig = &sRGXMMUPDEConfig_256KBDP;
474 gsPageSizeConfig256KB.psPTEConfig = &sRGXMMUPTEConfig_256KBDP;
475 gsPageSizeConfig256KB.psDevVAddrConfig = &sRGXMMUDevVAddrConfig_256KBDP;
476 gsPageSizeConfig256KB.uiRefCount = 0;
477 gsPageSizeConfig256KB.uiMaxRefCount = 0;
480 * Setup sRGXMMUPDEConfig_1MBDP. Not supported yet
482 sRGXMMUPDEConfig_1MBDP.uiBytesPerEntry = 0;
484 sRGXMMUPDEConfig_1MBDP.uiAddrMask = 0;
485 sRGXMMUPDEConfig_1MBDP.uiAddrShift = 0;
486 sRGXMMUPDEConfig_1MBDP.uiAddrLog2Align = 0;
488 sRGXMMUPDEConfig_1MBDP.uiVarCtrlMask = 0;
489 sRGXMMUPDEConfig_1MBDP.uiVarCtrlShift = 0;
491 sRGXMMUPDEConfig_1MBDP.uiProtMask = 0;
492 sRGXMMUPDEConfig_1MBDP.uiProtShift = 0;
494 sRGXMMUPDEConfig_1MBDP.uiValidEnMask = 0;
495 sRGXMMUPDEConfig_1MBDP.uiValidEnShift = 0;
498 * Setup sRGXMMUPTEConfig_1MBDP
500 sRGXMMUPTEConfig_1MBDP.uiBytesPerEntry = 8;
502 sRGXMMUPTEConfig_1MBDP.uiAddrMask = 0;
503 sRGXMMUPTEConfig_1MBDP.uiAddrShift = 0;
504 sRGXMMUPTEConfig_1MBDP.uiAddrLog2Align = 0;
506 sRGXMMUPTEConfig_1MBDP.uiProtMask = 0;
507 sRGXMMUPTEConfig_1MBDP.uiProtShift = 0;
509 sRGXMMUPTEConfig_1MBDP.uiValidEnMask = 0;
510 sRGXMMUPTEConfig_1MBDP.uiValidEnShift = 0;
513 * Setup sRGXMMUDevVAddrConfig_1MBDP
515 sRGXMMUDevVAddrConfig_1MBDP.uiPCIndexMask = 0;
516 sRGXMMUDevVAddrConfig_1MBDP.uiPCIndexShift = 0;
517 sRGXMMUDevVAddrConfig_1MBDP.uiNumEntriesPC = 0;
519 sRGXMMUDevVAddrConfig_1MBDP.uiPDIndexMask = 0;
520 sRGXMMUDevVAddrConfig_1MBDP.uiPDIndexShift = 0;
521 sRGXMMUDevVAddrConfig_1MBDP.uiNumEntriesPD = 0;
523 sRGXMMUDevVAddrConfig_1MBDP.uiPTIndexMask = 0;
524 sRGXMMUDevVAddrConfig_1MBDP.uiPTIndexShift = 0;
525 sRGXMMUDevVAddrConfig_1MBDP.uiNumEntriesPT = 0;
527 sRGXMMUDevVAddrConfig_1MBDP.uiPageOffsetMask = 0;
528 sRGXMMUDevVAddrConfig_1MBDP.uiPageOffsetShift = 0;
529 sRGXMMUDevVAddrConfig_1MBDP.uiOffsetInBytes = 0;
532 * Setup gsPageSizeConfig1MB
534 gsPageSizeConfig1MB.psPDEConfig = &sRGXMMUPDEConfig_1MBDP;
535 gsPageSizeConfig1MB.psPTEConfig = &sRGXMMUPTEConfig_1MBDP;
536 gsPageSizeConfig1MB.psDevVAddrConfig = &sRGXMMUDevVAddrConfig_1MBDP;
537 gsPageSizeConfig1MB.uiRefCount = 0;
538 gsPageSizeConfig1MB.uiMaxRefCount = 0;
541 * Setup sRGXMMUPDEConfig_2MBDP. Not supported yet
543 sRGXMMUPDEConfig_2MBDP.uiBytesPerEntry = 0;
545 sRGXMMUPDEConfig_2MBDP.uiAddrMask = 0;
546 sRGXMMUPDEConfig_2MBDP.uiAddrShift = 0;
547 sRGXMMUPDEConfig_2MBDP.uiAddrLog2Align = 0;
549 sRGXMMUPDEConfig_2MBDP.uiVarCtrlMask = 0;
550 sRGXMMUPDEConfig_2MBDP.uiVarCtrlShift = 0;
552 sRGXMMUPDEConfig_2MBDP.uiProtMask = 0;
553 sRGXMMUPDEConfig_2MBDP.uiProtShift = 0;
555 sRGXMMUPDEConfig_2MBDP.uiValidEnMask = 0;
556 sRGXMMUPDEConfig_2MBDP.uiValidEnShift = 0;
559 * Setup sRGXMMUPTEConfig_2MBDP
561 sRGXMMUPTEConfig_2MBDP.uiBytesPerEntry = 0;
563 sRGXMMUPTEConfig_2MBDP.uiAddrMask = 0;
564 sRGXMMUPTEConfig_2MBDP.uiAddrShift = 0;
565 sRGXMMUPTEConfig_2MBDP.uiAddrLog2Align = 0;
567 sRGXMMUPTEConfig_2MBDP.uiProtMask = 0;
568 sRGXMMUPTEConfig_2MBDP.uiProtShift = 0;
570 sRGXMMUPTEConfig_2MBDP.uiValidEnMask = 0;
571 sRGXMMUPTEConfig_2MBDP.uiValidEnShift = 0;
574 * Setup sRGXMMUDevVAddrConfig_2MBDP
576 sRGXMMUDevVAddrConfig_2MBDP.uiPCIndexMask = 0;
577 sRGXMMUDevVAddrConfig_2MBDP.uiPCIndexShift = 0;
578 sRGXMMUDevVAddrConfig_2MBDP.uiNumEntriesPC = 0;
580 sRGXMMUDevVAddrConfig_2MBDP.uiPDIndexMask = 0;
581 sRGXMMUDevVAddrConfig_2MBDP.uiPDIndexShift = 0;
582 sRGXMMUDevVAddrConfig_2MBDP.uiNumEntriesPD = 0;
584 sRGXMMUDevVAddrConfig_2MBDP.uiPTIndexMask = 0;
585 sRGXMMUDevVAddrConfig_2MBDP.uiPTIndexShift = 0;
586 sRGXMMUDevVAddrConfig_2MBDP.uiNumEntriesPT = 0;
588 sRGXMMUDevVAddrConfig_2MBDP.uiPageOffsetMask = 0;
589 sRGXMMUDevVAddrConfig_2MBDP.uiPageOffsetShift = 0;
590 sRGXMMUDevVAddrConfig_2MBDP.uiOffsetInBytes = 0;
593 * Setup gsPageSizeConfig2MB
595 gsPageSizeConfig2MB.psPDEConfig = &sRGXMMUPDEConfig_2MBDP;
596 gsPageSizeConfig2MB.psPTEConfig = &sRGXMMUPTEConfig_2MBDP;
597 gsPageSizeConfig2MB.psDevVAddrConfig = &sRGXMMUDevVAddrConfig_2MBDP;
598 gsPageSizeConfig2MB.uiRefCount = 0;
599 gsPageSizeConfig2MB.uiMaxRefCount = 0;
602 * Setup sRGXMMUDeviceAttributes
604 sRGXMMUDeviceAttributes.eMMUType = PDUMP_MMU_TYPE_MIPS_MICROAPTIV;
605 sRGXMMUDeviceAttributes.eTopLevel = MMU_LEVEL_1;
606 /* The page table fits in one big physical page as big as the page table itself */
607 sRGXMMUDeviceAttributes.ui32BaseAlign = RGXMIPSFW_LOG2_PAGETABLE_PAGE_SIZE;
608 /* The base configuration is set to 4kB pages*/
609 sRGXMMUDeviceAttributes.psBaseConfig = &sRGXMMUPTEConfig_4KBDP;
610 sRGXMMUDeviceAttributes.psTopLevelDevVAddrConfig = &sRGXMMUTopLevelDevVAddrConfig;
612 /* Functions for deriving page table/dir/cat protection bits */
613 sRGXMMUDeviceAttributes.pfnDerivePCEProt8 = RGXDerivePCEProt8;
614 sRGXMMUDeviceAttributes.pfnDerivePCEProt4 = RGXDerivePCEProt4;
615 sRGXMMUDeviceAttributes.pfnDerivePDEProt8 = RGXDerivePDEProt8;
616 sRGXMMUDeviceAttributes.pfnDerivePDEProt4 = RGXDerivePDEProt4;
617 sRGXMMUDeviceAttributes.pfnDerivePTEProt8 = RGXDerivePTEProt8;
618 sRGXMMUDeviceAttributes.pfnDerivePTEProt4 = RGXDerivePTEProt4;
620 /* Functions for establishing configurations for PDE/PTE/DEVVADDR
622 sRGXMMUDeviceAttributes.pfnGetPageSizeConfiguration = RGXGetPageSizeConfigCB;
623 sRGXMMUDeviceAttributes.pfnPutPageSizeConfiguration = RGXPutPageSizeConfigCB;
625 sRGXMMUDeviceAttributes.pfnGetPageSizeFromPDE4 = RGXGetPageSizeFromPDE4;
626 sRGXMMUDeviceAttributes.pfnGetPageSizeFromPDE8 = RGXGetPageSizeFromPDE8;
628 psDeviceNode->psFirmwareMMUDevAttrs = &sRGXMMUDeviceAttributes;
633 PVRSRV_ERROR RGXMipsMMUInit_Unregister(PVRSRV_DEVICE_NODE *psDeviceNode)
640 psDeviceNode->pfnMMUGetContextID = NULL;
643 psDeviceNode->psFirmwareMMUDevAttrs = NULL;
646 PVR_DPF((PVR_DBG_MESSAGE, "Variable Page Size Heap Stats:"));
647 PVR_DPF((PVR_DBG_MESSAGE, "Max 4K page heaps: %d",
648 gsPageSizeConfig4KB.uiMaxRefCount));
649 PVR_DPF((PVR_DBG_VERBOSE, "Current 4K page heaps (should be 0): %d",
650 gsPageSizeConfig4KB.uiRefCount));
651 PVR_DPF((PVR_DBG_MESSAGE, "Max 16K page heaps: %d",
652 gsPageSizeConfig16KB.uiMaxRefCount));
653 PVR_DPF((PVR_DBG_VERBOSE, "Current 16K page heaps (should be 0): %d",
654 gsPageSizeConfig16KB.uiRefCount));
655 PVR_DPF((PVR_DBG_MESSAGE, "Max 64K page heaps: %d",
656 gsPageSizeConfig64KB.uiMaxRefCount));
657 PVR_DPF((PVR_DBG_VERBOSE, "Current 64K page heaps (should be 0): %d",
658 gsPageSizeConfig64KB.uiRefCount));
659 PVR_DPF((PVR_DBG_MESSAGE, "Max 256K page heaps: %d",
660 gsPageSizeConfig256KB.uiMaxRefCount));
661 PVR_DPF((PVR_DBG_VERBOSE, "Current 256K page heaps (should be 0): %d",
662 gsPageSizeConfig256KB.uiRefCount));
663 PVR_DPF((PVR_DBG_MESSAGE, "Max 1M page heaps: %d",
664 gsPageSizeConfig1MB.uiMaxRefCount));
665 PVR_DPF((PVR_DBG_VERBOSE, "Current 1M page heaps (should be 0): %d",
666 gsPageSizeConfig1MB.uiRefCount));
667 PVR_DPF((PVR_DBG_MESSAGE, "Max 2M page heaps: %d",
668 gsPageSizeConfig2MB.uiMaxRefCount));
669 PVR_DPF((PVR_DBG_VERBOSE, "Current 2M page heaps (should be 0): %d",
670 gsPageSizeConfig2MB.uiRefCount));
672 if (gsPageSizeConfig4KB.uiRefCount > 0 ||
673 gsPageSizeConfig16KB.uiRefCount > 0 ||
674 gsPageSizeConfig64KB.uiRefCount > 0 ||
675 gsPageSizeConfig256KB.uiRefCount > 0 ||
676 gsPageSizeConfig1MB.uiRefCount > 0 ||
677 gsPageSizeConfig2MB.uiRefCount > 0
680 PVR_DPF((PVR_DBG_ERROR, "RGXMMUInit_Unregister: Unbalanced MMU API Usage (Internal error)"));
686 /*************************************************************************/ /*!
687 @Function RGXDerivePCEProt4
688 @Description calculate the PCE protection flags based on a 4 byte entry
690 */ /**************************************************************************/
691 static IMG_UINT32 RGXDerivePCEProt4(IMG_UINT32 uiProtFlags)
693 PVR_DPF((PVR_DBG_ERROR, "Page Catalog not supported on MIPS MMU"));
698 /*************************************************************************/ /*!
699 @Function RGXDerivePCEProt8
700 @Description calculate the PCE protection flags based on an 8 byte entry
702 */ /**************************************************************************/
703 static IMG_UINT64 RGXDerivePCEProt8(IMG_UINT32 uiProtFlags, IMG_UINT32 uiLog2DataPageSize)
705 PVR_UNREFERENCED_PARAMETER(uiProtFlags);
706 PVR_UNREFERENCED_PARAMETER(uiLog2DataPageSize);
708 PVR_DPF((PVR_DBG_ERROR, "Page Catalog not supported on MIPS MMU"));
713 /*************************************************************************/ /*!
714 @Function RGXDerivePDEProt4
715 @Description derive the PDE protection flags based on a 4 byte entry
717 */ /**************************************************************************/
718 static IMG_UINT32 RGXDerivePDEProt4(IMG_UINT32 uiProtFlags)
720 PVR_UNREFERENCED_PARAMETER(uiProtFlags);
721 PVR_DPF((PVR_DBG_ERROR, "Page Directory not supported on MIPS MMU"));
726 /*************************************************************************/ /*!
727 @Function RGXDerivePDEProt8
728 @Description derive the PDE protection flags based on an 8 byte entry
730 @Input uiLog2DataPageSize The log2 of the required page size.
731 E.g, for 4KiB pages, this parameter must be 12.
732 For 2MiB pages, it must be set to 21.
735 */ /**************************************************************************/
736 static IMG_UINT64 RGXDerivePDEProt8(IMG_UINT32 uiProtFlags, IMG_UINT32 uiLog2DataPageSize)
738 PVR_UNREFERENCED_PARAMETER(uiProtFlags);
739 PVR_DPF((PVR_DBG_ERROR, "Page Directory not supported on MIPS MMU"));
744 /*************************************************************************/ /*!
745 @Function RGXDerivePTEProt4
746 @Description calculate the PTE protection flags based on a 4 byte entry
748 */ /**************************************************************************/
749 static IMG_UINT32 RGXDerivePTEProt4(IMG_UINT32 uiProtFlags)
751 IMG_UINT32 ui32MMUFlags = 0;
753 if(((MMU_PROTFLAGS_READABLE|MMU_PROTFLAGS_WRITEABLE) & uiProtFlags) == (MMU_PROTFLAGS_READABLE|MMU_PROTFLAGS_WRITEABLE))
756 ui32MMUFlags |= RGX_MIPS_MMUCTRL_PT_DATA_WRITABLE_EN;
758 else if(MMU_PROTFLAGS_READABLE & uiProtFlags)
762 else if(MMU_PROTFLAGS_WRITEABLE & uiProtFlags)
765 ui32MMUFlags |= RGX_MIPS_MMUCTRL_PT_DATA_READ_INHIBIT_EN;
767 else if ((MMU_PROTFLAGS_INVALID & uiProtFlags) == 0)
769 PVR_DPF((PVR_DBG_ERROR, "RGXDerivePTEProt4: neither read nor write specified..."));
772 /* cache coherency */
773 if(MMU_PROTFLAGS_CACHE_COHERENT & uiProtFlags)
775 PVR_DPF((PVR_DBG_ERROR, "RGXDerivePTEProt4: cache coherency not supported for MIPS caches"));
779 if ((MMU_PROTFLAGS_CACHED & uiProtFlags) == 0)
781 ui32MMUFlags |= (RGX_MIPS_MMUCTRL_PT_UNCACHED_POLICY <<
782 RGX_MIPS_MMUCTRL_PT_CACHE_POLICY_SHIFT);
786 ui32MMUFlags |= (RGX_MIPS_MMUCTRL_PT_CACHED_POLICY <<
787 RGX_MIPS_MMUCTRL_PT_CACHE_POLICY_SHIFT);
790 if ((uiProtFlags & MMU_PROTFLAGS_INVALID) == 0)
792 ui32MMUFlags |= RGX_MIPS_MMUCTRL_PT_DATA_VALID_EN;
793 ui32MMUFlags |= RGX_MIPS_MMUCTRL_PT_DATA_GLOBAL_EN;
796 if (MMU_PROTFLAGS_DEVICE(PMMETA_PROTECT) & uiProtFlags)
798 /* PVR_DPF((PVR_DBG_WARNING, "RGXDerivePTEProt4: PMMETA Protect not existent for MIPS, option discarded")); */
804 /*************************************************************************/ /*!
805 @Function RGXDerivePTEProt8
806 @Description calculate the PTE protection flags based on an 8 byte entry
808 */ /**************************************************************************/
809 static IMG_UINT64 RGXDerivePTEProt8(IMG_UINT32 uiProtFlags, IMG_UINT32 uiLog2DataPageSize)
811 PVR_UNREFERENCED_PARAMETER(uiProtFlags);
812 PVR_UNREFERENCED_PARAMETER(uiLog2DataPageSize);
814 PVR_DPF((PVR_DBG_ERROR, "8-byte PTE not supported on this device"));
820 /*************************************************************************/ /*!
821 @Function RGXGetPageSizeConfig
822 @Description Set up configuration for variable sized data pages.
823 RGXPutPageSizeConfigCB has to be called to ensure correct
826 */ /**************************************************************************/
827 static PVRSRV_ERROR RGXGetPageSizeConfigCB(IMG_UINT32 uiLog2DataPageSize,
828 const MMU_PxE_CONFIG **ppsMMUPDEConfig,
829 const MMU_PxE_CONFIG **ppsMMUPTEConfig,
830 const MMU_DEVVADDR_CONFIG **ppsMMUDevVAddrConfig,
833 MMU_PAGESIZECONFIG *psPageSizeConfig;
835 switch (uiLog2DataPageSize)
837 case RGXMIPSFW_LOG2_PAGE_SIZE:
838 psPageSizeConfig = &gsPageSizeConfig4KB;
841 PVR_DPF((PVR_DBG_ERROR,
842 "RGXGetPageSizeConfigCB: Invalid Data Page Size 1<<0x%x",
843 uiLog2DataPageSize));
844 return PVRSRV_ERROR_MMU_INVALID_PAGE_SIZE_FOR_DEVICE;
847 /* Refer caller's pointers to the data */
848 *ppsMMUPDEConfig = psPageSizeConfig->psPDEConfig;
849 *ppsMMUPTEConfig = psPageSizeConfig->psPTEConfig;
850 *ppsMMUDevVAddrConfig = psPageSizeConfig->psDevVAddrConfig;
852 #if defined(SUPPORT_MMU_PAGESIZECONFIG_REFCOUNT)
853 /* Increment ref-count - not that we're allocating anything here
854 (I'm using static structs), but one day we might, so we want
855 the Get/Put code to be balanced properly */
856 psPageSizeConfig->uiRefCount ++;
858 /* This is purely for debug statistics */
859 psPageSizeConfig->uiMaxRefCount = MAX(psPageSizeConfig->uiMaxRefCount,
860 psPageSizeConfig->uiRefCount);
863 *phPriv = (IMG_HANDLE)(uintptr_t)uiLog2DataPageSize;
864 PVR_ASSERT (uiLog2DataPageSize == (IMG_UINT32)(uintptr_t)*phPriv);
869 /*************************************************************************/ /*!
870 @Function RGXPutPageSizeConfig
871 @Description Tells this code that the mmu module is done with the
872 configurations set in RGXGetPageSizeConfig. This can
874 Called after RGXGetPageSizeConfigCB.
876 */ /**************************************************************************/
877 static PVRSRV_ERROR RGXPutPageSizeConfigCB(IMG_HANDLE hPriv)
879 #if defined(SUPPORT_MMU_PAGESIZECONFIG_REFCOUNT)
880 MMU_PAGESIZECONFIG *psPageSizeConfig;
881 IMG_UINT32 uiLog2DataPageSize;
883 uiLog2DataPageSize = (IMG_UINT32)(uintptr_t) hPriv;
885 switch (uiLog2DataPageSize)
887 case RGXMIPSFW_LOG2_PAGE_SIZE:
888 psPageSizeConfig = &gsPageSizeConfig4KB;
891 PVR_DPF((PVR_DBG_ERROR,
892 "RGXPutPageSizeConfigCB: Invalid Data Page Size 1<<0x%x",
893 uiLog2DataPageSize));
894 return PVRSRV_ERROR_MMU_INVALID_PAGE_SIZE_FOR_DEVICE;
897 /* Ref-count here is not especially useful, but it's an extra
898 check that the API is being used correctly */
899 psPageSizeConfig->uiRefCount --;
901 PVR_UNREFERENCED_PARAMETER(hPriv);
906 static PVRSRV_ERROR RGXGetPageSizeFromPDE4(IMG_UINT32 ui32PDE, IMG_UINT32 *pui32Log2PageSize)
908 PVR_UNREFERENCED_PARAMETER(ui32PDE);
909 PVR_UNREFERENCED_PARAMETER(pui32Log2PageSize);
910 PVR_DPF((PVR_DBG_ERROR, "PDE not supported on MIPS"));
911 return PVRSRV_ERROR_MMU_INVALID_PAGE_SIZE_FOR_DEVICE;
914 static PVRSRV_ERROR RGXGetPageSizeFromPDE8(IMG_UINT64 ui64PDE, IMG_UINT32 *pui32Log2PageSize)
916 PVR_UNREFERENCED_PARAMETER(ui64PDE);
917 PVR_UNREFERENCED_PARAMETER(pui32Log2PageSize);
918 PVR_DPF((PVR_DBG_ERROR, "PDE not supported on MIPS"));
919 return PVRSRV_ERROR_MMU_INVALID_PAGE_SIZE_FOR_DEVICE;