Debugging LPC4088 with VSCode and CMSIS-DAP

Hi

I wanted to try PlatformIO with the LPC4088 Quickstart Board. With the default platform.ini I was able to upload an example project successfully, but the board needed a reset to start running.

After some searching, and looking for similar solutions (LPC1768) I switched my upload config to cmsis-dap. That worked better, but gave deprecation warnings from pyOCD. Final step was the following config:

[env:lpc4088]
platform = npclxp
board = lpc4088
framework = mbed
upload_protocol = custom
upload_command = pyocd flash $SOURCE

; first debug try:
; debug_tool = cmsis-dap

; first debug try:
; debug_tool = custom
; debug_server = pyocd-gdbserver

Uploading works and the board starts automatically.

But I am unable to debug. When I run the debug configuration, it successfully builds the app, then the debugging toolbar disappears after a few seconds. I was not able to find error logs anywhere in VSCode.

What is the best way to debug the debugging configuration?

Best regards,
Christian

Per board documentation, debugging via the CMSIS-DAP is already the default.

This logic will cause the debug logic to execute pyocd-gdbserver.py -t lpc4088 to start the GDB server.

As a sanity check, you should thus first try and start the GDB server yourself. In a CLI, execute

python C:\Users\<user>\.platformio\packages\tool-pyocd\pyocd-gdbserver.py -t lpc4088 

If all goes well, it should output something like

0000825:WARNING:gdb_server:pyocd-gdbserver is deprecated; please use the new combined pyocd tool.
0001157:INFO:board:Target type is cortex_m
0001175:INFO:dap:DP IDR = 0x1ba01477 (v1 rev1)
0001178:INFO:ap:AHB-AP#0 IDR = 0x14770011 (AHB-AP var1 rev1)
0001185:INFO:rom_table:AHB-AP#0 Class 0x1 ROM table #0 @ 0xe00ff000 (designer=020 part=410)
0001187:INFO:rom_table:[0]<e000e000:SCS-M3 class=14 designer=43b part=000>
0001188:INFO:rom_table:[1]<e0001000:DWT class=14 designer=43b part=002>
0001190:INFO:rom_table:[2]<e0002000:FPB class=14 designer=43b part=003>
0001192:INFO:rom_table:[3]<e0000000:ITM class=14 designer=43b part=001>
0001194:INFO:rom_table:[4]<e0040000:TPIU-M3 class=9 designer=43b part=923 devtype=11 archid=0000 devid=ca0:0:0>
0001195:INFO:cortex_m:CPU core #0 is Cortex-M3 r1p1
0001200:INFO:dwt:4 hardware watchpoints
0001202:INFO:fpb:6 hardware breakpoints, 4 literal comparators
0001217:INFO:server:Semihost server started on port 4444 (core 0)
0001230:INFO:gdbserver:GDB server started on port 3333 (core 0)

(I’m using a STM32 chip for reference here).

If it fails, it’s interesting to see why.

Thanks for the hints. As it turns out, disabling all other VSCode extensions helped to get the debugger to start. It seems that the preDebug task simply died. I will investigate what extension caused it later.

It starts the debugging process successfully, but dies at a later stage after uploading the firmware and the reset of the MCU.

This is the normal output:

Preparing firmware for debugging...
Processing lpc4088 (platform: nxplpc; board: lpc4088; framework: mbed)
--------------------------------------------------------------------------------
Verbose mode can be enabled via `-v, --verbose` option
CONFIGURATION: https://docs.platformio.org/page/boards/nxplpc/lpc4088.html
PLATFORM: NXP LPC (7.0.0+sha.241dc20) > Embedded Artists LPC4088 QuickStart Board
HARDWARE: LPC4088 120MHz, 96KB RAM, 512KB Flash
DEBUG: Current (cmsis-dap) On-board (cmsis-dap) External (jlink)
PACKAGES: 
- framework-mbed 6.51506.201227 (5.15.6) 
- toolchain-gccarmnoneeabi 1.90201.191206 (9.2.1)
Collecting mbed sources...
LDF: Library Dependency Finder -> http://bit.ly/configure-pio-ldf
LDF Modes: Finder ~ chain, Compatibility ~ soft
Found 4 compatible libraries
Scanning dependencies...
No dependencies
Building in debug mode
Checking size .pio/build/lpc4088/firmware.elf
Advanced Memory Usage is available via "PlatformIO Home > Project Inspect"
RAM:   [          ]   3.4% (used 3349 bytes from 98304 bytes)
Flash: [=         ]   6.9% (used 36288 bytes from 524288 bytes)
========================= [SUCCESS] Took 1.12 seconds =========================
undefined0000311:WARNING:gdb_server:pyocd-gdbserver is deprecated; please use the new combined pyocd tool.
0000728:INFO:board:Target type is lpc4088
0000768:INFO:dap:DP IDR = 0x2ba01477 (v1 rev2)
0000785:INFO:ap:AHB-AP#0 IDR = 0x24770011 (AHB-AP var1 rev2)
0000904:INFO:rom_table:AHB-AP#0 Class 0x1 ROM table #0 @ 0xe00ff000 (designer=43b part=4c4)
0000912:INFO:rom_table:[0]<e000e000:SCS-M4 class=14 designer=43b part=00c>
0000917:INFO:rom_table:[1]<e0001000:DWT class=14 designer=43b part=002>
0000922:INFO:rom_table:[2]<e0002000:FPB class=14 designer=43b part=003>
0000927:INFO:rom_table:[3]<e0000000:ITM class=14 designer=43b part=001>
0000932:INFO:rom_table:[4]<e0040000:TPIU-M4 class=9 designer=43b part=9a1 devtype=11 archid=0000 devid=ca1:0:0>
0000937:INFO:rom_table:[5]<e0041000:ETM-M4 class=9 designer=43b part=925 devtype=13 archid=0000 devid=0:0:0>
0000939:INFO:cortex_m:CPU core #0 is Cortex-M4 r0p1
0000947:INFO:cortex_m:FPU present: FPv4-SP-D16-M
0000951:INFO:dwt:4 hardware watchpoints
0000954:INFO:fpb:6 hardware breakpoints, 4 literal comparators
0000970:INFO:server:Semihost server started on port 4444 (core 0)
0000974:INFO:gdbserver:GDB server started on port 3333 (core 0)
Reading symbols from ~/Documents/PlatformIO/Projects/testtest/.pio/build/lpc4088/firmware.elf...
PlatformIO Unified Debugger -> http://bit.ly/pio-debug
PlatformIO: debug_tool = cmsis-dap
PlatformIO: Initializing remote target...
0001493:INFO:gdbserver:Client connected to port 3333!
main () at src/main.cpp:7
7	{
0001530:INFO:gdbserver:Attempting to load argon
0001530:INFO:gdbserver:Attempting to load freertos
0001531:INFO:gdbserver:Attempting to load rtx5
0001531:INFO:gdbserver:Attempting to load zephyr

Error: unrecognized command 'init'
Loading section .text, size 0x82e0 lma 0x0
Loading section .ARM.exidx, size 0x8 lma 0x82e0
Loading section .data, size 0xad8 lma 0x82e8
Loading section .heap, size 0xe200 lma 0x9000
[---|---|---|---|---|---|---|---|---|----]
[========================================]
0007887:INFO:loader:Erased 4096 bytes (1 sector), programmed 4096 bytes (8 pages), skipped 94208 bytes (184 pages) at 15.16 kB/s
Start address 0x1858, load size 94144
Transfer rate: 14 KB/sec, 1845 bytes/write.
Resetting target with halt
Successfully halted device on reset
Temporary breakpoint 1 at 0x1e90: file src/main.cpp, line 7.
PlatformIO: Initialization completed
PlatformIO: Resume the execution to `debug_init_break = tbreak main`
PlatformIO: More configuration options -> http://bit.ly/pio-debug
Note: automatically using hardware breakpoints for read-only addresses.
0009225:ERROR:gdbserver:Unhandled exception in handle_message: No ACK received
Traceback (most recent call last):
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/probe/cmsis_dap_probe.py", line 238, in flush
    self._link.flush()
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/utility/concurrency.py", line 28, in _locking
    return func(self, *args, **kwargs)
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/probe/pydapaccess/dap_access_cmsis_dap.py", line 672, in flush
    self._read_packet()
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/utility/concurrency.py", line 28, in _locking
    return func(self, *args, **kwargs)
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/probe/pydapaccess/dap_access_cmsis_dap.py", line 932, in _read_packet
    decoded_data = cmd.decode_data(raw_data)
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/probe/pydapaccess/dap_access_cmsis_dap.py", line 452, in decode_data
    data = self._decode_transfer_data(data)
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/probe/pydapaccess/dap_access_cmsis_dap.py", line 359, in _decode_transfer_data
    self._check_response(data[2])
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/probe/pydapaccess/dap_access_cmsis_dap.py", line 342, in _check_response
    raise DAPAccessIntf.TransferError("No ACK received")

pyocd.probe.pydapaccess.dap_access_api.DAPAccessIntf.TransferError: No ACK received

The above exception was the direct cause of the following exception:

Traceback (most recent call last):
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/gdbserver/gdbserver.py", line 427, in handle_message
    reply = handler(msg[msgStart:])
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/gdbserver/gdbserver.py", line 675, in v_command
    return self.v_cont(cmd)
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/gdbserver/gdbserver.py", line 726, in v_cont
    return self.resume(None)
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/gdbserver/gdbserver.py", line 580, in resume
    self.target.resume()
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/coresight/cortex_m.py", line 877, in resume
    self.flush()
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/core/target.py", line 233, in flush
    self.session.probe.flush()
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/probe/cmsis_dap_probe.py", line 240, in flush
    six.raise_from(self._convert_exception(exc), exc)
File "<string>", line 3, in raise_from
pyocd.core.exceptions.TransferError: No ACK received

warning: Remote failure reply: E01
0009228:ERROR:gdbserver:Unhandled exception in handle_message: No ACK received
Traceback (most recent call last):
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/probe/cmsis_dap_probe.py", line 286, in read_ap_result_callback
    return result()
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/probe/pydapaccess/dap_access_cmsis_dap.py", line 847, in read_reg_cb
    res = transfer.get_result()
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/probe/pydapaccess/dap_access_cmsis_dap.py", line 144, in get_result
    self.daplink.flush()
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/utility/concurrency.py", line 28, in _locking
    return func(self, *args, **kwargs)
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/probe/pydapaccess/dap_access_cmsis_dap.py", line 672, in flush
    self._read_packet()
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/utility/concurrency.py", line 28, in _locking
    return func(self, *args, **kwargs)
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/probe/pydapaccess/dap_access_cmsis_dap.py", line 932, in _read_packet
    decoded_data = cmd.decode_data(raw_data)
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/probe/pydapaccess/dap_access_cmsis_dap.py", line 452, in decode_data
    data = self._decode_transfer_data(data)
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/probe/pydapaccess/dap_access_cmsis_dap.py", line 359, in _decode_transfer_data
    self._check_response(data[2])
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/probe/pydapaccess/dap_access_cmsis_dap.py", line 342, in _check_response
    raise DAPAccessIntf.TransferError("No ACK received")
pyocd.probe.pydapaccess.dap_access_api.DAPAccessIntf.TransferError: No ACK received

The above exception was the direct cause of the following exception:


Traceback (most recent call last):
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/gdbserver/gdbserver.py", line 425, in handle_message
    reply = handler()
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/gdbserver/gdbserver.py", line 873, in get_registers
    return self.create_rsp_packet(self.target_facade.get_register_context())
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/gdbserver/context_facade.py", line 101, in get_register_context
    vals = self._context.read_core_registers_raw(self._full_reg_num_list)
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/debug/cache.py", line 48, in read_core_registers_raw
    return self._regcache.read_core_registers_raw(reg_list)
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/cache/register.py", line 96, in read_core_registers_raw
    if self._check_cache():
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/cache/register.py", line 77, in _check_cache
    if self._core.is_running():
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/coresight/cortex_m.py", line 861, in is_running
    return self.get_state() == Target.State.RUNNING
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/coresight/cortex_m.py", line 830, in get_state
    dhcsr = self.read_memory(CortexM.DHCSR)
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/coresight/cortex_m.py", line 435, in read_memory
    result = self.ap.read_memory(addr, transfer_size, now)
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/utility/concurrency.py", line 28, in _locking
    return func(self, *args, **kwargs)
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/coresight/ap.py", line 993, in _read_memory
    result = read_mem_cb()
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/coresight/ap.py", line 972, in read_mem_cb
    res = result_cb()
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/coresight/dap.py", line 717, in read_ap_cb
    result = result_cb()
File "~/.platformio/packages/tool-pyocd/site-packages/py38/pyocd/probe/cmsis_dap_probe.py", line 288, in read_ap_result_callback
    six.raise_from(self._convert_exception(error), error)
File "<string>", line 3, in raise_from
pyocd.core.exceptions.TransferError: No ACK received
Could not read registers; remote failure reply 'E01'

A full log with dev debug output can be found here: LPC4088 pyOCD Debug Output · GitHub

I’ve read about debug problems with pyOCD and LPC1768, and tried downgrading to pyOCD, but that did not help. It looks to me as if the board is in a power saving mode and does not respond to the debugger anymore.

Did you hit similar problems before?

I would love to get away from MCUXpresso to develop on the LPC4088.

Best regards,
Christian

And you’re using the exact same platformio.ini as above, nu costom debug_sever yes?

Hm let’s try an update first. The development platform has some changes that are not yet released officially, and one of them is a PyOCD update.

Modify your platformio.ini to remove or comment out (;) the platform = nxplpc line and instead put

platform = https://github.com/platformio/platform-nxplpc.git

(docs).

git needs to be installed for that.

Sadly, during experiments with different versions of pyOCD and the nxplpc platform, I must have bricked my board because I’m now unable to flash it over the onboard cmsis-dap (same for MCUXpresso).

I will report back as soon as I was able to recover the board using an external J-Link debugger. This has helped in the past.

In theory the following configuration “should” work:

Still trying to figure exact syntax of platform_packages for specific versions, but will figure out as soon as I have working boards. Then I will have to resolve the python problems when using older pyOCD version…

Hmm maybe also a general upate of the CMSIS-DAP firmware on the flasher is good? (GitHub - ARMmbed/DAPLink)

Such a regression woul be very bad and should be reported to Issues · pyocd/pyOCD · GitHub if it occurs in the latest version. NXP LPC chips are popular, still.

See docs and the search request for available versions. Available version codes are

  • 1.2900.210122 (pyOCD 0.29)
  • 1.2803.201229 (pyOC 0.28.3)
  • 0.801.0 (pyOC 0.8.1 from 2018)

so a directive would go

platform_packages = 
   tool-pyocd @ <version>

But you can also try and use the debug_tool = custom an debug_server directives to use your global installation an then arbitrarily install one via pip of a specific version with the available versions.

The DAPLink firmware was already updated to the newest version. But when the flashed configuration is corrupt, it does not allow to reflash with cmsis-dap. Because I new that JLink was able to fix the problem, I did not dig deeper, even if it was annoying.

With JLink, a was able to upload/debug on the first try, but it would be great if the onboard debugger would work as well.

Thanks for the hint with the API call, thats what I missed.

I agree, it seems that multiple LPC chips have that problem. When I narrowed down the reason, I will report it. Until now I have figured out the following:

  • Setting pyOCD 0.8.0 for tool-pyocd fails (uplod/debug) because platformio uses Python3 and v 0.8.0 is incompatible mainly because of using relative module imports.

  • Setting newer pyOCD for tool-pyocd can successfully upload with upload_protocol = cmsis-dap but fails to debug with pyocd.core.exceptions.TransferError: No ACK received from my initial post.

  • I tried forcing platformio to use python2, but could not get it to work… unsure why

  • The next experiment was a custom debug tool, that points to pyOCD 0.8.0 using python2 while platformio itself uses python3. Fails, I suspect mixing python3 and python2 is not the best idea…

    // upload sucessfully  finished
    ========================= [SUCCESS] Took 53.37 seconds =========================
    undefined  File "C:\Users\chris\.platformio\python3\lib\site.py", line 177
      file=sys.stderr)
          ^
    SyntaxError: invalid syntax
    Reading symbols from 
    c:\Users\chris\OneDrive\Dokumente\PlatformIO\Projects\test_lpc4088\.pio\build\lpc4088\firmware.elf...
    C:\Users\chris\.platformio\packages\toolchain-gccarmnoneeabi\bin\arm-none-eabi-gdb.exe: warning: 
    Couldn't determine a path for the index cache directory.
    PlatformIO Unified Debugger -> http://bit.ly/pio-debug
    PlatformIO: debug_tool = custom
    PlatformIO: Initializing remote target...
    .pioinit:13: Error in sourced command file:
    :3333: No connection could be made because the target machine actively refused it.
    
  • Somewhere I read that an external gdbserver is used when it is already running. I started (the python2 version) pyocd-gdbserver.exe -t lpc4088 and then starting debugging. This finally succeeded, although the breakpoints were mostly off-by-one… but at least it works.

I will now try to narrow down the pyOCD issue, and try to provide a fix. It might take me a while because it has not the highest priority for me. I will update this thread as soon as I have a better solution.

Thanks for the support and the hints :slight_smile:

hey tux,

I’m also trying to debug with the LPC 4088, but so far no luck. Im getting the same errors you are. Were you ever able to get this working? Would you mind sharing your solution?

Hi Claude

Unfortunately I had no time to dig deeper into this issue. I narrowed it down to a pyOCD problem LPC4088 QSB 'No ACK received' · Issue #1124 · pyocd/pyOCD · GitHub but did not receive help. In the end the most pragmatic solution is to use a JLink debugger.

A side note: I wanted to use newer MBed versions with this board and had to create custom board config. Let me know if you are interested in this.

Best regards,
Christian