Enabling Pretty Printing in VSCode for cortex-debug

Sooner or later if you're working with the Daisy development boards you're going to end up using some type which you can't easily see the values of with the breakpoint debugger. An example of these would be any of the std:: containers (standard caveats apply to using dynamic sized containers and the std lib on embedded devices).

Inspecting a std::string without pretty printing enabled looks something like this

That's not too helpful, although we can see the contents of the string in _M_dataplus _M_p it's not easy as once we have a larger string contents. For example the entire contents of a text file is not going to be possible to see.

We could go and inspect the memory since we have the address but again this is not very easy

Luckily GDB supports pretty printing variables using python, and it's quite easy to enable this. Unluckily the toolchain provided by Electrosmith was not compiled with Python support enabled so we're going to have to jump through some extra hoops to make it work.

Firstly we need to get an installation of the arm-non-eabi toolchain which has python support, we could of course compile it ourselves, but there are a lot of tools and a lot of headers and other things included with the toolchain, so it's much easier to get a pre-packaged version. The official arm versions of the toolchain also don't contain a copy of GDB compiled with Python, but luckily Xpack comes to the rescue here. You can find the install instructions for Xpack on their website https://xpack.github.io/dev-tools/arm-none-eabi-gcc/install/ I followed the manual install instructions as I didn't want/need to install their tool and I wanted to place the install inside the Daisy Toolchain folder. On OSX this is located at /Library/DaisyToolchain/0.2.0 and we need the toolchain to be in the arm subfolder. Since I want to keep the original toolchain, just incase, I renamed that folder to OLD-arm, and then installed the Xpack toolchain inside of the arm folder (actually I symlinked it from where I keep all my code, but that's un-necessary for most setups)

It's worth noting that this is upgrading your entire build toolchain, by default Daisy uses arm-non-eabi-gcc 10.3.1 and the current version of Xpack is 13.2.1. You can get old versions from the Xpack github releases page but so far I've not found any issues with using the newer version.

You'll see in the new version of the toolchain that we have a binary called arm-none-eabi-gdb-py3this is the version of the tool that is compiled with python support and which will let us pretty print, so what we need to do now is get VScode and cortex-debug to use this instead of the normal version. Luckily cortex-debug is very configurable so it's simple to do this. Just add

"gdbPath": "/Library/DaisyToolchain/0.2.0/arm/bin/arm-none-eabi-gdb-py3",

to your launch.json configuration for your project

At this point if you debug your project you would expect it to work, but unfortunately if you have a modern version of osx you're going to get into some issues with Gatekeeper because the Xpack toolchain is not signed.
Luckily this is easy to solve, just go to the toolchain directory in your terminal and remove the quarantine attribute from all the files by running
xattr -r -d com.apple.quarantine .

the -r flag will make it run recursively, so it should sort everything out with a single command.

At this point you should be up and running and able to debug your projects again. However pretty printing still isn't enabled yet, as there are a couple more steps to do. The gdb wiki explains these steps but essentially you need to clone the pretty printers repository using Subversion by running

svn co svn://gcc.gnu.org/svn/gcc/trunk/libstdc++-v3/python

and then you need to create a .gdbinit file in your Home ~/ folder which tells gdb to use them and where they are located. For example mine is as follows:

python
import sys
sys.path.insert(0, '/Users/twhiston/Code/gdb_printers')
from libstdcxx.v6.printers import register_libstdcxx_printers
register_libstdcxx_printers (None)
end

At this point when you start debugging pretty printing should "just work" so let's take a look at our fi object again and what we can see now

That's looking a lot better than it did before, and we can easily see the string contents.

Although string is a somewhat trivial example this setup makes a huge difference when we have more complex structures such as a vector (again caveats apply here, if you are using vectors you might want to look at managing memory yourself etc.). This is what a vector looks like before pretty printing

and this is after

I think we can all agree that the second version is much more useful for value debugging!