We are running a survey to help us improve the experience for all of our members. If you see the survey appear, please take the time to tell us about your experience if you can.
I haven't been able to get a watchpoint to work.
I'm playing with an STM32F4 series device and I'm using Atollic TrueSTUDIO for debugging.
I'd like to use a function for setting up a watchpoint, and I guess the debug events are handled right, because the breakpoints set via the IDE work fine,
but I haven't been able to get a watchpoint to work.
What am I missing?
(I seem to have problems with code-tags. I'll try to put the code tnto the next posting.)
#define DWT_ADDRESS 0xE0001000 #define DHCSR_ADDR 0xE000DEF0 #define DFSR_ADDR 0xE000ED30 #define DWT_CTRL (*((uint32_t *)DWT_ADDRESS)) #define DWT_COMP_0 (*((uint32_t *)DWT_ADDRESS + 0x20)) #define DWT_MASK_0 (*((uint32_t *)DWT_ADDRESS + 0x24)) #define DWT_FUNCTION_0 (*((uint32_t *)DWT_ADDRESS + 0x28)) #define DWT_COMP_1 (*((uint32_t *)DWT_ADDRESS + 0x20 + 1*16)) #define DWT_MASK_1 (*((uint32_t *)DWT_ADDRESS + 0x24 + 1*16)) #define DWT_FUNCTION_1 (*((uint32_t *)DWT_ADDRESS + 0x28 + 1*16)) #define DWT_DHCSR (*((uint32_t *)DHCSR_ADDR)) #define DWT_DEMCR (*((uint32_t *)DHCSR_ADDR + 12)) /* * address: within region * region_sz: region size as power of 2 * datasize: 0=none, 1 = byte, 2=half word, 3 = word * accessmode: 0 = none1 = RO, 2=WO, 3=RW * * if datasize = 0, then check for address only * if accessmode = 0, then remove watchpoint */ void set_watchpoint(uint32_t address, uint32_t region_sz, uint32_t data, uint8_t datasize, uint8_t accessmode) { uint32_t mask = 0; uint32_t tmp; tmp = DWT_DHCSR; tmp = DWT_DEMCR; if ((tmp & (1<<24)) == 0) // if TRACENA { DWT_DEMCR |= (1<<24); // DWT disabled, enable it } while(region_sz) { region_sz >>= 1; mask++; } /* address region to watch */ DWT_COMP_0 = address; DWT_MASK_0 = mask; if (datasize !=0) { /* address and data match used */ datasize -=1; DWT_FUNCTION_0 = 0; // DWT_COMP_0 is linked address comparator tmp = 0x0100; // data match + linked comparator 1 tmp |= (datasize << 10); DWT_COMP_1 = data; // DWT_COMP_1 is the data value comparator DWT_MASK_1 = 0; if (accessmode == 0) DWT_FUNCTION_1 = 0; else DWT_FUNCTION_1 = tmp | (4 + accessmode); } else { /* only address match used */ if (accessmode == 0) DWT_FUNCTION_0 = 0; else DWT_FUNCTION_0 = 4 + accessmode; } }
Some update:
I checked that in our system thread mode is privileged (by reading the CONTROL register). So accessing the debug registerd should be allowed.
Then I read the DHCSR and it was zero. DEMCR was also zero even after I tried to set the TRCENA-bit.
Any idea what keeps the TRCENA-bit low? The running debugger (SWD)?
To my understanding STM32F427 should have watchpoints implemented.
BTW, reading DWT_CTRL gives 0x40000000. Does this mean that the DWT is not locked?
And setting the TRACENA is refused for some other reason?