今回目指す環境
[Raspberry Pi 3] ⇔ [JTAGデバッガ] ⇔ [WindowsPC]
Raspberry Pi上ではベアメタルプログラムを動作させる。
OpneOCD + GDBを用いたフリーな環境を構築する。
WindowsでOpenOCD + GDBを動作させてデバッグを行う。
必要なもの
- Raspberry Pi 3 一式
- JTAGデバッガ
JTAGデバッガとしてARM-USB-TINY-Hを用いる。5000円程度で購入可能なもの。
https://www.olimex.com/Products/ARM/JTAG/ARM-USB-TINY-H/ - JTAG - Rpi3接続用の線材
- Windowsマシン
実際のJTAGデバッグはWindows PCで行う。 - Linuxマシン
OpenOCDのビルドにUbuntu14.04を用いた。
Windows上のMinGWやCygwinでもビルドできそうだが未確認。
ハードの接続
Raspberry Piのピン配置
基板のGPIOピンの位置
Raspberry Pi 2用の情報だが、Raspberry Pi 3と同じらしい。
https://www.raspberrypi.org/documentation/usage/gpio-plus-and-raspi2/README.md
GPIOピンのファンクション切り替え
Raspberry Piでは、レジスタ設定することで、それぞれのGPIOピンの機能を個別に切り替えることができる。
以下はRaspberry Pi 1用の情報だが参考になる。
GPIO22~27をALT4に切り替えてJTAGを接続する。
https://www.raspberrypi.org/documentation/hardware/raspberrypi/bcm2835/BCM2835-ARM-Peripherals.pdf
ARM-USB-TINY-Hのピン配置
https://www.olimex.com/Products/ARM/JTAG/_resources/ARM-USB-TINY_and_TINY_H_manual.pdf
ARM-USB-TINY-H本体のコネクタ面にLEDが付いている
コネクタ面のLEDが下になるように以下のピン配置を見る
pin | signal name | pin | signal name |
---|---|---|---|
1 | VREF | 2 | VREF |
3 | TTRST_N | 4 | GND |
5 | TTDI | 6 | GND |
7 | TTMS | 8 | GND |
9 | TTCK | 10 | GND |
11 | TRTCK | 12 | GND |
13 | TTDO | 14 | GND |
15 | TSRST_N | 16 | GND |
17 | NOT CONNECTED | 18 | GND |
19 | TARGET SUPPLY | 20 | GND |
○ LED側
Raspberry Pi 3 と ARM-USB-TINY-H の接続
接続はしっかり確認すること。間違えると壊れる可能性大。
RPi3信号名 | 結線 | ARM-USB-TINY-H信号名 |
---|---|---|
3.3v | <-> | VREF |
Ground | <-> | GND |
GPIO22 | <-> | TSRTS_N |
GPIO26 | <-> | TTDI |
GPIO27 | <-> | TTMS |
GPIO25 | <-> | TTCK |
GPIO23 | <-> | TRTCK |
GPIO24 | <-> | TTDO |
以下の写真のようにピン同士を直接つないだ。
本当は、専用コネクタ&ケーブルを用意しておくほうが便利かつ安全。
なお、テスト用にGPIO16にLEDをつないでいる。
ソフトの用意
OpenOCD
Ubuntu上でWindows用のOpenOCDをビルドする。
MinGWやCygwinでもビルドできそうだが未確認。
以下をインストールしておく
sudo apt-get install mingw-w64 automake libtool libudev-dev
openocdをビルドするにはlibusbライブラリが必要となる。
libusbをビルド&インストールしておく。
git clone git://git.libusb.org/libusb.git (2017/10/7 アクセスできなくなったため修正)
git clone https://github.com/libusb/libusb.git
cd ./libusb/
./autogen.sh
./configure --host=i686-w64-mingw32
make
sudo make install
raspberry pi 3 AArch64用のOpneOCDを作ってくれている方がいるので、それを利用させてもらった。
(2017/10/7 複数コアを停止した際に再開できなくなる問題あり)
git clone https://github.com/daniel-k/openocd.git openocd-armv8
cd openocd-armv8
git checkout armv8
./bootstrap
./configure --host=i686-w64-mingw32 --enable-ftdi
make
以下をWindows側に持ってくる
- openocd-armv8/src/openocd.exe
- openocd-armv8/tcl以下一式
試しにWindowsのコマンドプロンプト(or cygwin)でopenocd.exeを実行してみる。
libusbxxx.dllがないというようなエラーが出たら、別途入手してpathを通しておく。
GDB
LinaroのWindows用のGCCを用いる。
AArch64ベアメタル向けtoolchainにGDBが含まれている。
https://www.linaro.org/downloads/
Raspberry Piで動かすプログラム
Raspberry Piは電源ON直後は、全ピンの機能がGPIOになっている。
JTAGを使用するには、ピンの機能をJTAGに切り替えなければならない。
GPIO22~27をALT4に切り替える。
サンプルプログラムを以下に置いた。(2017/10/7)
https://github.com/YujiToshinaga/RPi64BareMetal/tree/master/JtagCon
ドライバインストール
http://zadig.akeo.ie/
Zadigを使用して"ARM-USB-OCD-H (Interface 0)"のデバイスにWinUSBを適用する。
"Interface 1"には適用してはいけない。
とりあえず、"Interface 1"のドライバはインストールしなくて良い。
JTAGデバッグ動作
OpenOCDによるデバッグ
OpenOCDの起動
Windows側でターミナル等で以下を実行する
openocd.exe -f tcl/interface/ftdi/olimex-arm-usb-tiny-h.cfg -f tcl/target/rpi3.cfg
大量にエラーが出力されるが特に問題なくJTAGデバッグできる。
あらかじめRPi側のキャッシュ、MMU等の設定を正しくしておけばエラーなく接続できた。
telnetでOpenOCDの設定
別のターミナルを開きtelnetでOpenOCDに接続
% telnet localhost 4444
以下コマンドでコア一覧(4コアの状態)が表示される
> targets
おそらく最初はコア3に接続中なので、以下コマンドでコア0に切り替える
> targets rpi3.cpu
GDBに接続するために、コア0を止めておく
> halt
よく使うコマンド例
コマンド例 | 説明 |
---|---|
targets | 全コアの状態を表示する |
targets rpi3.cpu1 | コア1に切り替える |
halt | コアを動作を停止する |
resume | コアの動作を開始する |
reg | レジスタの内容を表示する |
reg x1 0x5f5f | x1レジスタに0x5f5fを書き込む |
reg pc 0x200 | 0x200番地にジャンプする |
bp 0x1000 4 hw | 0x1000番地にブレークポイントを設定する |
rbp 0x1000 | 0x1000番地のブレークポイントを削除する |
mdw 0x400 | 0x400番地をワードサイズ分表示する |
mww 0x400 0x5f5f | 0x400番地にワードサイズ分0x5f5fを書き込む |
load_image test.bin 0x0 | 0x0番地にtest.binを展開する(test.binのパスはopenocd.exeの場所が基準となる) |
GDBによるデバッグ
aarch64-elf-gdb.exe xxx.axf
> target remote localhost 3333
あとはGDBコマンドでデバッグ可能になるはず