JTAG debugging with Bus pirate and OpenOCD

Bus Pirate v3

The Bus Pirate is an open source electronic circuit developed by Dangerous Prototypes. They also sell it at minimal cost. The Bus Pirate allows the communication between a PC with a USB connection and any chips through serial protocols like I²C and SPI. Recently I discovered that the Bus Pirate is JTAG capable.

A large community is using this device for diverse things like repairing devices, and recently it was used during a challenge at Insomni’hack CTF to communicate to a MSP430 microcontroller and exploit a software buffer overflow on this architecture. I explain below how to communicate with, and upgrade the Bus Pirate and how to use it with OpenOCD software to debug chips.

Open On-Chip Debugger (OpenOCD) software was created by Dominic Rath at the University of Applied Sciences Augsburg. The goal of this software is to provide debugging tools for a lot of different debugging adapters and platforms. It has a scripting language which allows creating configuration files for e.g. custom JTAG adapters or target platforms. The good news is that since a recent firmware update, the Bus Pirate is supported by OpenOCD as a JTAG adapter. I connected the Bus Pirate to my Ubuntu 13.10 machine (sorry did not have time to upgrade yet). I installed and ran minicom to communicate with it:

sudo apt-get install minicom
sudo minicom -s

To communicate with the Bus Pirate, I set the serial port setup as follows:

| A -    Serial Device      : /dev/ttyUSB0                    |
| B - Lockfile Location     : /var/lock                       |
| C -   Callin Program      :                                 |
| D -  Callout Program      :                                 |
| E -    Bps/Par/Bits       : 115200 8N1                      |
| F - Hardware Flow Control : No                              |
| G - Software Flow Control : No                              |
|                                                             |
|    Change which setting?                                    |

Note that my Bus Pirate was connected to /dev/ttyUSB0. You should select your own serial device port here. After the configuration, I entered in the Bus Pirate prompt:

Welcome to minicom 2.6.2

Compiled on Feb  8 2013, 07:03:03.
Port /dev/ttyUSB0, 11:34:56

Press CTRL-A Z for help on special keys


The “m” command enters the main menu:

1. HiZ                                  
2. 1-WIRE                               
3. UART                                 
4. I2C                                  
5. SPI
6. 2WIRE
7. 3WIRE
8. LCD
x. exit(without change)

The “i” command provides information about the firmware version of the Bus Pirate:

Bus Pirate v3.5
Firmware v5.10 r382  Bootloader v4.4
DEVID:0x0447 REVID:0x3043 (24FJ64GA002 B5)

As you can see I was using the version 3.5 of the Bus Pirate hardware and version 5.10 for the firmware. According to the Bus Pirate documentation, I needed to update the firmware to allow OpenOCD support for the Bus Pirate. I downloaded the last firmware version. I set the Bus Pirate in bootloader mode:

Are you sure? y

Finally I ran the firmware update tool from another terminal:

cd package/BPv3-firmware/
sudo chmod +x ./pirate-loader_lnx
sudo ./pirate-loader_lnx --dev=/dev/ttyUSB0 --hex=BPv3-frimware-v6.1.hex

Everything went well and I had the following result:

  Pirate-Loader for BP with Bootloader v4+  
  Loader version: 1.0.2  OS: Linux

Parsing HEX file [BPv3-frimware-v6.1.hex]
Found 21502 words (64506 bytes)
Fixing bootloader/userprogram jumps
Opening serial device /dev/ttyUSB0...OK
Configuring serial port settings...OK
Sending Hello to the Bootloader...OK

Device ID: PIC24FJ64GA002 [d4]
Bootloader version: 1,02
Erasing page 0, 0000...OK
Writing page 0 row 0, 0000...OK
Writing page 41 row 335, a780...OK

Firmware updated successfully :)!
Use screen /dev/ttyUSB0 115200 to verify

I restarted the Bus Pirate to leave the bootloader mode and I observed that the firmware was indeed updated:

Bus Pirate v3.5
Firmware v6.1 r1676  Bootloader v4.4
DEVID:0x0447 REVID:0x3043 (24FJ64GA002B5)

To install OpenOCD, get the last code version with git:

sudo apt-get install git
git clone git://git.code.sf.net/p/openocd/code

Then install the dependencies and compiled OpenOCD with Bus Pirate support option:

sudo apt-get install libtool autoconf texinfo libusb-dev libftdi-dev
git clone git://git.code.sf.net/p/openocd/code
cd code
./configure --enable-maintainer-mode --disable-werror --enable-buspirate
sudo make install

I was now ready to connect the Bus Pirate to the target chip. JTAG uses 5 pins in addition to the ground. A clock is provided through the Test Clock pin (TCK), and serial communication is achieved through Test Data In (TDI) and Test Data Out (TDO) pins. The next state of the JTAG state machine is determined by the Test Mode Select (TMS) pin which is read at each rising edge of TCK. The logic can be reset using the Test Reset (TRST) pin. This pin is optional. I connected the pins to the target board as shown in the picture below.
Bus Pirate pin header
My target device uses an ARM CPU so I used the VPU pin of the Bus Pirate to provide the target reference voltage (VTREF) and I plugged the pin TRST to the AUX pin of the Bus Pirate as described in the documentation. When the JTAG pins is unknown, the JTAGulator  is an excellent tool to identify them. To run OpenOCD I first created a configuration file “MyBuspirate.cfg” which contained:

source [find interface/buspirate.cfg]

buspirate_vreg 0
buspirate_mode open-drain
buspirate_pullup 1

buspirate_port /dev/ttyUSB0

Basically I said that I use Bus Pirate plugged to /dev/ttyUSB0 with pull up turned on. Other debug adapters configuration file can be found in repository:


These file can also help to support new debug adapters since the syntax is simple. I then ran OpenOCD (in root) and I get:

sudo openocd -f MyBuspirate.cfg 
Open On-Chip Debugger 0.7.0 (2014-04-09-15:05)
Licensed under GNU GPL v2
For bug reports, read
Warn: Adapter driver 'buspirate' did not declare which transports it allows; assuming legacy JTAG-only
Info : only one transport option; autoselect 'jtag'
srst_only separate srst_gates_jtag srst_open_drain connect_deassert_srst
Info : Buspirate Interface ready!
Info : This adapter doesn't support configurable speed
Warn : There are no enabled taps.  AUTO PROBING MIGHT NOT WORK!!
Warn : AUTO auto0.tap - use "jtag newtap auto0 tap -expected-id 0x0b7ae02f ..."
Warn : AUTO auto0.tap - use "... -irlen 4"
Warn : gdb services need one or more targets defined

When no target is defined, OpenOCD uses auto probing to discover TAPs. To define a target I added in the configuration file the line:

source [find board/ti_beagleboard.cfg]

Other board configuration files can be found in the repository:


For chip only TAPs configuration, the scripts are located in


Once again other target chip configurations can be created with custom files. I relaunched OpenOCD with the updated file. From another terminal I connected to OpenOCD server with telnet:

telnet localhost 4444

It opened a prompt which allowed all kinds of debug commands like halting CPU, reading registers and memory, and writing flash. A complete list of available commands is well described in OpenOCD user guide. I now have a complete set up for JTAG debugging.

Creative Commons License
This work is licensed under a Creative Commons Attribution-ShareAlike 4.0 International License.


Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s