This discussion has been locked.
You can no longer post new replies to this discussion. If you have a question you can start a new discussion

Memory Protection Unit in Keil IDE debugger not working

Hello I have a question regarding MPU and uKeil.

So basically I have following piece of code for testing read only permission:

static uint32_t test[128] __attribute__((aligned(32)));

static void test_mpu(void){
	MPU->RNR  = 0;                             
	MPU->RBAR = (uint32_t)test;               
	MPU->RASR = (MPU_AP_RO<<MPU_AP_Pos) | (MPU_ATTR_SRAM<<MPU_ATTR_Pos) | (MPU_REGION_SIZE_32b<<MPU_SIZE_Pos) | MPU_ENABLE;
	SCB->SHCSR |= SCB_SHCSR_MEMFAULTENA_Msk;
	MPU->CTRL = 0x05;                          
	
	test[0] = 0x99; /** trigger fault */
}

void MemoryManagement_Handler(void){
  uint32_t i = 0;
  while(1){
    __asm("bkpt 1");
    ++i;
  }
}

And the problem it doesn't trigger any fault, but the thing that confuse me, is that when I upload the same code using segger embedded studio everything is working fine, I end up in mem handler with address in MMFAR register.

So do I have to do some additional settings configuration in keil debugger itself or there's another way to fix this, because I prefer Keil over SES and don't really want switch to this second one.

Also I'm using nrf52840 with cortex m4 cpu and j-link.

Thanks in advance for any thoughts.

Parents
  • Hi bursztyn12,

    I have tried your code, and I have observed 2 things.

    1. Because your test variable was not specified as volatile, Arm Compiler at optimization level O3 did not even store the value to the memory it just had it in a register. You can force the write access by specifying test to be volatile:

    static volatile uint32_t test[128] __attribute__((aligned(32)));
    

    2. When single stepping with J-Link on board debugger the memory fault was not triggered, however if I just run the code with the debugger then the memory fault was triggered.

    Best regards, Milorad

Reply
  • Hi bursztyn12,

    I have tried your code, and I have observed 2 things.

    1. Because your test variable was not specified as volatile, Arm Compiler at optimization level O3 did not even store the value to the memory it just had it in a register. You can force the write access by specifying test to be volatile:

    static volatile uint32_t test[128] __attribute__((aligned(32)));
    

    2. When single stepping with J-Link on board debugger the memory fault was not triggered, however if I just run the code with the debugger then the memory fault was triggered.

    Best regards, Milorad

Children