CHAPTER16 SPI CORE
1つのマスタデバイスが複数のスレーブデバイスを持つ
SPIは3つの信号線により構成される
clock(クロック)
mosi (Master Out Slave In)
miso(Master In Slave Out)
スレーブを選択するための信号線も追加で持つこともある
ss_n(Slave Select)
マスタデバイスがクロックを生成、データの転送を行う
SPIコントローラを駆動するシステムクロックはSPIクロックよりも高速
Basic Timing
SPIバスはsclkのエッジをデータ転送に利用する
driving: 新しいビットをデータラインへ出力
sampling: データラインからビットを取り込み
https://gyazo.com/432d6757151e519ca939809fad62ef82
t0
マスタはss_nをアサート
指定されたスレーブは最初のデータビット(ビット7)をmisoライン上に配置
t1
マスタはSPIクロックを開始
マスタはmosiライン上のビットb7をドライブ
SPIクロック期間の前半が0であるため、sclkの値は変わりません
t2
マスタはSPIクロックを上げ、クロック期間の後半へと進みます
0から1への遷移エッジで、マスタはmiso上のデータをサンプルし、スレーブはmosi上のデータをサンプルする
t3
t3で、最初のSPIクロックサイクルが完了します。マスターは2番目のSPIクロック期間を開始し、sclkを下げます。マスターとスレーブは新しいビットをデータラインにドライブします
t4
t4で、マスターは再びsclkを上げ、マスターとスレーブは新しいデータビットをサンプルします。ドライビングとサンプリングの活動は、8つのデータビットが転送されるまで繰り返されます
t5
最後のデータはt5でサンプルされ
t6
sclkはt6で0に戻ります
t7
t7で、マスターはss_nを非アサートします
サンプリングとドライビングのタイミング
全てのサンプリングはsclkの立ち上がりエッジで実行され、全てのドライビング(最初のものを除く)はsclkの立ち下がりエッジで実行されることに注意してください
Operation modes
SPIのオペレーションモード(動作モード)は、「SPIのクロックエッジ」と「データ線のドライブとサンプリング」の関係を定義する
2つのパラメータ
clock polarity (cpol)
クロック極性
通信を行わない状態でのsclkの値(0か1か)
clock phase (cpha)
クロック位相
最初のデータビットの駆動(driving)にクロックエッジが使われるかどうか
cphaが1の場合、最初の遷移エッジでビットを駆動
cphaが0の場合、ゼロ番目の遷移エッジ(クロック開始前)でビットを駆動
動作モード
https://gyazo.com/b9378e960c658e59d493deb1e44724f7
モード0(cpol = 0, cpha = 0)
クロック極性は「正極性」、通信を行わない時は0に固定(cpol = 0)
最初のクロックの前に最初のデータが駆動される(cpha = 0)
クロックの「立ち上がり」エッジでサンプリング
モード1(cpol = 0, cpha = 1)
クロックの極性は「正極性」、通信を行わない時は0に固定(cpol = 0)
最初のクロックの立ち上がりエッジで最初のデータが駆動される(cpha = 1)
クロックの「立ち下がり」エッジでサンプリング
モード2(cpol = 1, cpha = 0)
クロックの極性は「負極性」、通信を行わない時は1に固定(cpol = 1)
最初のクロックの前に最初のデータが駆動される(cpha = 0)
クロックの「立ち下がり」エッジでサンプリング
モード3(cpol = 1, cpha = 1)
クロックの極性は「負極性」、通信を行わない時は1に固定(cpol = 1)
最初のクロックの立ち下がりで最初のデータ駆動される(cpha = 1)
クロックの「立ち上がり」エッジでサンプリング
「cpha = 0」のデータのドライブは、後述する ss_n がアサートされたタイミングでドライブすると良さそう
Undefined aspects
以下は標準化されているわけではない
ss_n シグナル
転送ビット数
ss_n シグナル(Slave Select)
マスターが ss_n をアサート
マスターとスレーブがデータビットを送受信
マスターは ss_n をデアサート
https://gyazo.com/0dae8d40d29fbaae725ab5a5a5076854
転送ビット数
8ビットのことが多いが、そうでない場合もある
MSBなのかLSBなのか
MSBなことが多いが、そうでない場合もある
このへんはデバイスによってまちまち
SPIコントローラの基本設計
SPIマスタコントローラを作成
8ビットをMSB firstで転送
ss_n はより上位で取り扱うため、今回作成するSPIコントローラの設計には登場しない
https://gyazo.com/3ea678cdc23c7c3fc5a961d42ab76c95
p0開始のタイミングで、コントローラは新しいビットを mosi へドライブする
同じタイミングで sclk を1から0へ立ち下げる
sclk の立ち下がりクロックエッジで、スレーブは miso へ新しいビットをドライブする
p0終了のタイミングでマスタは miso をサンプリングしてデータを取り込む
同じタイミング sclk を 0から1へ立ち上げる(sclk の立ち上がりエッジ)
sclk の立ち上がりエッジで、スレーブは mosi のデータをサンプリングする
これらのアクティビティが8回行われ、コントローラは8ビットのデータの送受信を行う
FSMDの構築
FSMDってなんだっけ?
SPIコントローラのインターフェース
input clk, reset
input din
slaveへ送信するデータ(8ビット)
input dvsr
input start
input cpol, cpha
Mode 0: sclk is 1 in p1 state and is 0 otherwise
Mode 1: sclk is 1 in p0 state and is 0 otherwise
Mode 2: sclk はモード0の反転
Mode 3: sclk はモード1の反転
output dout
slaveから受信したデータ(8ビット)
output spi_done_tick, ready
output sclk
input miso
master ← slave
input mosi
master → slave
FSMDを読み解く
https://gyazo.com/5cc032d6475a5a380c108ba284ea7a16
idle
ready = 1
もし start == 1 なら次へ、そうでないならIDLEの開始地点へ戻る
c<=0; n<=0; so<=din
p0(dvsr回待機後、si へ miso の値を取り込む)
もし c == dvsr なら、
c<=0
si <= (si<<1) & miso
既存の si をシフトして、空いたところに miso の値をセットする
si の値は dout へ送られる
そうでないなら、
c<=c+1 してp0の先頭へ戻る
p1(dvsr回待機後、)
もし c == dvsr なら、
もし n == 7 なら、
spi_done_tick <= 1
idle へ戻る
そうでないなら、
c<=0
so<=(so<<1)&0
n<=n+1
そうでないなら、
c<=c+1 してp1の先頭へ戻る
アサイン
入力
assign ready = ready_i;
assign spi_done_tick = spi_done_tick_i;
モード制御
assign p_clk = (state_next==p1 && ~cpha) || (state_next==p0 && cpha)
assign spi_clk_next = (cpol) ? ~p_clk : p_clk;
出力
assign dout = si_reg;
assign mosi = so_reg[7];
assign sclk = spi_clk_reg;
メモ
p_clk = (state_next==p1 && ~cpha) || (state_next == p0 && cpha) を読み解く
前提
Mode 0は cpha=0 かつ cpol=0
Mode1は cpha=1
レジスタマップ
SPIコントローラの読み書き
set(write) the value of dvsr
ディバイザの設定
set(write) the SPI mode via cpol and cpha
SPIモードの設定
activate and deactivate(write) the slave-select signals
Slaveの選択
specify(write) the output data and start the data transfer
出力データの指定と転送の開始
retrieve(read) the received data byte
入力データの取得
check(read) the ready signal to determine whether the controller is ready
コントローラのready信号の取得
SPIコントローラのレジスタ
リードレジスタ
オフセット0 (read data and status register)
bits 7 to 0: 8-bit received data
bit 8: ready status
ライトレジスタ
オフセット1 (slave-select register)
Slaveを選択
オフセット2 (write data and command register)
bits 7 to 0: 8-bit data
オフセット3 (control register)
bits 15 to 0: 16ビット divisor value
bit 16: 1-bit cpol value
bit 17: 1-bit cpha value
Wrapping circuit for the slot interface
モジュール
chu_spi_core
パラメータ
input logic clk, reset
// slot interface
input logic cs
input logic read
input logic write
input logic [4:0] addr
input logic [31:0] wr_data
output logic [31:0] rd_data
assign rd_data = {23'b0, spi_ready, spi_out};
// external signal
output logic spi_sclk
output logic spi_mosi
input logic spi_miso
output logic [S-1:0] spi_ss_n]
内部レジスタ
logic [17:0] ctrl_reg;
assign dvsr = ctrl_reg[15:0];
assign cpol = ctrl_reg[16];
assign cpha = ctrl_reg[17];
logic [S-1:0] ss_n_reg;
logic [7:0] spi_out;