Amosapientiam

備忘録

いかに僕がIOに20日以上を費やしたか

この記事は愚痴です。

動かないIOラッパ

まさかIOでハマるわけがないと思っていた。IOなんて夏学期と夏休みで何回も書いたはずなのに...

Carina 内部で用いるデータは4byte単位なので、夏学期に書いたIOをword=4bytes 単位アクセスできるようにちょっとラッパするだけだ。1日あれば終わるはずだった。まさか20日もハマるなんて。Carina 最大の誤算がこれだ。シミュレータでは動くのに実機では全く動かない現象。完全に寿命が縮んだ。

絶対ucfファイル確認しような(12 days)

実機は0x00を返すばかり。完全に謎だった。

SRAMRS232Cを用いる。そこでucfファイルは夏学期の実験で使用したものをコピペして使った。SRAMを使えているかのテストをし、デバッグ出力を実機に送信するという内容の実験だった。ここに大きな見落としがあって、この実験ではデータをPCから受信していないのでRS-RXの制約が抜けていたのだ。ucfの入れ忘れではなく、100行近いucfファイルに1行抜けがあったのだ。

ここのデバッグは概ね次の要領で行われた。

  1.  余計に待ってみたり、ラッチを入れたりして確実にデータを受け取る
  2.  シミュレータで正しく動くことを確認する
  3.  ucfがないので実機で正しく動かない
  4. タイミングのバグを疑う
  5. 1に戻る

ラッパするだけだったモジュールは、いつしか完全にグニャゲッティと化した。これが後述の full-empty-hack問題を起こす。

First Word Fall Through(2 days)

core generator が生成する同期FIFOには大きく2つのモードがある。Standard FIFOと FWFT FIFOだ。前者はread_enableを掛けると、次にREを掛けるまでFIFOの最後のデータが出力され続ける。後者はFIFOの最後のデータは到着以降常に出力されており、REを掛けるとFIFOが一つ流れて、次のデータが出力されるようになる。感覚としては前者のREは「データを読ませてくれ」のREであり、後者のREは「データを読んだので次を頼む」のREだ。

IOのbufferとしては後者のFIFOの方が良かった。前者だとREを掛けてから1clk待たねば読めないからだ。しかし、夏学期の僕は前者を用いてIO moduleを構成していた。そもそもFWFTモードの存在を知らなかったのである。コアは後者のFIFOを前提して組んでいた。ここの埋め合わせもIOラッパがしなければならない。IOラッパが更に水膨れする。

 full-empty-hack(3 days)

元々のIOユニットにはFIFOがついていたので、タイミングを気にすることなくバーストアクセスできるはずだった。しかしFIFOから4byteを読んで1wordのデータをこしらえている以上、それは不可能になった。どうするか。

最適な設計は、 FIFOをbyteではなくword単位のものに変えて、ラッパの外側におくことだろう。しかし、このIOラッパは下手なところを触ると途端に動かなくなった。それに今動いているところを書き直す体力は残っていなかった。そこで、FIFOから出てくるfull,emptyを誤魔化そうという発想に至った。ラッパで作業している最中はfullやemptyを立てておき、コア側からのアクセスを遠慮してもらう。自分がもはや正気で無いのはわかっていたが、一刻も早くIOの実装を終わらせたかった。

int main(){

  puts("hoge");

  return 0;

}

を2週間掛けても書けないでいるなんて!

test(1 day)

無心でテストを書いていた。IOを書くためだけに学校に10泊以上していた。たかがIOのために。テストケースが全て動作していることを確認すると、僕はIOフォルダに心の中で chmod 444 した。僕自身は二度とそのディレクトリを覗くことはないはずだ。アクセスごとにfullとemptyが数クロック起ち続けるゴミIOが一つ世に生まれた。

 IO revival(3 days)

衝撃の事実。raytracerはword-wise送信をしなかった。全てが無駄だった。

IOの中身も、プログラムローダも、コアも、この頃には闇IOラッパの闇と四つに組んでしまい分離不可能であった。byte-wiseアクセスモードを追加するのに3日要した。

 

IO再設計

完動した。次にすることは明らかだ。一番下から一番上までIOを再設計する。夏学期のIOは使わない。CarinaのIOラッパは見もしない。一から全部書き直す。前回の反省を踏まえてたっぷり2週間取った。

1日で完成した。

教訓

ダメなときはフルスクラッチしましょう。