Closed11

FPGAのBitstreamについて調査するログ

nozonozo

FPGAは大きく3種の要素から構成される。

  • 論理ブロック(LB) ... 任意の組み合わせ回路を実現するLUT(Look-Up Table)と、値を保持するFF(FlipFlop)で構成される
  • I/Oブロック(IOB) ... 外部とのI/O信号の入出力を行う
  • 配線要素 ... LB-LBやLB-IOBをプログラマブルな配線で接続する

上記の基本要素の他に、ブロックメモリや乗算などの固定機能回路も組み込まれている場合もある。

書籍の"3.11 コンフィグレーションチェーン"より:

FPGA上に回路を構成することをFPGAをコンフィギュレーションするといい,その際にFPGAに書き込まれる回路情報をコンフィギュレーションデータと呼ぶ.コンフィグレーションデータには,例えばLUTで実現する真理値表の内容や,スイッチブロック内における各スイッチのON/OFF情報など,FPGAに回路を構成するのに必要なすべての情報が含まれる.

上記からBitstreamはコンフィグレーションデータそのものに見える。

nozonozo

XILINXの7シリーズのコンフィグレーションに関するドキュメントには以下のようなものがある。

nozonozo

FPGAをコンフィギュレーションする方法には大きく2つのモードがある。

  • マスターモード:
    FPGAが能動的に外部のメモリからコンフィギュレーションデータを読み込む方法
  • スレーブモード:
    外部のプロセッサなどからFPGAへコンフィギュレーションデータを書き込む方法

それぞれのモードにおけるデータパスにはシリアルとパラレルを使用することができる。
また、インターフェースとしてJTAGを使用することもできる。

これらのコンフィグレーションモードはFPGAの入力ピンM[2:0]で指定される。

コンフィギュレーションモード M[2:0] バス幅
マスターシリアル 000 x1
マスターSPI 001 x1, x2, x4
マスターBPI 010 x8, x16
マスターSelectMAP 100 x8, x16
JTAG 101 x1
スレーブSelectMAP 110 x8, x16, x32
スレーブシリアル 111 x1
nozonozo

7シリーズFPGAのBitstreamは次の3つの部分で構成される。

  • バス幅の自動検出
  • 同期ワード
  • FPGAコンフィギュレーション
nozonozo

Vivadoで生成した適当なBitstreamファイルの中身を見てみる。

$ hexdump -C top.bit | less
00000000  00 09 0f f0 0f f0 0f f0  0f f0 00 00 01 61 00 25  |.............a.%|
00000010  74 6f 70 3b 55 73 65 72  49 44 3d 30 58 46 46 46  |top;UserID=0XFFF|
00000020  46 46 46 46 46 3b 56 65  72 73 69 6f 6e 3d 32 30  |FFFFF;Version=20|
00000030  32 30 2e 32 00 62 00 0c  37 73 35 30 63 73 67 61  |20.2.b..7s50csga|
00000040  33 32 34 00 63 00 0b 32  30 32 31 2f 30 32 2f 31  |324.c..2021/02/1|
00000050  38 00 64 00 09 31 38 3a  31 35 3a 34 38 00 65 00  |8.d..18:15:48.e.|
00000060  21 72 8c ff ff ff ff ff  ff ff ff ff ff ff ff ff  |!r..............|
00000070  ff ff ff ff ff ff ff ff  ff ff ff ff ff ff ff ff  |................|
00000080  ff ff ff 00 00 00 bb 11  22 00 44 ff ff ff ff ff  |........".D.....|
00000090  ff ff ff aa 99 55 66 20  00 00 00 30 02 20 01 00  |.....Uf ...0. ..|
--snip--

.bitファイルの先頭(ffが連続する前の部分)はヘッダー情報になっている。
ヘッダー情報は単にASCIIで保持されているようだが、フォーマットについてマニュアルからは見つけられなかった。

nozonozo

なぜかfileコマンドではヘッダー情報が取得できた。

$ file top.bit
top.bit: Xilinx BIT data - from top;UserID=0XFFFFFFFF;Version=2020.2 - for 7s50csga324 - built 2021/02/18(18:15:48) - data length 0x21728c

fileコマンドのソースを検索するとxilinxの.bitファイルの設定(?)のようなものは以下にあった。

https://github.com/file/file/blob/master/magic/Magdir/xilinx

nozonozo

Rustの勉強も兼ねてbitstreamデコーダの作成中。
バイナリの読み出し方はもっと良い書き方がありそう。

https://github.com/isNozo/bitdump/tree/8c61cc6776102ac10acfc3bd664373d1333e1b6b

ヘッダーのフォーマットに従って情報を取得できた。

Field 1 (some sort of header)
  length: 0x0009
  value : [0f, f0, 0f, f0, 0f, f0, 0f, f0, 00]
Field 2
  length: 0x0001
  value : a
Field 3 (NCD name)
  length: 0x0025
  value : top;UserID=0XFFFFFFFF;Version=2020.2^@
Field 4 (model/part number)
  key   : b
  length: 0x000c
  value : 7s50csga324^@
Field 5 (built date)
  key   : c
  length: 0x000b
  value : 2021/02/18^@
Field 6 (built time)
  key   : d
  length: 0x0009
  value : 18:15:48^@
Field 7 (data length)
  key   : e
  length: 0x0021728c

00000000 : ffffffff
00000004 : ffffffff
00000008 : ffffffff
0000000c : ffffffff
00000010 : ffffffff
00000014 : ffffffff
00000018 : ffffffff
0000001c : ffffffff
00000020 : 000000bb
00000024 : 11220044
--snip--
nozonozo

Bitstreamのヘッダー情報の後にはバス幅自動検出パターンというものが挿入されている。

00000000 : ffffffff
00000004 : ffffffff
00000008 : ffffffff
0000000c : ffffffff
*
00000020 : 000000bb
00000024 : 11220044
00000028 : ffffffff
0000002c : ffffffff

バス幅自動検出パターンはコンフィギュレーションモードのうちパラレルモードで利用される。(シリアルモードでは無視される)
このパターンを幅x8, x16, x32それぞれで読みだしたときの下位8bitをみると、x8のときはbbの後に11が、x16のときはbbの後に22が、x32のときはbbの後に44が検出される。そのため、bbの後に何がくるかでどのバス幅で読みだしていたかが検出できるという仕組み。

x8 x16 x32
[bb] 00[bb] 000000[bb]
[11] 11[22] 112200[44]
[22] 00[44]
[00]
[44]
nozonozo

バス幅自動検出パターンの後にはaa995566という同期ワードが挿入されており、FPGAは同期ワードが検出されてから後ろのFPGAコンフィギュレーション部分の処理に進む。

00000028 : ffffffff
0000002c : ffffffff
00000030 : aa995566  ※ 同期ワード
00000034 : 20000000
00000038 : 30022001
このスクラップは2021/07/29にクローズされました