Version 0.8
コントリビュータ: Alon Amid, Krste Asanovic, Allen Baum, Alex Bradbury, Tony Brewer, Chris Celio, Aliaksei Chapyzhenka, Silviu Chiricescu, Ken Dockser, Bob Dreyer, Roger Espasa, Sean Halle, John Hauser, David Horner, Bruce Hoult, Bill Huffman, Constantine Korikov, Ben Korpan, Robin Kruppe, Yunsup Lee, Guy Lemieux, Filip Moc, Rich Newell, Albert Ou, David Patterson, Colin Schmidt, Alex Solomatnikov, Steve Wallach, Andrew Waterman, Jim Wilson.
現在のバージョンで分かっている問題点:
- エンコーディングフォーマットをより改善する必要がある。
- ベクトルメモリに関するコンシステンシモデルを明らかにする必要がある。
- 特権アーキテクチャとの相互関係について説明する必要がある。
1. イントロダクション¶
このドキュメントはRISC-Vのベースベクトル拡張について説明するものである。このドキュメントはベースベクトル拡張のすべての個々の機能について説明するものである。
本ドキュメントは、実装及び評価に用いられるベクトル仕様の安定版プロポーザルのドラフト仕様である。ドラフトのラベルが外れると、Version 0.8はツールチェインの開発、機能シミュレータ、初期の実装に関して十分に安定しているという意図を持ち、マイナーチェンジ及びアップデートが行われていく。
「ベースベクトル拡張」という言葉はベクトルISAコンポーネントの標準的な集合を説明するためのインフォーマルな用語として使用されている。ドラフト版の仕様は特定のベクトル機能がベクトル命令としてどのように実装することができるのかについて把握する意味を持っているが、どのようなベクトル命令のセットが与えられたプラットフォームに対して十分であるかについて決定されている訳ではない。
各実際のプラットフォーム プロファイルは、そのプラットフォームで採用されているベクター拡張の必須コンポーネントを正式に指定します。“V”という文字のついたRISC-V仕様は、標準的なサーバ・アプリけーしょプロセッサ向けのプラットフォームプロファイルです。組み込みプラットフォームを含む他のプラットフォームは、これらの拡張機能のサブセットを実装することを選択できます。特定のプロファイルに準拠する実装の必須サポート手順の正確なセットは、各プロファイル仕様が批准されるまで変更される可能性があります。
このベースベクトル命令は、暗号処理や機械学習などの様々なドメイン向けに拡張された追加ベクトル命令として動作するように設計されている。
2. 実装により決定される定数パラメータ¶
各hartはベクトル拡張をサポートすることにより以下の3つのパラメータを持つことになる。
- 1ベクトル要素の最大ビットサイズELEN。2の累乗の必要がある。
- ベクトルレジスタのビットサイズVLEN ≥ ELEN, 2の累乗の必要がある。
- ストリップビット距離SLEN。VLEN ≥ SLEN ≥ 32 である必要がある。それぞれは2の累乗の必要がある。
プラットフォームのプロファイルにはこれらのパラメータに関して更なる制約が入る可能性がある。例えば、ELEN ≥ max(XLEN,FLEN)や、最小VLEN値、SLEN値の設定など。
VLENのサイズを2の累乗であるという制限を除去する提案が行われている。
ELENのサイズをLMULと異なる(xxx)ようにしようという提案が行われている。
ISAは上記の制約情報をバイナリコードで記述することができ、hartは個のバイナリコードを参照することで異なるパラメータで異なる動作ができるようになる。
コードにより実装パラメータの違いを表現できるようになる。
ベクトル状態がアクティブなスレッドコンテキストは、 VLEN, ELEN, SLENパラメータのいずれかが異なるハードウェアスレッド間では、 実行中に合流することはできない。
3. ベクトル拡張のプログラミングモデル¶
ベクトル拡張ではベースとなるスカラRISC-V
ISAに対して32個のベクトルレジスタと、5つの非特権CSRレジスタ(vstart
,
vxsat
, vxrm
, vtype
, vl
,
vlenb
)が加えられる。ベースのスカラISAが浮動小数点命令を含まない、fcsr
レジスタがさらに追加され、vxsat
とvxrm
のコピーが格納される。以下に各CSRレジスタの仕様を示す。
表1. 新ベクトルCSR
Address | Privilege | Name | Description |
---|---|---|---|
0x008 | URW | vstart | ベクトルスタート位置を示すレジスタ |
0x009 | URW | vxsat | 浮動小数点飽和フラグレジスタ |
0x00A | URW | vxrm | 浮動小数点丸めモードレジスタ |
0xC20 | URO | vl | ベクトル長レジスタ |
0xC21 | URO | vtype | ベクトルデータ型レジスタ |
0xC22 | URO | vlenb | VLEN/8 (ベクトルレジスタのバイト単位での長さ) |
3.1 ベクトルレジスタ¶
ベクトル拡張ではベースのスカラRISC-V
ISAに対して32個のアーキテクチャベクトルレジスタv0
-v31
が加わっている。
それぞれのベクトルレジスタはVLENビットだけのビットを保持する。
Zfinx(“F in X”)は新しいISAのオプションとして考えられているもので、浮動小数点命令が整数レジスタファイルをレジスタ引数として取ることができるようになるものである。0.8ベクトル拡張ではこのオプションとの互換性を持っている。
3.2 mstatus
内でのベクトルコンテキストの状態¶
mstatus[24:23]
にVS
フィールドとしてベクトルのコンテキスト状態を表すためのビットが追加された。これはsstatus[24:23]
のシャドウである。このビットは、浮動小数点のコンテキストを表現するためのFS
フィールドと同様の目的で定義されている。
VS
ビットフィールドがOffの状態で任意のベクトル命令を実行しようとするかvl
,
vtype
, vlenb
, vstart
CSRにアクセスしようとすると不定命令例外が発生する。
VS
フィールドがInitialもしくはCleanの状態でベクトルの状態を変更する任意の命令を実行するか、vl
,
vtype
,
vstart
レジスタへのアクセスを行うとVS
フィールドはDirtyに変更される。
実装では、ベクトルの状態に変更が発生しなくてもVS
フィールドの状態は常にDirtyに設定しておくこともできる。VS
フィールドを細かく実装するかどうかはオプションである。
浮動小数点コンテキスト状態を示すFS
ビットフィールドがOffに設定されている状態でf
レジスタへのアクセス、もしくはfcsr
,
vxsat
, vxrm
CSRへのアクセスを行うと不定命令例外が発生する。
VS
フィールドとFS
フィールドのどちらかがOffに設定されている場合、f
レジスタ、fcsr
,vxsat
,vxrm
にアクセスするベクトル命令はすべて不定命令例外が発生する。しかし、これらのCSRはFS
がOff以外の値に設定されている場合はCSRアクセス命令により読み出すことができる。この場合はVS
フィールドの状態には依存しない。
FS
がInitialかCleanに設定されている場合、fcsr
, vxsat
,
vxrm
CSRもしくはf
レジスタを変更させるような命令を実行すると、FS
フィールドはDirtyに変更される。
FS
フィールドがDirtyに設定されている場合、コンテキストスイッチングを行う場合にはすべてのfcsr
を退避しておかなければならない。
固定小数点演算のみの実装であり浮動小数点に関する情報を退避・復帰させるメリットが生じない場合、FS
フィールドをハードワイヤでDirty固定しておきコストを削減することができる。この場合、fcsr
レジスタはいつでもアクセス可能である。
3.3 ベクトル型レジスタ, vtype
¶
vtype
レジスタはXLENビット長のRead-onlyなCSRであり、ベクトルレジスタファイルに含まれるデフォルトのデータ型を示している。vtype
はvsetvl{i}
命令の実行でしかアップデートすることができない。ベクトル型は各ベクトルレジスタ内の要素の構成についても決定し、どのように複数のベクトルレジスタをグループ化するかについても決定する。
初期のドラフト版では、vtype
レジスタは通常のCSR書き込み命令でも書き込みを行うことが可能であった。vsetvl{i}
命令でのみアップデートが可能である仕様に変更したのは、vtype
レジスタの管理をより簡単化するためである。
ベースベクトル拡張では、vtype
レジスタは3つのフィールドを持っている。vill
,
vsew[2:0]
, vlmul[1:0]
である。
表2. vtype
レジスタレイアウト
Bits | Name | Description |
---|---|---|
XLEN-1 | vill | 不正な値が設定されると1が設定される |
XLEN-2:7 | 予約(write 0) | |
6:5 | vediv[1:0] | EDIV拡張に使用される |
4:2 | vsew[2:0] | SEW(Standard-Element -Width:標準エレメント幅)の設定に使用される |
1:0 | vlmul[1:0] | ベクトルレジ スタのグループ乗算(LMUL)の設定に使用される |
最小のベース実装では、
vtype
では4ビットが必要である。vsew[1:0]
の2ビットとvlmul[1:0]
の2ビットである。vill
の不正な値の設定は、vsew[1:0]
を使用した64ビットのコンビネーションによりエンコードできる。これによりvill
ビットの実装を省略することができる。
vediv[1:0]
フィールドは以下に説明するEDIV命令で使用される。
ベクトルベース拡張に対するさらなる標準・カスタム拡張に関しては、上記のフィールドを拡張してより多くのデータタイプをサポートできるようにする。
It is anticipated that an extended 64-bit instruction encoding would allow these fields to be specified statically in the instruction encoding.
3.2.1. ベクトル標準エレメント幅vsew
¶
vsew
の値は動的標準エレメント幅: standard element
width(SEW)を設定する。デフォルトでは、ベクトルレジスタはVLEN /
SEW標準幅エレメントに分割されているように見ることができる。ベースベクトル拡張では、SEWはmax(XLEN,FLEN)までのサイズを指定することができる。
表3. vsew[2:0]
(standard element width)エンコーディング
vsew[2:0] | SEW | ||
---|---|---|---|
0 | 0 | 0 | 8 |
0 | 0 | 1 | 16 |
0 | 1 | 0 | 32 |
0 | 1 | 1 | 64 |
1 | 0 | 0 | 128 |
1 | 0 | 1 | 256 |
1 | 1 | 0 | 512 |
1 | 1 | 1 | 1024 |
表4. VLEN=128ビットの場合の例
SEW | ベクトルサイズあたりの要素数 |
---|---|
64 | 2 |
32 | 4 |
16 | 8 |
8 | 16 |
3.2.2 ベクトルレジスタグルーピング(vlmul
)¶
複数のベクトルレジスタを1つにグループ化することができ、単一のベクトル命令で複数のベクトルレジスタを取り扱うことができる。ベクトルレジスタグループは、標準幅の要素から構成される、2倍以上のより長いベクトル長を操作することができるようになる。ベクトルレジスタグループは、よりベクトル長の長いアプリケーションにおいて効率的に命令を実行できるようになる。
ベクトルレジスタグループという名前はベクトル命令によって取り扱われる1つ以上のベクトルレジスタのことを指す。グループ内のベクトルレジスタの数はLMULにより管理される。この値は2の累乗である必要があり、vtype
レジスタのvlmul
フィールドで設定される(LMUL=2^vlmul[1:0]
)。
VLMAX=LMUL*VLEN/SEWは、現在のSEWおよびLMULの構成で実行できる単一のベクトル命令の最大データエレメントの数である。
vlmul | LMUL | #groups | VLMAX | Grouped registers | |
---|---|---|---|---|---|
0 | 0 | 1 | 32 | VLEN/SEW | vn (グループに1つのレジスタ) |
0 | 1 | 2 | 16 | 2*VLEN/SEW | vn, vn+1 |
1 | 0 | 4 | 8 | 4*VLEN/SEW | vn, …, vn+3 |
1 | 1 | 8 | 4 | 8*VLEN/SEW | vn, …, vn+7 |
vlmul=01
の場合、ベクトルレジスタv
nはベクトルレジスタv
n+1も含み、2倍のビット長を操作することになる。ベクトルオペランドにより指定されるオペランドで、奇数番号のベクトルレジスタを指定した場合は不定命令例外が発生する。
同様に、vlmul=10
である場合、ベクトル命令は4つのベクトルレジスタを同時に操作する。また、ベクトル命令により指定されるベクトルオペランドが4の倍数でなかった場合は不定命令例外が発生する。vlmul=11
である場合は、8つのベクトルレジスタを同時に操作し、ベクトルオペランドとして使用されるベクトルレジスタが8の倍数でない場合は不定命令例外が発生する。
このグループパタン(LMUL=8の場合のv0
,v8
,v16
,v24
)は0.6で初めて導入され、浮動小数点の値がベクトルレジスタにオーバライドされた場合に浮動小数点の呼び出し規約に問題が発生することを避けるために導入された。一方で過去の半ではベクトルレジスタのグループ名は連続して付けられていた(LMUL=8では、v0
,v1
,v2
,v3
となる)。0.7以降では、浮動小数点レジスタは再び分離された。
レジスタマスク命令は、LMULの設定に関係なく常に単一ベクトルレジスタに対して機能する。
3.2.3. ベクトルタイプ不正 vill
¶
vill
では直前に実行されたvsetvl{i}
命令によりサポートされない値がvtype
に書き込まれたことをエンコードするために使用される。
vill
ビットはCSRのXLEN-1ビットにより設定される。これにより、不正な値が設定されたかどうかを符号判定の分岐命令により判定できる。
もし、vill
ビットが設定されている場合、どのようなベクトル命令(ベクトルコンフィグレーション命令以外)を実行しても不定命令例外が発生する。
vill
が設定されていると、vtype
の他のXLEN-1
ビットは0に設定される。
3.3. ベクトル長レジスタvl
¶
XLENビット長の読み込み専用CSRであるvl
はvsetvli
およびvsetvl
命令でのみアップデートすることができるレジスタで、fault-only-firstベクトルロード命令バリアントである。
vl
レジスタは、ベクトル命令によりアップデートされる要素の数を符号なし整数として保持している。任意の書き込み先ベクトルレジスタグループにおいて、インデックスがvl
以上の場合は、ベクトル命令が実行されても何も変化しない。vstart
≥vl
の場合、書き込み先ベクトルレジスタグループにおいてどのような要素もアップデートされない。
結論として、vl
=0の場合はvstart
の値にかかわらず書き込み先ベクトルレジスタグループには何も書きこまれない。
スカラ整数レジスタもしくはスカラ浮動小数点レジスタの場合は
vstart
≦vl
でも実行される。
vl
に実装されるビットの長さは、その実装が最小のデータタイプにおいて実行することができる最大の要素数に依存する。最小のベクトル実装であるRV32IVでは、少なくともvl
では0-32までの値を保持する(VLEN=32, LMUL=8, SEW=8でVLMAXが32となる)を保持するために6ビットが必要となる。
3.4 ベクトルバイト長レジスタvlenb
¶
XLEN
ビット長の読み込み専用CSRレジスタvlenb
はVLEN/8の値、つまりバイト単位でのベクトル長を保持する。
vlenb
の値は任意の実装において、設計時に決められる定数である。
このCSRを使わない場合、いくつかの命令を実行してVLENのバイト単位での値を計算する必要がある。退避の必要な現在のvl
およびvtype
の値を取得して計算を行う必要がある。
3.5. ベクトルスタートインデックスCSRvstart
¶
vsatrt
は読み込み専用のCSRで、ベクトル命令により実行される最初の要素のインデックスを示している。
通常、vstart
はベクトル命令の例外時にハードウェアにより書き込まれる。vsatrt
の値はどの要素により例外がが発生したか(同期例外及び非同期例外で同様である)を示しており、復帰可能な例外である場合は、どの場所から復帰するかを示している。
すべてのベクトル命令はvstart
CSRで示されるエレメントの場所から実行され、例外が発生した要素よりも前の要素の結果が邪魔されることがないように設計されている。命令の実行が完了すると、vstart
CSRは0にリセットされる。
vsetvl{i}
命令を含むすべてのベクトル命令はvstart
CSRをゼロに設定する。
不定命令例外を発生させたベクトル命令では、vstart
の値は変更されない。
vstart
レジスタの値がvl
以上場合は、どの要素にも実行されず、書き込みベクトルレジスタのvl
がゼロに設定されることはない。
vstart
CSRは最大の要素インデックス(VLMAXよりも1つ小さな値)もしくはlg2(VLEN)まで書き込むことができるようなビットサイズが定義される。vstart
CSRの上位のビットはハード的にゼロが設定される(ゼロ読み出し、書き込みは無視される)。
ベクトル長の最大値はLMULの最大設定値(8)およびSEWの最小値(8)により計算され、VLMAX_max=8*VLEN/8=VLENとなる。例えば、VLEN=256であれば、vstart
は8ビットであり、0から255までを表現することができる。
vstart
CSRは非特権コードにより書き込みを行うことができるが、いくつかの実装ではvstart
にゼロ以外の値を書き込むと大幅に速度が低下する可能性がある。したがって、vstart
はアプリケーションプログラマが使用すべきではない。いくつかのベクトル命令ではvstart
が非ゼロの場合には実行することができず、以下に定義された不定命令例外が発生する。
特権用以外のコードでもvstart
が見えることによって、ユーザレベルのスレッドライブラリをサポートすることができる。
実装では、vstart
の値に何らかの値が設定されている状態では例外を発生することを許しており、そのような実装では同じvtype
設定においてベクトル命令は結果を生成しない。
たとえば、いくつかの実装ではベクトル算術演算を実行中には決して例外を発生せず、命令の実行が完了するまで例外の発生を待つことができる。このような実装ではベクトル算術演算命令においてvstart
が非ゼロである場合は例外が発生することを許している。
3.6. ベクトル固定小数点丸めモードレジスタvxrm
¶
ベクトル固定小数点丸めモードレジスタは2ビットのRead-Write丸めモードビットフィールドを持っている。ベクトル固定小数点丸めはfcsr
レジスタの上位ビットのビットフィールドを反映しているが、異なるCSRビットアドレスが割り当てられている。浮動小数点を持たないシステムの場合は、ベクトル拡張を追加する場合にはfcsr
レジスタを追加する必要がある。
固定小数点の丸めアルゴリズムは以下のように指定される。丸め前の値がv
であり、d
ビット長であるとする。この場合丸め後の値は(v >> d) + r
であり、r
は以下に示す丸めモードの表によって決定される。
Bits [1] | Bits[0] | 略称 | 丸めモード | 丸めイン
クリメントr |
---|---|---|---|---|
0 | 0 | rnu | r ound-to-nearest-up (add +0.5 LSB) | v[d-1] |
0 | 1 | rne | rou nd-to-nearest-even | v[d-1
] & (v[d-2:0]!=0 |
1 | 0 | rdn | round-down (truncate) | 0 |
1 | 1 | rod | round-to-odd (OR bits into LSB, aka “jam”) |
|
以下の丸め関数は、命令の説明時に丸めの操作を説明表現するために使用する。
roundoff_unsigned(v, d) = (unsigned(v) >> d) + r
roundoff_signed(v, d) = (signed(v) >> d) + r
Bits[XLEN-1:2]はゼロである。
丸めモードはcsrwi
命令により1命令で設定できる。
3.7. ベクトル固定小数点飽和フラグvxsat
¶
vxsat
CSRは1ビットの読み書き可能なビットを保持しており、固定小数点命令の計算結果が書き込み先レジスタのフォーマットに合わせるために飽和した場合に設定される。
vxsat
ビットはfcsr
レジスタの上位ビットにミラーリングされる。
3.7. fcsr
のベクトル固定小数点フィールド¶
vxrm
およびvxsat
は分離されたCSRであり浮動小数点CSRfcsr
からアクセスすることができる。fcsr
レジスタは浮動小数点をサポートしていない実装でも、ベクトル拡張をサポートしている場合には追加する必要がある。
Bits | Name | Description |
---|---|---|
10:9 | vxrm | 固定小数点丸めモード |
8 | vxsat | 固定小数点精度飽和フラグ |
7:5 | frm | 浮動小数点丸めモード |
4:0 | fflags | 浮動小数点例外フラグ |
これらのフィールドはfcsr
にパッキングされるのは、コンテキストの保存と回復を高速化させるためである。
3.8. ベクトル拡張のリセット状態について¶
ベクトル拡張はリセット時に矛盾の発生していない状態でなければならない。特に、vtype
およびvl
はvsetvl
命令により読み込みおよびリストアできなければならない。
リセット時にはvtype.vill
は1が設定されており、残りのvtype
レジスタはゼロが設定されており、vl
は0が設定されている状態が推奨される。
vstart
, vxrm
,vxsat
CSRはリセット時にはどのような値が設定されていても構わない。
ベクトルユニットを使用するときはいかなる時も最初にvsetvl{i}
を実行し、vstart
をリセットさせる必要がある。vxrm
およびvxsat
フィールドはソフトウェアにより使用前に明示的にリセットを行うべきである。
ベクトルレジスタはリセット時にはどのような値が設定されていても構わない。