LX9 MicroBoardを使ってみる
by K.I
2011/09/xx
Index
- 相変わらず、よく分からずに使っているので、いろいろ試行錯誤した記録として。
[top]
- Xilinxのサイトから、Webpack13.2をダウンロードしてインストール
- LicenseManagerで、Webpackライセンスを設定
- MicroBoardにはWebPackとSDKライセンスが付いてるので、それを使えば良いんだけど、
- とりあえず、WebPack評価用ライセンスを新規に申請して、そのライセンスを使った。
- Microblazeとか使う場合は、SDKライセンスが必要みたいだけど、今のところは興味がないので。
- MicroBoardに付いてくるライセンスの番号は大切なので、無くさないようにすること。
- まず、Microsoft VisualC++ 2008 ServicePack1
- ここから、vcredist_x86.exeをダウンロード
C:\Xilinx\13.2\ISE_DS\ISE\lib\nt\plugins\Digilent\libCseDigilentには、libCseDigilent.dll,libCseDigilent.xmlが入っているので、結局何もせずに、そのまま。
サンプルプログラムをダウンロード
- このサンプルは、66MHzから、DCMでクロックを作って、27bitカウンタに入れて、
- 1/2^26が、約1秒になっているので、DCMでは特に分周していないようだ。
- 何のためにDCM使ってるんだろう?DCMはクロック安定させる効果あるのかな?
- まぁ、少なくともLEDを点滅させるだけなら、66MHzの外部クロックを直接使っても何の問題も無い。
- 多分、DCMのプリミティブを使う例としての意味があるんだろうと思う。
- FlashROMへの書込みだが、LX9に搭載されているROMはN25Q128で、SPI接続なので、
- JTAGチェインでの書込みが出来ないけど、どうすればいいんだろう?
- iMPACTを起動して、Create PROM Fileをダブルクリックする。
- SPI Flashが選択できるようなので、
- Step1で、SPI Flash→Configure Single FPGAを選択
- Step2で、Auto Select PROMを選択(或は、128Mを選択)
- Step3で、Output File LocationとFile Nameを指定、File FormatをMCSにしてOKとする。
- 後は、以前と同じように「Start adding device file to Revision 0」というDialogが表示されるので、OKボタンを押して、bitファイルを指定
- 「Would you like to add another device file to Revision: 0?」でNOボタンを押す。
- デバイスの絵が表示された画面を右クリックして、Generate File...を選択すると、
- Generate Succeededと青く表示されるはず。
- メモリマップのようなものが表示されるけど、どのぐらいの大きさなのかわかんないので意味が無い気がするが、
- で、boundary scanを選択して、Cable Auto Connectで自動的に接続される。
- Cable Setup...で手動で接続する場合は、Degilent USB JTAGケーブルを選択する。
GUI --- Auto connect to cable...
INFO:iMPACT - Digilent Plugin: found 1 device(s).
INFO:iMPACT - Digilent Plugin: opening device: "obp", SN:000000000000
INFO:iMPACT - Digilent Plugin: User Name: obp
INFO:iMPACT - Digilent Plugin: Product Name: Avnet On-Board Programmer
INFO:iMPACT - Digilent Plugin: Serial Number: 000000000000
INFO:iMPACT - Digilent Plugin: Product ID: F030012D
INFO:iMPACT - Digilent Plugin: Firmware Version: 011B
INFO:iMPACT - Digilent Plugin: JTAG Port Number: 0
INFO:iMPACT - Digilent Plugin: JTAG Clock Frequency: 4000000 Hz
- Initialize Chainを選択すると、FPGAの上にSPI/BPI?という表示が点線枠で表示される。
- これを右クリックして、Add SPI/BPI Flash...を選択、MCSファイルを設定する。
- すると、デバイス選択のDialogが出るので、N25Q128 1.8/3.3Vを選択
- データ幅は1〜4が選べるが、回路図を見ると、MISOは4bitで接続されているので、4を設定してみた。
- でも、MCSファイルが1ビットで作成されているというDialogが出るので、やっぱり1にする。
- FPGA(xc6slx9)がbypassになっていることを確認して、
- FPGAの上にFlashが表示されるので、右クリックして、Programを選択。
- この書込み時間はものすごく時間が掛かる。ずっと0%のままでプログレスバーも変化しない。
- 待っていると、1%、2%と少しづつ変化する。フリーズしたかと思ってAbortすると実行中のままになってしまうので注意
- 我慢して、待っていると6分ちょっとで終了する。Program Succeededと青く表示されればOK.
- MCSファイルを4bitで作成すれば、少しは書込みが速くなるのかもしれないが、設定方法が分からないので、とりあえずはこれで良しとする。
- Flashの書込み時間が長いので、デバッグはFPGAに直接書込んだ方が良い。
- boundary scanで、FPGAの上で右クリックして、Assign new configuration fileを選択、bitファイルを指定する。
- Attach SPI/BPI PROMをNOとすれば、FlashROMには書込まれない。
- Generate Programming Fileのプロパティ、Configuration Optionsで、
- Set SPI Configuration Bus Widthを4に設定する。
- あとは、iMPACTのBoundary Scanの、Add SPI/BPI Flash...で、デバイスのデータ幅を4に設定すれば、
- 今度は、エラーが出ないので多分4bit書込みになってると思う。
- とりあえず、特に速くなるわけではないので、1bit書込みでも良いと思う。
- ちなみにMCSファイルを調べてみると、ただのINTEL HEXファーマットだった。
- レコードタイプ4を使っているので、アドレス拡張されている
- 00000〜5327Bのアドレス(約340kbyte)のデータだった。→これはロジックの規模で変わるのかどうか不明。
- FlashROMは、例えば最初の32Mbit(4Mbyte)がFPGAのコンフィグレーションに使われたとしても、
- 全部で、128Mbit(16Mbyte)あるので、残りはユーザエリアとして使用できるはず。
- Create PROM Fileで、Auto Select PROMを選択しない場合には、別のデータファイルを指定出来る。
- おそらく、INTEL HEXフォーマットでROMデータを記述しておけば、FlashROMの初期データとして使用可能だと思う。
追記: というのは間違いで、ROMデータはバイナリとして用意すれば良い。
- binファイルもバイナリフォーマットで、それを変換してMCSファイルにするので、
- その時に、ユーザデータも一緒にMCSファイルに変換するということだった。
- ちなみに、FPGAのコンフィグレーションは4Mbit(512Kbyte)あれば十分のようだ。
- つまり残りの124Mbitは、ユーザエリアとして自由に使えることになる。
- FPGAのコンフィグレーションは、回路の規模が大きくなっても、あまり変わらないようだ。
- せいぜい400kbyte程度に収まりそうなので、残りはユーザエリアとして利用出来る。
- iMPACTの、Create PROMで、
- Step1で、SPI Flash→Configure Single FPGAを選択
- Step2で、Add Storage Deviceを、仮に8Mとしておく→これは必要最小限のサイズ指定で良さそうな気がする
- Step3で、出力ファイルの指定に加えて、Add Non-Configuration Data FilesをYesにすれば良い。
- 通常通り、bitファイルの指定をした後に、Proceed to add Data File?のDialogが出るので、
- 開始アドレスを指定する。ここでは仮に80000としておく。
- それで、ユーザデータの初期データファイルを指定する。
- MCSファイルが、INTELHEXフォーマットだったので、
- 最初は、INTELHEXフォーマットファイルを指定1してみた。
- 画面上には、メモリマップが表示され、コンフィグレーションデータとユーザデータのエリアが表示される。
- メモリ上の配置がイメージで見られるので、とても分かりやすい。
- コンフィグレーションデータだけでは、あまり意味のない機能だと思ったんだけど、
- これは、ユーザデータの配置のための機能だったんだな〜。
- 最後にGenerate File...を忘れずに。。
- 書込み時間は、さらに掛かるようになる。
- ユーザデータの大きさにもよると思うけど、書き始めたら10分以上掛かる感じなので、別の事でもしてましょう。
- で、後で中身を確認してみると、書込みはされているが、全く違うデータだった。
- おかしいな〜と良くみると、どうもASCIIデータが書かれているようだ。
- 結局、INTELHEXファイルが、そのまま書込まれていることが分かった。
- つまり、DataFileにはバイナリデータを指定する必要があるらしい。
- DataFileを、バイナリ形式にしたら、ちゃんと書込まれました。
- 考えてみれば、binフォーマットはバイナリで、変換後にMCSになるんだから当たり前か。。
- これで、FlashROMを自由に使うことが出来そうだ。
- ちなみにデータエリアを書き換える必要が無い場合は、
- Add Storage Deviceを4Mぐらいに設定して、データエリアを消さないようにすれば、
- コンフィグレーションデータのみの書込みになるので、少し速くなる。
- というより、データエリアに余計なストレスを与えることになるので、
- データエリアには必要な時だけ書くようにするべきだと思う。
- 繰返しになるけど、CreatePROMの設定を変えたり、bitファイル作り直した時は、
- Generate File...を忘れがちなので、気をつけて。
- bitファイルの生成は、自分の環境では2分30秒ぐらいだが、
- コンフィグレーションデータのみでも、SPI Flashへの書込みは6分15秒ぐらい掛かる。
- 結局、全部で9分ぐらい掛かることになる。
- デバッグ時には、FPGAへ直接、bitファイルを書き込んでしまった方が良い。
- これなら12秒ぐらい、bitファイル生成を含めても3分で完了する。
- 約1/3の時間で済むことになるので、回路がある程度確定するまでは、bitファイルで書くようにする。
- 当然、電源を切ると消えてしまうが、SPIフラッシュへの書込みは時間掛かり過ぎ。
- まぁ、JTAGによるFPGA経由のSPI書込みだから、仕方ないところか。
- この速度は、自分の場合はTopJTAGのデバッグで、パラレル接続のJTAGケーブルを使ってるから、USBケーブルだとちょっと違うかも。
- でも、USBケーブルでも、そんなに速くなかったような気がする。
- Core Generatorで、クロックモジュール(DCM)を作ってみる。
- ISE13ではISE10と違って、CoreGeneratorが独立したアプリケーションになって、
- 最初にプロジェクトを作る必要がある。何かちょっとめんどくさい。。
- Partで、デバイスとパッケージを指定後、GenerationのDesign Entryで、Verilogを指定する。
- ここで指定しないとVHDLになってしまうが、Generate後にProjectOptionをVerilog直して、再度Generateしてもダメ2みたい。
- プロジェクトを作ったら、FPGA Features and Design→Clocking→Clocking Wizardをダブルクリックして、
- まず、好きなモジュール名を指定して、入力周波数とか、出力周波数とか指定3して、Generateする。
- そうするとipcore_dirに、作成したモジュールの.vとか.xcoファイルが生成される。
- このxcoファイルを、Add SourceでISEのプロジェクトに追加すれば良い。
- でもこれは、Spartan6の固有の事なんかじゃなくて、ISE13の一般的な話だなぁ。
1本当は、バイナリファイルを指定しなければならない。
2なんか、やり方を間違ってるのかもしれないが、分からないので、全部消してやり直した。
3説明がめんどくさいので省略。
[top]
- LX9 Microboardに付いているライセンスを使うと、ChipScopeというLogicアナライザのようなモジュールを生成することが出来る。
- あまり良く分かっていないのだけど、指定した信号の変化をRAMに保存して、
- 後で取り出すことが出来るような回路を合成してくれるんだと思う。
- ChipScopeのライセンスは1年なので、最初から取っても良いと思うが、
- FreeのWebPackライセンスでも、普通の回路の論理合成は出来るので、必要になってから取っても良いと思う。
- ChipScopeのライセンスは、デバイス限定だが1年なので、
- Microboardを何個か買っておけば、何年かはChipScopeが使えるということ4かな。。
- 最初、ChipScopeのインプリメント時に、ライセンスが無いとエラーになってしまって困った。
- Help→Manage Lisence...で確認しても、ChipScopeのライセンスが無い。
- 結局、別のライセンスファイルが参照されていただけだった。。
- ライセンスファイルが、ちゃんと参照されているかどうか確認しましょう。。
- Project→New Source...で、ChipScopeを組込む
- Hierarchyに、cdcファイルが追加されるので、
- ダブルクリックすると、ChipScopePro Core Inserterが起動する
- これで、クロックとトリガの設定、記録するNETの設定を行う。
- 最初のDEVICEウィンドウは、そのままNEXTボタンを押す
- 次のICONウィンドウも良く分からないので、そのままNEXT
- その次のILAウィンドウで、いろいろ設定する。
- Trigger Parametersの設定
- TriggerPortsというのは、トリガとなる信号毎に別のポートになるという意味かな?
- とりあえず、Trigger Portsは1のままにしておく。
- Trigger Widthは、記録する信号の数だと思うので、16にしてみる。
- あとは良くわからないので、そのままNEXT
- Capture Parametersの設定
- Data Depthで、記録するサンプル数を設定。とりあえずそのままNEXT
- ILAの設定では、Net Connectionsが未設定で赤になっているので設定する
- 論理合成時に、NETの名前が変わってしまわないようなので、
- これはSynthesizeのプロパティで、Keep HierarchyをYesにすれば良いようだ。
- でも自分の場合、inoutをモジュールに入れておいたらエラーになってしまったので、仕方なくOFFにして実行した。
- inoutで階層を保持することが出来ないというのは、どういうことなのかな。
- 普通、Hi-Zにしておいて、出力するときだけH,Lに設定する配線ってだけだと思うけど。。
- もしかすると、外部に繋がるバッファに接続するNETがHi-Zになるのはまずいかも。
- うーん。考えてみると、なんか、そんな気がしてきた。。
- 入出力バッファに接続する場合は、最上位階層まで入出力を分けておかないとダメなのかなぁ。
- まぁ、Keep Hierarchy設定しなければ良いんだけど。
- 何か、良い方法があるのかなぁ。それとも何か間違っているのか。。
4ライセンス取得自体に期限があるかもしれないけど。
[top]
- 12pinヘッダ(2x6 female)(内I/O8pin)x2個
- LX9ハードウェアマニュアルの、PMODのピン配置は間違ってはいないが、
- ものすごく判りづらいので、実際の配置に合わせて書き直した。
FPGA# | I/O Signal | PIN# | PIN# | I/O Signal | FPGA# |
F15 | FPGA_PMOD1_P1 | 1 | 7 | FPGA_PMOD1_P7 | F14 |
F16 | FPGA_PMOD1_P2 | 2 | 8 | FPGA_PMOD1_P8 | G14 |
C17 | FPGA_PMOD1_P3 | 3 | 9 | FPGA_PMOD1_P9 | D17 |
C18 | FPGA_PMOD1_P4 | 4 | 10 | FPGA_PMOD1_P10 | D18 |
‐ | GND | 5 | 11 | GND | ‐ |
‐ | +3.3V_LS1 | 6 | 12 | +3.3V_LS1 | ‐ |
FPGA# | I/O Signal | PIN# | PIN# | I/O Signal | FPGA# |
H12 | FPGA_PMOD2_P1 | 1 | 7 | FPGA_PMOD2_P7 | K12 |
G13 | FPGA_PMOD2_P2 | 2 | 8 | FPGA_PMOD2_P8 | K13 |
E16 | FPGA_PMOD2_P3 | 3 | 9 | FPGA_PMOD2_P9 | F17 |
E18 | FPGA_PMOD2_P4 | 4 | 10 | FPGA_PMOD2_P10 | F18 |
‐ | GND | 5 | 11 | GND | ‐ |
‐ | +3.3V_LS1 | 6 | 12 | +3.3V_LS1 | ‐ |
FPGA# | NetName |
P4 | FPGA_GPIO_LED1 |
L6 | FPGA_GPIO_LED2 |
F5 | FPGA_GPIO_LED3 |
C2 | FPGA_GPIO_LED4 |
FPGA# | NetName |
B3 | FPGA_DIP1 |
A3 | FPGA_DIP2 |
B4 | FPGA_DIP3 |
A4 | FPGA_DIP4 |
FPGA# | NetName |
V4 | USER_RESET |
FPGA# | SignalName | Clock |
V10(GCLK0) | USER_CLOCK | 40MHz(Programmable) |
K15(GCLK9) | CLOCK_Y2 | 66.7MHz(Programmable) |
C10(GCLK13) | CLOCK_Y3 | 100MHz(Programmable) |
R8(GCLK31) | BACKUP_CLOCK | 66.7MHz |
FPGA# | SignalName |
R7 | USB_RS232_RXD |
T7 | USB_RS232_TXD |
[top]
- いろいろメモ。特にISE13.2の使いにくいところとか。
- こちらの「AVNETのSpartan-6 LX9 MicroBoardがiMPACTに認識されない件の解決方法」を見たんだけど、実際に、Digilentフォルダをコピーしたかどうか忘れてしまった。
- 13.2では自動認識されると書いてあるので、結局はやらなかったような気がする。
- 実際、13.2では特に問題なく使えていたんだけど、iMPACTを終了せずにMicroBoardの接続を外すと、認識されなくなる問題があった。
- Cable Resetとか、Disconnectとか、いろいろ試したけどダメ。iMPACTやISEを再起動してもダメだったが、Windowsの再起動で直った。
- 上の操作をしてみたら、この問題は起きなくなったような気がする。(未確認)
- タブの文字が省略されないため、大き過ぎて数個しか表示されないので、いちいちスクロールしないといけない。
- それなのに、「ISE Design Suite 情報センター」とか「Design Summary (Programming File Generated)」なんてやたらに長ーいタブがデフォルトであったりするので、余計頭にくる。
- 必要ないのは消せば良いんだけど、Map ReportとかHierarchyから参照できなくなったので、Design Summaryは残しておきたい。
- とりあえず、出来るだけソースファイル名を短くするようにしているが、これは主客転倒だ。
- これは、以前のように、文字を省略して表示するようにして欲しい。
- Findコマンドの文字入力が下に固定されているが、Findボタンは上なので、カーソル移動が煩わしい。
- Findの文字入力をフローティングにするか、Findボタンとくっつけて欲しい。
- とりあえず、Findボタンはフローティングなので、下の方に持ってきて使っているが、けっこう邪魔。
- 最近、Findボタンを一番下に貼りつけれらると分ったので、それで使っていて少し慣れてきた。
- 同じ名前のソースファイルが複数開いてしまう。それだけなら良いんだけど、
- 編集すると他のエディタで更新されたので上書きするかどうか聞いてきて煩わしい。
- ISE10.xの時は、同じファイルが複数開くことは無かったので、バグだと思う。
- iMPACTも別ウィンドウで開くようになったが、最後にSaveしても書込み条件が残らない。
- 毎回、Create PROM Fileの設定をしなければならない。(やり方が悪いのかもしれないが)
- MCSファイルの生成、PROM File Formatterで、Step3のOutput File Locationのデフォルトでディレクトリが保存されていない?
- それで、iMPACTは立上げたままにしておけばいいんだけど、iMPACTが複数個起動したりするので、やっぱり煩わしい。
- さっきまで、普通に書込みが出来ていたのに、ケーブルを外したりした時、
- これは、シリアルポート経由でデバッグ中に発生するが、シリアルケーブルを外しても回復しない。
- ターミナルソフトを終了すると、また接続出来るようになる。
- Digilent USB JTAGケーブル接続なので、シリアルポートは関係ないような気がするが、
- ケーブルのチェックルーチンが、シリアルポートに異常があると、そこで終了してしまうのかもしれない。
- Number of LOCed IOBsが100%って、どういう意味なんだろう?
- IOバッファを使い切ったってこと?IOバッファって、元々全端子についてるんじゃないのかな?
- とりあえず、インプリメントできるみたいなので、気にしないことにする。
- generateを使うことで、複数のインスタンスを生成することが出来るみたい。
generate
genvar p;
for (p=0; p<POINT_N-1 ;p=p+1) begin : gen_dft_inst
bs_dft_unit bs_dft_inst (
.clk(clk),
.rst(rst),
.in(bibun_out),
.t(t[p]),
);
end
endgenerate
- DesignSummaryの数が微妙に違う。generateの方が僅かに小さい。
- でも、微妙だ。どういうことなんだろう?生成されていないのかな?
| Normal | generate |
Number of Slice Registers | 509 | 502 |
Number of Slice LUTs | 1153 | 1153 |
Number of occupied Slices | 362 | 360 |
Number of LUT Flip Flop pairs used | 1182 | 1194 |
- Impactで書込み時に、Program Faildと赤く表示される。
- Parallel Ceble IVでの接続時の話だけど。
- 何回かやり直してるうちに書けるようになったので、原因がよく分からなかった。
- Verilogって、下位モジュールのUCF定義って出来ないのかな。
- 例えば、下位モジュール内でUCF定義しておけば、上位モジュールではUCF定義要らないとか。
- メモリとか接続する場合、下位モジュールでしか使っていなくても、
- 下位モジュールから上位モジュールに、全配線を接続するのが面倒なんだけど。
- Spartan6 LX9ボードの、ISEのプロジェクト設定
Property_Name | Value |
Family | Spartan6 |
Device | XC6SLX9 |
Package | CSG324 |
Speed | −3 |
[top]
- SDRAMのメモリコントローラのIPも、SDRAMの基本が分かっていないと全く使いこなせない。
- まず、基本的な動作を確認するところから始めよう。ということで。
- DRAMって、そもそも使ったことが無い。SDRAMって何?というレベルなので、
- どんな挙動するものなのか全く分らずに、試行錯誤してるメモです。
- ちゃんとSDRAMを使おうという方には、全く参考になりませんので、あしからず。
- SDRAMの動作に関しては、メモリICの実践活用法(桑野雅彦著・CQ出版)がおすすめ。
- DDR-SDRAMの動作について、なかなか平易に書いてあるものが見つからなかったけど、この本を見てやっと理解することができた。
- SDRAM以外のメモリの動作についても、これだけ詳しく解説されているものは無いと思う。
- LX9ボード上には、MicronのSDRAMが載っている。
- MT46H32M16は、8M x 16 x 4banks構成
- Rowアドレス→A[12:0] (8K)
- Columnアドレス→A[9:0] (1K)
- Refresh count→8K
- つまりRowアドレスの10bit分のリフレッシュが必要ということ?
- LX9のユーザーマニュアルによると、SDRAMのアドレスはA[12:0]なので、
- RowアドレスとColumnアドレスを2回に分けて与える必要がある。
- SDRAMのクロックは、差動出力にしなければならないらしい。
- 差動出力のコンポーネントは、OBUFDSという奴だったと思うけど、
- Verilogでのインプリメント(いやインスタンシエートというのかな)は、どうすれば良いんだろう。
- で、調べてみると以下の資料が見つかった。日本語なのは有り難い。
- これで良いのかな?ただ、いきなり書けば良いのか。。
OBUFDS sdram_clock (
.O (sdram_ck),
.OB (sdram_ck_n),
.I (clk5));
- Implementでエラーが出た
- clk5はDCMで作ったものなんだけど、なんか制約をつけないとダメらしい。
ERROR:Place:1205 - This design contains a global buffer instance,
<bs_dcm_clk/clkout2_buf>, driving the net, <clk5>, that is driving the
following (first 30) non-clock load pins off chip.
< PIN: sdram_ck.O; >
This design practice, in Spartan-6, can lead to an unroutable situation due
to limitations in the global routing. If the design does route there may be
excessive delay or skew on this net. It is recommended to use a Clock
Forwarding technique to create a reliable and repeatable low skew solution:
instantiate an ODDR2 component; tie the .D0 pin to Logic1; tie the .D1 pin to
Logic0; tie the clock net to be forwarded to .C0; tie the inverted clock to
.C1. If you wish to override this recommendation, you may use the
CLOCK_DEDICATED_ROUTE constraint (given below) in the .ucf file to demote
this message to a WARNING and allow your design to continue. Although the net
may still not route, you will be able to analyze the failure in FPGA_Editor.
< PIN "bs_dcm_clk/clkout2_buf.O" CLOCK_DEDICATED_ROUTE = FALSE; >
ERROR:Place:1136 - This design contains a global buffer instance,
<bs_dcm_clk/clkout2_buf>, driving the net, <clk5>, that is driving the
following (first 30) non-clock load pins.
< PIN: sdram_ck.O; >
< PIN: sdram_clock/N/INV.A6; >
This is not a recommended design practice in Spartan-6 due to limitations in
the global routing that may cause excessive delay, skew or unroutable
situations. It is recommended to only use a BUFG resource to drive clock
loads. If you wish to override this recommendation, you may use the
CLOCK_DEDICATED_ROUTE constraint (given below) in the .ucf file to demote
this message to a WARNING and allow your design to continue.
< PIN "bs_dcm_clk/clkout2_buf.O" CLOCK_DEDICATED_ROUTE = FALSE; >
ERROR:Pack:1654 - The timing-driven placement phase encountered an error.
PIN "bs_dcm_clk/clkout2_buf.O" CLOCK_DEDICATED_ROUTE = FALSE;
- SDRAMは、基本的にRAS,CAS,WEの組合せで動作を決めるらしい。
Command | CK | CKE | CS | RAS | CAS | WE | ADRS | A10 | BA | Description |
MRS | ↑ | H | L | L | L | L | OPcode | OPcode | OPcode | Mode Reg Set |
REF | ↑ | H | L | L | L | H | X | X | X | Auto Reflesh |
ACTIVE | ↑ | H | L | L | H | H | Row | X | Bank | Active Row |
READ | ↑ | H | L | H | L | H | Column | EnableAP | Bank | Read Column |
WRITE | ↑ | H | L | H | L | L | Column | EnableAP | Bank | Write Column |
PRECHARGE | ↑ | H | L | L | H | L | X | AllBank | | Bank Precharge |
NOP | ↑ | H | L | H | H | H | X | X | X | No Operation |
- LX9 Microboardの場合、CSは100Ωでプルダウンされており、FPGAに接続されていない。
- 非選択にする場合以外は、CSを使用しないので特に問題なし。
- CKEは基本的にH固定にする。
- mcb3_rzqは、DDR3‐SDRAM用のキャリブレーション端子。使用しない。
- SDRAMのデバッグはピン数が多いので、かなり面倒。
- 各ピンに直接針当てするのは、実際上は無理という感じだし
- このLX9評価ボードの場合、デバッグ用に出力する端子の数が、恐ろしく少ないので
- 何より、SDRAMの振る舞いが分らないので、テストベンチの作り様が無い。
- 試しに、 TopJTAGというのを使ってみる。
- TopJTAGは、MitouJTAGに較べるとかなりシンプルなツールなんだけど、なかなか良さそう。
- 2010年4月が最終バージョンなので、更新止まってるのがちょっと残念だけど、
- 必要最低限の機能はあると思う。頑張ってUpdateして欲しい。
- Fileメニュー→NewProjectWizardを選択、ケーブルを選択5してNextボタンを押す
- Connection : Zilinx Parallel Cable III/IV
- Port : LPT1
- TCK freq : 200000Hz
- JTAG Chainで、デバイスが検出されるので、Nextボタンを押す
- BSDLファイルとパッケージをセットする。CLICK_HERE_TO_SETのリンクを押す
- BSDLファイルの入ったディレクトリをセットする。
- 自分の場合、C:\Xilinx\13.2\ISE_DS\ISE\aspartan6\dataを追加
- で、Searchボタンを押すと、BSDLファイルのリストが表示される。
- パッケージはCSG324なので、EntityがXA6SLX9_CSG324のものを選択
- xa6slx9_csg324.bsdと、xa6sxl9_csg324_1532.bsdがあるが、良く判らないので前者を選ぶ
- BSDLファイルとパッケージがセットされるので、OKボタンを押す。
- これで、パッケージの絵が表示され、Runボタンを押すと何か動いているような感じが判る。
- JTAGの速度は、バウンダリスキャンで全部シリアルでデータを読書きするので、ちょっと遅い
- というか、かなり遅いのでリアルタイムの波形観測は難しい。
- FPGAの内部クロックは、かなり速いので、この際、思い切り低速にする。
- 確実に動くように、クロックを数十Hz〜数Hzぐらいの目に見えるぐらいの速度まで落としてやる。
- 本来、SDRAMの駆動はあまり速度を落としたらダメなんだけど、
- まぁ多分ある程度は動くだろう。というイイカゲンな考えで。。
- このままだと、何がなんだか判らないので、ピン名を設定する。
- Pinsメニュー→Edit_Pin_names_and_Busesを選択
- Import...ボタンを押して、UCFファイルを選択する。
- すると、UCFファイルで定義されたピン名が設定される。
- この状態で、ピン名を選択して、Add to Waveformすれば、波形が表示される。
- でも、TopJTAGはステート表示できないので、ちょっと見辛い。
- とりあえず、RAS,CAS,WEを一纏めにしてstat[2:0]とすることで、数値で見れるようにしておく。
stat | SDRAMステート |
2 | PreCharge |
3 | Active & ROW |
4 | Write |
5 | Read |
7 | NOP |
- SDRAMに接続された端子の信号は、基本的にそのままバウンダリスキャンで観測できる。
- それ以外の信号は、LX9の回路図をみて、XC6SLX9の何も接続されていないピンに、デバッグしたい信号を割り当てる。
- 使っていない空きピンは結構あるので、足りないってことは多分無いと思う。
inout [15:0] sdram_data;
reg [15:0] sd_data;
assign sdram_data = sd_data;
rbuf <= sdram_data;
BA1_BA0 | An〜A7 | A6〜A4 | A3 | A2〜A0 |
StdMode | OpeMode | CASLate | BurstTyp | BurstLen |
0 0 | 0...0 | 2 or 3 | IL/Seq | 2〜16 |
- Standard Modeの設定は、BA1,BA0は00固定
- A2〜A0の3ビットは、バースト長。Read/Write共通で
A2 | A1 | A0 | BurstLength |
0 | 0 | 1 | 2 |
0 | 1 | 0 | 4 |
0 | 1 | 1 | 8 |
1 | 0 | 0 | 16 |
A3 | BurstType |
0 | Sequential |
1 | Interleaved |
A6 | A5 | A4 | CASLatency |
0 | 1 | 0 | 2 |
0 | 1 | 1 | 3 |
- バーストのデータ出力順は、BurstTypeとStartColumnAddressで変化する。
- Sequentialの場合は、スタートしたカラムアドレスから順に出力されるだけだが、
- Interleavedでは、かなり複雑なのでマニュアル参照。
- アドレスは0〜12なので、
- CASレイテンシ2、バーストタイプはシーケンシャル、バースト長2とすると、こういうこと?
000000_010_0_001
- でも、これをシーケンスの中に入れてMRSしたら、全くRead出来なくなった。
- DDR-SDRAMなので、データの読書きはクロック速度の倍になる
- CASレイテンシは、おそらく2
- DQSの立上りで、1回だけ書き込んだつもりなのに、DQS→Hi-Zのタイミングでも書き込まれている感じ
- SDRAMのマニュアルを見ると、バースト長の設定は、2,4,8,16のいずれか(Read/Writeの区別は無い)
- 書き込みのバースト長の所為で、Hi-Zのタイミングでも書き込まれている可能性高い
- 少なくとも2アドレスづつ読書きする必要があるということ?
- 2アドレスづつ書いて1個捨てても、メモリ容量は十分か。
- Writeは、dqsがHi-ZからLow→Highと変化した最初の立上りで1個目
- 次のHigh→Lowの立下りで2個目が書き込まれる
- これを2回繰返した場合、最後の立下り、立上りの書き込みが有効になる。
- というより、多分、やった回数だけ上書きされると思われる。
- 必ず、立上り、立下りの組合せにする必要がありそう→バースト長は偶数しか設定できないので
- 最後を立下りじゃなくHigh→Hi-Zにすると、そのタイミングでも書き込まれるようだ
- 読出しのバースト長が4になっている?
- そうじゃなくて、バースト長2を2回読んでるのかもしれない
- あぁ、そうか。Readサイクル中のクロック立上り回数分だけ読み込まれるみたいだ。
- SDRAMのマニュアルを読んでも、デフォルト値がわからん。
- でも、バースト長2、CASレイテンシ2のような気がする
- いろいろやっているうちに、やっとDDR-SDRAMの基本的な動作を確認出来た。
- やはりデフォルトは、バースト長2、レイテンシ2だと思う。
- Writeサイクル中のck立上りから1クロック以上置いて書込みデータを送る必要がある
- すぐに書き込むと、失敗する。→これで、結構ハマった。。
- 読出し時は、CASレイテンシがあるのが分かっていたけど、書込みでも少し間を置く必要があるのが分からなかった6
- Readサイクル中のckの立上りの回数分だけ、読み出される。
- そのckの立上りから数えて、2クロック後から、(レイテンシ2)
- 0.5クロック毎に2個のデータが出力される(バースト長2)
- Readと同じ様に、Writeシーケンス中にckの立上りが1個あれば、すぐNOPにしても2個書き込めそうだが、
- やってみたら、1個目は書けたが、2個目はダメだった。
- 以下に示したTopJTAGによる波形の例では、Writeシーケンスで2クロック入れてからNOPにしている
- この場合は、とりあえず書き込んだ内容を読み出すことが出来ている。
- statの値が、2:PreCharge, 3:Active, 4:Write, 5:Read, 7:NOP
- このようにNOPを入れる意味はあまり無いので、
- 書き込み中は、NOPにせずにWriteシーケンスを続けた方が良いのかもしれない。
- DDR-SDRAMなので、ckの立上り、立下りの両エッジで読出されていることが判る。
- 書込みは、クロックのエッジではなく、dqsの立上り、立下りで指定7する必要がある
- 読出しは、クロックエッジで、この場合dqsはクロックと同期して出力される
- バースト長は2なので、2アドレスづつ読書きしている
- 読出しはReadシーケンス中のクロック立上りの回数分だけ行われる。
- CASレイテンシが2なので、2クロック分遅れて2個のデータが出力される。
- ちなみに、この実験ではリフレッシュはしていないので、データはそのうち消える
- でも少なくとも数秒後ぐらいなら、問題なく保持されているようだ。
- 実験では、Columnアドレスをインクリメントしながらアクセスしていたが、
- リフレッシュを考えると、Rowアドレスをインクリメントする方が良いのかもしれない。
5ちなみにUSBによるJTAG接続は選べないので、パラレル接続のJTAGケーブルを使用している。
6実は前述の桑野さんの本には、書いてあったんだけど、後から気がついた。。
7この例ではシーケンサの関係でタイミング的にゆっくり書き込んでいるが、読出しと同様の速度で書き込むことも可能。
[top]
[電子工作関連に戻る]