mirror of https://github.com/acidanthera/audk.git
ArmPkg/ArmLib MMU: add functions to set/clear RO and XN bits on regions
Use the refactored UpdateRegionMapping () to traverse the translation tables, splitting block entries along the way if required, and apply a mask + or on each to set or clear the PXN/UXN/XN or RO bits. For now, the 32-bit ARM versions remain unimplemented. Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Ard Biesheuvel <ard.biesheuvel@linaro.org> Reviewed-by: Leif Lindholm <leif.lindholm@linaro.org> git-svn-id: https://svn.code.sf.net/p/edk2/code/trunk/edk2@18587 6f19259b-4bc3-4df7-8a09-765794883524
This commit is contained in:
parent
5ab77c6630
commit
4d9a4f62cf
|
@ -661,4 +661,28 @@ ArmUnsetCpuActlrBit (
|
||||||
IN UINTN Bits
|
IN UINTN Bits
|
||||||
);
|
);
|
||||||
|
|
||||||
|
RETURN_STATUS
|
||||||
|
ArmSetMemoryRegionNoExec (
|
||||||
|
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||||
|
IN UINT64 Length
|
||||||
|
);
|
||||||
|
|
||||||
|
RETURN_STATUS
|
||||||
|
ArmClearMemoryRegionNoExec (
|
||||||
|
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||||
|
IN UINT64 Length
|
||||||
|
);
|
||||||
|
|
||||||
|
RETURN_STATUS
|
||||||
|
ArmSetMemoryRegionReadOnly (
|
||||||
|
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||||
|
IN UINT64 Length
|
||||||
|
);
|
||||||
|
|
||||||
|
RETURN_STATUS
|
||||||
|
ArmClearMemoryRegionReadOnly (
|
||||||
|
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||||
|
IN UINT64 Length
|
||||||
|
);
|
||||||
|
|
||||||
#endif // __ARM_LIB__
|
#endif // __ARM_LIB__
|
||||||
|
|
|
@ -512,6 +512,96 @@ SetMemoryAttributes (
|
||||||
return RETURN_SUCCESS;
|
return RETURN_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
STATIC
|
||||||
|
RETURN_STATUS
|
||||||
|
SetMemoryRegionAttribute (
|
||||||
|
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||||
|
IN UINT64 Length,
|
||||||
|
IN UINT64 Attributes,
|
||||||
|
IN UINT64 BlockEntryMask
|
||||||
|
)
|
||||||
|
{
|
||||||
|
RETURN_STATUS Status;
|
||||||
|
UINT64 *RootTable;
|
||||||
|
|
||||||
|
RootTable = ArmGetTTBR0BaseAddress ();
|
||||||
|
|
||||||
|
Status = UpdateRegionMapping (RootTable, BaseAddress, Length, Attributes, BlockEntryMask);
|
||||||
|
if (RETURN_ERROR (Status)) {
|
||||||
|
return Status;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Invalidate all TLB entries so changes are synced
|
||||||
|
ArmInvalidateTlb ();
|
||||||
|
|
||||||
|
return RETURN_SUCCESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
RETURN_STATUS
|
||||||
|
ArmSetMemoryRegionNoExec (
|
||||||
|
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||||
|
IN UINT64 Length
|
||||||
|
)
|
||||||
|
{
|
||||||
|
UINT64 Val;
|
||||||
|
|
||||||
|
if (ArmReadCurrentEL () == AARCH64_EL1) {
|
||||||
|
Val = TT_PXN_MASK | TT_UXN_MASK;
|
||||||
|
} else {
|
||||||
|
Val = TT_XN_MASK;
|
||||||
|
}
|
||||||
|
|
||||||
|
return SetMemoryRegionAttribute (
|
||||||
|
BaseAddress,
|
||||||
|
Length,
|
||||||
|
Val,
|
||||||
|
~TT_ADDRESS_MASK_BLOCK_ENTRY);
|
||||||
|
}
|
||||||
|
|
||||||
|
RETURN_STATUS
|
||||||
|
ArmClearMemoryRegionNoExec (
|
||||||
|
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||||
|
IN UINT64 Length
|
||||||
|
)
|
||||||
|
{
|
||||||
|
UINT64 Mask;
|
||||||
|
|
||||||
|
// XN maps to UXN in the EL1&0 translation regime
|
||||||
|
Mask = ~(TT_ADDRESS_MASK_BLOCK_ENTRY | TT_PXN_MASK | TT_XN_MASK);
|
||||||
|
|
||||||
|
return SetMemoryRegionAttribute (
|
||||||
|
BaseAddress,
|
||||||
|
Length,
|
||||||
|
0,
|
||||||
|
Mask);
|
||||||
|
}
|
||||||
|
|
||||||
|
RETURN_STATUS
|
||||||
|
ArmSetMemoryRegionReadOnly (
|
||||||
|
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||||
|
IN UINT64 Length
|
||||||
|
)
|
||||||
|
{
|
||||||
|
return SetMemoryRegionAttribute (
|
||||||
|
BaseAddress,
|
||||||
|
Length,
|
||||||
|
TT_AP_RO_RO,
|
||||||
|
~TT_ADDRESS_MASK_BLOCK_ENTRY);
|
||||||
|
}
|
||||||
|
|
||||||
|
RETURN_STATUS
|
||||||
|
ArmClearMemoryRegionReadOnly (
|
||||||
|
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||||
|
IN UINT64 Length
|
||||||
|
)
|
||||||
|
{
|
||||||
|
return SetMemoryRegionAttribute (
|
||||||
|
BaseAddress,
|
||||||
|
Length,
|
||||||
|
TT_AP_NO_RO,
|
||||||
|
~(TT_ADDRESS_MASK_BLOCK_ENTRY | TT_AP_MASK));
|
||||||
|
}
|
||||||
|
|
||||||
RETURN_STATUS
|
RETURN_STATUS
|
||||||
EFIAPI
|
EFIAPI
|
||||||
ArmConfigureMmu (
|
ArmConfigureMmu (
|
||||||
|
|
|
@ -301,3 +301,39 @@ ArmConfigureMmu (
|
||||||
ArmEnableMmu();
|
ArmEnableMmu();
|
||||||
return RETURN_SUCCESS;
|
return RETURN_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
RETURN_STATUS
|
||||||
|
ArmSetMemoryRegionNoExec (
|
||||||
|
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||||
|
IN UINT64 Length
|
||||||
|
)
|
||||||
|
{
|
||||||
|
return RETURN_UNSUPPORTED;
|
||||||
|
}
|
||||||
|
|
||||||
|
RETURN_STATUS
|
||||||
|
ArmClearMemoryRegionNoExec (
|
||||||
|
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||||
|
IN UINT64 Length
|
||||||
|
)
|
||||||
|
{
|
||||||
|
return RETURN_UNSUPPORTED;
|
||||||
|
}
|
||||||
|
|
||||||
|
RETURN_STATUS
|
||||||
|
ArmSetMemoryRegionReadOnly (
|
||||||
|
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||||
|
IN UINT64 Length
|
||||||
|
)
|
||||||
|
{
|
||||||
|
return RETURN_UNSUPPORTED;
|
||||||
|
}
|
||||||
|
|
||||||
|
RETURN_STATUS
|
||||||
|
ArmClearMemoryRegionReadOnly (
|
||||||
|
IN EFI_PHYSICAL_ADDRESS BaseAddress,
|
||||||
|
IN UINT64 Length
|
||||||
|
)
|
||||||
|
{
|
||||||
|
return RETURN_UNSUPPORTED;
|
||||||
|
}
|
||||||
|
|
Loading…
Reference in New Issue