Sim's blog

電子工作はじめてみました

Altera DE0のJTAG通信?

2009-11-01 19:17:06 | FPGA
Altera DE0で使えそうなLCDを探してみましたの続きになります。

Altera DE0がきましたのコメントでnsxさんから、USBを使ってPCアプリと通信できるんでしょうか、というコメントを頂きました。付属CD-ROMにある回路図を見てJTAGしかつながってないから駄目っぽいという返事をしました。でもでも、よく考えてみると付属アプリであるDE0_ControlPanelを使ってPC側からLEDを点けたりVGAの出力を変えるというデモがあります。

これがDE0_ControlPanelの画面です。チェックボタンでLEDを点けたり消すことができます。


DE0_ControlPanelが動作している最中にXPのデバイスマネージャを見てもCOMとかはいません。Altera USB-Blasterがいるだけです。

DE0_ControlPanel.exeのいるフォルダには他に3つのdllがいます。
- TERASIC_DOWNLOAD.dll
- TERASIC_JTAG.dll
- TERASIC_JTAG_DRIVE.dll
このdllが怪しげです。JTAGの通信にまぎれて、アプリ間通信をするような機能がいるような雰囲気です。dumpbin.exeを使って中身を調べてみました。

TERASIC_DOWNLOAD.dllがexportしているAPIです。
    ordinal hint RVA      name
          2    0 00006108 @@Download@Finalize
          1    1 000060F0 @@Download@Initialize
         15    2 000063E4 @@Ftdicontrol@Finalize
         14    3 000063D4 @@Ftdicontrol@Initialize
         10    4 00006350 TERASIC_AsDownload
          3    5 00006120 TERASIC_DownloadEEPROMByByteBlaster
          7    6 00006284 TERASIC_DownloadNios2
          9    7 000062F4 TERASIC_FlashProgrammer
         12    8 000063BC TERASIC_GetQuatusVersion
         11    9 000063A8 TERASIC_IsUsbBlasterDriverReady
          5    A 000061CC TERASIC_JtagDownload
          4    B 00006174 TERASIC_JtagDownloadByteBlaster
          6    C 0000622C TERASIC_JtagDownloadChain
          8    D 000062DC TERASIC_Nios2Terminal
         13    E 000063C4 TERASIC_SetQuartusProgrammerPath
         16    F 0006A0F8 ___CPPdebugHook

いかにもダウンロード用といった感じのAPIが並んでいます。

TERASIC_JTAG.dllがexportしているAPIです。
    ordinal hint RVA      name
          2    0 000018B0 @@Jtagport@Finalize
          1    1 000018A0 @@Jtagport@Initialize
          4    2 00001938 TERASIC_JtagClose
          7    3 000019F0 TERASIC_JtagGetInfo
          3    4 000018C0 TERASIC_JtagOpen
          6    5 000019B8 TERASIC_JtagRead
          5    6 00001980 TERASIC_JtagWrite
          8    7 0000A0F8 ___CPPdebugHook

ReadとかWriteがあって、いかにも通信用って感じです。

TERASIC_JTAG_DRIVE.dllがexportしているAPIです。
    ordinal hint RVA      name
          1    0 00001E94 jtag_atlantic_clearstall
          2    1 00001B9C jtag_atlantic_get_offset
          3    2 00001B70 jtag_atlantic_init
          4    3 00001DEE jtag_atlantic_read
          5    4 00001D56 jtag_atlantic_status
          6    5 00001E39 jtag_atlantic_transfer
          7    6 00001DA3 jtag_atlantic_write
          8    7 00002889 jtag_avalon_address
          9    8 00002773 jtag_avalon_get_offset
         10    9 00002745 jtag_avalon_init
         11    A 000028AC jtag_avalon_mode
         12    B 00002912 jtag_avalon_read
         13    C 0000282A jtag_avalon_status
         14    D 000028CF jtag_avalon_write
         15    E 0000192A jtag_close
         16    F 00001963 jtag_command
         17   10 00001000 jtag_init
         18   11 00002671 jtag_pio_init
         19   12 000026FF jtag_pio_read_outputs
         20   13 00002678 jtag_pio_status
         21   14 00002722 jtag_pio_write_inputs

avalonとかatlanticって何なんでしょう?

デバッガを使ってDE0_ControlPanel.exeを追いかけてみるとTERASIC_JTAG.dllが通信用でした。Openは2つのパラメータ、ReadとWriteは3つのパラメータ、Closeは1つのパラメータを使っています。送っているデータを覗いてみると、次のような形式になっていました。

先頭の1バイト 0xaa 固定
2バイト目 コマンド (LED関連は0x02、VGA関連は0x0d等)
3バイト目 送信するデータのバイト数をnとすると n - 6
4バイト目 0x00 固定 (用途不明)
5バイト目から 送信データ
...
n-1バイト目 チェックサム (2バイト目からn-2バイト目までの総和 mod 256)
nバイト目 0x55固定

LED点灯コマンドのときは5バイト目がLED7~LED0、6バイト目がLED9,LED8の点灯パターンを送っています。全部点灯するときは5バイト目が0xff、6バイト目が0x03になります。全点灯するときに送信するデータです。
aa 02 02 00 ff 03 06 55
初期化のときに送っているデータです。
aa 00 00 00 55
VGAのパターンを選択するときに送っているデータです。
aa 0d 01 00 00 0e 55
受信するデータも同じ形式です。内部処理では最初に先頭の4バイトを読み込みます。続きの長さが分かるので、続きを読むという感じで2回に分けて可変長のデータを受信しています。

ソースとかドキュメントといった情報が全然見つかっていないので、無理矢理リバースエンジニアリングしてしまいました。JTAGラインを使ってデータを送受信していることくらいまでは分かりましたが、そこから先はさっぱりです。そもそもFPGA側にどんな回路を作ればいいのかも分かりません。Terasicが情報を公開しないかぎりは、これ以上は難しそうです。


なんてことを↑で書きましたが、NIOS IIとかAvaronでぐぐってみると、Avaron BUSとかJTAG UARTみたいなキーになりそうな言葉がひっかかってきます。自分で使うときはTERASIC_JTAG_DRIVE.DLLを直接叩くのかもしれません。