始めに
DRAMと接続してDキャッシュ版を公開して早くも半年、まだ納得いくところまでできていないですが、Cプログラムがそれなりに動いているので、I,Dキャッシュ双方が動作している版をmy-riscv-rv32i-dcにマージいたしました。これにより、命令とデータが同一DRAM上に搭載されて、CPUへのプログラムのアップロードがDRAMのみでの動作が可能となりました。
2025/5/21追記
- instruction RAM版でのいくつかのbug fixをしました。I,Dキャッシュのサイズを14ビット(arty A7 T100の場合)に設定すると、ctest/ 以下のほとんどのプログラムは動作するようになりました。しかし、I,Dキャッシュのサイズを8bitに絞ると動作しないものが出てきます。I,Dキャッシュ双方がスラッシングを起こすような条件で動作しない不具合がまだあるようです。
2025/11/7追記
- モニタ機能を強化しました。Break point機能の追加、IOレジスタ,CSRレジスタ,レジスタファイルのダンプができるようになり、プログラムを停止したときに各レジスタの値の読み書きが可能となりました。
- 継続的なBugfixにより安定度が増しております。現在わかっている不具合は、キャッシュサイズを小さく(DWIDTHが7bit以下)した場合に一部データが0化けを起こす、です。たぶんDキャッシュの入れ替えが行われる際にまだ不具合がでるパターンがあるようです。
- git のREADMEを整備すると同時に、英語のみの表記としました。ブラウザの翻訳機能を使ってください。
レポジトリ
https://github.com/yoshiki9636/my-riscv-rv32i-dc
参考URL
Tang PrimerまたはArty A7で自作riscv-rv32iを動かす
Arty A7で自作riscv-rv32iを動かす② DRAMでDキャッシュのみ版
Arty A7でAXIバス簡略仕様でDDR3 SDRAMへ読み書きしてみる ※MIG設定の参考
VivadoでMIG+DDR3のシミュレーションの走らせ方メモ&ModelsimでのMIGシミュレーションの走らせ方追加 ※MIGシミュレーション参考
Ver 0.5の機能・制約
- 単純なダイレクトマップのIキャッシュおよびDキャッシュを実装
- キャッシュのラインサイズは16byte
- IキャッシュとDキャッシュのスヌープは未実装
つまりプログラム実行中に命令を書き換えてもキャッシュに反映されない - I/Oは4セットのRGB LED、12ピン(outputのみ)
- 現在のクロック設定は200MHz/166.66667MHz/50MHz。
- uartモニターにbreak機能とIO/csr/RFダンプ・書き換え機能を追加
- Uartでの表字をI/Oで実現
- interruptピンを使った外部割込み(単体)、mretの実装を追加
- illegal operations exceptionを追加
- privilegeはM-modeのみ
- fence系、ecall以外のecall系未実装
- gccのrisc-vツールチェーンでのベアメタルCの動作確認済み
※コンパイル方法はctest/cmpl.shを参考にしてください。
※ただし、newlibのlibc_nanoやlibm_nanoを用いた場合に、sprintfを用いた浮動小数点の表示がうまくいきません。ctest/内部の*_test2.cというものがそれに当たります。詳細原因究明中。
※dijkstra_test.cが動作しません。linux上では動作確認しているので、まだCPUにバグがあります・・・。
使い方
特に変わっていないので mig対応によりModelsimシミュレーションの方法が大幅に変わったので、githubページのReadmeまたは、前回のページとVivadoでMIG+DDR3のシミュレーションの走らせ方メモ&ModelsimでのMIGシミュレーションの走らせ方追加を参考にしてください。
モニター機能一覧
g : goto PC address ( run program until quit ) : format: g <start addess>
Ctrl-c : quit from any command : format: Ctrl-c
w : write date to SDRAM : format: w <start adderss> <data> ....<data> Ctrl-c
r : read data from SDRAM : format: r <start address> <end adderss>
t : trashed memory data and 0 clear : format: t <start address> <end adderss>
s : program break point set : format: s <break address>
Setting address : using even number address
Unsetting address : using odd number address
p : read IO regs/csr/RF : format: p <start address> <end adderss> address : upper 2bits == 2'b11 : I/O registers
address : upper 2bits == 2'b10 : csr registers
address : upper 2bits == 2'b00 : Register Files
i : write IO regs/csr/RF : format: i <start adderss> <data> ....<data> Ctrl-c
address : upper 2bits == 2'b11 : I/O registers
address : upper 2bits == 2'b10 : csr registers
address : upper 2bits == 2'b00 : Register Files
j : print current PC value : format: j
z : parge D cache : format: z // currently not woring
終わりに
短い手抜きの記事でした。まだベアメタルCのテストで動かないものがあり、切り分けがだんだんと難しくなっています。モニタ機能を強化する必要があるのですが、 一方手元のArty A7-35Tでは搭載資源を食い尽くしつつあり、T100へのアップグレードの必要性に迫られています。悩みは尽きません。あとタイマー等のインプリとかも必要になってくるので、ぼちぼちとやって行こうと思います。