diff --git a/arch/arm64/src/common/arm64_mmu.c b/arch/arm64/src/common/arm64_mmu.c index cc0837d8f57..d4703cf379c 100644 --- a/arch/arm64/src/common/arm64_mmu.c +++ b/arch/arm64/src/common/arm64_mmu.c @@ -142,7 +142,9 @@ #define BASE_XLAT_TABLE_ALIGN NUM_BASE_LEVEL_ENTRIES * sizeof(uint64_t) #endif -#if (CONFIG_ARM64_PA_BITS == 48) +#if (CONFIG_ARM64_PA_BITS == 52) +#define TCR_PS_BITS TCR_PS_BITS_4PB +#elif (CONFIG_ARM64_PA_BITS == 48) #define TCR_PS_BITS TCR_PS_BITS_256TB #elif (CONFIG_ARM64_PA_BITS == 44) #define TCR_PS_BITS TCR_PS_BITS_16TB @@ -267,6 +269,10 @@ static uint64_t get_tcr(int el) tcr |= TCR_TG0_4K | TCR_SHARED_INNER | TCR_ORGN_WBWA | TCR_IRGN_WBWA | TCR_TBI_FLAGS; +#if (CONFIG_ARM64_PA_BITS == 52) + tcr |= TCR_DS; +#endif + return tcr; } @@ -487,7 +493,8 @@ static void init_xlat_tables(const struct arm_mmu_region *region) level_size = 1ULL << LEVEL_TO_VA_SIZE_SHIFT(level); - if (size >= level_size && !(virt & (level_size - 1))) + if (size >= level_size && !(virt & (level_size - 1)) + && ((level == 0 && CONFIG_ARM64_PA_BITS == 52) || level != 0)) { /* Given range fits into level size, * create block/page descriptor diff --git a/arch/arm64/src/common/arm64_mmu.h b/arch/arm64/src/common/arm64_mmu.h index 053f4f54239..68862f4fc6c 100644 --- a/arch/arm64/src/common/arm64_mmu.h +++ b/arch/arm64/src/common/arm64_mmu.h @@ -156,6 +156,7 @@ #define TCR_TG0_64K (1ULL << 14) #define TCR_TG0_16K (2ULL << 14) #define TCR_EPD1_DISABLE (1ULL << 23) +#define TCR_DS (1ULL << 59) #define TCR_AS_SHIFT 36U #define TCR_ASID_8 (0ULL << TCR_AS_SHIFT) @@ -181,6 +182,7 @@ #define TCR_PS_BITS_4TB 0x3ULL #define TCR_PS_BITS_16TB 0x4ULL #define TCR_PS_BITS_256TB 0x5ULL +#define TCR_PS_BITS_4PB 0x6ULL #define CTR_EL0_DMINLINE_SHIFT 16 #define CTR_EL0_DMINLINE_MASK BIT_MASK(4)