Penglai-Enclave-sPMP
Penglai-Enclave-sPMP copied to clipboard
For Penglai with OpenSBI-v1.0, pmp0 config for monitor protection.
For Penglai with OpenSBI-v1.0(under directory opensbi-1.0), pmp0 configuration for monitor protection is inaccurate. It now uses _fw_start and _fw_end to decide pmp0 configuration, which facilitates the migration on dev boards. Although they are set correctly(include the hole firmware) during build time, it seems _fw_start and _fw_end will be changed at boot time, which make this protection method incomplete.
hi, I also find here is an anothor issue. The pmp size calculated by _fw_end - _fw_start may not satisfy the requirement of 2 ^ power value, which is checked in set_pmp-->check_pmp_region_protectable. I made a forced alignment to the bigger 2 ^ power, but here may cause waste. If there any other method?
implementation
static unsigned long form_pmp_size(unsigned long pmp_size) {
int i;
// make lower bits all ones
// 0x00ee --> 0x00ff
for (i = 1; i <= 32; i = i << 1)
pmp_size |= (pmp_size >> i);
// return (0x00ff + 1) = 0x0100
return (pmp_size + 1);
}
reference
int platform_init()
{
struct pmp_config_t pmp_config;
//Clear pmp1, this pmp is reserved for allowing kernel
//to config page table for enclave in enclave's memory.
//There is no need to broadcast to other hart as every
//hart will execute this function.
//clear_pmp(1);
clear_pmp_and_sync(1);
//config the PMP 0 to protect security monitor
pmp_config.paddr = (uintptr_t)SM_BASE;
->pmp_config.size = form_pmp_size((unsigned long)SM_SIZE);
pmp_config.mode = PMP_A_NAPOT;
pmp_config.perm = PMP_NO_PERM;
set_pmp_and_sync(0, pmp_config);
//config the last PMP to allow kernel to access memory
pmp_config.paddr = 0;
pmp_config.size = -1UL;
pmp_config.mode = PMP_A_NAPOT;
pmp_config.perm = PMP_R | PMP_W | PMP_X;
//set_pmp(NPMP-1, pmp_config);
set_pmp_and_sync(NPMP-1, pmp_config);
printm("[Penglai Monitor@%s] setting initial PMP ready\r\n", __func__);
return 0;
}