Assembly code breakpoint does not work as expected - debugging

I am developing a STM32F2 device using GCC 4.7.4 and a Lauterbach Combiprobe JTAG debugger. In my code, I have the following statement to always break at a certain spot for testing purposes:
asm volatile ("BKPT #0");
This is the only breakpoint. When I run the program, I can see that my program reaches the breakpoint, but I cannot step beyond this breakpoint using my JTAG debugger. Instead, I have to move the PC counter past this instruction to get the program to execute.
This was working in the past, but I am at a loss to figure out why the behavior is different now. Any clues or hints would be appreciated.

There are so many broken JTAG debuggers. Probably you installed an update for the JTAG adapter?
When you have GDB as Debugger you might check if you can add a macro set PC=PC+4 to a button or key. But if this is possible depends on your IDE.

There is no general rule what happens with the program counter if you have a breakpoint instruction in you application code. Some CPUs stop at the address containing the breakpoint instruction, others stop after the breakpoint instruction.
Since you use the tag "lauterbach" I assume you are using a TRACE32 debugger from Lauterbach.
If you think the debuggers behavior was different in the past, I think you should contact the Lauterbach support.
For now you can workaround the issue with the following TRACE32 command
Break.Set T:0x1000 /Program /CMD "Register.Set PP r(PP)+2"
(where 0x1000 stands for the address, where your BKPT instruction is located.)

Related

Cannot set breakpoints in AXI-SRAM on STM32CubeIDE for STM32H753

I'm working on a STM32H753 with STM32CubeIDE 1.4.0.
I have created an empty "STM32 Cortex-M C/C++ Application project". My executable is built by a separate makefile (arm-none-eabi-gcc based). I only use STM32CubeIDE to debug through a remote GDB server.
This setup has been working fine for a long time. Now I changed the memory mapping of my code. Before the code was executing from ITCM RAM and now I moved it to AXi-SRAM. Of course the code is copied from Flash to RAM by a kind of bootloader.
Now breakpoints seem to not work properly. They still work fine in the bootloader (in Flash) but as long as I set a bkpt in AXI SRAM the code doesn't stop. I checked that the assembly is correct. When I break in my code, I can see the correct assembly at the correct adress.
With the previous memory mapping, setting bkpt in ITCM RAM was working fine.
I tried to set bkpt through the GUI and through GDB commands it's the same.
Is there a particularity or a limitation regarding bkpt in AXI SRAM ?
thank you
I have had problems with breakpoints in RAM as soon as the application enables ICache (SCB_EnableICache). For debugging, I comment out that line of code so the ICache isn't enabled. For my setup (cube ide 1.8) this fixes the issue and I am able to set breakpoints and single step through code. For release candidate code, I use that call to enable the ICache.

Any way to set a breakpoint in GDB without stopping the target?

I'm using GDB (through an IDE) to debug an arm cortex microcontroller, and I've encountered an issue where the micro is halted briefly (for 10-20ms) whenever a breakpoint is set or cleared (not hit, but set, as in the code has not yet reached the breakpoint). This long of a pause can cause significant problems when driving an electric motor, for example.
The IDE has a debug console which shows that the GDB client is sending a SIGINT to the GDB server whenever I add or remove a breakpoint. I know that in the command-line client you have to use ctrl+c to interrupt the process to issue any command, but for modern microcontrollers (ARM cortex-m, etc.) it is not necessary to interrupt the processor to insert breakpoints, read memory, and in some cases to trace program execution. I am wondering if this is something that is being imposed by the GDB interface artificially.
Is there any way to create a new breakpoint without halting the target?
I have tried using "async" mode in GDB, but it informs me that I must halt the program to insert breakpoints. I have also verified that breakpoints can be set with the underlying debug server (OpenOCD) without halting, so in this case GDB is incorrect.
Any input is appreciated, and thanks in advance.

how to set a memory breakpoint in windbg kernel mode?

I would like to set a memory breakpoints on access in windbg in the kernel mode debugger
I want the debugger breaks everytime a specific module in usermode is hit with the kernel debugger.
but I've read somewhere its impossible to set it, in order to make a memory breakpoints I have to write a plugin to make it
I tried to use SDbgExt plugin with the !vprotect command, but it fails to set memory bp
If I have to write a plugin to allow memory bp in kernel mode It has to be a driver?
I've read some chapters in windows internals book, but it doesn't help me at all.
I couldn't find too much info how to start deal with it
You can set breakpoints on user mode addresses from kernel mode. The only thing you should take care is to switch to the right process with ".process /i " command
If it is a one-off breakpoint -- that is, you are content with process being destroyed by debugging -- zero out the entire module using e command (edit memory). Set the whole thing to cc (which is int 3 as far as I remember)... zeros will do as well. You will break as soon as you touch any of the module's code.
Next step, remember where you were (relative to the module) and set a proper breakpoint.
Hope that helps.
(editing) Do you have full symbols? If you do, did you try bm module!*
Sounds like you want to set a "breakpoint on access" but instead of specifying an address you want to specify a range? I have never seen it done in windbg. The BA breakpoints uses HW debug registers instead of inserting INTs like SW breakpoints so this is definitely HW platform specific.
I have done this on an ARM chipset once using a HW debugger. ETM on ARM allows you to set triggers on address ranges.

Breakpoints not being hit in remote linux kernel debugging using gdb

I am trying to remotely debug a linux kernel running on an arm cortex-a9 target using jtag probe and gdb.
I can connect to the kernel and halt it with gdb. I am able to set breakpoints in the kernel code and gdb confirms there placement as well but the problem is that once I start the execution and issue a continue command, the breakpoints are never hit and the kernel continues to run....
Please help me out in this regard.
Thanks.
As pointed in this thread, you should set the breakpoints as hardware breakpoints, namely - using the hbreak command. Only then the breakpoints will be hit.
For anyone reading this, the debugger will not break with software breakpoints by default, see the relevant doc:
"If the architecture that you are using supports the kernel option CONFIG_STRICT_KERNEL_RWX, you should consider turning it off. This option will prevent the use of software breakpoints because it marks certain regions of the kernel’s memory space as read-only. If kgdb supports it for the architecture you are using, you can use hardware breakpoints if you desire to run with the CONFIG_STRICT_KERNEL_RWX option turned on, else you need to turn off this option."
at https://www.kernel.org/doc/html/v4.14/dev-tools/kgdb.html
Disable RWX and recompile, then software breakpoints should work (they started working normally here after this)
Is some cases, KASLR (Kernel Address Space Layout Randomization) can be the culprit.
Even though you setup hbreak, the actual code location can be different from the address seen from the .elf file when using KASLR, so either pass --append "nokaslr" to the kernel boot argument, or configure the kernel with RANDOMIZE_BASE=n. This applies for arm64 and x86_64. (maybe other architectures too).

CodeWarrior for FreeScale trying to debug a simple program using the 56800E simulator

I'm just getting started learning FreeScale DSCs (MC56F800x series). I've done some work with AVRs using both AVR Studio on Windows and Eclipse and avr-gcc on Linux. CodeWarrior is just not as intuitive.
Right now I'm stuck trying to debug a simple program. I start the debugger using the built-in simulator, but it never reaches the first line of main(). Instead it seems to get stuck in some initialization code (MC56F8006_init.asm), specifically this line:
;; Loop until OCCS_STAT[LCK0] = 1
wait_for_lock:
brclr #OCCS_STAT_LCK0,x:>OCCS_STAT,wait_for_lock
I've let it run for quite a while and it never gets past this. It's obviously waiting for something, but what? You would think the simulator would just work... argh. Maybe there's some options I can change to make it pass this step?
I'm going to keep digging and will post an answer here if I find it first.
Updates:
Here's what I've found:
OCCS
On Chip Clock Synthesis
brclr
Branch if Bits Clear
The instruction loops until OCCS_STAT LCK0 is set. This register means the on-chip oscillator's PLL has locked (waits for clock stabilization).
I'm still not sure why the simulator spins forever on this line, and how I can solve this without resorting to hacking up the init code (which is part of the code library and not within my project).
I am not familiar with the part or the simulator, but it seems likely that the simulator is instruction-set-only and does not simulate the PLL hardware.
In most embedded development systems, the run-time startup code is provided as source and you could modify it (or rather make a local copy in your project and assemble and link that to override the default start-up). Alternately you could simply place a breakpoint in this loop, and advance the program-counter register to get it out of the loop. In many debuggers it is possible to attach a script to a breakpoint to do this automatically.

Resources