Hello Experts,
I have a problem with establishing the level 3 table in MMU for cortex-a53 processor. Level 1 and Level2 table works as expected but I need a 4KB memory block for my project. Below is the code that I wrote to configure the mmu. Could someone look at what is wrongly set so that the level 3 table is not configured correctly?
MOV x0, #0x44 /* Inner/outer cacheable WB */MSR mair_el3, x0/* Invalidate TLBs at the current exception level */TLBI alle3
/* RES1RES1PS 40-bitORGN0 outer WB no WA cacheableIRGN0 inner WB no WA cacheableT0SZ 39-bit region size */LDR x0, =(1 << 31) | (1 << 23) | (2 << 16) | (3 << 10) | (3 << | 25MSR tcr_el3, x0
/* Page table setup */
LDR x1, =ttb // Address of L1 table
//0x0000,0000 - 0x3FFF,FFFFLDR x2, =ttb1 // Get address of L2 tableMOV x0, #0x03 // Entry template for pointer to next level tableORR x0, x0, x2 // Combine template with L2 table Base addressSTR x0, [x1]
//0x4000,0000 - 0x7FFF,FFFFMOV x0, #0x405 // Entry templateORR x0, x0, #0x40000000 // 'OR' template with base physical addressSTR x0, [x1, #8]
LDR x1, =ttb1 // Address of L2 table
//0x0000,0000 - 0x2000,0000MOV x0, #0x401MOV x2, #0x1001:STR x0, [x1], #8ADD x0, x0, #0x200000 // Increment the physical address fieldSUB x2, x2, #1CBNZ x2, 1b
//0x2000,0000 - 0x3400,0000 (Fault)MOV x0, #0x0ORR x0, x0, #0x20000000 // 'OR' template with base physical addressMOV x2, #0xA01:STR x0, [x1], #8ADD x0, x0, #0x200000 // Increment the physical address fieldSUB x2, x2, #1CBNZ x2, 1b
//0x3400,0000 - 0x3480,0000 (SDRAM)
mov x0, #0x401MOV x6, #0x34000000ORR x0, x0, x6 // 'OR' template with base physical addressMOV x2, #21:STR x0, [x1], #8ADD x0, x0, #0x200000 // Increment the physical address fieldSUB x2, x2, #1CBNZ x2, 1b
LDR x2, =ttb2 // Get address of L3 tableMOV x0, #0x03 // Entry template for pointer to next level tableORR x0, x0, x2 // Combine template with L3 tableSTR x0, [x1]
MOV x0, #0x405 // Entry template
MOV x6, #0x34600000ORR x0, x0, x6 // 'OR' template with base physical addressSTR x0, [x1, #8]
LDR x1, =ttb2 // Address of L3 table
//0x3440,0000 - 0x3460,0000MOV x0, #0x401MOV x6, #0x34400000ORR x0, x0, x6 // 'OR' template with base physical addressMOV x2, #0x2001:STR x0, [x1], #8ADD x0, x0, #0x1000 // Increment the physical address fieldSUB x2, x2, #1CBNZ x2, 1bDSB SY
/* Ensure all translation table writes have drained into memory,the TLB invalidation is complete,and translation register writes are committed before enabling the MMU */DSB ISHISBLDR x0, =ttb // Address of L1 tableMSR ttbr0_el3, x0 // set TTBR
MRS x0, S3_1_c15_c2_1 // cpuectlr_el1ORR x0, x0, #0x40MSR S3_1_c15_c2_1, x0
MRS x0, sctlr_el3bic x0, x0, #(1 << 1) /* clear A, disable alignment fault check *//* I enable instruction cacheC enable data and unified cachesM enable EL3 MMU */LDR x1, =(1 << 12) | (1 << 2) | 1ORR x0, x0, x1 /* set bits */MSR sctlr_el3, x0/* Ensure the MMU enable takes effect immediately */ISB
When I use a configuration like presented above I have no access to variables that are configured to be located in the memory area starting from 0x3440,0000. When this region is configured with 2MB granulation it works correctly.
When you access the variables, does it notice any fault or exception? Could you please provide the specific memory map based on your design?
I have got a Synchronous exception but it is called when MMU is enabling. Memory mapping I want to achieve is:
0x0000,0000 - 0x1FFF,FFFF - accessable memory (CPU registers)
0x2000,0000 - 0x33FF,FFFF - Fault
0x3400,0000 - 0x343F,FFFF - SDRAM memory used for the code
0x3440,0000 - 0x3440,3FFF - SDRAM used for special data
0x3440,4000 - 0x3440,7FFF - SDRAM used for another special data
0x4000,0000 - 0x7FFF,FFFF - perypherial registers
I checked your code. Since the region from 0x3440000 is indexed at L3 table and each entry of L3 table is block descriptor, the lowest two bits is 0x11 (//0x3440,0000 - 0x3460,0000 MOV x0, #0x401, here, may change into 0x403). You can have a try and check if any other faults. Thanks.