(日々の記録)デジタルオシロを買った。(木)エラーのないFPGAのUARTコードを自作するFPGAのフォトフレームプロジェクトは、いよいよ第一期完成フェーズにあたる第7ステップに進んだ。SDカードにあるビットマップ画像データを液晶モニターに表示する段階である。フォトフレームを作ると決めてブログで宣言したのが今年の2月末。6ヶ月かけてここまできたことになる。このあいだには、XilinxのFPGAチップと液晶モニターをプローブの誤接触で壊したり、HDL言語(VerilogHDL)の習得にてこずったり、今回も多くのドラマ(?)が生まれた。電子工作を始めて2年半、自分でも感心するほど多種多様な工作をしてきたが、ひとつのプロジェクトにこんなに長く(半年)かけたことはない。FPGAはやはりてごわい。これまで何度も書いているように、当研究所では電子工作には必ず何らかの実用的(こじつけでも良い)な目的を決めてから、工作を始めることにしている。定年後の楽しみに始めたアマチュアの電子工作である。何をやろうと、どこでやめようと誰もとがめる人はいないのだが、これだけ目的にこだわるのは理由がある。自分は飽きっぽい性格で、めげやすい。何の規制もせずにやりたいことだけやっていたら、いつまでたっても技術の向上は望めない。電子工作は幸い、初心者からプロまで、どんなレベルであろうと、それなりに夢中になり楽しめる世界だが、悔しいことに技術レベルが上がれば上がるほど楽しめる範囲が広くなっていくことは否定できない。何でも良いから具体的な目標(仕様)を設定しておくと、何とかそれを実現しようと、一生懸命に工夫、努力をする。飽きっぽい割には、一旦こだわると意地になる習性がある。これによって技術レベルは確実に上がる。遊びとは言いながら少しでも技術レベルを上げて今まで出来なかったことを可能にし、世界を広げたい。当研究所の所長は、この40年間、ほぼコンピューターのシステム開発を仕事にしていた(後半は企画と管理ばっかりだったが)。この世界ではコンピューターのハードウエアというものはいわば神が創ったものであり、これに注文をつけることはとんでもないことで、仕様どおり有難く使わせていただくものだった。PCやマイクロコンピューターでも似たようなものである。FPGAはこういう今までの常識をくつがえすディバイスである。作ろうと思えば、自らが思いのままプロセッサーを自作できるのだ。何とかこのディバイスを自由自在に操れるようにしておきたい。フォトフレームプロジェクトは現物を作るだけでなくFPGAをマスターするということもプロジェクトの大きな目的にしている。そんなこともあってまた少し道草を食って、本来のフォトフレームとは関係ないFPGAのUARTにはまりこんでいた。雑誌のサンプルUARTソースがうまく動いていない(8/16)SPIのバグ取りに散々苦労して、わかって見ればその原因はUARTの方だったという話は前回にした。このFPGAのUARTのVerilogHDLソースコードは、雑誌のデザインウエーブマガジン(その後季刊のデジタルデザインテクノロジーに改称)2008年10月号P86のサンプルソースをそっくり利用させてもらっている。雑誌のサンプルソースにバグはないはずなのだが、SRAMからのUART出力には明らかにエラーが出ている。エラーの頻度はそう高くないので、これまで気が付かなかった。これとは別のfpga4fun.comのUARTに較べれば、はるかに安定していると思っていた。詳しく調べると、1KBに数文字の字化け(エラー)があるようだ。リセット直後の数文字はたいていおかしい。フォトフレームプロジェクトではそろそろデジタル液晶の準備にかからなければいけない(ケース工作はほぼ完成)のだが、ここはそれ、しつこい性格である。気になると、他の事に手が付かなくなる。この際、徹底的にデバッグすることにした。折りしも、SPIのトラブルのとき勧められた、「HDLによる高性能デジタル回路設計」という本を入手し、FPGAを本格的に勉強しはじめたこともある。ロジアナを使って、雑誌サンプルソースの不具合の原因解明を始めた。犯行現場の現場検証が重要だ。字化けの事実を検証する。テスト用にボーレートカウンターの動きをFPGA出力ピンに出すコードをソースに追加して、これをロジアナで拾い、少しづつデータを送ってはロジアナでタイミングチャートを分析する。その結果、どこで字化けが起きるかは、ほぼ確定できた。UARTのデータの送出順序はLSBファーストである。字化けは必ずMSBで起きている。データの最後の方を集中的に調べていくと、添付画像にあるように、8ビット目の最後がボーレートの半分で終わり、そのままストップビットになるところがいくつも見つかった。UART受信はボーレート期間中の多数決論理でHかLを決めているので、ボーレートが少しずれると半分の幅しかないMSBで0のデータが1になる可能性がある。これが前回の記事で1や2が半角のアやイになる理由である。スタートビットはこのあと正しく出ているので、エラーはここだけに止まる。字化けが起きる原因はつきとめられた。このUARTの最後のビットがボーレート通りの時間にならないかがわからない。ソースコードにはおかしなところはない。ボーレートの時間通りウェイトが入っている(はずである)。「HDLによる高性能デジタル回路設計」で勉強する。(8/18)すんさんの掲示板で勧められ、絶版だと聞いていたが、秋葉原の書泉で探してみたら最後の一冊らしいカバーが少し汚れたものが見つかり早速手に入れた。噂には聞いていたが、高度な内容である。非同期回路だけでなく、同期回路も安心ならないことを学ぶ。それ以外にも考慮しなければならないことが沢山ある。自分がいかに能天気にRTL設計をしていたかを思い知らされる。QuartusII)は、この本を読み進むうち、かなりな問題があることがわかってきた。送信要求のビットはキーボード押下で発生する非同期パルスだが、その配慮がなされていないこと、状態遷移のレジスターが多段(5ビット)で、単なるバイナリーコードであるうえに、これをインクリメントするステップと、状態遷移をするロジックが同一クロック時に動いており、これが正しく評価されない可能性があることなどである。本に拠れば、非同期はもちろんであるが、同期回路といえども、ハザード(出力が不定になるところ)は、常に起きる可能性があり、その対処が必要としている。それから言えば、この雑誌のサンプルソースはあやしいところが沢山ある。それにこのソースには不可解なところがある。UARTは非同期通信なので、同期シリアル(USART)と違ってデータはクロックのエッジではなく、HighかLowでデータを採取する。それなのにサンプリング周波数はボーレートの2倍にとってある。少なくとも送信の場合はオーバーサンプリングしても無意味である。受信側のモジュールとボーレートを共通にするためだと思うが、ソースコードを読めば読むほど、何かあやしくなってきた。具体的にどこでハザードが起き、それによってボーレートが最後だけ短くなるのかは、まだ経験が浅くてつきとめられない。現実に字化けが起きていることは事実である。なったら、自前でUARTのソースコードを書いてみたくなってきた。参考書で学んだテクニックを応用する絶好の機会だ。ここまで勉強したら自分で作ってみよう(8/21)擬似コーディングを念入りにやって、自前のUART送信コードを書き始めた。UARTは、クロックパルスを持たない非同期通信なので、スタートビットからの時間間隔(ボーレート)だけでデータをHかLに設定して送信する。雑誌の2倍サンプリングをやめて、ボーレートだけのステートマシンにする。自慢は、ステートレジスターのグレイコード化(1ビットづつ変化する遷移ビット)と、同時に多数のビットを変えないロジック、ボーレートカウンターのような多数のビットを変更するときは、ステートをあけて結果を利用するなどのテクニックだ。おお、前よりステートメント数も少なくなっている。これで動けばいうことなしだ。期待に胸をふくらませて論理合成する。祈る気持ちでUART端末を立ち上げる。ARMからデータを送り、FPGA側のUARTのスペースキー(出力指示)を押した。やった、やったぞ、最初の文字から全く誤りなくテキスト文書が表示される。